Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Test preview properly #25

Merged
merged 1 commit into from
Feb 3, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 4 additions & 2 deletions pyproject.toml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ dependencies = [
"htmlmin",
"jsmin",
"Pygments",
"requests",
]
description = "Write Markdown and Jinja2 templates to create a website"
maintainers = [
Expand All @@ -43,7 +44,7 @@ Repository = "https://github.com/siecje/htmd.git"

[tool.ruff.lint]
ignore = [
"D100", "D101", "D103", "D104", "D203", "D211", "D212", "D213",
"D100", "D101", "D103", "D104", "D105", "D107", "D203", "D211", "D212", "D213",
"INP001",
"RET504",
"S101",
Expand All @@ -65,11 +66,12 @@ lines-after-imports = 2
order-by-type = false
section-order = ["future", "standard-library", "third-party", "first-party", "local-folder"]

[tool.ruff.per-file-ignores]
[tool.ruff.lint.per-file-ignores]
"tests/test_app.py" = ["ARG001"]
"tests/test_build.py" = ["I001"]
"tests/test_drafts.py" = ["ARG001", "I001"]
"tests/test_post_dates.py" = ["I001"]
"tests/test_preview.py" = ["I001"]
"tests/test_verify.py" = ["I001"]

[tool.setuptools]
Expand Down
3 changes: 2 additions & 1 deletion requirements.txt
Original file line number Diff line number Diff line change
@@ -1,10 +1,11 @@
beautifulsoup4==4.12.3
click==8.1.7
csscompressor==0.9.5
feedwerk==1.1.0
feedwerk==1.2.0
Flask==3.0.1
Flask-FlatPages==0.8.2
Frozen-Flask==1.0.1
htmlmin==0.1.12
jsmin==3.0.1
Pygments==2.17.2
requests==2.31.0
123 changes: 114 additions & 9 deletions tests/test_preview.py
Original file line number Diff line number Diff line change
@@ -1,25 +1,130 @@
from pathlib import Path
import time
from types import TracebackType

from click.testing import CliRunner
from htmd.cli import preview
import pytest
import requests
import subprocess
import sys


def invoke_preview(run_start: CliRunner, args: list[str]) -> None:
"""
run_start.invoke(preview) fails but it is used to track test coverage.

I get a message that the path I pass to pytest is not found.
I've track it down to this subprocess call.
https://github.com/pallets/werkzeug/blob/d3dd65a27388fbd39d146caacf2563639ba622f0/src/werkzeug/_reloader.py#L273
str(args) is "['/path/to/venv/bin/python', '-m', 'pytest', 'tests']"
ERROR: file or directory not found: tests
Which is how I'm running my tests.
If I pass tests/test_preview.py then I see
ERROR: file or directory not found: tests/test_preview.py
"""
run_start.invoke(preview, args)


class run_preview: # noqa: N801
def __init__(
self: 'run_preview',
args: list[str] | None = None,
max_tries: int = 10,
) -> None:
self.args = args
self.max_tries = max_tries

def test_preview(run_start: CliRunner) -> None:
result = run_start.invoke(preview)
# Why is this 5?
expected_exit_code = 5
assert result.exit_code == expected_exit_code
def __enter__(self: 'run_preview') -> None:
cmd = [sys.executable, '-m', 'htmd', 'preview']
if self.args:
cmd += self.args
self.task = subprocess.Popen(cmd) # noqa: S603
url = 'http://localhost:9090/'
count = 0
while count < self.max_tries: # pragma: no branch
try:
requests.get(url, timeout=1)
except requests.exceptions.ConnectionError:
count += 1
time.sleep(0.1)
else:
break

def __exit__(
self: 'run_preview',
exc_type: type[BaseException] | None,
exc_value: BaseException | None,
traceback: TracebackType | None,
) -> None:
self.task.terminate()


def test_preview(run_start: CliRunner) -> None: # noqa: ARG001
url = 'http://localhost:9090/'
with pytest.raises(requests.exceptions.ConnectionError):
requests.get(url, timeout=1)
success = 200
with run_preview():
response = requests.get(url, timeout=0.01)
assert response.status_code == success


def test_preview_css_minify_js_minify(run_start: CliRunner) -> None:
run_start.invoke(preview, ['--css-minify', '--js-minify'])
args = ['--css-minify', '--js-minify']
invoke_preview(run_start, args)
urls = (
(200, 'http://localhost:9090/static/combined.min.css'),
(200, 'http://localhost:9090/static/combined.min.js'),
)
js_path = Path('static') / 'scripts.js'
with js_path.open('w') as js_file:
js_file.write('document.getElementsByTagName("body");')

with run_preview(args):
for status, url in urls:
response = requests.get(url, timeout=0.01)
assert response.status_code == status


def test_preview_no_css_minify(run_start: CliRunner) -> None:
run_start.invoke(preview, ['--no-css-minify', '--js-minify'])
args = ['--no-css-minify', '--js-minify']
invoke_preview(run_start, args)
urls = (
(404, 'http://localhost:9090/static/combined.min.css'),
(200, 'http://localhost:9090/static/combined.min.js'),
)
js_path = Path('static') / 'scripts.js'
with js_path.open('w') as js_file:
js_file.write('document.getElementsByTagName("body");')

with run_preview(args):
for status, url in urls:
response = requests.get(url, timeout=0.01)
assert response.status_code == status


def test_preview_css_minify_no_js_minify(run_start: CliRunner) -> None:
run_start.invoke(preview, ['--css-minify', '--no-js-minify'])
args = ['--css-minify', '--no-js-minify']
invoke_preview(run_start, args)
urls = (
(200, 'http://localhost:9090/static/combined.min.css'),
(404, 'http://localhost:9090/static/combined.min.js'),
)
with run_preview(args):
for status, url in urls:
response = requests.get(url, timeout=0.01)
assert response.status_code == status


def test_preview_no_css_minify_no_js_minify(run_start: CliRunner) -> None:
run_start.invoke(preview, ['--no-css-minify', '--no-js-minify'])
args = ['--no-css-minify', '--no-js-minify']
invoke_preview(run_start, args)
urls = (
(404, 'http://localhost:9090/static/combined.min.css'),
(404, 'http://localhost:9090/static/combined.min.js'),
)
with run_preview(args):
for status, url in urls:
response = requests.get(url, timeout=0.01)
assert response.status_code == status
Loading