Skip to content

Commit

Permalink
feature/sc 61/rationalize testing improve coverage (#13)
Browse files Browse the repository at this point in the history
* add cov cmd to makefile

* update make cmd to generate xml report, update gitignore

* add tests for line.py

* line cov to 100

* test cov to api to 100

* improve dialect test coverage

* improve splitter test coverage

* improve parser test coverage

* bump pytest version
  • Loading branch information
tconbeer authored Oct 26, 2021
1 parent 7d7ba53 commit 269824f
Show file tree
Hide file tree
Showing 13 changed files with 469 additions and 94 deletions.
2 changes: 1 addition & 1 deletion .coveragerc
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
[html]
directory = tests/coverage
directory = tests/.coverage
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
.coverage
tests/coverage
tests/.coverage
tests/.results
.mypy_cache
.pytest_cache
Expand Down
8 changes: 6 additions & 2 deletions Makefile
Original file line number Diff line number Diff line change
@@ -1,7 +1,11 @@
.PHONY: check
test:
check:
pytest
isort .
black .
flake8 .
mypy .
mypy .

.PHONY: unit
unit:
pytest --cov=sqlfmt --cov-report term-missing --cov-report xml:tests/.coverage/cov.xml tests/unit_tests
4 changes: 2 additions & 2 deletions Pipfile
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,8 @@ flake8 = "*"
isort = "*"
mypy = "*"
pre-commit = "*"
pytest = ">=5.2"
pytest-cov = ">=2.0"
pytest = ">=6.2"
pytest-cov = ">=3.0"

[requires]
python_version = "3.8"
Expand Down
14 changes: 10 additions & 4 deletions Pipfile.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

9 changes: 1 addition & 8 deletions src/sqlfmt/api.py
Original file line number Diff line number Diff line change
Expand Up @@ -25,14 +25,7 @@ def run(files: List[str], mode: Mode) -> int:
2 indicates unhandled exception
"""
matched_paths: Set[Path] = set()
for s in files:
p = Path(s)

if p.is_file() and p.suffix in (mode.SQL_EXTENSIONS):
matched_paths.add(p)

elif p.is_dir():
matched_paths.update(gen_sql_files(p.iterdir(), mode))
matched_paths.update(gen_sql_files([Path(s) for s in files], mode))

results = list(_generate_results(matched_paths, mode))

Expand Down
2 changes: 1 addition & 1 deletion src/sqlfmt/dialect.py
Original file line number Diff line number Diff line change
Expand Up @@ -179,7 +179,7 @@ def search_for_token(
else:
for t in token_types:
prog = self.programs[t]
match = prog.search(line, skipchars)
match = prog.match(line, start)
if match:
final_type = t
break
Expand Down
16 changes: 14 additions & 2 deletions src/sqlfmt/line.py
Original file line number Diff line number Diff line change
Expand Up @@ -473,14 +473,26 @@ def ends_with_comment(self) -> bool:

@property
def is_standalone_comment(self) -> bool:
if len(self.nodes) == 2 and self.ends_with_comment:
if len(self.nodes) == 1 and self.ends_with_comment:
return True
elif (
len(self.nodes) == 2
and self.ends_with_comment
and self.nodes[-1].is_newline
):
return True
else:
return False

@property
def is_standalone_multiline_node(self) -> bool:
if len(self.nodes) == 2 and self.contains_multiline_node:
if len(self.nodes) == 1 and self.contains_multiline_node:
return True
if (
len(self.nodes) == 2
and self.contains_multiline_node
and self.nodes[-1].is_newline
):
return True
else:
return False
Expand Down
42 changes: 35 additions & 7 deletions tests/unit_tests/test_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@

import pytest

from sqlfmt.api import _generate_results, _update_source_files, format_string
from sqlfmt.api import _generate_results, _update_source_files, format_string, run
from sqlfmt.mode import Mode
from tests.util import copy_test_data_to_tmp

Expand All @@ -14,12 +14,6 @@ def mode() -> Mode:
return Mode()


def test_format_empty_string(mode: Mode) -> None:
source = expected = ""
actual = format_string(source, mode)
assert expected == actual


@pytest.fixture
def preformatted_dir(tmp_path: Path) -> Path:
"""
Expand Down Expand Up @@ -52,6 +46,12 @@ def unformatted_files(unformatted_dir: Path) -> List[Path]:
return list(unformatted_dir.iterdir())


def test_format_empty_string(mode: Mode) -> None:
source = expected = ""
actual = format_string(source, mode)
assert expected == actual


def test_generate_results_preformatted(
preformatted_files: List[Path], mode: Mode
) -> None:
Expand Down Expand Up @@ -141,3 +141,31 @@ def test_update_source_files_unformatted(
new_file_contents = f.read()
assert new_file_contents == res.formatted_string
assert new_file_contents != res.source_string


def test_run_unformatted_update(
unformatted_dir: Path, mode: Mode, monkeypatch: pytest.MonkeyPatch
) -> None:

# confirm that we call the _update_source function
monkeypatch.delattr("sqlfmt.api._update_source_files")
with pytest.raises(NameError):
_ = run(files=[str(unformatted_dir)], mode=mode)


def test_run_preformatted_check(preformatted_files: List[Path]) -> None:
check_mode = Mode(output="check")
exit_code = run(files=[str(f) for f in preformatted_files], mode=check_mode)
assert exit_code == 0


def test_run_unformatted_check(unformatted_files: List[Path]) -> None:
check_mode = Mode(output="check")
exit_code = run(files=[str(f) for f in unformatted_files], mode=check_mode)
assert exit_code == 1


def test_run_unformatted_diff(unformatted_files: List[Path]) -> None:
diff_mode = Mode(output="diff")
exit_code = run(files=[str(f) for f in unformatted_files], mode=diff_mode)
assert exit_code == 2
46 changes: 46 additions & 0 deletions tests/unit_tests/test_dialect.py
Original file line number Diff line number Diff line change
Expand Up @@ -104,3 +104,49 @@ def test_regex_should_not_match_empty_string(self, postgres: Postgres) -> None:
for token_type, prog in postgres.programs.items():
match = prog.match("")
assert match is None, str(token_type)

def test_error_token(self, postgres: Postgres) -> None:
gen = postgres.tokenize_line(line="?\n", lnum=0)
t = next(gen)

expected_token = Token(
type=TokenType.ERROR_TOKEN,
prefix="",
token="?",
spos=(0, 0),
epos=(0, 2),
line="?\n",
)
assert t == expected_token

def test_search_for_one_token(self, postgres: Postgres) -> None:
line = "select 1 from my_table\n"

expected_token = Token(
type=TokenType.NUMBER,
prefix="select ",
token="1",
spos=(0, 7),
epos=(0, 8),
line="select 1 from my_table\n",
)

actual_token = postgres.search_for_token([TokenType.NUMBER], line=line, lnum=0)
assert actual_token == expected_token

def test_search_for_multiple_tokens(self, postgres: Postgres) -> None:
line = "select 1 from my_table\n"

expected_token = Token(
type=TokenType.NUMBER,
prefix=" ",
token="1",
spos=(0, 7),
epos=(0, 8),
line="select 1 from my_table\n",
)

actual_token = postgres.search_for_token(
[TokenType.NUMBER, TokenType.UNTERM_KEYWORD], line=line, lnum=0, skipchars=6
)
assert actual_token == expected_token
Loading

0 comments on commit 269824f

Please sign in to comment.