2017-11-10 18:48:16 +00:00
|
|
|
"""
|
|
|
|
Tests for various datasette helper functions.
|
|
|
|
"""
|
|
|
|
|
2017-11-10 19:25:54 +00:00
|
|
|
from datasette import utils
|
2017-10-24 05:54:58 +00:00
|
|
|
import pytest
|
2017-10-24 14:58:41 +00:00
|
|
|
import json
|
2017-10-24 05:54:58 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('path,expected', [
|
|
|
|
('foo', ['foo']),
|
|
|
|
('foo,bar', ['foo', 'bar']),
|
|
|
|
('123,433,112', ['123', '433', '112']),
|
|
|
|
('123%2C433,112', ['123,433', '112']),
|
|
|
|
('123%2F433%2F112', ['123/433/112']),
|
|
|
|
])
|
|
|
|
def test_compound_pks_from_path(path, expected):
|
2017-11-10 19:25:54 +00:00
|
|
|
assert expected == utils.compound_pks_from_path(path)
|
2017-10-24 05:54:58 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('row,pks,expected_path', [
|
|
|
|
({'A': 'foo', 'B': 'bar'}, ['A', 'B'], 'foo,bar'),
|
|
|
|
({'A': 'f,o', 'B': 'bar'}, ['A', 'B'], 'f%2Co,bar'),
|
2017-10-24 14:10:58 +00:00
|
|
|
({'A': 123}, ['A'], '123'),
|
2017-10-24 05:54:58 +00:00
|
|
|
])
|
|
|
|
def test_path_from_row_pks(row, pks, expected_path):
|
2017-11-10 19:25:54 +00:00
|
|
|
actual_path = utils.path_from_row_pks(row, pks, False)
|
2017-10-24 05:54:58 +00:00
|
|
|
assert expected_path == actual_path
|
2017-10-24 14:58:41 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('obj,expected', [
|
|
|
|
({
|
|
|
|
'Description': 'Soft drinks',
|
|
|
|
'Picture': b"\x15\x1c\x02\xc7\xad\x05\xfe",
|
|
|
|
'CategoryID': 1,
|
|
|
|
}, """
|
|
|
|
{"CategoryID": 1, "Description": "Soft drinks", "Picture": {"$base64": true, "encoded": "FRwCx60F/g=="}}
|
|
|
|
""".strip()),
|
|
|
|
])
|
|
|
|
def test_custom_json_encoder(obj, expected):
|
|
|
|
actual = json.dumps(
|
|
|
|
obj,
|
2017-11-10 19:25:54 +00:00
|
|
|
cls=utils.CustomJSONEncoder,
|
2017-10-24 14:58:41 +00:00
|
|
|
sort_keys=True
|
|
|
|
)
|
|
|
|
assert expected == actual
|
2017-10-25 00:06:23 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('args,expected_where,expected_params', [
|
2017-10-25 01:46:49 +00:00
|
|
|
(
|
|
|
|
{
|
|
|
|
'name_english__contains': ['foo'],
|
|
|
|
},
|
2017-11-10 18:43:54 +00:00
|
|
|
'"name_english" like :p0',
|
2017-10-25 01:46:49 +00:00
|
|
|
['%foo%']
|
|
|
|
),
|
|
|
|
(
|
|
|
|
{
|
|
|
|
'foo': ['bar'],
|
|
|
|
'bar__contains': ['baz'],
|
|
|
|
},
|
2017-11-10 18:43:54 +00:00
|
|
|
'"bar" like :p0 and "foo" = :p1',
|
2017-10-25 01:46:49 +00:00
|
|
|
['%baz%', 'bar']
|
|
|
|
),
|
|
|
|
(
|
|
|
|
{
|
|
|
|
'foo__startswith': ['bar'],
|
|
|
|
'bar__endswith': ['baz'],
|
|
|
|
},
|
2017-11-10 18:43:54 +00:00
|
|
|
'"bar" like :p0 and "foo" like :p1',
|
2017-10-25 01:46:49 +00:00
|
|
|
['%baz', 'bar%']
|
|
|
|
),
|
|
|
|
(
|
|
|
|
{
|
|
|
|
'foo__lt': ['1'],
|
|
|
|
'bar__gt': ['2'],
|
|
|
|
'baz__gte': ['3'],
|
|
|
|
'bax__lte': ['4'],
|
|
|
|
},
|
2017-11-10 18:43:54 +00:00
|
|
|
'"bar" > :p0 and "bax" <= :p1 and "baz" >= :p2 and "foo" < :p3',
|
|
|
|
[2, 4, 3, 1]
|
2017-10-25 01:46:49 +00:00
|
|
|
),
|
2017-10-25 01:53:01 +00:00
|
|
|
(
|
|
|
|
{
|
|
|
|
'foo__like': ['2%2'],
|
|
|
|
'zax__glob': ['3*'],
|
|
|
|
},
|
2017-11-10 18:43:54 +00:00
|
|
|
'"foo" like :p0 and "zax" glob :p1',
|
2017-10-25 01:53:01 +00:00
|
|
|
['2%2', '3*']
|
|
|
|
),
|
2017-10-25 00:06:23 +00:00
|
|
|
])
|
|
|
|
def test_build_where(args, expected_where, expected_params):
|
2017-11-10 20:41:14 +00:00
|
|
|
sql_bits, actual_params = utils.build_where_clauses(args)
|
|
|
|
actual_where = ' and '.join(sql_bits)
|
2017-10-25 00:06:23 +00:00
|
|
|
assert expected_where == actual_where
|
2017-11-10 18:43:54 +00:00
|
|
|
assert {
|
|
|
|
'p{}'.format(i): param
|
|
|
|
for i, param in enumerate(expected_params)
|
|
|
|
} == actual_params
|
2017-11-05 02:49:18 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('bad_sql', [
|
|
|
|
'update blah;',
|
|
|
|
'PRAGMA case_sensitive_like = true'
|
|
|
|
"SELECT * FROM pragma_index_info('idx52')",
|
|
|
|
])
|
|
|
|
def test_validate_sql_select_bad(bad_sql):
|
2017-11-10 19:25:54 +00:00
|
|
|
with pytest.raises(utils.InvalidSql):
|
|
|
|
utils.validate_sql_select(bad_sql)
|
2017-11-05 02:49:18 +00:00
|
|
|
|
|
|
|
|
|
|
|
@pytest.mark.parametrize('good_sql', [
|
|
|
|
'select count(*) from airports',
|
|
|
|
'select foo from bar',
|
|
|
|
'select 1 + 1',
|
|
|
|
])
|
|
|
|
def test_validate_sql_select_good(good_sql):
|
2017-11-10 19:25:54 +00:00
|
|
|
utils.validate_sql_select(good_sql)
|