Overriding admin view methods - Django - python

I need to override the an add form within the admin panel.
I'm thinking of accomplishing this by writing a view which would then point to the admin view for the final result.
Something similar to this (where admin_basic_ass_user_view is the admin view)
#required_login
def add_user(request):
if condition:
return admin_basic_add_user_view(request)
return render_to_response("admin/auth/user/add_form.html", { ... })
Any ideas?

Why not just override the relevant methods with your ModelAdmin subclass? That's why it's a class, after all.

Add something like this to your urls.py
((r'^admin/auth/users/add/$', 'Project.SomeAPP.admin_views.add_user'),
The path needs to point to your new view. You should see the results of your new view in the admin interface's add user page.
EDIT: I forgot to mention, make sure you add that line BEFORE the normal admin interface line in the urls.py

Related

Is it necessary to have a model and inheritance in class based views?

class home(ListView):
template_name='blog/base.html'
This doesn't work and gives this error --
ImproperlyConfigured at /
home is missing a QuerySet. Define home.model, home.queryset, or override
home.get_queryset().
but when I create a model with no data
class home(ListView):
model = Post
template_name='blog/base.html'
This works perfectly fine
-> In same way when I don't inherit ListView
class home():
model = Post
template_name='blog/base.html'
It gives the following error in urls.py
from django.urls import path,include
from . import views
from .views import home
urlpatterns = [
# path('',views.home,name='blog-home'),
path('',home.as_view(),name='blog-home')
]
AttributeError: type object 'home' has no attribute 'as_view'
I don't have any idea about both of these
Yes, passing the modal is important in django generic views because ListView inherits from BaseListView which is again inherits from MultipleObjectMixin. The MultipleObjectMixin makes it mandatory to pass modal in the query_set.
See Django code of MultipleObjectMixin to get a better understanding.
I agree to the answer by "Vivek Singh".
But apart from that, your second question where you do not inherit ListView you get the error in urls is because, for as_view() to work, you have to inherit some sort of View class. Such as ListView, DetailView (which come under Generic Views) or just simply View.
In my understanding your questions is rather aiming at "the reason why" and not so much for code:
Django class based ListView/DetailedView etc. are made with the purpose to simplify the typical web pages with a list and details of e.g. products which are stored in a database table (=django model). Thus reducing coding effort. Therefore a model is required that contains the items to list and to detail. If the model given is empty can only be found at runtime when the list page is called an the query is executed - you then just get a web page with an empty product list.
Also inheriting from ListView and defining the model only makes sense if on the rendered html template you use the (automatically) filled context to display the model list.
roughly what happens when you call YourListView.as_view():
-> request
-> dispatch request via urls.py
-> YourListView.as_view()
-> instantiate YourListView with model
-> fill context with query result of the model (!!!)
-> render html template with context
-> return response
(and this is only a small basic example of what ListView can simplify for you)
If you dont need a list/details of a model, there is obviously no need to inherit from those standard views. Then you have simply different needs.
You are free to define your own ClassBased Views, without that functionality provided by ListView etc.
Hope that helps you.

django admin custom template for model redirection

A curious question
Suppose I have a module/app say Demo which contains a model say "anything". Now I registered this model to admin.py.
Now when I log in to admin and see this model I see general update, delete option in admin template.
Is it possible that when I see this model in admin and click that model it redirects to another url that is of that module's url and it display in another template and I can show anything I like from view..
I am sorry if it is confusing. What I want is I want to show the admin's model property like update, add and delete in another custom template made by me and it should be redirected to url defined in the module's urls.py
Thanks in advance.. :)
This can be done by extending your base get_urls() method docs here

How to use the Django admin template for a form?

I want to use the existing Django Admin template for a form of my own. The situation is like there are two models. say A and B and I want a form that displays the details about both the models in a songle form of my own. So I am using a ModelForm. But I want to use the templates from the django admin. How can I do that?
I think its better to override the admin interface.
https://docs.djangoproject.com/en/dev/ref/contrib/admin/#overriding-admin-templates
Would a Class-based generic view work for you?

how do you style a form already inside django

I'm using django-registration. I'd like to update the AuthenticationForm in 'django.contrib.auth.forms'. Specifically, I would like to pass the 'attrs' dict to add a few attributes. How do I update a form that comes with django?
You can use the views that come with auth and override the form parameter with your own form:
django.contrib.auth.views.login(request[, template_name, redirect_field_name, authentication_form])
More info here.
The standard way is to subclass AuthenticationForm, change the attrs in constructor, pass the form to login view and write a new entry in urls.py.
This is a nightmare: in order to add html attribute to a field it is necessary to use python subclassing, to know how exactly django's form metaclass work (self.fields['field'].widget.attrs, not just self.field.widget.attrs), to know regexes (for urls.py), to know how django's urls.py work (should you put the overriding line before of after include('django.contrib.auth.urls')?) and to know where is the auth form and auth view imported from.
And now the "commercial break": just use http://pypi.python.org/pypi/django-widget-tweaks for your task ;)

Multiple versions of django admin page for the same model

In my django admin section, I'd like to show different versions of the admin page depending on what kind of user is currently logged in. I can think of a couple ways this might work, but haven't figured out how to do any of them.
Perhaps I could put logic into the admin.ModelAdmin to look at the current user and change the 'exclude' field dynamically. Does that work? Or maybe run different custom templates based on who's logged in, and have the templates include / exclude the fields as appropriate.
I could register two versions of the admin.ModelAdmin class, one for each type of user, and maybe restrict access through permissions? But the permissions system seems to believe fairly deeply in one set of permissions per model class so I'm not sure how to change that.
I could grab a couple of the widgets that are used in rendering the admin page templates, and include them in my own page that does the one specific job I need powerful users to be able to do.
I could set up multiple AdminSites and restrict access to them through the url / view system. But then I'm not sure how to register different admin.ModelAdmin classes with the different AdminSites.
Any advice on this would be appreciated.
Answer
Thanks for the hint. Here's how I did it...
def get_form(self, request, obj=None, **kwargs):
"""This dynamically inserts the "owners" field into the exclude list
if the current user is not superuser.
"""
if not request.user.is_superuser:
if self.exclude:
self.exclude.append('owners')
else:
self.exclude = ['owners']
else:
# Necessary since Admin objects outlive requests
try:
self.exclude.remove('owners')
except:
pass
return super(OwnersModelAdmin,self).get_form(request, obj=None, **kwargs)
There are quite a few hooks provided in the ModelAdmin class for this sort of thing.
One possibility would be to override the get_form method. This takes the request, as well as the object being edited, so you could get the current user from there, and return different ModelForms dependent on the user.
It's worth looking at the source for ModelAdmin - it's in django.contrib.admin.options - to see if overriding this or any other other methods might meet your needs.

Categories