5

I used to create dynamic filters like

q = Session.query(Table)    
search_conditions = "%s ILIKE '%s%s%s'" % (str(nm), '%', val ,'%')
q = q.filter(search_conditions)

It work ok for string and int statements, but now I need to filter dates the way like this. I have a date column and trying to filter it like this

date = '01.01.2011'
fd,fm,fy = date.split('.')
from_date = dt.date(int(fy),int(fm),int(fd))

ffilter = "%s > %r" %(str(ft), fromdate)
q = q.filter(ffilter)

Can you help me with this?

best regards, Sergey

3
  • Possible typo. it should be q = Session.query(Table), not qeuery. Commented Aug 16, 2011 at 20:12
  • @Iwolf: Is the field you want to check, a DATE field? Commented Aug 16, 2011 at 20:13
  • thanks of course it query... and type is DATE Commented Aug 16, 2011 at 21:02

3 Answers 3

4

That doesn't look like terribly idiomatic sqlalchemy. You already have a Table object you're using to build your query, you can also use it to express the predicates in the generated WHERE clause, even dynamically:

date = '01.01.2011'
from_date = dt.datetime.strptime(date, "%d.%m.%Y").date()
q = session.query(Table) \
     .filter(Table.c[nm].like('%%%s%%' % val) ) \
     .filter(Table.c[ft] > from_date)

If anything, this is the main advantage of using sqlalchemy.

This pattern extends to almost every corner of sqlalchemy, for instance, if you must specify which table to select from in a dynamic fashion, this can be handled by accessing the MetaData.tables property, which is also a dict.

If you really need the full generality of expressiveness exposed to the user, you probably will be better served by just allowing them to enter SQL statements, Mixing the generative queries in the style of sqlalchemy with user entered expressions is probably not going to help you or your users. You could possibly use SQLalchemy to generate skeleton queries and then let users edit them to customize them in the ways they need.

Sign up to request clarification or add additional context in comments.

6 Comments

I have a lot of dynamic filters and I cannot use Table_name object in filter statements
can you tell us more about the filters you'd like to generate? You might be surprised just what you can do using sqlalchemy.
I need to form queries based on data from users, and I dont know beforehand with which table I should work. Some time ago I already tried to do this using sqlalchemy orm features with no luck. In example you wrote "TABLE" is an object and I didnt know a way to provide it using string, also filters (Table.Column) cannot be provided as string Of course it will be great to liquidate this raw sql statements, if you know how to do this please enlighten me )
can't find anything about use of "MetaData.tables" dict, can you tell me more about it or give a link where to read?
I mean how to construct queries this way. something like tablename = a. colname = b, q = Session.query(metadata.tables[tablename]).filter(metadata.tables[tablename].c[colname]>10), right?
|
2

Not sure, but why not to do the following:

date = '01.01.2011'

ffilter = "%s > CAST('%s' AS DATE)" %(str(ft), date)
q = q.filter(ffilter)

7 Comments

thanks a lot man, this is exactly what I need... I'm using DATE instead of DATETIME and it works like a charm
You are welcome, Sergei, and don't forget to (down)vote solutions you (dis)like
Why send this to database: aDateField > CAST('01.01.2011' AS DATE)? And not rewrite it in Python as aDateField > '2011-01-01'?
@Artsiom: Are you sure CAST('05.12.2011' AS DATE) will be translated as 5-Dec-2011 and not May-12-2011 ?
@ypercube I dont know why it doesnot work, anyway I've got an working code, thanks for your help
|
0

The filter you want should finally be, (before sent to the database) like this:

date_field > '2011-01-01'

So, try this:

date = '01.01.2011'
fd,fm,fy = date.split('.')
from_date = '-'.join([fy,fm,fd])

ffilter = "%s > '%r'" %(date_field, from_date)
q = q.filter(ffilter)

UPDATE: Quotes where missing around %r

1 Comment

Although I'm not sure I understand correctly which string represents the table field and which your testDate.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.