Как написать много столбцов в разделе с sqlalchemy

Пожалуйста, предложите способ написать запрос в нескольких столбцах в статье с использованием SQLAlchemy?

Вот пример фактического запроса:

SELECT url FROM pages WHERE (url_crc, url) IN ((2752937066, 'http://members.aye.net/~gharris/blog/'), (3799762538, 'http://www.coxandforkum.com/')); 

У меня есть таблица с первичным ключом из двух столбцов, и я надеюсь избежать добавления еще одного ключа, который будет использоваться только как индекс.

PS Я использую mysql DB.

Обновление: этот запрос будет использоваться для пакетной обработки – поэтому мне нужно будет поместить несколько сотен пар в предложение in. С подходом IN clause я надеюсь узнать фиксированное ограничение того, сколько пар я могу вставить в один запрос. Как и в случае с Oracle, по умолчанию задано ограничение 1000 переходов.

Использование комбинации AND / OR может быть ограничено длиной запроса в символах. Который был бы переменным и менее предсказуемым.

3 Solutions collect form web for “Как написать много столбцов в разделе с sqlalchemy”

Предполагая, что ваша модель определена на Page , вот пример использования tuple_ :

 keys = [ (2752937066, 'http://members.aye.net/~gharris/blog/'), (3799762538, 'http://www.coxandforkum.com/') ] select([ Page.url ]).select_from( Page ).where( tuple_(Page.url_crc, Page.url).in_(keys) ) 

Или, используя API запросов:

 session.query(Page.url).filter(tuple_(Page.url_crc, Page.url).in_(keys)) 

Я не думаю, что в настоящее время это возможно в sqlalchemy, и не все RDMBS поддерживают это.
Вы всегда можете преобразовать это в условие OR(AND...) хотя:

 filter_rows = [ (2752937066, 'http://members.aye.net/~gharris/blog/'), (3799762538, 'http://www.coxandforkum.com/'), ] qry = session.query(Page) qry = qry.filter(or_(*(and_(Page.url_crc == crc, Page.url == url) for crc, url in filter_rows))) print qry 

должен произвести что-то вроде (для SQLite):

 SELECT pages.id AS pages_id, pages.url_crc AS pages_url_crc, pages.url AS pages_url FROM pages WHERE pages.url_crc = ? AND pages.url = ? OR pages.url_crc = ? AND pages.url = ? -- (2752937066L, 'http://members.aye.net/~gharris/blog/', 3799762538L, 'http://www.coxandforkum.com/') 

Кроме того , вы можете объединить два столбца в один:

 filter_rows = [ (2752937066, 'http://members.aye.net/~gharris/blog/'), (3799762538, 'http://www.coxandforkum.com/'), ] qry = session.query(Page) qry = qry.filter((func.cast(Page.url_crc, String) + '|' + Page.url).in_(["{}|{}".format(*_frow) for _frow in filter_rows])) print qry 

который создает ниже (для SQLite), поэтому вы можете использовать IN :

 SELECT pages.id AS pages_id, pages.url_crc AS pages_url_crc, pages.url AS pages_url FROM pages WHERE (CAST(pages.url_crc AS VARCHAR) || ? || pages.url) IN (?, ?) -- ('|', '2752937066|http://members.aye.net/~gharris/blog/', '3799762538|http://www.coxandforkum.com/') 

Я закончил использование решения на основе test (): сгенерировал «(a, b) in ((: a1,: b1), (: a2,: b2), …)» с именованными связями vars и создавал словарь со связью ценности варов.

 params = {} for counter, r in enumerate(records): a_param = "a%s" % counter params[a_param] = r['a'] b_param = "b%s" % counter params[b_param] = r['b'] pair_text = "(:%s,:%s)" % (a_param, b_param) enum_pairs.append(pair_text) multicol_in_enumeration = ','.join(enum_pairs) multicol_in_clause = text( " (a,b) in (" + multicol_in_enumeration + ")") q = session.query(Table.id, Table.a, Table.b).filter(multicol_in_clause).params(params) 

Еще один вариант, который я подумал об использовании mysql upserts, но это сделало бы все включено даже менее портативным для другого db-механизма, а затем использовало бы предложение multicolumn in.

Обновление SQLAlchemy имеет конструкцию sqlalchemy.sql.expression.tuple _ (* clauses, ** kw), которая может использоваться для этой же цели. (Я еще не пробовал)

Python - лучший язык программирования в мире.