Define a verbose name for an entire Django model - django

I want to create a model named Model. I'm pretty sure this isn't allowed, so I'm forced to use some other term for the model name. Let's say I call it Mdl. However from the user perspective, I want to still refer to the table as Model. Is there a way to define a verbose name for the entire model Mdl the same way you can for model fields? In my templates, I reference the name of the current table at the top of the document:
{{ model }}
which gets passed from a view. If I can't define a verbose name, then I'm going to have to call some function every time to translate Mdl's name to Model just for that one table. Does anyone have an alternate suggestion?

You want Meta.verbose_name

Related

Django: order formset without form change

I have a form with only one field (name of family members).
class FamilyMemeberItem(forms.Form):
name= forms.CharField(label=_('name'), max_length=20)
Now I want my form be sorted (arbitrary order) defined by the user. For example in a family, I want to show A first, then B and then C, while the creation sequence may be C, B and A. Is there anyway to do that?
I searched and realized I should add an order field to my form and override the __iter__() method. Is that the only way? If there is no way to do that without change in form?
And could anyone please tell me about the field can_order of formset_factory? When I add it, an extra filed is loaded next to my form, and that's and integer presenting the number of that field. Can I change and save that so that the order changes?
I answered a similar question you posted.
I'll just repeat the last part here:
If you want to store the order in the database, you need to define a new field in you model and store the order in that. The order of formsets is only present inside a single request/response, after that its gone.

Change one django form field value relative to another

Let say I have two fields in a django form country and state.I want the values of state to relatively change with the values of country.i.e. I want the state field to list out the states of the country that user has selected. Also the state field should be empty during form initiation.I know that this can be done using java script and other scripts.But,I would like to know if there are any conventional methods exists in django to do the same.???
Sounds like you need to create a model for Country and State.
State model should have a foreign key linking to Country. This means many states can be related to one country. Then, populate the tables with all countries and states you want.
In your form, you can override the 'init' method with custom behavior. So, if you have declared a field 'state' then you can do something like self.fields['state'].choices = State.object.filter(country_id=some_country_id). This assumes you have some_country_id already and you can pass this through as a kwarg during instantiation.

In Django, what does symmetrical=True do?

For example:
class Contact(models.Model):
contacts = models.ManyToManyField('self', through='ContactRelationship', symmetrical=False)
What does the symmetrical=False parameter do?
When should it be left as True, and when should it be set as False?
How does this settings affect the database (does it create extra columns etc)?
Let's say you have two instances of Contact, John and Judy. You may decide to make John a contact of Judy. Should this action also make Judy a contact of John? If so, symmetrical=True. If not, symmetrical=False
Here is what is says in the documentation:
Only used in the definition of ManyToManyFields on self. Consider the following model:
from django.db import models
class Person(models.Model):
friends = models.ManyToManyField("self")
When Django processes this model, it identifies that it has a ManyToManyField on itself, and as a result, it doesn’t add a person_set attribute to the Person class. Instead, the ManyToManyField is assumed to be symmetrical – that is, if I am your friend, then you are my friend.
By default, the value of symmetrical is True for Many to Many Field which is a bi-directional relationship.
Using a through table (symmetrical=False):
But you can also imagine a situation where you don't need this type of relationship so you can add symmetrical=False. And, this can be achieved by using a through table because by default symmetrical is False if you use a through table:
Recursive relationships using an intermediary model are always defined as non-symmetrical – that is, with symmetrical=False – therefore, there is the concept of a “source” and a “target”. In that case 'field1' will be treated as the “source” of the relationship and 'field2' as the “target”.
So you can imagine a situation where you do need the direction i.e. let's say there is a Node model and it has a relationship with itself using a through table. If we didn't have the requirement of direction here we could go with the example shown earlier. But now we also need a direction from one node to another where one being source and another one being target and due to nature of this relationship it cannot be symmetrical.

Django annotate a field value to queryset

I want to attach a field value (id) to a QS like below, but Django throws a 'str' object has no attribute 'lookup' error.
Book.objects.all().annotate(some_id='somerelation__id')
It seems I can get my id value using Sum()
Book.objects.all().annotate(something=Sum('somerelation__id'))
I'm wondering is there not a way to simply annotate raw field values to a QS? Using sum() in this case doesn't feel right.
There are at least three methods of accessing related objects in a queryset.
using Django's double underscore join syntax:
If you just want to use the field of a related object as a condition in your SQL query you can refer to the field field on the related object related_object with related_object__field. All possible lookup types are listed in the Django documentation under Field lookups.
Book.objects.filter(related_object__field=True)
using annotate with F():
You can populate an annotated field in a queryset by refering to the field with the F() object. F() represents the field of a model or an annotated field.
Book.objects.annotate(added_field=F("related_object__field"))
accessing object attributes:
Once the queryset is evaluated, you can access related objects through attributes on that object.
book = Book.objects.get(pk=1)
author = book.author.name # just one author, or…
authors = book.author_set.values("name") # several authors
This triggers an additional query unless you're making use of select_related().
My advice is to go with solution #2 as you're already halfway down that road and I think it'll give you exactly what you're asking for. The problem you're facing right now is that you did not specify a lookup type but instead you're passing a string (somerelation_id) Django doesn't know what to do with.
Also, the Django documentation on annotate() is pretty straight forward. You should look into that (again).
You have <somerelation>_id "by default". For example comment.user_id. It works because User has many Comments. But if Book has many Authors, what author_id supposed to be in this case?

Django ORM: SELECT on field attributes

I have a model that contains a FileField. I want to search for a specific filename. How do I do it? I was trying:
MyModel.objects.get(document__name=FOO)
I got a Join on field 'document' is not permitted.
Thanks!
The attributes of a FileField are not stored in the database, and cannot be used in a query. For example, the name is simply the upload_to string plus the filename. If you want to store extra data about the file you have to put that data into other fields on the database, as the example documentation shows with a Car having a name of "57 Chevy".
Also, typically the double underscore in Django's ORM denotes following a database relationship, either a ForeignKey or a ManyToMany. So in the example ORM call you provided, I would assume that MyModel had a field document that was either a ForeignKey or ManyToMany to another model, and that other model has a field called name. Which doesn't sound like is the case.
Hope that helps some.
Do this instead:
MyModel.objects.get(document__icontains='FOO')
You can filter on document, and it'll filter by the string that is the path on disk to the file.