Comparing two fields in django queryset - mysql

How would I do the following SQL query in the Django ORM?
SELECT * FROM my_table WHERE date_added > date_created;

I'm guessing you don't have the date_created available as a variable (as #tttthomasssss assumes) so it will be something like this:
from django.db import models
YourTable.objects.filter(date_added__gt=models.F('date_created')
Docs on F expressions: https://docs.djangoproject.com/en/dev/ref/models/expressions/#f-expressions

You can use F() expressions in queries like this:
MyModel.objects.filter(date_added__gt=F('date_created'))

You can use __gt for >: MyModel.objects.filter(date_added__gt=date_created).
See the documentation for querysets here.
EDIT:
If date_created isn't available to you, then #Wolph's solution is the one.

Related

How to use whereBetween and like operator together in laravel?

I need to change the below MySQL code to laravel format using where, between and like operators together:
select count(id) from tbl1
where created_at BETWEEN
'2018-12-10%' AND '2018-12-12%'
I found the answer as below:
\DB::table('tbl1')->whereBetween('created_at',[$sdate.'%', $enddate.'%'])->count();
If you're using a Model you could use the whereBetween method, take a look at the following example:
User::query()->whereBetween('created_at', [$start, $end])->count();

Convert SQLite to Django ORM

I have a query in SQLite which groups the fields by weeks and performs sum and average over distance and time fields in the same table:
select
strftime('%W', datetime) WeekNumber,
sum(distance) as TotalDistance,
sum(distance)/sum(time) as AverageSpeed
from sample_login_run
group by WeekNumber;
I am trying to convert this query to Django ORM and avoid using Raw function. I understand that I would need to use extra in Django ORM. That should not be a problem though. I came up this:
Run.objects.extra(select={'week': "strftime('%%W', datetime)"}).values(
'week','distance').annotate(
total_distance=Sum('distance'), average_time=F('distance') / F('time'))
But this is also grouping the data by average_time and average_distance field. Any help will be really appreciated. Thank you.
Right solution for this is:
Run.objects.extra(select={'week': "cast(strftime('%%W', date_run) as integer)"}).values('week').annotate(
total_distance=Sum('distance'), average_time=F('distance') / F('time'))
Fields passed in values will go under group by part of the query.

Django sort queryset by related model field

I have the following models (abbreviated for clarity):
class Order(models.Model):
some fields
class OrderStatus(models.Model):
order = models.ForiegnKey(Order)
status = models.CharField(choices=['ORDERED', 'IN_TRANSIT', 'RECEIVED'])
time = models.DateTimeField()
I would like to sort all Orders that contain all three OrderStatuses by their order received time.
In other words, select the orders that have records of Ordered, In Transit, and Received like so:
Order.objects.filter(orderstatus__status=OrderStatus.ORDERED)
.filter(orderstatus__status=OrderStatus.IN_TRANSIT)
.filter(orderstatus__status=OrderStatus.RECEIVED)
... and then sort them by the time field of their related OrderStatus model for which status=OrderStatus.RECEIVED.
This is where I'm stuck. I have read the Django docs on the .extra() queryset modifier and direct SQL injection, but I'm still at a loss. Could I achieve it with an annotated field and Q objects or am I better going the .extra route?
Didn't you try to do like this?
Order.objects.filter(orderstatus__status=OrderStatus.ORDERED)
.filter(orderstatus__status=OrderStatus.IN_TRANSIT)
.filter(orderstatus__status=OrderStatus.RECEIVED)
.order_by('orderstatus__time')
On my models it worked as expected - order_by picked the last joined orderstatus just as you need. If you're not sure you can check the real query like this (in django shell):
from django.db import connection
# perform query
print(connection.queries)
Also it can be done like this:
OrderStatus.objects.filter(status=OrderStatus.RECEIVED)
.order_by('time').select_related('order')
.filter(order__orderstatus__status=OrderStatus.ORDERED)
.filter(order__orderstatus__status=OrderStatus.IN_TRANSIT)

What is the "Rails Way" of doing a query with an OR clause using ActiveRecord?

I'm using Rails 3 with a MySQL database, and I need to programmatically create a query like this:
select * from table where category_name like '%category_name_1%'
OR category_name like '%category_name_2%'
(...snip...)
OR category_name like '%category_name_n%'
Given the table size and the project scope (500 rows at most, I think), I feel that using something like thinking sphinx would be overkill.
I know I could simply do this by writing the query string directly, but wanted to know if there's an ActiveRecord way to do this. There's no mention of this on the official guide, and I've been googling for a long while now, just to end empty-handed :(
Also, is there a reason (maybe a Rails reason?) to not to include the OR clause?
Thanks!
Assuming you have an array names with category names:
Model.where( names.map{"category_name LIKE ?"}.join(" OR "),
*names.map{|n| "%#{n}%" } )
you should google first, there is already an answer.
Look here and then here
and you'll get something like this:
accounts = Account.arel_table
Account.where(accounts[:name].matches("%#{user_name}%").or(accounts[:name].matches("%#{user_name2}%")))
If you look at the guide, they have examples that can easily be modified to this:
Client.where("orders_count = ? OR locked = ?", params[:orders], false)
Mysql has a regexp function now that can clean things up a bit, assuming there's no regex metachars in your category names:
Table.where "category_name regexp '#{names.join('|')}'"

How do I do mysql "LIKE" in django?

SELECT * from myapp_mymodel WHERE code LIKE "914%";
I would recommend reading the manual, it clearly tells you how to do this: http://docs.djangoproject.com/en/dev/ref/models/querysets/#startswith
MyModel.objects.filter(code__startswith='914')