4

グループ内のユーザーが、グループに変更権限がないフィールドを変更できないように制限しようとしています。例えば:

class StudentReferral(models.Model):
    teacher = models.CharField(max_length=50)
    referral_first_name = models.CharField(max_length=50)
    referral_last_name = models.CharField(max_length=50)
    accepted = models.BooleanField(blank=True)

これで、教師はすべて 1 つのユーザー グループに属し、紹介を受け入れるか拒否する人は別のユーザー グループに属します。教師ユーザー グループは、次のフィールドのみを編集できる必要があります: teacherreferral_first_nameおよびreferral_last_name。他のユーザー グループは、承認されたフィールドのみを編集できる必要があります。両方のグループがすべてのフィールドを表示できる必要があります。

これを可能にするDjangoに組み込まれたもの、またはこれを行うためのカスタム方法はありますか?

4

1 に答える 1

8

をオーバーライドModelAdmin.get_fieldsetsし、次のようにします。

class MyModelAdmin(admin.ModelAdmin):
    ...
    fieldsets = (
        ... # Standard/all fields
    )
    teacher_fieldsets = (
        ... # Only fields teachers can see
    )

    def get_fieldsets(self, request, obj=None):
        if request.user.groups.filter(name='Teachers').exists():
            return self.teacher_fieldsets
        else:
            return super(MyModelAdmin, self).get_fieldsets(request, obj=obj)

編集

申し訳ありませんが、すべてのフィールドを表示できるはずであり、編集することはできません。まだ役に立つかもしれないので、元の回答をそのまま残しました。ただし、このためには、オーバーライドする必要がありますModelAdmin.get_readonly_fields

class MyModelAdmin(admin.ModelAdmin):
    ...
    readonly_fields = ('teacher', 'referral_first_name', 'referral_last_name')
    teacher_readonly_fields = ('accepted',)

    def get_readonly_fields(self, request, obj=None):
        if request.user.groups.filter(name='Teachers').exists():
            return self.teacher_readonly_fields
        else:
            return super(MyModelAdmin, self).get_readonly_fields(request, obj=obj)

ここでは、選択肢は教師または「他のユーザー」のみであると想定しています。考慮すべき他のタイプがある場合、またはある状況でフィールドをまったく制限したくない場合は、readonly_fields属性を削除して のようなものに置き換え、それにother_readonly_fields応じて分岐することをお勧めします ( のデフォルト値readonly_fieldsは、editable=Falseモデル上)。

また、フィールドが必須の場合は、読み取り専用にすることもできないことに注意してください。これらのいくつかが必須フィールドである場合ModelForm.__init__、それらが読み取り専用になる状況でそれらを不要にするために、同様にオーバーライドする必要がありModelFormますrequest

class MyModelForm(forms.ModelForm):
    class Meta:
        model = MyModel

    def __init__(self, *args, **kwargs):
        self.request = kwargs.pop('request')
        super(MyModelForm, self).__init__(*args, **kwargs)

        if self.request is not None:
            if self.request.user.groups.filter(name='Teachers').exists():
                self.fields['accepted'].required = False

class MyModelAdmin(admin.ModelAdmin):
    form = MyModelForm
    ...
    def get_form(self, request, obj=None, **kwargs):
        ModelForm = super(MyModelAdmin, self).get_form(request, obj=obj, **kwargs)
        class WrapperModelForm(ModelForm):
            def __new__(cls, *args, **kwargs):
                kwargs['request'] = request
                return ModelForm(*args, **kwargs)
        return WrapperModelForm
于 2012-07-19T20:51:18.687 に答える