В операциях SQL обычно необходимо использовать значения переменных Python. Необходимо остерегаться использования строковых операций Python для сборки запросов, т.к. они уязвимы для атак с использованием SQL-инъекций. Например, злоумышленник может просто закрыть одинарную кавычку и ввести OR TRUE
, чтобы выбрать все строки:
# Никогда не делай этого! >>> symbol = input() # ' OR TRUE; -- >>> sql = "SELECT * FROM stocks WHERE symbol = '%s'" % symbol >>> print(sql) # SELECT * FROM stocks WHERE symbol = '' OR TRUE; --' >>> cur.execute(sql)
Во избежании атак с использованием SQL-инъекций, необходимо использовать подстановку параметров DB-API. Чтобы вставить переменную в строку запроса, используйте заполнитель в строке и подставьте фактические значения в запрос, передав их в виде кортежа значений во второй аргумент метода курсора Cursor.execute()
.
В операторе SQL может использоваться один из двух типов заполнителей: вопросительные знаки ?
(стиль qmark
) или именованные заполнители (именованный стиль). Для стиля qmark
параметры должны представлять собой последовательность, длина которой должна соответствовать количеству заполнителей, иначе возникнет ошибка ProgrammingError
. Для именованного стиля параметры должны быть экземпляром словаря dict
(или подкласса), который должен содержать ключи для всех именованных параметров; любые дополнительные элементы игнорируются.
con = sqlite3.connect(":memory:") cur = con.execute("CREATE TABLE lang(name, first_appeared)") # Это именованный стиль, используемый с `executemany()`: data = ( {"name": "C", "year": 1972}, {"name": "Fortran", "year": 1957}, {"name": "Python", "year": 1991}, {"name": "Go", "year": 2009}, ) cur.executemany("INSERT INTO lang VALUES(:name, :year)", data) # Это стиль `qmark`, используемый в `SELECT query`: params = (1972,) cur.execute("SELECT * FROM lang WHERE first_appeared = ?", params) print(cur.fetchall())