Passed
Push — master ( 4374a3...7dc675 )
by Alexander
02:05
created

tcms.kiwi_auth.admin.KiwiUserAdmin.delete_model()   A

Complexity

Conditions 1

Size

Total Lines 2
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
eloc 2
dl 0
loc 2
rs 10
c 0
b 0
f 0
cc 1
nop 3
1
# -*- coding: utf-8 -*-
2
3
from django import forms
4
from django.urls import reverse
5
from django.contrib import admin
6
from django.http import HttpResponseRedirect
7
from django.contrib.auth import get_user_model
8
from django.contrib.auth.models import Permission
9
from django.contrib.auth.forms import UserChangeForm
10
from django.utils.translation import ugettext_lazy as _
11
from django.contrib.auth.admin import UserAdmin, sensitive_post_parameters_m
12
13
from tcms.utils.user import delete_user
14
15
User = get_user_model()  # pylint: disable=invalid-name
16
17
18
class MyUserChangeForm(UserChangeForm):
19
    """
20
        Enforces unique user emails.
21
    """
22
    email = forms.EmailField(required=True)
23
24
    def clean_email(self):
25
        query_set = User.objects.filter(email=self.cleaned_data['email'])
26
        if self.instance:
27
            query_set = query_set.exclude(pk=self.instance.pk)
28
        if query_set.count():
29
            raise forms.ValidationError(_('This email address is already in use'))
30
31
        return self.cleaned_data['email']
32
33
34
def _modifying_myself(request, object_id):
35
    return request.user.pk == int(object_id)
36
37
38
class KiwiUserAdmin(UserAdmin):
39
    list_display = UserAdmin.list_display + ('is_superuser', 'date_joined', 'last_login')
40
    ordering = ['-pk']  # same as -date_joined
41
42
    # override standard form and make the email address unique
43
    # even when adding users via admin panel
44
    form = MyUserChangeForm
45
46
    def has_change_permission(self, request, obj=None):
47
        return request.user.is_superuser or obj is not None
48
49
    # pylint: disable=too-many-arguments
50
    def render_change_form(self, request, context, add=False, change=False, form_url='', obj=None):
51
        if obj and not (_modifying_myself(request, obj.pk) or request.user.is_superuser):
52
            context.update({
53
                'show_save': False,
54
                'show_save_and_continue': False,
55
            })
56
        return super().render_change_form(request,
57
                                          context,
58
                                          add=add,
59
                                          change=change,
60
                                          form_url=form_url,
61
                                          obj=obj)
62
63
    def get_readonly_fields(self, request, obj=None):
64
        if request.user.is_superuser:
65
            return super().get_readonly_fields(request, obj)
66
67
        readonly_fields = ['username', 'is_staff', 'is_active',
68
                           'is_superuser', 'last_login', 'date_joined',
69
                           'groups', 'user_permissions']
70
        if obj and not _modifying_myself(request, obj.pk):
71
            readonly_fields.extend(['first_name', 'last_name', 'email'])
72
73
        return readonly_fields
74
75
    def get_fieldsets(self, request, obj=None):
76
        # super-user adding new account
77
        if not obj and request.user.is_superuser:
78
            return super().get_fieldsets(request, obj)
79
80
        first_fieldset_fields = ('username',)
81
        if obj and _modifying_myself(request, obj.pk):
82
            first_fieldset_fields = first_fieldset_fields + ('password',)
83
84
        remaining_fieldsets = (
85
            (_('Personal info'), {'fields': ('first_name', 'last_name', 'email')}),
86
            (_('Permissions'), {'fields': ('is_active', 'groups')}),
87
        )
88
89
        if request.user.is_superuser:
90
            field_sets = super().get_fieldsets(request, obj)
91
            if field_sets[0][0] is None and 'password' in field_sets[0][1]['fields']:
92
                remaining_fieldsets = field_sets[1:]
93
94
        return ((None, {'fields': first_fieldset_fields}),) + remaining_fieldsets
95
96
    @sensitive_post_parameters_m
97
    def user_change_password(self, request, id, form_url=''):  # pylint: disable=redefined-builtin
98
        return HttpResponseRedirect(reverse('admin:password_change'))
99
100
    @admin.options.csrf_protect_m
101
    def delete_view(self, request, object_id, extra_context=None):
102
        if not _modifying_myself(request, object_id):
103
            return super().delete_view(request, object_id, extra_context)
104
105
        # allow deletion of the user own account
106
        permission = Permission.objects.get(content_type__app_label='auth',
107
                                            codename='delete_user')
108
        try:
109
            request.user.user_permissions.add(permission)
110
            return super().delete_view(request, object_id, extra_context)
111
        finally:
112
            request.user.user_permissions.remove(permission)
113
114
    def response_delete(self, request, obj_display, obj_id):
115
        result = super().response_delete(request, obj_display, obj_id)
116
117
        if not _modifying_myself(request, obj_id):
118
            return result
119
120
        # user doesn't exist anymore so go to the index page
121
        # instead of returning to the user admin page
122
        return HttpResponseRedirect(reverse('core-views-index'))
123
124
    def has_delete_permission(self, request, obj=None):
125
        # allow to delete yourself without having 'delete' permission
126
        # explicitly assigned
127
        if _modifying_myself(request, getattr(obj, 'pk', 0)):
128
            return True
129
130
        return super().has_delete_permission(request, obj)
131
132
    def delete_model(self, request, obj):
133
        delete_user(obj)
134
135
136
# user admin extended functionality
137
admin.site.unregister(User)
138
admin.site.register(User, KiwiUserAdmin)
139