web-dev-qa-db-fra.com

Requête SQLAlchemy dans laquelle une colonne contient une sous-chaîne

Je construis une requête utilisant SQLAlchemy et SQLite3 dans laquelle j'aimerais sélectionner des lignes dans lesquelles une colonne String contient une sous-chaîne particulière. Quelle est la meilleure façon d'y parvenir? 

21
Dave

Filtrer par db.table.column.like('%needle%'). Il existe également ilike pour une recherche insensible à la casse.

Pour une interface plus sophistiquée, vous pouvez autoriser les caractères génériques "dir" connus.

if '*' in needle or '_' in needle: 
    looking_for = needle.replace('_', '__')\
                        .replace('*', '%')\
                        .replace('?', '_')
else:
    looking_for = '%{0}%'.format(needle)

result = db.table.filter(db.table.column.ilike(looking_for))

Remarques:

  • db.table.filter et db.table.column sont pour SQLSoup ( SQLSoup est utile si la base de données a été créée par une autre application)
  • pour SQLAlchemy Core, il s'agit de select(column_list).where(table.c.column.ilike(expr)). Cette interface est la solution idéale lorsque vous souhaitez tirer parti de toute la puissance du SQL brut sans avoir à composer manuellement les instructions à l'aide d'une interpolation de chaîne (utilisez-la avec SQLSoup pour l'introspection, vous n'avez donc pas besoin de déclarer des tables)
  • pour SQLAlchemy Declarative (celui utilisé dans Flask), il s'agit de Model.query.filter(Model.field.ilike(expr))
26
Paulo Scardine

Essaye ça 

Model.query.filter(Model.columnName.contains('sub_string'))
50
kakapy

Si table.c.column.like("%...%") devrait fonctionner, il existe un moyen plus direct de dire ce que vous voulez:

table.c.column.contains("needle")

Cela générera généralement la même requête SQL mais il est préférable de lire pour les non-initiés. Notez que contient ne semble pas échapper à "_" et "%".

11
Bluehorn
@app.route('/<var>', methods=['GET'])
def getdb(var):
    look_for = '%{0}%'.format(var)
    log1 = table.query.filter(table.col.like(look_for))

J'ai utilisé SQLAlchemy et Flask (app.route est un décorateur.) dans une autre variable appelée look_for (car var ne peut pas être utilisée directement dans la requête) en utilisant le format () et log1 stocke les nuplets demandés.

1