Det kan du ikke gøre med din lagrede procedure som skrevet. Det vil kun indsætte en række ad gangen, så for at indsætte n rækker skal du kalde det n gange.
Så vidt jeg ved kan du heller ikke ændre den lagrede procedure for at indsætte n rækker uden at bruge en midlertidig tabel eller en anden løsning, fordi MySQL ikke understøtter tabelværdiparametre til lagrede procedurer.
Du kan dog indsætte flere rækker på én gang, hvis du bruger en almindelig INSERT-sætning og .executemany
. pymysql vil bundte indsættelserne i en eller flere multi-række indsættelser
mssql_crsr = mssql_cnxn.cursor()
mssql_stmt = """\
SELECT 1 AS id, N'Alfa' AS txt
UNION ALL
SELECT 2 AS id, N'Bravo' AS txt
UNION ALL
SELECT 3 AS id, N'Charlie' AS txt
"""
mssql_crsr.execute(mssql_stmt)
mssql_rows = []
while True:
row = mssql_crsr.fetchone()
if row:
mssql_rows.append(tuple(row))
else:
break
mysql_cnxn = pymysql.connect(host='localhost', port=3307,
user='root', password='_whatever_',
db='mydb', autocommit=True)
mysql_crsr = mysql_cnxn.cursor()
mysql_stmt = "INSERT INTO stuff (id, txt) VALUES (%s, %s)"
mysql_crsr.executemany(mysql_stmt, mssql_rows)
Ovenstående kode producerer følgende i MySQL general_log
190430 10:00:53 4 Connect [email protected] on mydb
4 Query INSERT INTO stuff (id, txt) VALUES (1, 'Alfa'),(2, 'Bravo'),(3, 'Charlie')
4 Quit
Bemærk, at pymysql ikke kan samle opkald til en lagret procedure på samme måde, så hvis du skulle bruge
mysql_stmt = "CALL stuff_one(%s, %s)"
i stedet for en almindelig INSERT ville general_log indeholde
190430 9:47:10 3 Connect [email protected] on mydb
3 Query CALL stuff_one(1, 'Alfa')
3 Query CALL stuff_one(2, 'Bravo')
3 Query CALL stuff_one(3, 'Charlie')
3 Quit