Skip to content

Commit 07fbc45

Browse files
authored
fix: Executing existing DDL statements on executemany statement execution (#1032)
* Executing existing DDL statements on executemany statement execution * Fixing test * Added more tests and resolved comments * Fixing test * Resolved comments
1 parent e5acb56 commit 07fbc45

File tree

2 files changed

+154
-1
lines changed

2 files changed

+154
-1
lines changed

google/cloud/spanner_dbapi/cursor.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -315,6 +315,10 @@ def executemany(self, operation, seq_of_params):
315315
"Executing DDL statements with executemany() method is not allowed."
316316
)
317317

318+
# For every operation, we've got to ensure that any prior DDL
319+
# statements were run.
320+
self.connection.run_prior_DDL_statements()
321+
318322
many_result_set = StreamedManyResultSets()
319323

320324
if class_ in (parse_utils.STMT_INSERT, parse_utils.STMT_UPDATING):

tests/system/test_dbapi.py

Lines changed: 150 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,6 @@
2727
from google.cloud.spanner_v1 import gapic_version as package_version
2828
from . import _helpers
2929

30-
3130
DATABASE_NAME = "dbapi-txn"
3231

3332
DDL_STATEMENTS = (
@@ -344,6 +343,156 @@ def test_DDL_autocommit(shared_instance, dbapi_database):
344343
op.result()
345344

346345

346+
def test_ddl_execute_autocommit_true(shared_instance, dbapi_database):
347+
"""Check that DDL statement in autocommit mode results in successful
348+
DDL statement execution for execute method."""
349+
350+
conn = Connection(shared_instance, dbapi_database)
351+
conn.autocommit = True
352+
cur = conn.cursor()
353+
cur.execute(
354+
"""
355+
CREATE TABLE DdlExecuteAutocommit (
356+
SingerId INT64 NOT NULL,
357+
Name STRING(1024),
358+
) PRIMARY KEY (SingerId)
359+
"""
360+
)
361+
table = dbapi_database.table("DdlExecuteAutocommit")
362+
assert table.exists() is True
363+
364+
cur.close()
365+
conn.close()
366+
367+
368+
def test_ddl_executemany_autocommit_true(shared_instance, dbapi_database):
369+
"""Check that DDL statement in autocommit mode results in exception for
370+
executemany method ."""
371+
372+
conn = Connection(shared_instance, dbapi_database)
373+
conn.autocommit = True
374+
cur = conn.cursor()
375+
with pytest.raises(ProgrammingError):
376+
cur.executemany(
377+
"""
378+
CREATE TABLE DdlExecuteManyAutocommit (
379+
SingerId INT64 NOT NULL,
380+
Name STRING(1024),
381+
) PRIMARY KEY (SingerId)
382+
""",
383+
[],
384+
)
385+
table = dbapi_database.table("DdlExecuteManyAutocommit")
386+
assert table.exists() is False
387+
388+
cur.close()
389+
conn.close()
390+
391+
392+
def test_ddl_executemany_autocommit_false(shared_instance, dbapi_database):
393+
"""Check that DDL statement in non-autocommit mode results in exception for
394+
executemany method ."""
395+
396+
conn = Connection(shared_instance, dbapi_database)
397+
cur = conn.cursor()
398+
with pytest.raises(ProgrammingError):
399+
cur.executemany(
400+
"""
401+
CREATE TABLE DdlExecuteManyAutocommit (
402+
SingerId INT64 NOT NULL,
403+
Name STRING(1024),
404+
) PRIMARY KEY (SingerId)
405+
""",
406+
[],
407+
)
408+
table = dbapi_database.table("DdlExecuteManyAutocommit")
409+
assert table.exists() is False
410+
411+
cur.close()
412+
conn.close()
413+
414+
415+
def test_ddl_execute(shared_instance, dbapi_database):
416+
"""Check that DDL statement followed by non-DDL execute statement in
417+
non autocommit mode results in successful DDL statement execution."""
418+
419+
conn = Connection(shared_instance, dbapi_database)
420+
want_row = (
421+
1,
422+
"first-name",
423+
)
424+
cur = conn.cursor()
425+
cur.execute(
426+
"""
427+
CREATE TABLE DdlExecute (
428+
SingerId INT64 NOT NULL,
429+
Name STRING(1024),
430+
) PRIMARY KEY (SingerId)
431+
"""
432+
)
433+
table = dbapi_database.table("DdlExecute")
434+
assert table.exists() is False
435+
436+
cur.execute(
437+
"""
438+
INSERT INTO DdlExecute (SingerId, Name)
439+
VALUES (1, "first-name")
440+
"""
441+
)
442+
assert table.exists() is True
443+
conn.commit()
444+
445+
# read the resulting data from the database
446+
cur.execute("SELECT * FROM DdlExecute")
447+
got_rows = cur.fetchall()
448+
449+
assert got_rows == [want_row]
450+
451+
cur.close()
452+
conn.close()
453+
454+
455+
def test_ddl_executemany(shared_instance, dbapi_database):
456+
"""Check that DDL statement followed by non-DDL executemany statement in
457+
non autocommit mode results in successful DDL statement execution."""
458+
459+
conn = Connection(shared_instance, dbapi_database)
460+
want_row = (
461+
1,
462+
"first-name",
463+
)
464+
cur = conn.cursor()
465+
cur.execute(
466+
"""
467+
CREATE TABLE DdlExecuteMany (
468+
SingerId INT64 NOT NULL,
469+
Name STRING(1024),
470+
) PRIMARY KEY (SingerId)
471+
"""
472+
)
473+
table = dbapi_database.table("DdlExecuteMany")
474+
assert table.exists() is False
475+
476+
cur.executemany(
477+
"""
478+
INSERT INTO DdlExecuteMany (SingerId, Name)
479+
VALUES (%s, %s)
480+
""",
481+
[want_row],
482+
)
483+
assert table.exists() is True
484+
conn.commit()
485+
486+
# read the resulting data from the database
487+
cur.execute("SELECT * FROM DdlExecuteMany")
488+
got_rows = cur.fetchall()
489+
490+
assert got_rows == [want_row]
491+
492+
cur.close()
493+
conn.close()
494+
495+
347496
@pytest.mark.skipif(_helpers.USE_EMULATOR, reason="Emulator does not support json.")
348497
def test_autocommit_with_json_data(shared_instance, dbapi_database):
349498
"""

0 commit comments

Comments
 (0)