Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django user-to-groups in userAdmin, and group-to-users in groupAdmin

Is it possible to have many-to-many widget in admin-panel in user-tab to pick groups, that user belong to, and similar many-to-many widget in group-tab to pick users, which should belong to that group?

like image 901
zie1ony Avatar asked Nov 02 '13 23:11

zie1ony


1 Answers

There's the easy way and the hard way.

The easy way is to use Django's InlineModelAdmin objects. This way, however, you cannot use the group widget.

from django.contrib.auth.admin import GroupAdmin
from django.contrib.auth.models import User, Group

class UserSetInline(admin.TabularInline):
    model = User.groups.through
    raw_id_fields = ('user',)  # optional, if you have too many users

class MyGroupAdmin(GroupAdmin):
    inlines = [UserSetInline]

# unregister and register again
admin.site.unregister(Group)
admin.site.register(Group, MyGroupAdmin)

The hard way requires you to build your own form, manually load and save the related users:

from django import forms
from django.contrib import admin
from django.contrib.auth.admin import GroupAdmin
from django.contrib.auth.models import User, Group

class GroupForm(forms.ModelForm):
    users = forms.ModelMultipleChoiceField(
        label='Users',
        queryset=User.objects.all(),
        required=False,
        widget=admin.widgets.FilteredSelectMultiple(
            "users", is_stacked=False))

    class Meta:
        model = Group
        exclude = ()  # since Django 1.8 this is needed
        widgets = {
            'permissions': admin.widgets.FilteredSelectMultiple(
                "permissions", is_stacked=False),
        }


class MyGroupAdmin(GroupAdmin):
    form = GroupForm

    def save_model(self, request, obj, form, change):
        # save first to obtain id
        super(GroupAdmin, self).save_model(request, obj, form, change)
        obj.user_set.clear()
        for user in form.cleaned_data['users']:
             obj.user_set.add(user)

    def get_form(self, request, obj=None, **kwargs):
        if obj:
            self.form.base_fields['users'].initial = [o.pk for o in obj.user_set.all()]
        else:
            self.form.base_fields['users'].initial = []
        return GroupForm

# unregister and register again
admin.site.unregister(Group)
admin.site.register(Group, MyGroupAdmin)
like image 178
augustomen Avatar answered Nov 11 '22 23:11

augustomen