Django model form cant use two modelforms - django

I was wondering how i can use two models in a modelform
I tried :
from django import forms
from .models import Question, Choice
class CreateQuestionForm(forms.ModelForm):
class Meta:
model = question, choice
Fields = [
'question'
'choice_text
]

You have to use formsets in order to use two different forms in the same.
Firstly, you have to define each form from their models.
Then, you can use formset_factory to combine both forms.

Related

Two model in one UpdateView "Django"

my views :
from .models import Settings, SocialMediaSetting
class UpdateSocialMediaSetting(LoginRequiredMixin, UpdateView):
model = SocialMediaSetting
fields = '__all__'
template_name = "staff/settings/social-media-settings-update.html"
class UpdateSettings(LoginRequiredMixin, UpdateView):
model = Settings
fields = '__all__'
template_name = "staff/settings/settings-update.html"
two different class in models without any relation, I want show both in one html and one form both models has just one object
you'll need to ditch the UpdateView, but this way won't take long to implement
Use a TemplateView (at least you won't have to change your other mixin)
Create two ModelForms
override the get_context_data() to pass the forms to the template
when forms are submitted, override the post() method to save them yourself
mchesler613 wrote an awesome article explaining how to do this here.
(make sure to give him a star)

Django admin: postgres DateTimeRangeField not displayed properly

Some of my models have postgres-specific django.contrib.postgres.fields.DateTimeRangeFields, and those fields are exposed in the corresponding admin panels. I expected that the ranges forms would consist of two Django-style datetime pickers, with a separate one for the date part and a separate part for the time part (just like the DateTimeField would). However, I get two text inputs which expect input in a very particular format. Is there anything I am missing or have to configure separately?
The relevant code is:
from django.contrib.postgres.fields import DateTimeRangeField
...
class MyModel(models.Model):
time_off = DateTimeRangeField()
admin:
#register(MyModel)
class MyModelAdmin(admin.ModelAdmin):
pass
You are looking for SplitDateTimeWidget.
Simply change the admin part as:
class MyModelAdminForm(forms.ModelForm):
class Meta:
model = MyModel
widgets = {
'time_off': RangeWidget(SplitDateTimeWidget())
}
#register(MyModel)
class MyModelAdmin(admin.ModelAdmin):
form = MyModelAdminForm
or use formfield_overrides to override the widget if you wish.

Django: Search many to many field while creating object

I've got a use case where I have multiple Ingredient that can be linked to a Recipe through the Django admin. Now I have around a hundred ingredients which makes it very difficult to select the ingredients in the following UI.
Is there a way to add a search field or something similar to the django admin for easier selection?
You have few choices.
1. filter_horizontal
With filter_horizontal, you can use horizontal m2m ui in admin. I prefer this way using m2m in admin.
class YourAdmin(admin.ModelAdmin):
filter_horizontal = ('m2m_field',)
...
And the result will be...
2. raw_id_fields docs
You can use raw_id_fields for using pop-up modal with your m2m fields.
It's bit useful when you have lots of m2m field. Also, it's easy to filter which m2m obj to add.
class YourAdmin(admin.ModelAdmin):
raw_id_fiedls = ('m2m_field',)
...
I suppose you want to filter over ingredients and select it one by one on admin UI
You can use django forms builtin CheckboxSelectMultiple
widget in place of SelectMultiple to make selection easy
from django import forms
from django.contrib import admin
class RecipeForm(forms.ModelForm):
class Meta(object):
model = Recipe
widgets = {
'Ingredient': forms.CheckboxSelectMultiple,
}
class RecipeAdmin(admin.ModelAdmin):
form = RecipeForm
admin.site.register(Recipe, RecipeAdmin)
Alternatively, you can use django-better-filter-widget
package if you want a search input on choices, Refer Github repo for
installation
It is a custom widget, created by overriding SelectMultiple widget of
django forms
from django import forms
from django.contrib import admin
from better_filter_widget import BetterFilterWidget
class RecipeForm(forms.ModelForm):
class Meta(object):
model = Recipe
widgets = {
'Ingredient': BetterFilterWidget(),
}
class RecipeAdmin(admin.ModelAdmin):
form = RecipeForm
admin.site.register(Recipe, RecipeAdmin)

Update two or more models at same time with UpdateView

Is there some way to update two or more models at the same time with UpdateView? For example having this:
class PEEncargadoView(UpdateModelMixin,UpdateView):
model = Encargado
form_class = FormEncargado
success_url = '/'
template_name = 'productores/PE/encargado.html'
Update other models besides of Encargado but in this same view
I know that this could be possible overriding get_context_data, but exactly how? if I don't need to pass any variables to the template.
you can't do it with UpdateModelMixin - it's designed for working with a single model.
This question shows how to work with multiple forms in CBV: Django: Can class-based views accept two forms at a time?.
Django has formsets https://docs.djangoproject.com/en/1.8/topics/forms/formsets/ which can be used together with ModelForm to allow edition of multiple models on one page.

Django Filtering Admin Dropdowns

It seems this questions has been answered many times, but I am new to Django and apparently missing something when I try to work through the answers I have been finding. I have 2 Models, Model A is the main one and has a foreign key to Model B. When I make a new Model A in the Django Admin, I want the drop down for picking a Model B to only show the Model B's that have not already been assigned to a Model A. Can anyone point the right way?
You need to provide a custom form to the admin, telling it to only show a certain queryset for the Model B field:
from django import forms
from django.contrib import admin
from myapp.models import Person
class ModelAForm(forms.ModelForm):
model_b = ModelChoiceField(
queryset=ModelB.objects.exclude(model_a__isnull=False))
class Meta:
model = ModelA
class ModelAAdmin(admin.ModelAdmin):
form = ModelAForm