Migration: backfill CaseMembership for existing cases #69

Closed
opened 2026-05-23 01:35:52 +00:00 by Mark · 3 comments
Owner

Parent Issue: #36 (Case-level access control) / #53

Scope

Data migration to backfill CaseMembership rows for existing cases, plus a one-time admin "claim unowned cases" flow.

Background

  • Existing cases in the database have no CaseMembership rows
  • created_by field on Case model is never populated
  • Without backfill, all existing cases become inaccessible to non-admin users once access control is enforced

Acceptance Criteria

  • Alembic migration that:
    1. Sets created_by on existing cases where possible (e.g., from audit log CREATE events)
    2. Creates CaseMembership(owner) rows for each existing case, assigned to the creator (or first admin if creator unknown)
    3. For cases with no creator info, assigns to the first admin user
  • Migration is idempotent (safe to run multiple times)
  • Migration handles edge cases: no users exist, no cases exist, no admin users exist
  • Test for the migration

Dependencies

  • #64 (membership management must be implemented first for the model to exist)

Implementation Notes

  • Check AuditEvent table for CREATE Case events to determine original creator
  • If no audit trail, fall back to assigning to the user with role=admin who has the lowest id
  • Log any cases that couldn't be auto-assigned so admins can review
## Parent Issue: #36 (Case-level access control) / #53 ## Scope Data migration to backfill `CaseMembership` rows for existing cases, plus a one-time admin "claim unowned cases" flow. ## Background - Existing cases in the database have no `CaseMembership` rows - `created_by` field on Case model is never populated - Without backfill, all existing cases become inaccessible to non-admin users once access control is enforced ## Acceptance Criteria - [ ] Alembic migration that: 1. Sets `created_by` on existing cases where possible (e.g., from audit log `CREATE` events) 2. Creates `CaseMembership(owner)` rows for each existing case, assigned to the creator (or first admin if creator unknown) 3. For cases with no creator info, assigns to the first admin user - [ ] Migration is idempotent (safe to run multiple times) - [ ] Migration handles edge cases: no users exist, no cases exist, no admin users exist - [ ] Test for the migration ## Dependencies - #64 (membership management must be implemented first for the model to exist) ## Implementation Notes - Check `AuditEvent` table for `CREATE Case` events to determine original creator - If no audit trail, fall back to assigning to the user with `role=admin` who has the lowest `id` - Log any cases that couldn't be auto-assigned so admins can review
Author
Owner

Quickfix overseer report

After 2 attempts, the quickfix could not proceed due to infrastructure issues:

  • nvidia/glm-5.1: API key expired (403 Authorization failed)
  • openadapter: API key invalid (403)
  • opencode/zen: API key expired (401)
  • openrouter: API key expired (401)
  • ollama: Service not running locally

All cloud provider API keys in the opencode config are expired/invalid. Retrying would produce the same result.

Action taken:

  • Killed stuck opencode process (was waiting indefinitely on broken API call)
  • Removed quickfix label → promoted to normal pipeline
  • Issue remains triage-approved

To resolve: Update one or more API keys in /home/b/.config/opencode/opencode.json or start the local Ollama service, then re-apply quickfix label.

**Quickfix overseer report** After 2 attempts, the quickfix could not proceed due to infrastructure issues: - **nvidia/glm-5.1**: API key expired (403 Authorization failed) - **openadapter**: API key invalid (403) - **opencode/zen**: API key expired (401) - **openrouter**: API key expired (401) - **ollama**: Service not running locally All cloud provider API keys in the opencode config are expired/invalid. Retrying would produce the same result. **Action taken:** - Killed stuck opencode process (was waiting indefinitely on broken API call) - Removed `quickfix` label → promoted to normal pipeline - Issue remains `triage-approved` **To resolve:** Update one or more API keys in `/home/b/.config/opencode/opencode.json` or start the local Ollama service, then re-apply `quickfix` label.
Author
Owner

GSD VERIFY phase failed after 3 attempts.
═══ Gate: verify-passed (osint-hub#69) ═══
Mode: Tier 1 (functional only)

GATE OK: All gates up to 'implement' pass
── Tier 1: Functional ────────────────────────────────
Running tests...
❌ Tests failed (exit 4)
configfile: pyproject.toml
plugins: anyio-4.13.0, httpx-0.36.2, timeout-2.4.0, xdist-3.8.0, cov-7.1.0, split-0.11.0, asyncio-1.4.0
timeout: 60.0s
timeout method: signal
timeout func_only: False
asyncio: mode=Mode.STRICT, debug=False, asyncio_default_fixture_loop_scope=None, asyncio_default_test_loop_scope=function
collected 0 items

============================ no tests ran in 0.00s =============================
ERROR: file or directory not found: tests/

============================= test session starts ==============================
platform linux -- Python 3.11.14, pytest-9.0.3, pluggy-1.6.0
rootdir: /home/b/Projects/osint-hub
configfile: pyproject.toml
plugins: anyio-4.13.0, httpx-0.36.2, timeout-2.4.0, xdist-3.8.0, cov-7.1.0, split-0.11.0, asyncio-1.4.0
asyncio: mode=Mode.STRICT, debug=False, asyncio_default_fixture_loop_scope=None, asyncio_default_test_loop_scope=function
collected 0 items

============================ no tests ran in 0.00s =============================
Running linter...
✅ Lint clean
Running type checker...
✅ Types check clean
Previous test count: unknown

❌ GATE FAIL: verify-passed
- Tests failed with exit code 4
GATE FAIL: verify — blocked at 2026-05-26T22:38:18Z
Class: test-failure
Evidence: Verification failed: 1 failures
Git tag: osint-hub#69-gate-verify-fail-85facb8335be (use gate-retry after fixing)

GSD VERIFY phase failed after 3 attempts. ═══ Gate: verify-passed (osint-hub#69) ═══ Mode: Tier 1 (functional only) GATE OK: All gates up to 'implement' pass ── Tier 1: Functional ──────────────────────────────── Running tests... ❌ Tests failed (exit 4) configfile: pyproject.toml plugins: anyio-4.13.0, httpx-0.36.2, timeout-2.4.0, xdist-3.8.0, cov-7.1.0, split-0.11.0, asyncio-1.4.0 timeout: 60.0s timeout method: signal timeout func_only: False asyncio: mode=Mode.STRICT, debug=False, asyncio_default_fixture_loop_scope=None, asyncio_default_test_loop_scope=function collected 0 items ============================ no tests ran in 0.00s ============================= ERROR: file or directory not found: tests/ ============================= test session starts ============================== platform linux -- Python 3.11.14, pytest-9.0.3, pluggy-1.6.0 rootdir: /home/b/Projects/osint-hub configfile: pyproject.toml plugins: anyio-4.13.0, httpx-0.36.2, timeout-2.4.0, xdist-3.8.0, cov-7.1.0, split-0.11.0, asyncio-1.4.0 asyncio: mode=Mode.STRICT, debug=False, asyncio_default_fixture_loop_scope=None, asyncio_default_test_loop_scope=function collected 0 items ============================ no tests ran in 0.00s ============================= Running linter... ✅ Lint clean Running type checker... ✅ Types check clean Previous test count: unknown ❌ GATE FAIL: verify-passed - Tests failed with exit code 4 GATE FAIL: verify — blocked at 2026-05-26T22:38:18Z Class: test-failure Evidence: Verification failed: 1 failures Git tag: osint-hub#69-gate-verify-fail-85facb8335be (use gate-retry after fixing)
Author
Owner

GSD PLAN: response missing GATE: line.

GSD PLAN: response missing GATE: line.
Mark closed this issue 2026-06-08 17:55:20 +00:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
Mark/osint-hub#69
No description provided.