For example, I have a Post model:
Class Post(models.Model):
title = models.Charfield(max_length=200)
# other fields
I wonder is there a way to create multiple posts at once in admin. In other words, I need a formset instead of single form on post creation page.
I've heard recently about a django app that exactly does this job. It's called django-bulk-admin and enables bulk add/update in the admin.
Possibly, the best way to do exactly what you want is extend the ModelAdmin class, because it has no formsets on it, except for those used on InlineFormsets.
After that you could customize the admin change_form template, to include your formsets
The quick-and-dirty way to do it using admin is wrap your Post model as an inline formset of another modeladmin and add the extra option to it.
Related
I have a model with fields name, roll_no, birth_date
I am using the django admin's list display and list editable to have these fields displayed and edited in a list format in a single page. However, to add a new entry I have to go to the create_form page.
Is it possible to simply add new objects from the list_display page itself?
Unfortunately this feature is not available out-of-the box in the Django admin like the ModelAdmin.list_editable feature.
I'm curious to see if there are other shortcuts, but at the moment the only way I see is to customize the formset like descibed in the official Docs:
from django import forms
class MyForm(forms.ModelForm):
# customize your 'extra' forms here
class MyModelAdmin(admin.ModelAdmin):
def get_changelist_form(self, request, **kwargs):
return MyForm
And finally manually extend the changelist form template of the admin. To override a Django admin template, please follow the intructions in the Official Docs here. The template to be customized is the following folder:
.../django/contrib/admin/templates/admin/change_list.html
and you probably need to override the {% block result_list %} in that file.
NB: the customization of an admin template can be very tricky. Consider to use a CMS (like DjangoCMS) if you need to extend the user experience. The idea behind the Django admin is to make your life easier with an out-of-the-box interface for CRUDs on your DB. IMHO try to avoid complex customizations of the Django Admin if not strictly needed.
Lets say for example I have a Model called "Client" and a model called "PhoneNumbers"
class PhoneNumbers(models.Model):
number = forms.IntegerField()
class Client(models.Model):
number = forms.ManyToManyField(PhoneNumbers)
Client has a ManyToMany relationship with PhoneNumbers. PhoneNumbers has almost 500,000 records in it so when it comes to editing a Client record from a model form with a MultiSelect widget that comes with a M2M filed, it takes forever to load. In fact, it never does. It just sits there trying to load all of those phone objects I am assuming.
My workaround was to so some tedious things with ajax and jquery to edit only the phone numbers in a Client record. Before wasting my time with all of that I wanted to see if there is somehow another way to go about it without having my page hang.
You need to create a custom widget for this field that lets you autocomplete for the correct record. If you don't want to roll your own: http://django-autocomplete-light.readthedocs.io/
I've used this for its generic relationship support, the M2M autocomplete looks pretty easy and intuitive as well. see video of use here: http://www.youtube.com/watch?v=fJIHiqWKUXI&feature=youtu.be
After reading your comment about needing it outside the admin, I took another look at the django-autocomplete-light library. It provides widgets you can use outside the admin.
from dal import autocomplete
from django import forms
class PersonForm(forms.ModelForm):
class Meta:
widgets = {
'myformfield': autocomplete.ModelSelect2(
# ...
),
}
Since Django 2.0, Django Admin ships with an autocomplete_fields attribute that generates autocomplete widgets for foreign keys and many-to-many fields.
class PhoneNumbersAdmin(admin.ModelAdmin):
search_fields = ['number']
class ClientAdmin(admin.ModelAdmin):
autocomplete_fields = ['number']
Note that this only works in the scope of Django admin of course. To get autocomplete fields outside the admin you would need an extra package such as django-autocomplete-light as already suggested in other answers.
Out of the box, the model admin has a raw_id_fields option that let your page load much quicker. However, the user interface of raw id fields isn't very intuitive, so you might have to roll your own solution.
We use this 3rd party widget for this:
https://github.com/crucialfelix/django-ajax-selects
Btw, your 'example' above is really bad DB design for a bunch of reasons. You should just have the phone number as a text field on the Client model and then you would have none of these issues. ;-)
I would like to store groups of pages under different tags. So I create these models:
class Page(models.Model):
title = models.CharField(max_length=50)
class Tag(models.Model):
title = models.CharField(max_length=50)
pages = models.ManyToManyField(Page)
I would then like to create a model form(set?) that will allow me to edit the tag, and every page attached to that tag, as one big form. I believe this is what happens when you use Model Inline Formset, but that uses foreign keys. This is a reusable app, right now I'm just rendering the form in a template, but I would prefer to use django forms so it's easier to reuse.
I can't seem to figure out how this is done, any suggestions would be greatly appreciated.
Take a look at django-tagging application.
I have setup for Django non-rel with Mongodb as backend. In models, I used EmbeddedModelField for quite a few times as I love those concepts of Non relational DBs. But, when it comes to rendering forms. I got stuck,
I created Form as normal form of Django but django showing Type error {model} in the title bar.
Has anybody know how can I create form fields for EmbeddedModelField in Django non-rel?
Just implement a formfield class by yourself.
implement formfield in forms.py
specify which form you want to use with this model in models.py
implementing a formfield is a piece of cake, you just need to implement these two methods in the class:
to_python(self, value)
prepare_value(self, value)
If you implement it with inheritance of old formfield class, you could use the widget attached on that formfield. (widget means the UI will be rendered on the webpage by template system)
Reference for implementing formfield: How to use ListFields in Django's admin
And you could implement your own widget by overriding the original widget of a formfield.
For instance, take a look at django documentations: Django docs - widgets
I need a model field composed of a numeric string for a Django app I'm working on and since one doesn't exist I need to roll my own. Now I understand how "get_db_prep_value" and such work, and how to extend the Model itself (the django documentation on custom model fields is an invaluable resource.), but for the life of me I can't seem to figure out how to make the admin interface error properly based on input constraints.
How do I make the associated form field in the admin error on incorrect input?
Have a look at the Form and field validation section in the Django documentation, maybe that's what you're looking for?
You would have to make a new type of form field for your custom model field.
All you need to do is define a custom modelform which uses your new field, and then tell the admin to use that form to edit your models.
class MyModelForm(forms.ModelForm):
myfield = MyCustomField()
class Meta:
model = MyModel
class MyModelAdmin(admin.ModelAdmin):
form = MyModelForm