Skip to content

Commit 3d42cd9

Browse files
author
Erlend Egeberg Aasland
authored
bpo-45243: Use connection limits to simplify sqlite3 tests (GH-29356)
1 parent 71e8a3e commit 3d42cd9

File tree

3 files changed

+54
-21
lines changed

3 files changed

+54
-21
lines changed

Lib/test/test_sqlite3/test_dbapi.py

Lines changed: 31 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,6 @@
2929

3030
from test.support import (
3131
SHORT_TIMEOUT,
32-
bigmemtest,
3332
check_disallow_instantiation,
3433
threading_helper,
3534
)
@@ -48,6 +47,22 @@ def managed_connect(*args, in_mem=False, **kwargs):
4847
unlink(TESTFN)
4948

5049

50+
# Helper for temporary memory databases
51+
def memory_database():
52+
cx = sqlite.connect(":memory:")
53+
return contextlib.closing(cx)
54+
55+
56+
# Temporarily limit a database connection parameter
57+
@contextlib.contextmanager
58+
def cx_limit(cx, category=sqlite.SQLITE_LIMIT_LENGTH, limit=128):
59+
try:
60+
_prev = cx.setlimit(category, limit)
61+
yield limit
62+
finally:
63+
cx.setlimit(category, _prev)
64+
65+
5166
class ModuleTests(unittest.TestCase):
5267
def test_api_level(self):
5368
self.assertEqual(sqlite.apilevel, "2.0",
@@ -650,6 +665,15 @@ def __getitem__(slf, x):
650665
with self.assertRaises(ZeroDivisionError):
651666
self.cu.execute("select name from test where name=?", L())
652667

668+
def test_execute_too_many_params(self):
669+
category = sqlite.SQLITE_LIMIT_VARIABLE_NUMBER
670+
msg = "too many SQL variables"
671+
with cx_limit(self.cx, category=category, limit=1):
672+
self.cu.execute("select * from test where id=?", (1,))
673+
with self.assertRaisesRegex(sqlite.OperationalError, msg):
674+
self.cu.execute("select * from test where id!=? and id!=?",
675+
(1, 2))
676+
653677
def test_execute_dict_mapping(self):
654678
self.cu.execute("insert into test(name) values ('foo')")
655679
self.cu.execute("select name from test where name=:name", {"name": "foo"})
@@ -1036,14 +1060,12 @@ def test_cursor_executescript_with_surrogates(self):
10361060
insert into a(s) values ('\ud8ff');
10371061
""")
10381062

1039-
@unittest.skipUnless(sys.maxsize > 2**32, 'requires 64bit platform')
1040-
@bigmemtest(size=2**31, memuse=3, dry_run=False)
1041-
def test_cursor_executescript_too_large_script(self, maxsize):
1042-
con = sqlite.connect(":memory:")
1043-
cur = con.cursor()
1044-
for size in 2**31-1, 2**31:
1045-
with self.assertRaises(sqlite.DataError):
1046-
cur.executescript("create table a(s);".ljust(size))
1063+
def test_cursor_executescript_too_large_script(self):
1064+
msg = "query string is too large"
1065+
with memory_database() as cx, cx_limit(cx) as lim:
1066+
cx.executescript("select 'almost too large'".ljust(lim-1))
1067+
with self.assertRaisesRegex(sqlite.DataError, msg):
1068+
cx.executescript("select 'too large'".ljust(lim))
10471069

10481070
def test_cursor_executescript_tx_control(self):
10491071
con = sqlite.connect(":memory:")

Lib/test/test_sqlite3/test_regression.py

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,8 @@
2828
import functools
2929
from test import support
3030

31-
from .test_dbapi import managed_connect
31+
from .test_dbapi import memory_database, managed_connect, cx_limit
32+
3233

3334
class RegressionTests(unittest.TestCase):
3435
def setUp(self):
@@ -356,17 +357,18 @@ def test_surrogates(self):
356357
self.assertRaises(UnicodeEncodeError, cur.execute, "select '\ud8ff'")
357358
self.assertRaises(UnicodeEncodeError, cur.execute, "select '\udcff'")
358359

359-
@unittest.skipUnless(sys.maxsize > 2**32, 'requires 64bit platform')
360-
@support.bigmemtest(size=2**31, memuse=4, dry_run=False)
361-
def test_large_sql(self, maxsize):
362-
# Test two cases: size+1 > INT_MAX and size+1 <= INT_MAX.
363-
for size in (2**31, 2**31-2):
364-
con = sqlite.connect(":memory:")
365-
sql = "select 1".ljust(size)
366-
self.assertRaises(sqlite.DataError, con, sql)
367-
cur = con.cursor()
368-
self.assertRaises(sqlite.DataError, cur.execute, sql)
369-
del sql
360+
def test_large_sql(self):
361+
msg = "query string is too large"
362+
with memory_database() as cx, cx_limit(cx) as lim:
363+
cu = cx.cursor()
364+
365+
cx("select 1".ljust(lim-1))
366+
# use a different SQL statement; don't reuse from the LRU cache
367+
cu.execute("select 2".ljust(lim-1))
368+
369+
sql = "select 3".ljust(lim)
370+
self.assertRaisesRegex(sqlite.DataError, msg, cx, sql)
371+
self.assertRaisesRegex(sqlite.DataError, msg, cu.execute, sql)
370372

371373
def test_commit_cursor_reset(self):
372374
"""

Lib/test/test_sqlite3/test_userfunctions.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@
3131
import sqlite3 as sqlite
3232

3333
from test.support import bigmemtest
34+
from .test_dbapi import cx_limit
3435

3536

3637
def with_tracebacks(strings, traceback=True):
@@ -223,6 +224,14 @@ def test_func_error_on_create(self):
223224
with self.assertRaises(sqlite.OperationalError):
224225
self.con.create_function("bla", -100, lambda x: 2*x)
225226

227+
def test_func_too_many_args(self):
228+
category = sqlite.SQLITE_LIMIT_FUNCTION_ARG
229+
msg = "too many arguments on function"
230+
with cx_limit(self.con, category=category, limit=1):
231+
self.con.execute("select abs(-1)");
232+
with self.assertRaisesRegex(sqlite.OperationalError, msg):
233+
self.con.execute("select max(1, 2)");
234+
226235
def test_func_ref_count(self):
227236
def getfunc():
228237
def f():

0 commit comments

Comments
 (0)