Author: cito
Date: Thu Jan 14 12:32:01 2016
New Revision: 743
Log:
Test error messages and security of the get() method
The get() method should be immune against SQL hacking with apostrophes in
values, and give a proper and helpful error message if a row is not found.
Modified:
branches/4.x/tests/test_classic_dbwrapper.py
trunk/pg.py
trunk/tests/test_classic_dbwrapper.py
Modified: branches/4.x/tests/test_classic_dbwrapper.py
==============================================================================
--- branches/4.x/tests/test_classic_dbwrapper.py Thu Jan 14 11:01:34
2016 (r742)
+++ branches/4.x/tests/test_classic_dbwrapper.py Thu Jan 14 12:32:01
2016 (r743)
@@ -724,6 +724,45 @@
self.assertIn('v4', r)
self.assertEqual(r['v4'], 'abc4')
+ def testGetLittleBobbyTables(self):
+ get = self.db.get
+ query = self.db.query
+ query("drop table if exists test_students")
+ query("create table test_students (firstname varchar primary key,"
+ " nickname varchar, grade char(2))")
+ query("insert into test_students values ("
+ "'D''Arcy', 'Darcey', 'A+')")
+ query("insert into test_students values ("
+ "'Sheldon', 'Moonpie', 'A+')")
+ query("insert into test_students values ("
+ "'Robert', 'Little Bobby Tables', 'D-')")
+ r = get('test_students', 'Sheldon')
+ self.assertEqual(r, dict(
+ firstname="Sheldon", nickname='Moonpie', grade='A+'))
+ r = get('test_students', 'Robert')
+ self.assertEqual(r, dict(
+ firstname="Robert", nickname='Little Bobby Tables', grade='D-'))
+ r = get('test_students', "D'Arcy")
+ self.assertEqual(r, dict(
+ firstname="D'Arcy", nickname='Darcey', grade='A+'))
+ try:
+ get('test_students', "D' Arcy")
+ except pg.DatabaseError as error:
+ self.assertEqual(str(error),
+ 'No such record in public.test_students where firstname = '
+ "'D'' Arcy'")
+ try:
+ get('test_students', "Robert'); TRUNCATE TABLE test_students;--")
+ except pg.DatabaseError as error:
+ self.assertEqual(str(error),
+ 'No such record in public.test_students where firstname = '
+ "'Robert''); TRUNCATE TABLE test_students;--'")
+ q = "select * from test_students order by 1 limit 4"
+ r = query(q).getresult()
+ self.assertEqual(len(r), 3)
+ self.assertEqual(r[1][2], 'D-')
+ query('drop table test_students')
+
def testInsert(self):
insert = self.db.insert
query = self.db.query
Modified: trunk/pg.py
==============================================================================
--- trunk/pg.py Thu Jan 14 11:01:34 2016 (r742)
+++ trunk/pg.py Thu Jan 14 12:32:01 2016 (r743)
@@ -370,6 +370,10 @@
params.append(value)
return '$%d' % len(params)
+ def _list_params(self, params):
+ """Create a human readable parameter list."""
+ return ', '.join('$%d=%r' % (n, v) for n, v in enumerate(params, 1))
+
@staticmethod
def _prepare_qualified_param(name, param):
"""Quote parameter representing a qualified name.
@@ -660,7 +664,8 @@
q = self.db.query(q, params)
res = q.dictresult()
if not res:
- raise _db_error('No such record in %s where %s' % (table, where))
+ raise _db_error('No such record in %s\nwhere %s\nwith %s' % (
+ table, where, self._list_params(params)))
for n, value in res[0].items():
if n == 'oid':
n = qoid
Modified: trunk/tests/test_classic_dbwrapper.py
==============================================================================
--- trunk/tests/test_classic_dbwrapper.py Thu Jan 14 11:01:34 2016
(r742)
+++ trunk/tests/test_classic_dbwrapper.py Thu Jan 14 12:32:01 2016
(r743)
@@ -816,6 +816,45 @@
self.assertIn('v4', r)
self.assertEqual(r['v4'], 'abc4')
+ def testGetLittleBobbyTables(self):
+ get = self.db.get
+ query = self.db.query
+ query("drop table if exists test_students")
+ query("create table test_students (firstname varchar primary key,"
+ " nickname varchar, grade char(2))")
+ query("insert into test_students values ("
+ "'D''Arcy', 'Darcey', 'A+')")
+ query("insert into test_students values ("
+ "'Sheldon', 'Moonpie', 'A+')")
+ query("insert into test_students values ("
+ "'Robert', 'Little Bobby Tables', 'D-')")
+ r = get('test_students', 'Sheldon')
+ self.assertEqual(r, dict(
+ firstname="Sheldon", nickname='Moonpie', grade='A+'))
+ r = get('test_students', 'Robert')
+ self.assertEqual(r, dict(
+ firstname="Robert", nickname='Little Bobby Tables', grade='D-'))
+ r = get('test_students', "D'Arcy")
+ self.assertEqual(r, dict(
+ firstname="D'Arcy", nickname='Darcey', grade='A+'))
+ try:
+ get('test_students', "D' Arcy")
+ except pg.DatabaseError as error:
+ self.assertEqual(str(error),
+ 'No such record in test_students\nwhere "firstname" = $1\n'
+ 'with $1="D\' Arcy"')
+ try:
+ get('test_students', "Robert'); TRUNCATE TABLE test_students;--")
+ except pg.DatabaseError as error:
+ self.assertEqual(str(error),
+ 'No such record in test_students\nwhere "firstname" = $1\n'
+ 'with $1="Robert\'); TRUNCATE TABLE test_students;--"')
+ q = "select * from test_students order by 1 limit 4"
+ r = query(q).getresult()
+ self.assertEqual(len(r), 3)
+ self.assertEqual(r[1][2], 'D-')
+ query('drop table test_students')
+
def testInsert(self):
insert = self.db.insert
query = self.db.query
_______________________________________________
PyGreSQL mailing list
[email protected]
https://mail.vex.net/mailman/listinfo.cgi/pygresql