diff options
Diffstat (limited to 'test/test_smart_completion_public_schema_only.py')
-rw-r--r-- | test/test_smart_completion_public_schema_only.py | 389 |
1 files changed, 389 insertions, 0 deletions
diff --git a/test/test_smart_completion_public_schema_only.py b/test/test_smart_completion_public_schema_only.py new file mode 100644 index 0000000..b60e67c --- /dev/null +++ b/test/test_smart_completion_public_schema_only.py @@ -0,0 +1,389 @@ +import pytest +from unittest.mock import patch +from prompt_toolkit.completion import Completion +from prompt_toolkit.document import Document +import mycli.packages.special.main as special + +metadata = { + 'users': ['id', 'email', 'first_name', 'last_name'], + 'orders': ['id', 'ordered_date', 'status'], + 'select': ['id', 'insert', 'ABC'], + 'réveillé': ['id', 'insert', 'ABC'] +} + + +@pytest.fixture +def completer(): + + import mycli.sqlcompleter as sqlcompleter + comp = sqlcompleter.SQLCompleter(smart_completion=True) + + tables, columns = [], [] + + for table, cols in metadata.items(): + tables.append((table,)) + columns.extend([(table, col) for col in cols]) + + comp.set_dbname('test') + comp.extend_schemata('test') + comp.extend_relations(tables, kind='tables') + comp.extend_columns(columns, kind='tables') + comp.extend_special_commands(special.COMMANDS) + + return comp + + +@pytest.fixture +def complete_event(): + from unittest.mock import Mock + return Mock() + + +def test_special_name_completion(completer, complete_event): + text = '\\d' + position = len('\\d') + result = completer.get_completions( + Document(text=text, cursor_position=position), + complete_event) + assert result == [Completion(text='\\dt', start_position=-2)] + + +def test_empty_string_completion(completer, complete_event): + text = '' + position = 0 + result = list( + completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert list(map(Completion, completer.keywords + + completer.special_commands)) == result + + +def test_select_keyword_completion(completer, complete_event): + text = 'SEL' + position = len('SEL') + result = completer.get_completions( + Document(text=text, cursor_position=position), + complete_event) + assert list(result) == list([Completion(text='SELECT', start_position=-3)]) + + +def test_table_completion(completer, complete_event): + text = 'SELECT * FROM ' + position = len(text) + result = completer.get_completions( + Document(text=text, cursor_position=position), complete_event) + assert list(result) == list([ + Completion(text='users', start_position=0), + Completion(text='orders', start_position=0), + Completion(text='`select`', start_position=0), + Completion(text='`réveillé`', start_position=0), + ]) + + +def test_function_name_completion(completer, complete_event): + text = 'SELECT MA' + position = len('SELECT MA') + result = completer.get_completions( + Document(text=text, cursor_position=position), complete_event) + assert list(result) == list([Completion(text='MAX', start_position=-2), + Completion(text='MASTER', start_position=-2), + ]) + + +def test_suggested_column_names(completer, complete_event): + """Suggest column and function names when selecting from table. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT from users' + position = len('SELECT ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0), + ] + + list(map(Completion, completer.functions)) + + [Completion(text='users', start_position=0)] + + list(map(Completion, completer.keywords))) + + +def test_suggested_column_names_in_function(completer, complete_event): + """Suggest column and function names when selecting multiple columns from + table. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT MAX( from users' + position = len('SELECT MAX(') + result = completer.get_completions( + Document(text=text, cursor_position=position), + complete_event) + assert list(result) == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)]) + + +def test_suggested_column_names_with_table_dot(completer, complete_event): + """Suggest column names on table name and dot. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT users. from users' + position = len('SELECT users.') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)]) + + +def test_suggested_column_names_with_alias(completer, complete_event): + """Suggest column names on table alias and dot. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT u. from users u' + position = len('SELECT u.') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)]) + + +def test_suggested_multiple_column_names(completer, complete_event): + """Suggest column and function names when selecting multiple columns from + table. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT id, from users u' + position = len('SELECT id, ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)] + + list(map(Completion, completer.functions)) + + [Completion(text='u', start_position=0)] + + list(map(Completion, completer.keywords))) + + +def test_suggested_multiple_column_names_with_alias(completer, complete_event): + """Suggest column names on table alias and dot when selecting multiple + columns from table. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT u.id, u. from users u' + position = len('SELECT u.id, u.') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)]) + + +def test_suggested_multiple_column_names_with_dot(completer, complete_event): + """Suggest column names on table names and dot when selecting multiple + columns from table. + + :param completer: + :param complete_event: + :return: + + """ + text = 'SELECT users.id, users. from users u' + position = len('SELECT users.id, users.') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='email', start_position=0), + Completion(text='first_name', start_position=0), + Completion(text='last_name', start_position=0)]) + + +def test_suggested_aliases_after_on(completer, complete_event): + text = 'SELECT u.name, o.id FROM users u JOIN orders o ON ' + position = len('SELECT u.name, o.id FROM users u JOIN orders o ON ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='u', start_position=0), + Completion(text='o', start_position=0), + ]) + + +def test_suggested_aliases_after_on_right_side(completer, complete_event): + text = 'SELECT u.name, o.id FROM users u JOIN orders o ON o.user_id = ' + position = len( + 'SELECT u.name, o.id FROM users u JOIN orders o ON o.user_id = ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='u', start_position=0), + Completion(text='o', start_position=0), + ]) + + +def test_suggested_tables_after_on(completer, complete_event): + text = 'SELECT users.name, orders.id FROM users JOIN orders ON ' + position = len('SELECT users.name, orders.id FROM users JOIN orders ON ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='users', start_position=0), + Completion(text='orders', start_position=0), + ]) + + +def test_suggested_tables_after_on_right_side(completer, complete_event): + text = 'SELECT users.name, orders.id FROM users JOIN orders ON orders.user_id = ' + position = len( + 'SELECT users.name, orders.id FROM users JOIN orders ON orders.user_id = ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='users', start_position=0), + Completion(text='orders', start_position=0), + ]) + + +def test_table_names_after_from(completer, complete_event): + text = 'SELECT * FROM ' + position = len('SELECT * FROM ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='users', start_position=0), + Completion(text='orders', start_position=0), + Completion(text='`select`', start_position=0), + Completion(text='`réveillé`', start_position=0), + ]) + + +def test_auto_escaped_col_names(completer, complete_event): + text = 'SELECT from `select`' + position = len('SELECT ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == [ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='`insert`', start_position=0), + Completion(text='`ABC`', start_position=0), + ] + \ + list(map(Completion, completer.functions)) + \ + [Completion(text='select', start_position=0)] + \ + list(map(Completion, completer.keywords)) + + +def test_un_escaped_table_names(completer, complete_event): + text = 'SELECT from réveillé' + position = len('SELECT ') + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + assert result == list([ + Completion(text='*', start_position=0), + Completion(text='id', start_position=0), + Completion(text='`insert`', start_position=0), + Completion(text='`ABC`', start_position=0), + ] + + list(map(Completion, completer.functions)) + + [Completion(text='réveillé', start_position=0)] + + list(map(Completion, completer.keywords))) + + +def dummy_list_path(dir_name): + dirs = { + '/': [ + 'dir1', + 'file1.sql', + 'file2.sql', + ], + '/dir1': [ + 'subdir1', + 'subfile1.sql', + 'subfile2.sql', + ], + '/dir1/subdir1': [ + 'lastfile.sql', + ], + } + return dirs.get(dir_name, []) + + +@patch('mycli.packages.filepaths.list_path', new=dummy_list_path) +@pytest.mark.parametrize('text,expected', [ + # ('source ', [('~', 0), + # ('/', 0), + # ('.', 0), + # ('..', 0)]), + ('source /', [('dir1', 0), + ('file1.sql', 0), + ('file2.sql', 0)]), + ('source /dir1/', [('subdir1', 0), + ('subfile1.sql', 0), + ('subfile2.sql', 0)]), + ('source /dir1/subdir1/', [('lastfile.sql', 0)]), +]) +def test_file_name_completion(completer, complete_event, text, expected): + position = len(text) + result = list(completer.get_completions( + Document(text=text, cursor_position=position), + complete_event)) + expected = list((Completion(txt, pos) for txt, pos in expected)) + assert result == expected |