Django admin particular data for particular user - django

I am using django admin site to let people manage database easier.
For some reason, I want to hide some data from some user.
Let's say I have a model named Book and there are a lot of books in database. I want different user has the different scope of books he can view.
How would I do that?
I am thinking about permission. Is that possible to set the permission to filter the data?
I know how to create permission according to a specified model. However, after that, how do I suppose to use that permission? I believe I may need to override part of "changelist_view" method under BookAdmin class, right?
Any help would works.
Thanks in advance

Use the queryset method on your admin model. Something like:
class BookAdmin(admin.ModelAdmin):
def queryset(self, request):
return super(BookAdmin, self).queryset(request).filter(owner=request.user)
Obviously the filter will vary depending on your book model, but this is the general idea.

Related

Django - Is it better to store user information by customising the default User model, or should I create a separate Model for this?

This is for a practice project I am building to learn Django. The site will need to track certain data about the user. Should I customise the default User model? Or create a new model like -
class UserData(models.Model):
'''holds user info'''
owner = models.ForeignKey(User)
# data
I couldn't find a clear answer.
It really depends. I would recommend keeping User model small, and put most of the additional information in some kind of Profile model. However, there are certain important things that you may want to place in the User model, for example:
user_type field - you may have multiple Profile models (think CustomerProfile, VendorProfile etc.) and you need a way to distinguish User and grant appropriate access to them
Something related to authorization, like require_2fa field
If you are starting a new project and don't expect a lot of additional info, you may keep them in the User model just for simplicity, especially if you are already customizing it (i.e. to replace username with email)
Users are special so it is better to use django.contrib.auth.models.AbstractUser to keep the the default user model behaviour and add your custom fields there.
from django.contrib.auth.models import AbstractUser
class CustomUser(AbstractUser):
pass
I've wrote an article about it that I think it would be userful in this case.

exclude object from queryset in many to many relation in django

so i have a many to many relation between my own Role model and the django auth permission model, the thing is, i tried to get all permissions associated with a specific role like this role.permisos (permisos being the many to many atribute), it works ok.
Now, im looking forward to add that queryset to a form, but before that i tried to filter some permissions i don't want the user to see
i did role1.permisos.exclude(name="Can change somethings") (being role1 an instance of role) but it just dosn't work
If you're working with a template, add it to your context. If it's a class-based view, override the get_context_data method.
You can also do it overriding the get_initial_data method.

Django - permission_required on view level

I am looking at the built-in authentication functionality from Django for my custom app.
If I understand this right, I can assign add, change, delete rights to models.
I am looking for a solution to assign view/show rights to a user.
My basic idea is to use the permission_required decorator for this, but as stated this only works for add, change, delete and in addition it seems only to work for models. I have functions where I am using multi-objects from models.
The best would be to have something that collects my custom permission_required decorators and gives me the possibility to edit this e.g. in the Django admin UI.
E.g.
#permission_required('user.profile.view')
def myProfile(request):
...
#permission_required('user.profile.edit')
def editMyProfile(request):
...
Any idea or suggestion is welcome.
Thanks in advanced!
Creating custom permissions is well documented. Once you've created custom permissions, you'll be able to assign them to users through the usual user admin page.

Project platform suggestion for web application with proper User Auth and integration support

So, I have an idea to build a web app. I am new to this business but am a programmer. I liked Python and thought let me start with Django. I ran into a problem with the built-in Django User Auth system as pointed by this question of mine on SO.
In short, I am using Django's built-in User auth and thought that it will easily fill my user field (the foreignkey) in my model but it does not. I have Googled and asked questions but only got a very convoluted answer or that I have to use the Admin section if I want anything like that.
My simple need is that whenever user saves anything in their profile, the user field should get populated so that I can reference it. To me, it sounds like the most basic need for any web app.
Am I wrong. I need advice. If Django is not good for this then I am ready to learn any other good framework or platform if need be.
In short, I am using Django's built-in
User auth and thought that it will
easily fill my user field (the
foreignkey) in my model but it does
not.
This won't just magically happen. You will have make it happen. Models are separated from the request so this would happen in your view, or a model method (perhaps save) that is passed the active user.
MVC / MTV design separates the database from the view / control logic. I don't see what framework has to do with this: unless you write the functionality yourself, the database doesn't know what to do with some User table and the currently logged in user (also separated from the data). Building in this functionality would inconvenience a lot of people as well...
In general, the python/django philosophy is: Explicit is better than implicit.
Now the solutions:
If you wanted this behavior in the view, for any form, you could potentially write:
instance = MyForm.save(commit=False) # commit=False prevents DB save.
instance.user = request.user
instance.save()
You could overwrite the save method on the model that accepts an optional user argument as well.
def save(self, *args, **kwargs):
user = kwargs.pop(user, None)
self.user = user
super(MyModel, self).save(*args, **kwargs)
mymodel = MyModel()
mymodel.save(user=request.user)

Django databrowse with custom queryset?

Django's databrowse is very different from the rest of django in that the docs literally don't exist. Has anyone tried to do more that databrowse.site.register on a model? Any code examples?
In particular, I've got a model that has a ForeignKey to an auth.Group and I want databrowse to use this queryset instead of .all():
qs = Model.objects.filter(group__in=request.user.groups.all())
Bonus points for making it possible to have a button that does stuff with the current object (edit/delete/clone/etc). I basically need a simple way to browse and edit rows without giving users access to the admin.
It'd be even better if there was a way to do that on the admin, but I don't want to give users the staff privilege.
There's no way to do this through databrowse. You could try writing a custom Manager for your Model and return the required query set by default.