blob: 6057805f65c0c8844dfaa12393006312aab4b88a [file] [log] [blame]
Petri Lehtinenf8547992012-02-02 17:17:36 +02001#-*- coding: iso-8859-1 -*-
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00002# pysqlite2/test/dbapi.py: tests for DB-API compliance
3#
Gerhard Häringf9cee222010-03-05 15:20:03 +00004# Copyright (C) 2004-2010 Gerhard Häring <gh@ghaering.de>
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005#
6# This file is part of pysqlite.
7#
8# This software is provided 'as-is', without any express or implied
9# warranty. In no event will the authors be held liable for any damages
10# arising from the use of this software.
11#
12# Permission is granted to anyone to use this software for any purpose,
13# including commercial applications, and to alter it and redistribute it
14# freely, subject to the following restrictions:
15#
16# 1. The origin of this software must not be misrepresented; you must not
17# claim that you wrote the original software. If you use this software
18# in a product, an acknowledgment in the product documentation would be
19# appreciated but is not required.
20# 2. Altered source versions must be plainly marked as such, and must not be
21# misrepresented as being the original software.
22# 3. This notice may not be removed or altered from any source distribution.
23
24import unittest
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000025import sqlite3 as sqlite
Victor Stinner45df8202010-04-28 22:31:17 +000026try:
27 import threading
Brett Cannoncd171c82013-07-04 17:43:24 -040028except ImportError:
Victor Stinner45df8202010-04-28 22:31:17 +000029 threading = None
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000030
Antoine Pitrou902fc8b2013-02-10 00:02:44 +010031from test.support import TESTFN, unlink
32
33
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000034class ModuleTests(unittest.TestCase):
35 def CheckAPILevel(self):
36 self.assertEqual(sqlite.apilevel, "2.0",
37 "apilevel is %s, should be 2.0" % sqlite.apilevel)
38
39 def CheckThreadSafety(self):
40 self.assertEqual(sqlite.threadsafety, 1,
41 "threadsafety is %d, should be 1" % sqlite.threadsafety)
42
43 def CheckParamStyle(self):
44 self.assertEqual(sqlite.paramstyle, "qmark",
45 "paramstyle is '%s', should be 'qmark'" %
46 sqlite.paramstyle)
47
48 def CheckWarning(self):
Ezio Melottib3aedd42010-11-20 19:04:17 +000049 self.assertTrue(issubclass(sqlite.Warning, Exception),
Guido van Rossumcd16bf62007-06-13 18:07:49 +000050 "Warning is not a subclass of Exception")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000051
52 def CheckError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000053 self.assertTrue(issubclass(sqlite.Error, Exception),
Guido van Rossumcd16bf62007-06-13 18:07:49 +000054 "Error is not a subclass of Exception")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000055
56 def CheckInterfaceError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000057 self.assertTrue(issubclass(sqlite.InterfaceError, sqlite.Error),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000058 "InterfaceError is not a subclass of Error")
59
60 def CheckDatabaseError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000061 self.assertTrue(issubclass(sqlite.DatabaseError, sqlite.Error),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000062 "DatabaseError is not a subclass of Error")
63
64 def CheckDataError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000065 self.assertTrue(issubclass(sqlite.DataError, sqlite.DatabaseError),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000066 "DataError is not a subclass of DatabaseError")
67
68 def CheckOperationalError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000069 self.assertTrue(issubclass(sqlite.OperationalError, sqlite.DatabaseError),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000070 "OperationalError is not a subclass of DatabaseError")
71
72 def CheckIntegrityError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000073 self.assertTrue(issubclass(sqlite.IntegrityError, sqlite.DatabaseError),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000074 "IntegrityError is not a subclass of DatabaseError")
75
76 def CheckInternalError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000077 self.assertTrue(issubclass(sqlite.InternalError, sqlite.DatabaseError),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000078 "InternalError is not a subclass of DatabaseError")
79
80 def CheckProgrammingError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000081 self.assertTrue(issubclass(sqlite.ProgrammingError, sqlite.DatabaseError),
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000082 "ProgrammingError is not a subclass of DatabaseError")
83
84 def CheckNotSupportedError(self):
Gregory P. Smith04cecaf2009-07-04 08:32:15 +000085 self.assertTrue(issubclass(sqlite.NotSupportedError,
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000086 sqlite.DatabaseError),
87 "NotSupportedError is not a subclass of DatabaseError")
88
89class ConnectionTests(unittest.TestCase):
R. David Murrayd35251d2010-06-01 01:32:12 +000090
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000091 def setUp(self):
92 self.cx = sqlite.connect(":memory:")
93 cu = self.cx.cursor()
94 cu.execute("create table test(id integer primary key, name text)")
95 cu.execute("insert into test(name) values (?)", ("foo",))
96
97 def tearDown(self):
98 self.cx.close()
99
100 def CheckCommit(self):
101 self.cx.commit()
102
103 def CheckCommitAfterNoChanges(self):
104 """
105 A commit should also work when no changes were made to the database.
106 """
107 self.cx.commit()
108 self.cx.commit()
109
110 def CheckRollback(self):
111 self.cx.rollback()
112
113 def CheckRollbackAfterNoChanges(self):
114 """
115 A rollback should also work when no changes were made to the database.
116 """
117 self.cx.rollback()
118 self.cx.rollback()
119
120 def CheckCursor(self):
121 cu = self.cx.cursor()
122
123 def CheckFailedOpen(self):
124 YOU_CANNOT_OPEN_THIS = "/foo/bar/bla/23534/mydb.db"
Berker Peksag1003b342016-06-12 22:34:49 +0300125 with self.assertRaises(sqlite.OperationalError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000126 con = sqlite.connect(YOU_CANNOT_OPEN_THIS)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000127
128 def CheckClose(self):
129 self.cx.close()
130
131 def CheckExceptions(self):
132 # Optional DB-API extension.
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000133 self.assertEqual(self.cx.Warning, sqlite.Warning)
134 self.assertEqual(self.cx.Error, sqlite.Error)
135 self.assertEqual(self.cx.InterfaceError, sqlite.InterfaceError)
136 self.assertEqual(self.cx.DatabaseError, sqlite.DatabaseError)
137 self.assertEqual(self.cx.DataError, sqlite.DataError)
138 self.assertEqual(self.cx.OperationalError, sqlite.OperationalError)
139 self.assertEqual(self.cx.IntegrityError, sqlite.IntegrityError)
140 self.assertEqual(self.cx.InternalError, sqlite.InternalError)
141 self.assertEqual(self.cx.ProgrammingError, sqlite.ProgrammingError)
142 self.assertEqual(self.cx.NotSupportedError, sqlite.NotSupportedError)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000143
R. David Murrayd35251d2010-06-01 01:32:12 +0000144 def CheckInTransaction(self):
145 # Can't use db from setUp because we want to test initial state.
146 cx = sqlite.connect(":memory:")
147 cu = cx.cursor()
148 self.assertEqual(cx.in_transaction, False)
149 cu.execute("create table transactiontest(id integer primary key, name text)")
150 self.assertEqual(cx.in_transaction, False)
151 cu.execute("insert into transactiontest(name) values (?)", ("foo",))
152 self.assertEqual(cx.in_transaction, True)
153 cu.execute("select name from transactiontest where name=?", ["foo"])
154 row = cu.fetchone()
155 self.assertEqual(cx.in_transaction, True)
156 cx.commit()
157 self.assertEqual(cx.in_transaction, False)
158 cu.execute("select name from transactiontest where name=?", ["foo"])
159 row = cu.fetchone()
160 self.assertEqual(cx.in_transaction, False)
161
162 def CheckInTransactionRO(self):
163 with self.assertRaises(AttributeError):
164 self.cx.in_transaction = True
165
Antoine Pitrou902fc8b2013-02-10 00:02:44 +0100166 def CheckOpenUri(self):
167 if sqlite.sqlite_version_info < (3, 7, 7):
168 with self.assertRaises(sqlite.NotSupportedError):
169 sqlite.connect(':memory:', uri=True)
170 return
171 self.addCleanup(unlink, TESTFN)
172 with sqlite.connect(TESTFN) as cx:
173 cx.execute('create table test(id integer)')
174 with sqlite.connect('file:' + TESTFN, uri=True) as cx:
175 cx.execute('insert into test(id) values(0)')
176 with sqlite.connect('file:' + TESTFN + '?mode=ro', uri=True) as cx:
177 with self.assertRaises(sqlite.OperationalError):
178 cx.execute('insert into test(id) values(1)')
179
Berker Peksag7bea2342016-06-12 14:09:51 +0300180 def CheckSameThreadErrorOnOldVersion(self):
181 if sqlite.sqlite_version_info >= (3, 3, 1):
182 self.skipTest('test needs sqlite3 versions older than 3.3.1')
183 with self.assertRaises(sqlite.NotSupportedError) as cm:
184 sqlite.connect(':memory:', check_same_thread=False)
185 self.assertEqual(str(cm.exception), 'shared connections not available')
Antoine Pitrou902fc8b2013-02-10 00:02:44 +0100186
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000187class CursorTests(unittest.TestCase):
188 def setUp(self):
189 self.cx = sqlite.connect(":memory:")
190 self.cu = self.cx.cursor()
191 self.cu.execute("create table test(id integer primary key, name text, income number)")
192 self.cu.execute("insert into test(name) values (?)", ("foo",))
193
194 def tearDown(self):
195 self.cu.close()
196 self.cx.close()
197
198 def CheckExecuteNoArgs(self):
199 self.cu.execute("delete from test")
200
201 def CheckExecuteIllegalSql(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300202 with self.assertRaises(sqlite.OperationalError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000203 self.cu.execute("select asdf")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000204
205 def CheckExecuteTooMuchSql(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300206 with self.assertRaises(sqlite.Warning):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000207 self.cu.execute("select 5+4; select 4+5")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000208
209 def CheckExecuteTooMuchSql2(self):
210 self.cu.execute("select 5+4; -- foo bar")
211
212 def CheckExecuteTooMuchSql3(self):
213 self.cu.execute("""
214 select 5+4;
215
216 /*
217 foo
218 */
219 """)
220
221 def CheckExecuteWrongSqlArg(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300222 with self.assertRaises(ValueError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000223 self.cu.execute(42)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000224
225 def CheckExecuteArgInt(self):
226 self.cu.execute("insert into test(id) values (?)", (42,))
227
228 def CheckExecuteArgFloat(self):
229 self.cu.execute("insert into test(income) values (?)", (2500.32,))
230
231 def CheckExecuteArgString(self):
232 self.cu.execute("insert into test(name) values (?)", ("Hugo",))
233
Petri Lehtinen023fe332012-02-01 22:18:19 +0200234 def CheckExecuteArgStringWithZeroByte(self):
235 self.cu.execute("insert into test(name) values (?)", ("Hu\x00go",))
236
237 self.cu.execute("select name from test where id=?", (self.cu.lastrowid,))
238 row = self.cu.fetchone()
239 self.assertEqual(row[0], "Hu\x00go")
240
Berker Peksagc4154402016-06-12 13:41:47 +0300241 def CheckExecuteNonIterable(self):
242 with self.assertRaises(ValueError) as cm:
243 self.cu.execute("insert into test(id) values (?)", 42)
244 self.assertEqual(str(cm.exception), 'parameters are of unsupported type')
245
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000246 def CheckExecuteWrongNoOfArgs1(self):
247 # too many parameters
Berker Peksag1003b342016-06-12 22:34:49 +0300248 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000249 self.cu.execute("insert into test(id) values (?)", (17, "Egon"))
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000250
251 def CheckExecuteWrongNoOfArgs2(self):
252 # too little parameters
Berker Peksag1003b342016-06-12 22:34:49 +0300253 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000254 self.cu.execute("insert into test(id) values (?)")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000255
256 def CheckExecuteWrongNoOfArgs3(self):
257 # no parameters, parameters are needed
Berker Peksag1003b342016-06-12 22:34:49 +0300258 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000259 self.cu.execute("insert into test(id) values (?)")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000260
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000261 def CheckExecuteParamList(self):
262 self.cu.execute("insert into test(name) values ('foo')")
263 self.cu.execute("select name from test where name=?", ["foo"])
264 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000265 self.assertEqual(row[0], "foo")
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000266
267 def CheckExecuteParamSequence(self):
268 class L(object):
269 def __len__(self):
270 return 1
271 def __getitem__(self, x):
272 assert x == 0
273 return "foo"
274
275 self.cu.execute("insert into test(name) values ('foo')")
276 self.cu.execute("select name from test where name=?", L())
277 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000278 self.assertEqual(row[0], "foo")
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000279
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000280 def CheckExecuteDictMapping(self):
281 self.cu.execute("insert into test(name) values ('foo')")
282 self.cu.execute("select name from test where name=:name", {"name": "foo"})
283 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000284 self.assertEqual(row[0], "foo")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000285
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000286 def CheckExecuteDictMapping_Mapping(self):
287 class D(dict):
288 def __missing__(self, key):
289 return "foo"
290
291 self.cu.execute("insert into test(name) values ('foo')")
292 self.cu.execute("select name from test where name=:name", D())
293 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000294 self.assertEqual(row[0], "foo")
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000295
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000296 def CheckExecuteDictMappingTooLittleArgs(self):
297 self.cu.execute("insert into test(name) values ('foo')")
Berker Peksag1003b342016-06-12 22:34:49 +0300298 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000299 self.cu.execute("select name from test where name=:name and id=:id", {"name": "foo"})
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000300
301 def CheckExecuteDictMappingNoArgs(self):
302 self.cu.execute("insert into test(name) values ('foo')")
Berker Peksag1003b342016-06-12 22:34:49 +0300303 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000304 self.cu.execute("select name from test where name=:name")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000305
306 def CheckExecuteDictMappingUnnamed(self):
307 self.cu.execute("insert into test(name) values ('foo')")
Berker Peksag1003b342016-06-12 22:34:49 +0300308 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000309 self.cu.execute("select name from test where name=?", {"name": "foo"})
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000310
311 def CheckClose(self):
312 self.cu.close()
313
314 def CheckRowcountExecute(self):
315 self.cu.execute("delete from test")
316 self.cu.execute("insert into test(name) values ('foo')")
317 self.cu.execute("insert into test(name) values ('foo')")
318 self.cu.execute("update test set name='bar'")
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000319 self.assertEqual(self.cu.rowcount, 2)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000320
Georg Brandlf78e02b2008-06-10 17:40:04 +0000321 def CheckRowcountSelect(self):
322 """
323 pysqlite does not know the rowcount of SELECT statements, because we
324 don't fetch all rows after executing the select statement. The rowcount
325 has thus to be -1.
326 """
327 self.cu.execute("select 5 union select 6")
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000328 self.assertEqual(self.cu.rowcount, -1)
Georg Brandlf78e02b2008-06-10 17:40:04 +0000329
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000330 def CheckRowcountExecutemany(self):
331 self.cu.execute("delete from test")
332 self.cu.executemany("insert into test(name) values (?)", [(1,), (2,), (3,)])
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000333 self.assertEqual(self.cu.rowcount, 3)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000334
335 def CheckTotalChanges(self):
336 self.cu.execute("insert into test(name) values ('foo')")
337 self.cu.execute("insert into test(name) values ('foo')")
338 if self.cx.total_changes < 2:
339 self.fail("total changes reported wrong value")
340
341 # Checks for executemany:
342 # Sequences are required by the DB-API, iterators
343 # enhancements in pysqlite.
344
345 def CheckExecuteManySequence(self):
346 self.cu.executemany("insert into test(income) values (?)", [(x,) for x in range(100, 110)])
347
348 def CheckExecuteManyIterator(self):
349 class MyIter:
350 def __init__(self):
351 self.value = 5
352
Georg Brandla18af4e2007-04-21 15:47:16 +0000353 def __next__(self):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000354 if self.value == 10:
355 raise StopIteration
356 else:
357 self.value += 1
358 return (self.value,)
359
360 self.cu.executemany("insert into test(income) values (?)", MyIter())
361
362 def CheckExecuteManyGenerator(self):
363 def mygen():
364 for i in range(5):
365 yield (i,)
366
367 self.cu.executemany("insert into test(income) values (?)", mygen())
368
369 def CheckExecuteManyWrongSqlArg(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300370 with self.assertRaises(ValueError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000371 self.cu.executemany(42, [(3,)])
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000372
373 def CheckExecuteManySelect(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300374 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000375 self.cu.executemany("select ?", [(3,)])
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000376
377 def CheckExecuteManyNotIterable(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300378 with self.assertRaises(TypeError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000379 self.cu.executemany("insert into test(income) values (?)", 42)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000380
381 def CheckFetchIter(self):
382 # Optional DB-API extension.
383 self.cu.execute("delete from test")
384 self.cu.execute("insert into test(id) values (?)", (5,))
385 self.cu.execute("insert into test(id) values (?)", (6,))
386 self.cu.execute("select id from test order by id")
387 lst = []
388 for row in self.cu:
389 lst.append(row[0])
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000390 self.assertEqual(lst[0], 5)
391 self.assertEqual(lst[1], 6)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000392
393 def CheckFetchone(self):
394 self.cu.execute("select name from test")
395 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000396 self.assertEqual(row[0], "foo")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000397 row = self.cu.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000398 self.assertEqual(row, None)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000399
400 def CheckFetchoneNoStatement(self):
401 cur = self.cx.cursor()
402 row = cur.fetchone()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000403 self.assertEqual(row, None)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000404
405 def CheckArraySize(self):
406 # must default ot 1
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000407 self.assertEqual(self.cu.arraysize, 1)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000408
409 # now set to 2
410 self.cu.arraysize = 2
411
412 # now make the query return 3 rows
413 self.cu.execute("delete from test")
414 self.cu.execute("insert into test(name) values ('A')")
415 self.cu.execute("insert into test(name) values ('B')")
416 self.cu.execute("insert into test(name) values ('C')")
417 self.cu.execute("select name from test")
418 res = self.cu.fetchmany()
419
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000420 self.assertEqual(len(res), 2)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000421
422 def CheckFetchmany(self):
423 self.cu.execute("select name from test")
424 res = self.cu.fetchmany(100)
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000425 self.assertEqual(len(res), 1)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000426 res = self.cu.fetchmany(100)
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000427 self.assertEqual(res, [])
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000428
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000429 def CheckFetchmanyKwArg(self):
430 """Checks if fetchmany works with keyword arguments"""
431 self.cu.execute("select name from test")
432 res = self.cu.fetchmany(size=100)
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000433 self.assertEqual(len(res), 1)
Gerhard Häringe7ea7452008-03-29 00:45:29 +0000434
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000435 def CheckFetchall(self):
436 self.cu.execute("select name from test")
437 res = self.cu.fetchall()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000438 self.assertEqual(len(res), 1)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000439 res = self.cu.fetchall()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000440 self.assertEqual(res, [])
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000441
442 def CheckSetinputsizes(self):
443 self.cu.setinputsizes([3, 4, 5])
444
445 def CheckSetoutputsize(self):
446 self.cu.setoutputsize(5, 0)
447
448 def CheckSetoutputsizeNoColumn(self):
449 self.cu.setoutputsize(42)
450
451 def CheckCursorConnection(self):
452 # Optional DB-API extension.
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000453 self.assertEqual(self.cu.connection, self.cx)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000454
455 def CheckWrongCursorCallable(self):
Berker Peksag1003b342016-06-12 22:34:49 +0300456 with self.assertRaises(TypeError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000457 def f(): pass
458 cur = self.cx.cursor(f)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000459
460 def CheckCursorWrongClass(self):
461 class Foo: pass
462 foo = Foo()
Berker Peksag1003b342016-06-12 22:34:49 +0300463 with self.assertRaises(TypeError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000464 cur = sqlite.Cursor(foo)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000465
Victor Stinner45df8202010-04-28 22:31:17 +0000466@unittest.skipUnless(threading, 'This test requires threading.')
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000467class ThreadTests(unittest.TestCase):
468 def setUp(self):
469 self.con = sqlite.connect(":memory:")
470 self.cur = self.con.cursor()
471 self.cur.execute("create table test(id integer primary key, name text, bin binary, ratio number, ts timestamp)")
472
473 def tearDown(self):
474 self.cur.close()
475 self.con.close()
476
477 def CheckConCursor(self):
478 def run(con, errors):
479 try:
480 cur = con.cursor()
481 errors.append("did not raise ProgrammingError")
482 return
483 except sqlite.ProgrammingError:
484 return
485 except:
486 errors.append("raised wrong exception")
487
488 errors = []
489 t = threading.Thread(target=run, kwargs={"con": self.con, "errors": errors})
490 t.start()
491 t.join()
492 if len(errors) > 0:
493 self.fail("\n".join(errors))
494
495 def CheckConCommit(self):
496 def run(con, errors):
497 try:
498 con.commit()
499 errors.append("did not raise ProgrammingError")
500 return
501 except sqlite.ProgrammingError:
502 return
503 except:
504 errors.append("raised wrong exception")
505
506 errors = []
507 t = threading.Thread(target=run, kwargs={"con": self.con, "errors": errors})
508 t.start()
509 t.join()
510 if len(errors) > 0:
511 self.fail("\n".join(errors))
512
513 def CheckConRollback(self):
514 def run(con, errors):
515 try:
516 con.rollback()
517 errors.append("did not raise ProgrammingError")
518 return
519 except sqlite.ProgrammingError:
520 return
521 except:
522 errors.append("raised wrong exception")
523
524 errors = []
525 t = threading.Thread(target=run, kwargs={"con": self.con, "errors": errors})
526 t.start()
527 t.join()
528 if len(errors) > 0:
529 self.fail("\n".join(errors))
530
531 def CheckConClose(self):
532 def run(con, errors):
533 try:
534 con.close()
535 errors.append("did not raise ProgrammingError")
536 return
537 except sqlite.ProgrammingError:
538 return
539 except:
540 errors.append("raised wrong exception")
541
542 errors = []
543 t = threading.Thread(target=run, kwargs={"con": self.con, "errors": errors})
544 t.start()
545 t.join()
546 if len(errors) > 0:
547 self.fail("\n".join(errors))
548
549 def CheckCurImplicitBegin(self):
550 def run(cur, errors):
551 try:
552 cur.execute("insert into test(name) values ('a')")
553 errors.append("did not raise ProgrammingError")
554 return
555 except sqlite.ProgrammingError:
556 return
557 except:
558 errors.append("raised wrong exception")
559
560 errors = []
561 t = threading.Thread(target=run, kwargs={"cur": self.cur, "errors": errors})
562 t.start()
563 t.join()
564 if len(errors) > 0:
565 self.fail("\n".join(errors))
566
567 def CheckCurClose(self):
568 def run(cur, errors):
569 try:
570 cur.close()
571 errors.append("did not raise ProgrammingError")
572 return
573 except sqlite.ProgrammingError:
574 return
575 except:
576 errors.append("raised wrong exception")
577
578 errors = []
579 t = threading.Thread(target=run, kwargs={"cur": self.cur, "errors": errors})
580 t.start()
581 t.join()
582 if len(errors) > 0:
583 self.fail("\n".join(errors))
584
585 def CheckCurExecute(self):
586 def run(cur, errors):
587 try:
588 cur.execute("select name from test")
589 errors.append("did not raise ProgrammingError")
590 return
591 except sqlite.ProgrammingError:
592 return
593 except:
594 errors.append("raised wrong exception")
595
596 errors = []
597 self.cur.execute("insert into test(name) values ('a')")
598 t = threading.Thread(target=run, kwargs={"cur": self.cur, "errors": errors})
599 t.start()
600 t.join()
601 if len(errors) > 0:
602 self.fail("\n".join(errors))
603
604 def CheckCurIterNext(self):
605 def run(cur, errors):
606 try:
607 row = cur.fetchone()
608 errors.append("did not raise ProgrammingError")
609 return
610 except sqlite.ProgrammingError:
611 return
612 except:
613 errors.append("raised wrong exception")
614
615 errors = []
616 self.cur.execute("insert into test(name) values ('a')")
617 self.cur.execute("select name from test")
618 t = threading.Thread(target=run, kwargs={"cur": self.cur, "errors": errors})
619 t.start()
620 t.join()
621 if len(errors) > 0:
622 self.fail("\n".join(errors))
623
624class ConstructorTests(unittest.TestCase):
625 def CheckDate(self):
626 d = sqlite.Date(2004, 10, 28)
627
628 def CheckTime(self):
629 t = sqlite.Time(12, 39, 35)
630
631 def CheckTimestamp(self):
632 ts = sqlite.Timestamp(2004, 10, 28, 12, 39, 35)
633
634 def CheckDateFromTicks(self):
635 d = sqlite.DateFromTicks(42)
636
637 def CheckTimeFromTicks(self):
638 t = sqlite.TimeFromTicks(42)
639
640 def CheckTimestampFromTicks(self):
641 ts = sqlite.TimestampFromTicks(42)
642
643 def CheckBinary(self):
Guido van Rossumbae07c92007-10-08 02:46:15 +0000644 b = sqlite.Binary(b"\0'")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000645
646class ExtensionTests(unittest.TestCase):
647 def CheckScriptStringSql(self):
648 con = sqlite.connect(":memory:")
649 cur = con.cursor()
650 cur.executescript("""
651 -- bla bla
652 /* a stupid comment */
653 create table a(i);
654 insert into a(i) values (5);
655 """)
656 cur.execute("select i from a")
657 res = cur.fetchone()[0]
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000658 self.assertEqual(res, 5)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000659
Gerhard Häringf9cee222010-03-05 15:20:03 +0000660 def CheckScriptSyntaxError(self):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000661 con = sqlite.connect(":memory:")
662 cur = con.cursor()
Berker Peksag1003b342016-06-12 22:34:49 +0300663 with self.assertRaises(sqlite.OperationalError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000664 cur.executescript("create table test(x); asdf; create table test2(x)")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000665
666 def CheckScriptErrorNormal(self):
667 con = sqlite.connect(":memory:")
668 cur = con.cursor()
Berker Peksag1003b342016-06-12 22:34:49 +0300669 with self.assertRaises(sqlite.OperationalError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000670 cur.executescript("create table test(sadfsadfdsa); select foo from hurz;")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000671
Berker Peksagc4154402016-06-12 13:41:47 +0300672 def CheckCursorExecutescriptAsBytes(self):
673 con = sqlite.connect(":memory:")
674 cur = con.cursor()
675 with self.assertRaises(ValueError) as cm:
676 cur.executescript(b"create table test(foo); insert into test(foo) values (5);")
677 self.assertEqual(str(cm.exception), 'script argument must be unicode.')
678
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000679 def CheckConnectionExecute(self):
680 con = sqlite.connect(":memory:")
681 result = con.execute("select 5").fetchone()[0]
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000682 self.assertEqual(result, 5, "Basic test of Connection.execute")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000683
684 def CheckConnectionExecutemany(self):
685 con = sqlite.connect(":memory:")
686 con.execute("create table test(foo)")
687 con.executemany("insert into test(foo) values (?)", [(3,), (4,)])
688 result = con.execute("select foo from test order by foo").fetchall()
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000689 self.assertEqual(result[0][0], 3, "Basic test of Connection.executemany")
690 self.assertEqual(result[1][0], 4, "Basic test of Connection.executemany")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000691
692 def CheckConnectionExecutescript(self):
693 con = sqlite.connect(":memory:")
694 con.executescript("create table test(foo); insert into test(foo) values (5);")
695 result = con.execute("select foo from test").fetchone()[0]
Gregory P. Smith04cecaf2009-07-04 08:32:15 +0000696 self.assertEqual(result, 5, "Basic test of Connection.executescript")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000697
Gerhard Häringf9cee222010-03-05 15:20:03 +0000698class ClosedConTests(unittest.TestCase):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000699 def setUp(self):
700 pass
701
702 def tearDown(self):
703 pass
704
705 def CheckClosedConCursor(self):
706 con = sqlite.connect(":memory:")
707 con.close()
Berker Peksag1003b342016-06-12 22:34:49 +0300708 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000709 cur = con.cursor()
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000710
711 def CheckClosedConCommit(self):
712 con = sqlite.connect(":memory:")
713 con.close()
Berker Peksag1003b342016-06-12 22:34:49 +0300714 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000715 con.commit()
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000716
717 def CheckClosedConRollback(self):
718 con = sqlite.connect(":memory:")
719 con.close()
Berker Peksag1003b342016-06-12 22:34:49 +0300720 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000721 con.rollback()
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000722
723 def CheckClosedCurExecute(self):
724 con = sqlite.connect(":memory:")
725 cur = con.cursor()
726 con.close()
Berker Peksag1003b342016-06-12 22:34:49 +0300727 with self.assertRaises(sqlite.ProgrammingError):
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000728 cur.execute("select 4")
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000729
Gerhard Häringf9cee222010-03-05 15:20:03 +0000730 def CheckClosedCreateFunction(self):
731 con = sqlite.connect(":memory:")
732 con.close()
733 def f(x): return 17
Berker Peksag1003b342016-06-12 22:34:49 +0300734 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000735 con.create_function("foo", 1, f)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000736
737 def CheckClosedCreateAggregate(self):
738 con = sqlite.connect(":memory:")
739 con.close()
740 class Agg:
741 def __init__(self):
742 pass
743 def step(self, x):
744 pass
745 def finalize(self):
746 return 17
Berker Peksag1003b342016-06-12 22:34:49 +0300747 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000748 con.create_aggregate("foo", 1, Agg)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000749
750 def CheckClosedSetAuthorizer(self):
751 con = sqlite.connect(":memory:")
752 con.close()
753 def authorizer(*args):
754 return sqlite.DENY
Berker Peksag1003b342016-06-12 22:34:49 +0300755 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000756 con.set_authorizer(authorizer)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000757
758 def CheckClosedSetProgressCallback(self):
759 con = sqlite.connect(":memory:")
760 con.close()
761 def progress(): pass
Berker Peksag1003b342016-06-12 22:34:49 +0300762 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000763 con.set_progress_handler(progress, 100)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000764
765 def CheckClosedCall(self):
766 con = sqlite.connect(":memory:")
767 con.close()
Berker Peksag1003b342016-06-12 22:34:49 +0300768 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000769 con()
Gerhard Häringf9cee222010-03-05 15:20:03 +0000770
771class ClosedCurTests(unittest.TestCase):
772 def setUp(self):
773 pass
774
775 def tearDown(self):
776 pass
777
778 def CheckClosed(self):
779 con = sqlite.connect(":memory:")
780 cur = con.cursor()
781 cur.close()
782
783 for method_name in ("execute", "executemany", "executescript", "fetchall", "fetchmany", "fetchone"):
784 if method_name in ("execute", "executescript"):
785 params = ("select 4 union select 5",)
786 elif method_name == "executemany":
787 params = ("insert into foo(bar) values (?)", [(3,), (4,)])
788 else:
789 params = []
790
Berker Peksag1003b342016-06-12 22:34:49 +0300791 with self.assertRaises(sqlite.ProgrammingError):
Gerhard Häringf9cee222010-03-05 15:20:03 +0000792 method = getattr(cur, method_name)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000793 method(*params)
Gerhard Häringf9cee222010-03-05 15:20:03 +0000794
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000795def suite():
796 module_suite = unittest.makeSuite(ModuleTests, "Check")
797 connection_suite = unittest.makeSuite(ConnectionTests, "Check")
798 cursor_suite = unittest.makeSuite(CursorTests, "Check")
799 thread_suite = unittest.makeSuite(ThreadTests, "Check")
800 constructor_suite = unittest.makeSuite(ConstructorTests, "Check")
801 ext_suite = unittest.makeSuite(ExtensionTests, "Check")
Gerhard Häringf9cee222010-03-05 15:20:03 +0000802 closed_con_suite = unittest.makeSuite(ClosedConTests, "Check")
803 closed_cur_suite = unittest.makeSuite(ClosedCurTests, "Check")
804 return unittest.TestSuite((module_suite, connection_suite, cursor_suite, thread_suite, constructor_suite, ext_suite, closed_con_suite, closed_cur_suite))
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000805
806def test():
807 runner = unittest.TextTestRunner()
808 runner.run(suite())
809
810if __name__ == "__main__":
811 test()