Use GET parameters as query filters - django

I have a URL with parameters such as:
field1__lt=7&field2__contains=bar
I understand how to get these values from the cleaned_data dict, but how can I put them into filter() statements? filter doesn't seem to like the key being a string.
This is for trusted users only, so there are no security concerns.

Use dict unpacking. If you have a dict like {'field1__lt':7, 'field2__contains':'bar'} in a variable lookups, then you can write filter(**lookups).

I think you need to pass few arguments in .filter method? Then you will need to use Q objects. So, something like this will work correctly.
MyModel.objects.filter(Q(field1__lt=7)&Q(field2__contains=bar))

Related

How to turn a Django QueryDict into a list of Django ORM OR filters?

I would like to turn this:
http://127.0.0.1:8000/fields_data/?field_name__exact=053&field_name__exact=064
into this:
fields = Fields.objects.filter(Q(field_name__exact='053')| Q(field_name__exact=field'064))
There could be additional numbers of field_name__exacts, it's not known until runtime.
In views.py, I can turn the URL into a QueryDict easily because request.GET is already a QueryDict object. According to the docs, QueryDict was designed in part so that the same key name could be used with multiple values, a common pattern in urls.
I then try to turn the QueryDict into something compatible with **kwargs by using:
fields = serialize('geojson', Fields.objects.filter(**request.GET.dict())), but request.GET.dict() looks like this:
{'field_name__exact': ['053', '064']}. As a result, I only ever get back the second object.
I'm starting to suspect I may need to write something more sophisticated involving comprehensions, but I feel like I'm really close. Can someone help me with the correct syntax to turn the QueryDict (multi-valued keys) into an OR'd set of Q()'s?
You can use list comprehension here:
from django.db.models import Q
Fields.objects.filter(
Q(*[(k,v) for k,vs in request.GET.lists() for v in vs], _connector=Q.OR)
)
This will then make a query that makes a logical OR between the items in the QueryDict.

Check if object T exists field-wise in queryset of T

I have an address objects in my app which has the usual street, street_nr, etc. fields.
Is there a better way to do this:
Address.objects.filter(street=data["street"],
street_nr=data["street_nr"],
zip_code=data["zip_code"],
city_name=data["city_name"],
country_name=data["country_name"]).exists()
Mind that I check only for the passed fields.
As long as the key names in the data dictionary match the field names you want to query on, you can use the **kwargs syntax:
Address.objects.filter(**data)

Django - Query results as 'associative' dict?

I was wondering if there was any handy helpers in Django which would return the results of a query into a more 'usuable' format so I don't have to iterate through them in my view.
I have a query like this:
self.filter(key__in=keys).values('key','value')
What I want to end up is an object which looks like
{'some_key':'some value', 'some_other_key':'some_other_value'}
So in my model I could do something like this:
settings = Setting.objects.get_keys(['some_setting','some_other_setting'])
print settings.some_setting # returns 'some value'
Where 'get_keys' is a manager function which runs the above filter query. Any idea how I might do this? I wouldn't be opposed to iterating through the results in the Settings Manager because I could store them for later... I couldn't quite figure our how to create a 'global' model variable though.
Any help would be greatly appreciated!
If you use values_list rather than values, it will return a set of two-tuples, which you can then pass to dict() to create a dictionary:
return dict(self.filter(key__in=keys).values_list('key','value'))
I think what you're looking for is: http://docs.djangoproject.com/en/stable/ref/models/querysets/#in-bulk
This function takes a list of primary keys and return a dictionary of the models mapped to the keys. It sounds like this is exactly what you want?

Using a string as the argument to a Django filter query

I'm trying to do a django query, but with the possibility of several different WHERE parameters. So I was thinking of doing something like:
querystring = "subcat__id__in=[1,3,5]"
Listing.objects.filter(querystring)
Here Listing is defined in my model, and it contains the Many-To-Many field subcat. However, that raises a ValueError because filter doesn't accept a string as its argument. Is there a way in Python to have a string evaluated as just its contents rather than as a string? Something like a print statement that prints the value of the string inline rather than to the standard output.
By the way, the reason I don't just do
querystring = [1,3,5]
Listing.objects.filter(subcat__id__in=querystring)
is that I'm not always filtering for subcat__id, sometimes it's one or several other parameters, and I'd rather not have to write out a bunch of separate queries controlled by if statements. Any advice is much appreciated.
Perhaps...
filter_dict = {'subcat__id__in': [1,3,5]}
Listing.objects.filter(**filter_dict)
Listing.objects.filter(**{"subcat__id__in": ast.literal_eval("[1,3,5]")})

Django: Sort order the list in objects

I have list1 in order by id. Like this:
['4','2','1','17'] #edited
How to get list2 from object Entry in order of list1.
In the case Query ValueList, as well as on the question.
[u'4', u'2', u'1', u'17']
Because some properties are not in QuerySet
Thanks for your answers !
Also you can use in_bulk() and then just get dict values in defined order. Wrap this in custom manager for further comfort
You'll need to use CASE ... WHEN ... THEN ... END in order to sort your IDs. Pass the full CASE clause in the select argument of extra(), and the use the order_by argument with the given field name.