fix: test suite — seed reset, FK mappings, standalone focus tests

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-03-04 03:09:04 +00:00
parent d5dce02451
commit 73d44ef804
3 changed files with 1162 additions and 55 deletions

View File

@@ -23,10 +23,9 @@ SEED_IDS = {
"meeting": "a0000000-0000-0000-0000-000000000007",
"decision": "a0000000-0000-0000-0000-000000000008",
"appointment": "a0000000-0000-0000-0000-000000000009",
"weblink_folder": "a0000000-0000-0000-0000-00000000000a",
"link_folder": "a0000000-0000-0000-0000-00000000000a",
"list": "a0000000-0000-0000-0000-00000000000b",
"link": "a0000000-0000-0000-0000-00000000000c",
"weblink": "a0000000-0000-0000-0000-00000000000d",
"capture": "a0000000-0000-0000-0000-00000000000e",
"focus": "a0000000-0000-0000-0000-00000000000f",
"process": "a0000000-0000-0000-0000-000000000010",
@@ -34,6 +33,7 @@ SEED_IDS = {
"process_run": "a0000000-0000-0000-0000-000000000012",
"time_budget": "a0000000-0000-0000-0000-000000000013",
"file": "a0000000-0000-0000-0000-000000000014",
"focus_standalone": "a0000000-0000-0000-0000-000000000015",
}
@@ -94,140 +94,179 @@ def all_seeds(sync_conn):
cur.execute("""
INSERT INTO domains (id, name, color, description, sort_order, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Domain', '#FF5733', 'Auto test domain', 0, false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET name='Test Domain', color='#FF5733', description='Auto test domain',
sort_order=0, is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["domain"],))
# Area
cur.execute("""
INSERT INTO areas (id, name, domain_id, description, status, sort_order, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Area', %s, 'Auto test area', 'active', 0, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["area"], d["domain"]))
ON CONFLICT (id) DO UPDATE SET name='Test Area', domain_id=%s, description='Auto test area',
status='active', sort_order=0, is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["area"], d["domain"], d["domain"]))
# Project
cur.execute("""
INSERT INTO projects (id, name, domain_id, area_id, description, status, priority, sort_order, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Project', %s, %s, 'Auto test project', 'active', 2, 0, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["project"], d["domain"], d["area"]))
ON CONFLICT (id) DO UPDATE SET name='Test Project', domain_id=%s, area_id=%s,
description='Auto test project', status='active', priority=2, sort_order=0,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["project"], d["domain"], d["area"], d["domain"], d["area"]))
# Task (status='open' matches DB default, not 'todo')
cur.execute("""
INSERT INTO tasks (id, title, domain_id, project_id, description, priority, status, sort_order, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Task', %s, %s, 'Auto test task', 2, 'open', 0, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["task"], d["domain"], d["project"]))
ON CONFLICT (id) DO UPDATE SET title='Test Task', domain_id=%s, project_id=%s,
description='Auto test task', priority=2, status='open', sort_order=0,
is_deleted=false, deleted_at=NULL, completed_at=NULL, updated_at=now()
""", (d["task"], d["domain"], d["project"], d["domain"], d["project"]))
# Contact
cur.execute("""
INSERT INTO contacts (id, first_name, last_name, company, email, is_deleted, created_at, updated_at)
VALUES (%s, 'Test', 'Contact', 'TestCorp', 'test@example.com', false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET first_name='Test', last_name='Contact', company='TestCorp',
email='test@example.com', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["contact"],))
# Note
cur.execute("""
INSERT INTO notes (id, title, domain_id, body, content_format, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Note', %s, 'Test body content', 'markdown', false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["note"], d["domain"]))
ON CONFLICT (id) DO UPDATE SET title='Test Note', domain_id=%s, body='Test body content',
content_format='markdown', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["note"], d["domain"], d["domain"]))
# Meeting
cur.execute("""
INSERT INTO meetings (id, title, meeting_date, status, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Meeting', '2025-06-15', 'scheduled', false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET title='Test Meeting', meeting_date='2025-06-15',
status='scheduled', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["meeting"],))
# Decision
cur.execute("""
INSERT INTO decisions (id, title, status, impact, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Decision', 'decided', 'high', false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET title='Test Decision', status='decided', impact='high',
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["decision"],))
# Appointment
cur.execute("""
INSERT INTO appointments (id, title, start_at, end_at, all_day, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Appointment', '2025-06-15 10:00:00', '2025-06-15 11:00:00', false, false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET title='Test Appointment', start_at='2025-06-15 10:00:00',
end_at='2025-06-15 11:00:00', all_day=false, is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["appointment"],))
# Weblink folder
# Link folder
cur.execute("""
INSERT INTO weblink_folders (id, name, is_deleted, created_at, updated_at)
INSERT INTO link_folders (id, name, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Folder', false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["weblink_folder"],))
ON CONFLICT (id) DO UPDATE SET name='Test Folder', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["link_folder"],))
# List
cur.execute("""
INSERT INTO lists (id, name, domain_id, project_id, list_type, is_deleted, created_at, updated_at)
VALUES (%s, 'Test List', %s, %s, 'checklist', false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["list"], d["domain"], d["project"]))
ON CONFLICT (id) DO UPDATE SET name='Test List', domain_id=%s, project_id=%s,
list_type='checklist', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["list"], d["domain"], d["project"], d["domain"], d["project"]))
# Link
cur.execute("""
INSERT INTO links (id, label, url, domain_id, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Link', 'https://example.com', %s, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["link"], d["domain"]))
ON CONFLICT (id) DO UPDATE SET label='Test Link', url='https://example.com', domain_id=%s,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["link"], d["domain"], d["domain"]))
# Weblink
# Link folder junction
cur.execute("""
INSERT INTO weblinks (id, label, url, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Weblink', 'https://example.com/wl', false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["weblink"],))
# Link weblink to folder via junction table
cur.execute("""
INSERT INTO folder_weblinks (folder_id, weblink_id)
INSERT INTO folder_links (folder_id, link_id)
VALUES (%s, %s) ON CONFLICT DO NOTHING
""", (d["weblink_folder"], d["weblink"]))
""", (d["link_folder"], d["link"]))
# Capture
cur.execute("""
INSERT INTO capture (id, raw_text, processed, is_deleted, created_at, updated_at)
VALUES (%s, 'Test capture item', false, false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET raw_text='Test capture item', processed=false,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["capture"],))
# Daily focus
# Daily focus (task-linked)
cur.execute("""
INSERT INTO daily_focus (id, task_id, focus_date, completed, created_at, updated_at)
VALUES (%s, %s, CURRENT_DATE, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["focus"], d["task"]))
ON CONFLICT (id) DO UPDATE SET task_id=%s, focus_date=CURRENT_DATE, completed=false,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["focus"], d["task"], d["task"]))
# Daily focus (standalone text item)
cur.execute("""
INSERT INTO daily_focus (id, focus_date, completed, title, domain_id, project_id, created_at, updated_at)
VALUES (%s, CURRENT_DATE, false, 'Test Standalone Focus', %s, %s, now(), now())
ON CONFLICT (id) DO UPDATE SET focus_date=CURRENT_DATE, completed=false,
title='Test Standalone Focus', domain_id=%s, project_id=%s,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["focus_standalone"], d["domain"], d["project"], d["domain"], d["project"]))
# Junction table seeds for contact tabs
cur.execute("""
INSERT INTO contact_tasks (contact_id, task_id, role)
VALUES (%s, %s, 'assignee') ON CONFLICT DO NOTHING
""", (d["contact"], d["task"]))
cur.execute("""
INSERT INTO contact_projects (contact_id, project_id, role)
VALUES (%s, %s, 'stakeholder') ON CONFLICT DO NOTHING
""", (d["contact"], d["project"]))
cur.execute("""
INSERT INTO contact_meetings (contact_id, meeting_id, role)
VALUES (%s, %s, 'attendee') ON CONFLICT DO NOTHING
""", (d["contact"], d["meeting"]))
cur.execute("""
INSERT INTO contact_lists (contact_id, list_id, role)
VALUES (%s, %s, 'contributor') ON CONFLICT DO NOTHING
""", (d["contact"], d["list"]))
# Process
cur.execute("""
INSERT INTO processes (id, name, process_type, status, category, is_deleted, created_at, updated_at)
VALUES (%s, 'Test Process', 'checklist', 'active', 'Testing', false, now(), now())
ON CONFLICT (id) DO NOTHING
ON CONFLICT (id) DO UPDATE SET name='Test Process', process_type='checklist', status='active',
category='Testing', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["process"],))
# Process step
cur.execute("""
INSERT INTO process_steps (id, process_id, title, instructions, sort_order, is_deleted, created_at, updated_at)
VALUES (%s, %s, 'Test Step', 'Do the thing', 0, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["process_step"], d["process"]))
ON CONFLICT (id) DO UPDATE SET process_id=%s, title='Test Step', instructions='Do the thing',
sort_order=0, is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["process_step"], d["process"], d["process"]))
# Process run
cur.execute("""
INSERT INTO process_runs (id, process_id, title, status, process_type, task_generation, is_deleted, created_at, updated_at)
VALUES (%s, %s, 'Test Run', 'not_started', 'checklist', 'all_at_once', false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["process_run"], d["process"]))
ON CONFLICT (id) DO UPDATE SET process_id=%s, title='Test Run', status='not_started',
process_type='checklist', task_generation='all_at_once', is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["process_run"], d["process"], d["process"]))
# Time budget
cur.execute("""
INSERT INTO time_budgets (id, domain_id, weekly_hours, effective_from, is_deleted, created_at, updated_at)
VALUES (%s, %s, 10, CURRENT_DATE, false, now(), now())
ON CONFLICT (id) DO NOTHING
""", (d["time_budget"], d["domain"]))
ON CONFLICT (id) DO UPDATE SET domain_id=%s, weekly_hours=10, effective_from=CURRENT_DATE,
is_deleted=false, deleted_at=NULL, updated_at=now()
""", (d["time_budget"], d["domain"], d["domain"]))
# File (create a dummy file on disk for download/serve tests)
import os
@@ -253,6 +292,11 @@ def all_seeds(sync_conn):
# Cleanup: delete all seed data (reverse dependency order)
try:
# Junction tables first
cur.execute("DELETE FROM contact_tasks WHERE task_id = %s", (d["task"],))
cur.execute("DELETE FROM contact_projects WHERE project_id = %s", (d["project"],))
cur.execute("DELETE FROM contact_meetings WHERE meeting_id = %s", (d["meeting"],))
cur.execute("DELETE FROM contact_lists WHERE list_id = %s", (d["list"],))
cur.execute("DELETE FROM files WHERE id = %s", (d["file"],))
if os.path.exists(dummy_file_path):
os.remove(dummy_file_path)
@@ -260,13 +304,13 @@ def all_seeds(sync_conn):
cur.execute("DELETE FROM process_runs WHERE id = %s", (d["process_run"],))
cur.execute("DELETE FROM process_steps WHERE id = %s", (d["process_step"],))
cur.execute("DELETE FROM processes WHERE id = %s", (d["process"],))
cur.execute("DELETE FROM daily_focus WHERE id = %s", (d["focus_standalone"],))
cur.execute("DELETE FROM daily_focus WHERE id = %s", (d["focus"],))
cur.execute("DELETE FROM capture WHERE id = %s", (d["capture"],))
cur.execute("DELETE FROM folder_weblinks WHERE weblink_id = %s", (d["weblink"],))
cur.execute("DELETE FROM weblinks WHERE id = %s", (d["weblink"],))
cur.execute("DELETE FROM folder_links WHERE link_id = %s", (d["link"],))
cur.execute("DELETE FROM links WHERE id = %s", (d["link"],))
cur.execute("DELETE FROM lists WHERE id = %s", (d["list"],))
cur.execute("DELETE FROM weblink_folders WHERE id = %s", (d["weblink_folder"],))
cur.execute("DELETE FROM link_folders WHERE id = %s", (d["link_folder"],))
cur.execute("DELETE FROM appointments WHERE id = %s", (d["appointment"],))
cur.execute("DELETE FROM decisions WHERE id = %s", (d["decision"],))
cur.execute("DELETE FROM meetings WHERE id = %s", (d["meeting"],))
@@ -336,3 +380,7 @@ def seed_list(all_seeds):
@pytest.fixture(scope="session")
def seed_appointment(all_seeds):
return {"id": all_seeds["appointment"], "title": "Test Appointment"}
@pytest.fixture(scope="session")
def seed_focus_standalone(all_seeds):
return {"id": all_seeds["focus_standalone"], "title": "Test Standalone Focus"}

View File

@@ -24,15 +24,18 @@ from tests.introspect import FormField
# FK fields map to seed fixture keys
FK_FIELD_MAP = {
"domain_id": "domain",
"quick_domain_id": "domain",
"area_id": "area",
"project_id": "project",
"task_id": "task",
"folder_id": "weblink_folder",
"parent_id": None, # Usually optional, skip
"meeting_id": None,
"meeting_id": "meeting",
"contact_id": "contact",
"release_id": None,
"note_id": "note",
"link_id": "link",
"decision_id": "decision",
"list_id": "list",
"process_id": "process",
"run_id": "process_run",
@@ -80,6 +83,11 @@ NAME_PATTERNS: list[tuple[str, Any]] = [
("notes", "Test notes field"),
("weekly_hours", "10"),
("effective_from", None), # Resolved dynamically as date
("item_ids", ""), # Comma-separated UUIDs for reorder
("item_id", ""), # Single item ID for reorder
("direction", "up"), # Reorder direction
("label", "Test Label Auto"), # Link label
("content", "Test content"), # List item content
]

File diff suppressed because it is too large Load Diff