sql >> Databasteknik >  >> RDS >> PostgreSQL

Generera SQL-satser med python

Jag vet att detta är en gammal fråga, men jag har ofta velat ha vad det verkar som OP vill ha:ETT MYCKET enkelt bibliotek för att generera grundläggande SQL.

Funktionerna nedan gör just det. Du ger dem ett tabellnamn och en ordlista som innehåller de data du vill använda och de returnerar SQL-frågan för den operation du behöver.

Nyckel/värdeparen representerar fältnamn och värden i databasraderna.

def read(table, **kwargs):
    """ Generates SQL for a SELECT statement matching the kwargs passed. """
    sql = list()
    sql.append("SELECT * FROM %s " % table)
    if kwargs:
        sql.append("WHERE " + " AND ".join("%s = '%s'" % (k, v) for k, v in kwargs.iteritems()))
    sql.append(";")
    return "".join(sql)


def upsert(table, **kwargs):
    """ update/insert rows into objects table (update if the row already exists)
        given the key-value pairs in kwargs """
    keys = ["%s" % k for k in kwargs]
    values = ["'%s'" % v for v in kwargs.values()]
    sql = list()
    sql.append("INSERT INTO %s (" % table)
    sql.append(", ".join(keys))
    sql.append(") VALUES (")
    sql.append(", ".join(values))
    sql.append(") ON DUPLICATE KEY UPDATE ")
    sql.append(", ".join("%s = '%s'" % (k, v) for k, v in kwargs.iteritems()))
    sql.append(";")
    return "".join(sql)


def delete(table, **kwargs):
    """ deletes rows from table where **kwargs match """
    sql = list()
    sql.append("DELETE FROM %s " % table)
    sql.append("WHERE " + " AND ".join("%s = '%s'" % (k, v) for k, v in kwargs.iteritems()))
    sql.append(";")
    return "".join(sql)

Du använder det som så. Ge det bara ett tabellnamn och en ordbok (eller använd funktionen **kwargs i python):

>>> upsert("tbl", LogID=500, LoggedValue=5)
"INSERT INTO tbl (LogID, LoggedValue) VALUES ('500', '5') ON DUPLICATE KEY UPDATE LogID = '500', LoggedValue = '5';"

>>> read("tbl", **{"username": "morten"})
"SELECT * FROM tbl WHERE username = 'morten';"

>>> read("tbl", **{"user_type": 1, "user_group": "admin"})
"SELECT * FROM tbl WHERE user_type = '1' AND user_group = 'admin';"

Men AKTA DIG FÖR SQL-INJEKTIONSATTACKER

Titta vad som händer när en illvillig användare av din kod gör detta:

>>> read("tbl", **{"user_group": "admin'; DROP TABLE tbl; --"})
"SELECT * FROM tbl WHERE user_group = 'admin'; DROP TABLE tbl; --';"

Det är lätt att göra din egen provisoriska ORM men du får bara vad du ser -- du måste fly själv :)



  1. SQL korsreferenser en annan tabell för att kontrollera data

  2. Använd som '%' och matcha NULL-värden med NUMBER kolumner

  3. Leasing jobb (atomic update and get) från en MySQL-databas

  4. 7 fakta om SQL Server-synonymer du bör känna till