I have created a custom Django admin page. I have two types of users who can access admin page (staff user and superuser). Superuser can see all the users and can change their settings. He can also add or delete users. The staff user can only see their settings and can change some of them. I currently have a problem that staff users can see all users of the web application and can add or delete them. I restricted staff users to see certain settings but could not change it.
I do not know how to restrict staff users to see only their settings.
Here is my code: Admin.py
from django.contrib import admin
from django.contrib.auth import get_user_model
from django.contrib.auth.admin import UserAdmin as BaseUserAdmin
from .forms import UserAdminChangeForm, UserAdminCreationForm
from .models import UpLoadFile
User = get_user_model()
admin.site.site_header = 'SRC Orkestracija'
admin.site.index_title = 'Administration'
admin.site.register(UpLoadFile)
class UserAdmin(BaseUserAdmin):
# The forms to add and change user instances
form = UserAdminChangeForm
add_form = UserAdminCreationForm
# The fields to be used in displaying the User model.
# These override the definitions on the base UserAdmin
# that reference specific fields on auth.User.
list_display = ('username', 'superuser', 'active', 'staff')
list_filter = ('superuser', 'active', 'staff')
readonly_fields = [
'last_login'
]
actions = [
'activate_users',
]
filter_horizontal = ('user_permissions', 'groups')
fieldsets = (
(None, {'fields': ('username', 'password', 'config_file')}),
('Permissions', {'fields': ('superuser', 'active', 'staff', 'groups', 'user_permissions')}),
('Important dates', {'fields': ('last_login',)}),
)
# add_fieldsets is not a standard ModelAdmin attribute. UserAdmin
# overrides get_fieldsets to use this attribute when creating a user.
add_fieldsets = (
(None, {
'classes': ('wide',),
'fields': ('username', 'password1', 'password2', 'config_file')}
),
)
search_fields = ('username',)
ordering = ('username',)
def get_form(self, request, obj=None, **kwargs):
form = super().get_form(request, obj, **kwargs)
is_superuser = request.user.is_superuser
disabled_fields = set()
if not is_superuser:
disabled_fields |= {
'username',
'active',
'superuser',
'staff',
'groups',
'user_permissions'
}
if (
not is_superuser
and obj is not None
and obj == request.user
):
disabled_fields |= {
'username',
'active',
'superuser',
'staff',
'groups',
'user_permissions'
}
for f in disabled_fields:
if f in form.base_fields:
form.base_fields[f].disabled = True
return form
def activate_users(self, request, queryset):
is_superuser = request.user.is_superuser
if is_superuser:
cnt = queryset.filter(active=False).update(active=True)
self.message_user(request, 'Activated {} users.'.format(cnt))
activate_users.short_description = 'Activate Users'
admin.site.register(User, UserAdmin)
Models.py:
class UserManager(BaseUserManager):
def create_user(self, username, config_file, password=None, is_active=True, is_staff=False, is_superuser=False):
if not username:
raise ValueError("User must have username!")
if not password:
raise ValueError("User must have password!")
if not config_file:
raise ValueError("Select config file!")
user_obj = self.model(
username=username,
)
user_obj.config_file = config_file
user_obj.staff = is_staff
user_obj.superuser = is_superuser
user_obj.active = is_active
user_obj.set_password(password)
user_obj.save(using=self._db)
return user_obj
def create_staffuser(self, username, config_file, password=None):
user = self.create_user(
username=username,
config_file=config_file,
password=password,
is_staff=True
)
return user
def create_superuser(self, username, config_file, password=None):
user = self.create_user(
username=username,
config_file=config_file,
password=password,
is_staff=True,
is_superuser=True
)
return user
class CustomUser(AbstractBaseUser, PermissionsMixin):
class Meta:
verbose_name = "User"
verbose_name_plural = "Users"
OPTIONS = (
('1', '1'),
('2', '2'),
('3', '3'),
('4', '4'),
)
username = models.CharField(unique=True, max_length=255)
active = models.BooleanField(default=True,
help_text='Designates whether this user should be treated as active. Unselect this instead of deleting accounts.')
staff = models.BooleanField(default=False, help_text='Designates whether the user can log into this admin site.')
superuser = models.BooleanField(default=False,
help_text='Designates that this user has all permissions without explicitly assigning them.')
config_file = models.CharField(choices=OPTIONS, max_length=255)
USERNAME_FIELD = 'username'
REQUIRED_FIELDS = ['config_file']
object = UserManager()
def __str__(self):
return self.username
def has_perm(self, perm, obj=None):
return True
def has_module_perms(self, app_lable):
return True
@property
def is_staff(self):
return self.staff
@property
def is_superuser(self):
return self.superuser
@property
def is_active(self):
return self.active
def path(user, filename):
return os.path.join(str(user))
I will appreciate any help or instructions how can I add this feature.
You can set superusers to only have add/delete permissions in the admin class.
class UserAdmin(BaseUserAdmin):
...
def has_add_permission(self, request, obj=None):
return request.user.is_superuser
def has_delete_permission(self, request, obj=None):
return request.user.is_superuser
Note the above is also achievable by not granting the add or delete permissions to any group or user in the admin interface.
The following will only allow users to change all users if they are a superuser. Else they will only be able to change their own user.
def has_change_permission(self, request, obj=None):
return request.user.is_superuser or (obj and obj.id == request.user.id)
And if you want them to be able to see the user list page with only their user visible you can modify get_queryset
def get_queryset(self, request):
qs = super().get_queryset(request)
user = request.user
return qs if user.is_superuser else qs.filter(id=user.id)
In your template:
{% if request.user.is_superuser %}
<!-- Only superusers can view things in here -->
{% endif %}
In your view, you also will have to control what can be edited and what cannot be.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.