""" Tests for search page integration Tests cover: - Search page rendering - Search results display - Search box in navigation - Empty state handling - Error state handling - Pagination controls """ import pytest from pathlib import Path from starpunk import create_app from starpunk.notes import create_note @pytest.fixture def app(tmp_path): """Create test application with FTS5 enabled""" test_data_dir = tmp_path / "data" test_data_dir.mkdir(parents=True, exist_ok=True) test_config = { "TESTING": True, "DATABASE_PATH": test_data_dir / "starpunk.db", "DATA_PATH": test_data_dir, "NOTES_PATH": test_data_dir / "notes", "SESSION_SECRET": "test-secret-key", "ADMIN_ME": "https://test.example.com", "SITE_URL": "https://example.com", "SITE_NAME": "Test Blog", "DEV_MODE": False, } app = create_app(config=test_config) return app @pytest.fixture def client(app): """Create test client""" return app.test_client() @pytest.fixture def test_notes(app): """Create test notes for searching""" with app.app_context(): notes = [] for i in range(5): note = create_note( content=f"# Test Note {i}\n\nThis is test content about topic {i}.", published=True ) notes.append(note) return notes def test_search_page_renders(client): """Test that search page renders without errors""" response = client.get("/search") assert response.status_code == 200 assert b"Search Results" in response.data def test_search_page_shows_empty_state(client): """Test that search page shows empty state without query""" response = client.get("/search") assert response.status_code == 200 assert b"Enter search terms" in response.data or b"Search" in response.data def test_search_page_displays_results(client, test_notes): """Test that search page displays results""" response = client.get("/search?q=test") assert response.status_code == 200 # Should show query and results assert b"test" in response.data.lower() assert b"Test Note" in response.data def test_search_page_displays_result_count(client, test_notes): """Test that search page displays result count""" response = client.get("/search?q=test") assert response.status_code == 200 # Should show "Found X results" assert b"Found" in response.data or b"result" in response.data.lower() def test_search_page_handles_no_results(client, test_notes): """Test that search page handles no results gracefully""" response = client.get("/search?q=nonexistent") assert response.status_code == 200 # Should show "no results" message assert b"No results" in response.data or b"didn't match" in response.data def test_search_page_preserves_query(client, test_notes): """Test that search page preserves query in search box""" response = client.get("/search?q=python") assert response.status_code == 200 # Search form should have the query pre-filled assert b'value="python"' in response.data def test_search_page_shows_pagination(client, test_notes): """Test that search page shows pagination controls when appropriate""" response = client.get("/search?q=test") assert response.status_code == 200 # May or may not show pagination depending on result count # Just verify page renders without error def test_search_page_pagination_links(client, test_notes): """Test that pagination links work correctly""" # Get second page response = client.get("/search?q=test&offset=20") assert response.status_code == 200 # Should render without error assert b"Search Results" in response.data def test_search_box_in_navigation(client): """Test that search box appears in navigation on all pages""" # Check on homepage response = client.get("/") assert response.status_code == 200 assert b'type="search"' in response.data assert b'name="q"' in response.data assert b'action="/search"' in response.data def test_search_box_preserves_query_on_results_page(client, test_notes): """Test that search box preserves query on results page""" response = client.get("/search?q=test") assert response.status_code == 200 # Navigation search box should also have the query # (There are two search forms: one in nav, one on the page) assert response.data.count(b'value="test"') >= 1 def test_search_page_escapes_html_in_query(client): """Test that search page escapes HTML in query display""" response = client.get("/search?q=") assert response.status_code == 200 # Should not contain unescaped script tag assert b"" not in response.data # Should contain escaped version assert b"<script>" in response.data or b"alert" in response.data def test_search_page_shows_excerpt_with_highlighting(client, test_notes): """Test that search page shows excerpts with highlighting""" response = client.get("/search?q=test") assert response.status_code == 200 # Should contain tags for highlighting (from FTS5 snippet) # or at least show the excerpt assert b"Test" in response.data def test_search_page_shows_note_dates(client, test_notes): """Test that search page shows note publication dates""" response = client.get("/search?q=test") assert response.status_code == 200 # Should contain time element with datetime assert b"