How to filter in django - python

I want to filter Consultants(this is my model from where I want to filter)
on the basis of username.
But when I try to filter it returns a empty list.
my code is
username=request.user.username
print "value of requested logged in user is",username
user=Consultants.objects.filter(username='username')
print user.consul_id
When I print consul_id it says QuerySet object has no attribute consul_id.
How can I filter? Should I use get to filter.I have used get but it didn't solve my problem.

You should change this:
user=Consultants.objects.filter(username='username')
print user.consul_id
to
user=Consultants.objects.filter(username='username').first()
print user.consul_id if user else 'None'
Because calling filter() returns a Queryset. You need to get the first element from that queryset(hence use first()). Also you can use get() method

Related

How to retrieve value from queryset in django?

I am trying to retrieve different .values() from query sets but am having an issue with it returning the proper values. How to write my model so that I can retrieve attributes using the .values() method?
I have tried to change the model's __str__ method to return a dictionary but that does not work or I am doing it wrong.
class Settings(models.Model):
bb_bonus_qualify = models.CharField(max_length=16, default=38.00)
service_breakpoint = models.CharField(max_length=16, default=1700.00)
def __str__(self):
return '%s: %s, %s: %s' % (
'bb_bonus', self.bb_bonus_qualify, 'service_breakpoint', self.service_breakpoint)
I would like to say Settings.objects.last().values('bb_bonus') and be returned the value which is self.bb_bonus_qualify. The common error I seem to get is: AttributeError: 'Settings' object has no attribute 'values'
The problem here is that your .last() will retrieve the last Settings object. You thus will call .values('bb_bonus') on the Settings object. Since a model has no .values(..) method, it will thus not return anything.
You can however retrieve the value of a certain column from a queryset, with:
Settings.objects.values_list('bb_bonus_qualify', flat=True).last()
We here thus use .values_list(..) [Django-doc], this accepts the names of the columns as parameters. It will then usually return a QuerySet of lists with these values. But if you specify one column; then, as the documentation says:
If you only pass in a single field, you can also pass in the flat parameter. If True, this will mean the returned results are single values, rather than one-tuples.
So that means we create a QuerySet of singular values, and we then will retrieve the last entry of that queryset. Note that we do not fetch all the elements from the queryset, the .last() is "injected" in the query we perform on the database, so the result is the scalar value of that column for the last record.
The .values_list(..) thus needs to be performed before the .last(), since otherwise you are talking to a Settings object, not to a QuerySet.
AFAIK __str__ has nothing to do with .values() - the problem here is that you need to specify the values before getting a specific item, rather than the other way round:
Settings.objects.values('bb_bonus').last()

Django how to query objects one by one

I have to query an object from a model, this object is called "exercise" and has many fields(title, body, answers, etc.) I need to get "exercise objects" one by one with all their fields, do some rendering on them and give back a pdf of the exercise as result.
The problem is, if I do:
exercises = ExerciseModel.objects.all()
I get all of them. If I do:
some_exercises = ExerciseModel.objects.filter(something=something)
I get "some of them" depending on filter. And if i do:
exercise = ExerciseModel.objects.get()
I get
error get() returned more than one exercise
How can I get them one by one? I must be able to use them as input for another function.
If you need to perform the task on only 1 exercise, use get() instead. In such case, you need a criteria to make sure get() will return 1 and only 1 result.
Example:
ex = ExerciseModel.objects.get(pk=123)
From the doc:
Returns the object matching the given lookup parameters, which should be in the format described in Field lookups.
get() raises MultipleObjectsReturned if more than one object was found. The MultipleObjectsReturned exception is an attribute of the model class.
get() raises a DoesNotExist exception if an object wasn’t found for the given parameters. This exception is an attribute of the model class.
When you have a QuerySet with filters that ensure the underlying SQL request will return only 1 row, you can call get() without argument on the QuerySet. This return the row as model instance, instead of returning it as a list containing 1 elemnt.
Original answer:
Both filter() and all() methods return a QuerySet instance. You can iterate on it to perform a task for each "exercise" returned by your request
for exercise in ExerciseModel.objects.filter(something=something):
# ... do what you need on your exercise
From the documentation:
A QuerySet is iterable, and it executes its database query the first time you iterate over it. For example, this will print the headline of all entries in the database
What you need is .iterator() which will turn a queryset to an iterator:
exercises = ExerciseModel.objects.all().iterator()
then you get iterate over it in a for loop:
for exercise in exercises:
...
This will improve performance when you have large number of items. However, it has some downsides as well as stated in the docs
Hope it helps!
.get() must return a single object, not a QuerySet instance. If you want to get a single exercise then you must pass a parameter to the .get instance. For example, retrieving an object by name would require the following code:
exercise = ExerciseModel.objects.get(name="an_exercise")
If you want to iterate through all the objects without actually retrieving a QuerySet containing the objects, you could use the following code:
for i in range(Exercise.objects.all().count()):
exercise = Exercise.objects.get(pk=i)
... operate on object ...

Cannot assign "(<Blog: title1>, False)": "Post.blog" must be a "Blog" instance [duplicate]

I'm trying to use get_or_create for some fields in my forms, but I'm getting a 500 error when I try to do so.
One of the lines looks like this:
customer.source = Source.objects.get_or_create(name="Website")
The error I get for the above code is:
Cannot assign "(<Source: Website>, False)": "Customer.source"
must be a "Source" instance.
From the documentation get_or_create:
# get_or_create() a person with similar first names.
p, created = Person.objects.get_or_create(
first_name='John',
last_name='Lennon',
defaults={'birthday': date(1940, 10, 9)},
)
# get_or_create() didn't have to create an object.
>>> created
False
Explanation:
Fields to be evaluated for similarity, have to be mentioned outside defaults. Rest of the fields have to be included in defaults. In case CREATE event occurs, all the fields are taken into consideration.
It looks like you need to be returning into a tuple, instead of a single variable, do like this:
customer.source,created = Source.objects.get_or_create(name="Website")
get_or_create returns a tuple.
customer.source, created = Source.objects.get_or_create(name="Website")
get_or_create() returns a tuple:
customer.source, created = Source.objects.get_or_create(name="Website")
created → has a boolean value, is created or not.
customer.source → has an object of get_or_create() method.
Following #Tobu answer and #mipadi comment, in a more pythonic way, if not interested in the created flag, I would use:
customer.source, _ = Source.objects.get_or_create(name="Website")
The issue you are encountering is a documented feature of get_or_create.
When using keyword arguments other than "defaults" the return value of get_or_create is an instance. That's why it is showing you the parens in the return value.
you could use customer.source = Source.objects.get_or_create(name="Website")[0] to get the correct value.
Here is a link for the documentation:
http://docs.djangoproject.com/en/dev/ref/models/querysets/#get-or-create-kwargs
get_or_create method would actually return a tuple.
The trick with the get_or_create method is that it actually returns a tuple of (object, created). The first element is an instance of the model you are trying to retrieve and the second is a boolean flag to tell if the instance was created or not. True means the instance was created by the get_or_create method and False means it was retrieved from the database
So you can do something like to get the source instance
``` customer.source = Source.objects.get_or_create(name="Website")[0]
```
Important warning.
you should take care of the following before using the get_or_create , https://docs.djangoproject.com/en/4.0/ref/models/querysets/.
....
Warning
This method is atomic assuming that the database enforces uniqueness of the keyword arguments (see unique or unique_together). If the fields used in the keyword arguments do not have a uniqueness constraint, concurrent calls to this method may result in multiple rows with the same parameters being inserted.

from list to select menu in django

I thought I had it figured out but now I'm missing something.
First I have a QuerySet, records
records = Record.objects.all()
Now I want to make this into a list of one of the columns of the table, columnA
alist = records.values_list('columnA')
And then I want to pass this list in as a parameter to a custom form.
FilterForm(alist)
Here's my form
class FilterForm(forms.Form,list):
numbers = forms.ChoiceField(list)
but keep getting an error that 'type' object is not iterable. I'm not sure the problem has to do with the passing of the list because when I try and run this code in the shell, I get the error message when just importing the FilterForm
EDIT: I changed my FilterForm so now it looks like this.
class FilterForm(forms.Form):
def __init__(self,numbers):
number = forms.ChoiceField(numbers)
so now I think it's more evident what I'm trying to do, pass in a list to the FilterForm. However when I render my template and pass the form, no form field shows up. No error message though
EDIT EDIT: Also tried this, saw it online
class FilterForm(forms.Form):
number = forms.ChoiceField()
def __init__(self,numbers):
super(FilterForm,self).__init__()
self.fields['number'].choices=numbers
but error:
Exception Type: TemplateSyntaxError
Exception Value:
Caught ValueError while rendering: need more than 1 value to unpack
The problem is the word list in this line:
numbers = forms.ChoiceField(list)
You need to provide a specific list to ChoiceField.
Here's an error:
class FilterForm(forms.Form,list):
numbers = forms.ChoiceField(list)
You make FilterForm a subclass of forms.Form and list; then you expect list to be available as argument to the ChoiceField.
I think you are looking for dynamic ChoiceFields.
Further reading:
django model/modelForm - How to get dynamic choices in choiceField?

Correct way to use get_or_create?

I'm trying to use get_or_create for some fields in my forms, but I'm getting a 500 error when I try to do so.
One of the lines looks like this:
customer.source = Source.objects.get_or_create(name="Website")
The error I get for the above code is:
Cannot assign "(<Source: Website>, False)": "Customer.source"
must be a "Source" instance.
From the documentation get_or_create:
# get_or_create() a person with similar first names.
p, created = Person.objects.get_or_create(
first_name='John',
last_name='Lennon',
defaults={'birthday': date(1940, 10, 9)},
)
# get_or_create() didn't have to create an object.
>>> created
False
Explanation:
Fields to be evaluated for similarity, have to be mentioned outside defaults. Rest of the fields have to be included in defaults. In case CREATE event occurs, all the fields are taken into consideration.
It looks like you need to be returning into a tuple, instead of a single variable, do like this:
customer.source,created = Source.objects.get_or_create(name="Website")
get_or_create returns a tuple.
customer.source, created = Source.objects.get_or_create(name="Website")
get_or_create() returns a tuple:
customer.source, created = Source.objects.get_or_create(name="Website")
created → has a boolean value, is created or not.
customer.source → has an object of get_or_create() method.
Following #Tobu answer and #mipadi comment, in a more pythonic way, if not interested in the created flag, I would use:
customer.source, _ = Source.objects.get_or_create(name="Website")
The issue you are encountering is a documented feature of get_or_create.
When using keyword arguments other than "defaults" the return value of get_or_create is an instance. That's why it is showing you the parens in the return value.
you could use customer.source = Source.objects.get_or_create(name="Website")[0] to get the correct value.
Here is a link for the documentation:
http://docs.djangoproject.com/en/dev/ref/models/querysets/#get-or-create-kwargs
get_or_create method would actually return a tuple.
The trick with the get_or_create method is that it actually returns a tuple of (object, created). The first element is an instance of the model you are trying to retrieve and the second is a boolean flag to tell if the instance was created or not. True means the instance was created by the get_or_create method and False means it was retrieved from the database
So you can do something like to get the source instance
``` customer.source = Source.objects.get_or_create(name="Website")[0]
```
Important warning.
you should take care of the following before using the get_or_create , https://docs.djangoproject.com/en/4.0/ref/models/querysets/.
....
Warning
This method is atomic assuming that the database enforces uniqueness of the keyword arguments (see unique or unique_together). If the fields used in the keyword arguments do not have a uniqueness constraint, concurrent calls to this method may result in multiple rows with the same parameters being inserted.

Categories