Используя ядро SQLAlchemy (не ORM), я пытаюсь вставить несколько строк, используя подзапросы в значениях.Для MySQL фактический SQL будет выглядеть примерно так:
INSERT INTO widgets (name, type) VALUES
('Melon', (SELECT type FROM widgetTypes WHERE type='Squidgy')),
('Durian', (SELECT type FROM widgetTypes WHERE type='Spiky'))
Но мне кажется, что я могу использовать подзапросы только при использовании метода values()
в insert()
предложение, которое позволяет мне делать только одну вставку за раз.Я хотел бы вставить несколько значений одновременно, передав их все методу Connection
s execute()
в виде списка параметров связывания, но это не поддерживается.
Можно ли сделать то, что я хочу, за один вызов execute()
?
Вот отдельная демонстрация.Обратите внимание, что здесь используется движок sqlite, который не поддерживает множественные вставки так же, как MySQL , но код SQLAlchemy по-прежнему не работает так же, как и настоящее приложение MySQL.
from sqlalchemy import *
if __name__ == "__main__":
# Construct database
metadata = MetaData()
widgetTypes = Table('widgetTypes', metadata,
Column('id', INTEGER(), primary_key=True),
Column('type', VARCHAR(), nullable=False),
)
widgets = Table('widgets', metadata,
Column('id', INTEGER(), primary_key=True),
Column('name', VARCHAR(), nullable=False),
Column('type', INTEGER(), nullable=False),
ForeignKeyConstraint(['type'], ['widgetTypes.id']),
)
engine = create_engine("sqlite://")
metadata.create_all(engine)
# Connect and populate db for testing
conn = engine.connect()
conn.execute(widgetTypes.insert(), [
{'type': 'Spiky'},
{'type': 'Squidgy'},
])
# Some select queries for later use.
select_squidgy_id = select([widgetTypes.c.id]).where(
widgetTypes.c['type']=='Squidgy'
).limit(1)
select_spiky_id = select([widgetTypes.c.id]).where(
widgetTypes.c['type']=='Squidgy'
).limit(1)
# One at a time works via values()
conn.execute(widgets.insert().values(
{'name': 'Tomato', 'type': select_squidgy_id},
))
# And multiple values work if we avoid subqueries
conn.execute(
widgets.insert(),
{'name': 'Melon', 'type': 2},
{'name': 'Durian', 'type': 1},
)
# Check above inserts did actually work
print conn.execute(widgets.select()).fetchall()
# But attempting to insert many at once with subqueries does not work.
conn.execute(
widgets.insert(),
{'name': 'Raspberry', 'type': select_squidgy_id},
{'name': 'Lychee', 'type': select_spiky_id},
)
Запустите его и он умирает при последнем execute()
вызове с:
sqlalchemy.exc.InterfaceError: (InterfaceError) Параметр привязки ошибки 1 - возможно, неподдерживаемый тип.u'INSERT INTO виджеты (имя, тип) VALUES (?,?) '((' Raspberry ',), («Личи»,))