Self-hosted knowledge keeper for 3D printing projects
# Fast tests (contract tests only) - ~30 seconds
make test-fast
# Standard tests (contract + integration) - ~2 minutes
make test
# Validation tests (input validation) - ~5 minutes
make test-validation
# E2E tests (browser tests) - ~10 minutes
# Requires server to be running first!
make test-e2e
# E2E smoke tests (public + user + admin, no manual admin env required)
make test-e2e-smoke
# Full test suite - ~15 minutes
make test-full
# With coverage report
make test-coverage
# Security-focused tests only
make test-security
# All test levels
./scripts/run-qa-tests.sh fast
./scripts/run-qa-tests.sh standard
./scripts/run-qa-tests.sh validation
./scripts/run-qa-tests.sh e2e
./scripts/run-qa-tests.sh e2e-smoke
./scripts/run-qa-tests.sh full
./scripts/run-qa-tests.sh coverage
./scripts/run-qa-tests.sh security
tests/
├── contract/ # API contract tests
│ ├── test_auth_endpoints.py
│ ├── test_projects_*.py
│ └── test_keys_*.py
│
├── integration/ # Multi-component tests
│ ├── test_auth_flow.py
│ └── test_api_key_scopes.py
│
├── validation/ # Input validation tests
│ ├── test_auth_validation.py
│ ├── test_project_validation.py
│ └── test_api_key_validation.py
│
├── e2e/ # End-to-end browser tests
│ ├── pages/ # Page object models
│ ├── test_auth_flow.py
│ └── test_project_crud.py
│
├── fixtures/ # Test data factories
│ ├── factories.py
│ └── example_usage.py
│
└── manual/ # Manual QA checklists
└── qa-checklist.md
def test_create_project(client):
"""Test project creation."""
response = client.post("/api/v1/projects", json={
"name": "Test Project",
"description": "Test"
})
assert response.status_code == 201
assert response.json()["name"] == "Test Project"
@pytest.mark.parametrize("name,expected_status", [
("", 400), # Empty
("a", 400), # Too short
("a" * 300, 400), # Too long
])
def test_invalid_names(client, name, expected_status):
response = client.post("/api/v1/projects", json={"name": name})
assert response.status_code == expected_status
def test_create_project(logged_in_page):
"""Test project creation flow."""
project_page = ProjectPage(logged_in_page)
project_page.navigate_to_projects()
project_page.create_project("Test Project", "Description")
assert project_page.project_exists("Test Project")
from tests.fixtures.factories import UserFactory, ProjectFactory
# Create test user
user = UserFactory.build() # With defaults
user = UserFactory.build(username="testuser") # With custom values
# Create multiple users
users = UserFactory.build_batch(10)
# Get invalid variations
for variant, data in UserFactory.build_invalid("username"):
# Test each invalid username variant
pass
# Create test project
project = ProjectFactory.build()
project = ProjectFactory.build_with_unicode()
project = ProjectFactory.build_with_special_chars()
# Mark as smoke test (critical path)
@pytest.mark.smoke
def test_login():
pass
# Mark as security test
@pytest.mark.security
def test_sql_injection():
pass
# Mark as slow test
@pytest.mark.slow
def test_large_upload():
pass
# Mark as E2E test
@pytest.mark.e2e
def test_full_workflow():
pass
# Run by marker
pytest -m smoke
pytest -m security
pytest -m "not slow"
# Run by keyword
pytest -k "test_login"
pytest -k "sql_injection or xss"
# Run specific file
pytest tests/validation/test_auth_validation.py
# Run specific test
pytest tests/validation/test_auth_validation.py::test_empty_username
pytest tests/e2e/ --headed
pytest tests/e2e/ --browser firefox
pytest tests/e2e/ --browser webkit
pytest tests/e2e/ --headed --slowmo 1000
pytest tests/e2e/ --tracing on
playwright show-trace test-results/trace.zip
# Generate coverage report
make test-coverage
# View in browser
open htmlcov/index.html
# View in terminal
pytest --cov=src/backend --cov-report=term-missing
<script>alert('XSS')</script><img src=x onerror=alert('XSS')><svg onload=alert('XSS')>javascript:alert('XSS')' OR '1'='1'; DROP TABLE users;--admin'--1' OR '1' = '1../../../etc/passwd..\\..\\..\\windows\\system32\\config\\sam日本語ÑoñoМосква- name: Run QA Tests
run: |
make test-fast
make test-validation
- name: Run E2E Tests
run: |
make dev & # Start server
sleep 5
make test-e2e
# Check environment variables
echo $DATABASE_URL
# Reset test database
rm -f tests/test.db
# Make sure server is running
curl http://localhost:8000/api/v1/health
# Check port isn't in use
lsof -i :8000
pip install playwright pytest-playwright
playwright install chromium
chmod +x scripts/run-qa-tests.sh