Is Django admin functionality used in production on large sites or do you use it for testing only? - django

I have been working through the Django tutorial and I note on page 7...
https://docs.djangoproject.com/en/2.2/intro/tutorial07/
...that the much touted "admin for free" feature of Django is rather weak. The tutorial shows how to add Choice objects to Question objects in the Polls admin. Three Choices are added by the ChoiceInline class, but the problem is that none of those three may be removed. Only Choices added by clicking the Add button may be removed. This is poor UI/UX because it mixes static and dynamic behaviour in an arbitrary way. It doesn't look so bad in the tutorial example, but if the feature is deployed thoroughly, it can result in new Question objects having three Choices (or however many are specified) that cannot be deleted. One solution is to use no Choices by default and only use the Add button, but that is not good either, as there should be at least one Choice object by default, or rather two of them, since we're working on a Poll. But the fields should all have the same functionality, they should all be removable.
Having seen this, my question for those experienced in working with Django on large projects: Is the "admin for free" feature used in production? Or would it be wiser to "roll your own" instead of trying to find workarounds for the weaknesses? I've identified one weakness, perhaps there are others.

It is excellent in all environments. The functionality is there is not explained in your tutorial. For example, if you want at least 3 answers within the TabularInline you would specify min_num = 3

Related

Django Master/Detail

I am designing a master/detail solution for my app. I have searched for ever in the django docs, also here and elsewhere I could, so I guess the answer is not that obvious, despite being an answer many people look for - not only in django, but in every language, I think.
Generally, in most cases, the master already exists: for example, the Django Docs illustrate the Book example, where we already have an Author and we want to add several Books for that Author.
In my case, the parent is not yet present on the database think of a purchase order, for instance.
I have thought to divide the process in two steps: the user would start to fill in the info for the master model (regular form) and then proceed to another view to add the lines (inline formset). But I don't think this is the best process at all - there are a lot of possible flaws in it.
I also thought about creating a temporary parent object in a different table and only having a definitive master when the children are finally created. But it still doesn't look clean.
Because of that, for my app it would be ideal to create the master object at the same time as the detail objects (lines) - again, like an order.
Is there a way where I can have the same view to manage both master and detail? Like this I would receive both in the same POST request and it would make a lot more sense, not to say it would be much cleaner.
Sorry if it's too long, and thank you in advance!
So I found out that in my case the process could actually be split in two phases.
For this I simply use the traditional model form and inline formset.
But! I also found out that there could be several answers to this:
We could get crazy and build some spaceship in AJAX that would get the job done, simply by sending a JSON object (in which the lines could be an array of objects)
Django also has its ways and it's possible to send multiple forms in the same request! (thank you #mousetail for the tip).
Of course, be there as it may, there are many ways to build a house, these are just the ones I found out.

Joomla 2.5 registering different kinds of users

Maybe this isn't the correct place to ask, but I asked this question on Joomla forums and did not get any answers. If someone can help me or at least point me in the right direction, I would really appreciate.
My question is: In a Joomla 2.5 website, I want to create two different kinds of forms for registering users. Maybe "registering" isn't the correct term. I want to create something like a very simple database which will hold records for two kinds of users:
- one which will be interested in working in projects, so in this case the form will have more fields and specific details to fill
- one which will be interested only in receiving newsletters from the site, and in this case only basic contact information will be required.
I did some research and found an extension named AcyMailing which can handle the newsletters for example, but I need to have all my potential users registered as Joomla users. I would like to avoid that if possible. If not, how can I differentiate the two kinds of users on registration, so the visitor can choose which option he wants and in this case, add more information to the registering process, if possible.
I'm not very experienced with Joomla, but since the site in question is already implemented using it, I don't have much choice.
Thanks in advance!
Chronoforms. Most definitely here would be a great use for their AWESOME free component. Your forms can work as registration forms (should you desire that); or can also just be free standing forms that log the information filled out on them to your database which you can later use however you would like (i.e. compiling a mailing list or something of that sort).
The form wizard makes it almost bullet proof, then you can have a form for 1 type of user to fill out, and a form for a different user build different ways.
That will get you the data - in order to mass mail those people you'll need a way to extract their emails out of the database (or find an email component that will let you email based on certain fields in the database or what have you); but it's totally possible and would be easily done I think with 1 simple mySQL query on your database table created by chronoforms.
In terms of something that will solve your issue quickly and get you the info you're looking for in two separate ways - chronoforms will do that exactly.

Letting Django superuser define new badges in gamification component

We are implementing the gamification component of a project in Django. We would like the superuser to be able to define new badges and redefine existing ones inside the Django admin interface.
The problem as we see it is that defining the sometimes complicated conditions for badges needs to be done in code. The superuser will be technically knowledgeable, but will not be a programmer.
How would you go about letting the superuser do this in the Django admin interface, rather than alter the application?
Here are some examples of badges:
Created 10 tags that have been used on 10 questions by 10 different
members.
Answered 10 unanswered questions.
Wrote 20 comments to a question (comments got at least 5 points each).
You don't say if you expect the superuser to be a programmer or not.
If you can assume this then you could include Python code in a database field and use eval or exec to run it.
For example:
badge.function = """
def award_badge(user):
return False
"""
vars = {}
exec(badge.function, vars)
if vars["award_badge"](user):
...
Clearly this has a lot of scope for abuse or mistakes, and certainly wouldn't be suitable if you expect non-technical users to be creating badges.
Depending on the complexity of the rules you need to create you might be able to create rules engine for executing them. In this case you create a sort of mini-language where each step in the process of deciding whether to award a badge or not is specified by a row in the database. Rules engines are a complicated topic so I won't go into detail here.
You're probably better off hard coding the rules for badges in your code than using either of these suggestions.

Avoiding circular dependencies in Django applications

While working on my Django-based projects I'm always trying to follow Django's approach to reusable apps - I'm trying to decouple my applications from each other and especially trying to avoid cross references but sometimes it does not seem to be possible.
Let's consider a simple example with 2 applications: articles and users. Articles application defines article model, articles list view and single article view, users application defines user model and user profile view. Article is referencing user from the author field, so articles application is obviously dependent on users application which is fine.
But when it comes to user profile, I want to display latest articles authored by the user (and may be latest articles viewed by the user) on that page but that makes users application aware of articles application which is what I'm trying to avoid.
I can obviously try to push all such references to the template level but it still does not solve the issue completely and at the same time may be very inefficient in terms of database queries sometimes.
What do you guys do in such cases?
If you are really set on not having any conversation between the 'user' app and the 'article' app, then you need a third app to act as interface. That would know about users and articles and define all the coupling between them. Your article view would be in there, since it has to get the user data, and your user profile view would be in there, because it needs to say "Fred wrote 5 articles".
Whether this level of decoupling is worth it, I don't know. Sometimes programming for re-usability gets in the way of making the thing usable in the first place.
The standard (or preferred) way of keeping coupled apps decoupled is to add a conditional coupling - like in some apps that try to import django-notification and only if they find it, they report events to it.
Still, if you have two apps that talks to each other by design, then I don't see any point in decoupling them - there are plenty of examples in Django world of apps that just require other apps. Note that I'm talking here about writing real-world software, not about some academic delibrations :-)
It seems that in this case, the dependency of users on articles is in a method, not a field. (Whether it's a model method, a model class method, or a manager method is immaterial). If that's so, you can do a lazy import of articles inside the method. By the time this import is performed, users.models will be fully loaded, so even if this is a circular import, it will not cause problems. The "import users" statement in articles will not have to re-load users and will have the full users namespace available.

Django: django-transmeta - sorting comments

I have created an article site, where articles are published in several languages. I am using transmeta (http://code.google.com/p/django-transmeta/) to support multiple languages in one model.
Also I am using generic comments framework, to make articles commentable. I wonder what will happen if the same article will be commented in one language and then in another. Looks like all comments will be displayed on both variants....
The question actually is:
Is there a possibility to display only comments submitted with current language of the article?
I tried the approach of transmeta for translation of dynamic texts and I had the following experience:
You want another language, you need to change the database model which is generally undesirable
You need every item in both languages, which is not flexible
You have problems linking with other objects (as you point out in your question)
If you take the way of transmeta you will need two solutions:
The transmeta solution for translating fields in a model
For objects connected to a model using transmeta you will need an additional field to determine the language, say CharField with "en", "de", "ru" etc.
These were major drawbacks that made me rethink the approach and switch to another solution: django.contrib.sites. Every model that needs internationalization inherits from a SiteModel:
class SiteModel(models.Model):
site = models.ForeignKey(Site)
Every object that would need transmeta translation is connected to a site. Every connected object can determine its language from the parent object's site attribute.
I basically ran the wikipedia approach and had a Site object for every language on a subdomain (en., de., ru.). For every site I started a server instance that had a custom settings file which would set the SITE_ID and the language of the site. I used django.contrib.sites.managers.CurrentSiteManagerto display only the items in the language of the current site. I also had a manager that would give you objects of every language. I constructed a model that connects objects of the same model from different languages denoting that they are semantically the same (think languages left column on wikipedia). The sites all use the same database and share the same untranslated User model, so users can switch between languages without any problem.
Advantages:
Your database schema doesn't need to change for additional languages
You are flexible: add languages easily, have objects in one language only etc.
Works with (generic) foreign keys, they connect to an object and know what language it is. You can display the comments of an object and they will be in one language. This solves your problem.
Disadvantages:
It's a greater deal to setup: you need a django server instance for every site and some more glue code
If you need e.g an article in different languages, you need another model to connect them
You may not need the django Site model and could implement something that does the same without the need of multiple django server instances.
I don't know what you are trying to build and what I described might not fit to your case, but it worked out perfectly for my project (internationalized community platform built upon pinax: http://www.bpmn-community.org/ ). So if you disclose some more about your project, I might be able to advise an approach.
To finally answer your question: No, the generic comments will not work out of the box with transmeta. As you realised you will have to display comments in both languages for the article that is displayed in one language. Or you will have to hack into the comments and change the model and do other dirty stuff (not recommended). The approach I described works with comments and any other pluggable app.
To answer your questions:
Two Django instances can share one database, no problem there.
If you don't want two Django instances, but one, you will have to do the following: A middleware checks the incoming request, extracts desired language from URL (en.example.com or example.com/en/ etc.) and saves the language preference in the request object. The view will have to take the request object with the language and take care of the filtering of objects accordingly. Since there is no dedicated server for the language (like in the sites approach where the language is stored in the settings.py file), you can only get the language from the request and you will have to pass attributes from the request object to Model managers to filter objects.
You could try to fake a global language state in the django application with an approach like threadlocals middleware, however I don't know if this plays out nicely with django I18N engine (which is also does some thread magic).
If you want to go big with your site in multiple languages, I recommend going for the sites-approach.