# Phase 22: Approval UI (LiveLink) - Discussion Log

> **Audit trail only.** Do not use as input to planning, research, or execution agents.
> Decisions are captured in CONTEXT.md — this log preserves the alternatives considered.

**Date:** 2026-07-16
**Phase:** 22-approval-ui-livelink-addressable-campaign-review-and-approve
**Areas discussed:** Page chrome & feel, Approve/remediate action UX, Not-yet-triaged empty state, URL evidence rendering safety

---

## Page chrome & feel

| Option | Description | Selected |
|--------|-------------|----------|
| Full Pulse shell | Top nav, PageHeader, standard container padding — same chrome as /admin, /analyzer | ✓ |
| Standalone/focused (no top nav) | Distraction-free landing page, like /kiosk, /mobile | |

**User's choice:** Full Pulse shell.

| Option | Description | Selected |
|--------|-------------|----------|
| LiveLink only for now | No new nav link anywhere in Pulse | |
| Also worth a nav entry | Add a lightweight link/section for staff to find recent campaigns | ✓ |

**User's choice:** Also worth a nav entry.
**Notes:** This required a scope-boundary check — a nav entry needs a target page, and REVIEW-01..06 only scope the ticket-ID page.

| Option | Description | Selected |
|--------|-------------|----------|
| Defer the list page (recommended) | Phase 22 stays scoped to ticket-ID page only; note campaigns-list+nav as a deferred idea | |
| Add a minimal list page now | Expands Phase 22 scope to include a simple /phishing list page + nav link | ✓ |

**User's choice:** Add a minimal list page now — explicit scope expansion, confirmed after the tradeoff was surfaced.
**Notes:** Captured as D-00 in CONTEXT.md with an explicit note to planner that this is additive scope, not part of REVIEW-01..06.

---

## Approve/remediate action UX

| Option | Description | Selected |
|--------|-------------|----------|
| Checkbox list + param editor | Each recommended action as a checkbox, editable default params, one "Approve selected" button | ✓ |
| One-click buttons, no override | Each action gets its own "Approve" button using classifier defaults, no override UI | |

**User's choice:** Checkbox list + param editor.

| Option | Description | Selected |
|--------|-------------|----------|
| Refetch the campaign data | Re-call the campaign detail endpoint after a successful action | ✓ |
| Optimistic local update | Update local state immediately without a round-trip | |

**User's choice:** Refetch the campaign data.

| Option | Description | Selected |
|--------|-------------|----------|
| Disappear, replaced by status | Buttons gone once resolved, replaced by a status line | |
| Stay visible but disabled | Buttons remain, greyed out with a tooltip explaining why | ✓ |

**User's choice:** Stay visible but disabled.

---

## Not-yet-triaged empty state

| Option | Description | Selected |
|--------|-------------|----------|
| Friendly empty state + manual trigger | Explains "not yet triaged", offers a button to call the existing on-demand analyze endpoint | ✓ |
| Plain 404 / not found | Simplest — ticket has no report, page says not found | |

**User's choice:** Friendly empty state + manual trigger.

| Option | Description | Selected |
|--------|-------------|----------|
| Show the report standalone | Render the report's own evidence with a note that grouping/classification hasn't completed | ✓ |
| Treat same as not-yet-triaged | Show the same empty/pending state, one code path | |

**User's choice:** Show the report standalone.

---

## URL evidence rendering safety

| Option | Description | Selected |
|--------|-------------|----------|
| Inert copy-only text | Plain monospace text with copy-to-clipboard, never an `<a href>` | ✓ |
| Clickable but sanitized | Real link with query strings/fragments stripped | |

**User's choice:** Inert copy-only text.

| Option | Description | Selected |
|--------|-------------|----------|
| Plain evidence display | Filename/type/size/hash shown as-is | ✓ |
| Filename hidden, hash-only | Only show type/size/hash, hide filename as extra caution | |

**User's choice:** Plain evidence display.

---

## Claude's Discretion

- Exact nav placement for the new list page's entry (top-level vs. nested under an existing menu)
- Whether the campaign-detail data comes from extending the existing `GET /api/phishing/campaigns/[id]` in place, or a new page-specific endpoint
- Whether a new ticket→campaign resolution route is a dedicated endpoint or resolved another way (must still go through the API-route pattern)
- Blast-radius freshness — fresh `getBlastRadius()` call per page view vs. reading what the classification already persisted
- Exact timeline merge/sort implementation and visual treatment (vertical timeline vs. simple ordered list)
- Exact columns/layout of the minimal campaigns list page

## Deferred Ideas

- Campaigns list page filtering/sorting beyond a minimal "recent" view
- Real remediation provider wiring (unchanged from Phase 20 — REMEDEXEC-01..05, v2)
- False-positive reversibility (unchanged from Phase 20's deferred item)
