ML-165: implementation

This commit is contained in:
Claudio Ortolina
2026-05-05 13:43:18 +01:00
parent 008dc20ff4
commit cccd28a9f9
10 changed files with 1084 additions and 86 deletions
@@ -1,9 +1,10 @@
---
id: doc-12
title: 'Research: Mute and Resolve Production Errors Implementation Routes'
title: "Research: Mute and Resolve Production Errors Implementation Routes"
type: specification
created_date: '2026-05-05 11:24'
created_date: "2026-05-05 11:24"
---
# Research: Mute and Resolve Production Errors Implementation Routes
**Task:** ML-165 — Mute and resolve production errors from pi
@@ -13,21 +14,21 @@ created_date: '2026-05-05 11:24'
### Backend (Elixir/Phoenix)
| Component | File | Status |
|---|---|---|
| Error schema | `deps/error_tracker/lib/error_tracker/schemas/error.ex` | Has `status` (:resolved/:unresolved) and `muted` (boolean) fields |
| Error context | `lib/music_library/errors.ex` | Read-only: `list_errors/1`, `get_error/1` — no update functions |
| Error controller | `lib/music_library_web/controllers/error_controller.ex` | `GET /api/v1/errors` (index), `GET /api/v1/errors/:id` (show) |
| Error JSON views | `lib/music_library_web/controllers/error_json.ex` | Renders error/occurrence data |
| Router | `lib/music_library_web/router.ex` | `/api/v1/errors` routes in API scope (Bearer token auth) |
| Auth | `lib/music_library_web/auth.ex` | `require_api_token/2` plug — Bearer token comparison |
| Component | File | Status |
| ---------------- | ------------------------------------------------------- | ----------------------------------------------------------------- |
| Error schema | `deps/error_tracker/lib/error_tracker/schemas/error.ex` | Has `status` (:resolved/:unresolved) and `muted` (boolean) fields |
| Error context | `lib/music_library/errors.ex` | Read-only: `list_errors/1`, `get_error/1` — no update functions |
| Error controller | `lib/music_library_web/controllers/error_controller.ex` | `GET /api/v1/errors` (index), `GET /api/v1/errors/:id` (show) |
| Error JSON views | `lib/music_library_web/controllers/error_json.ex` | Renders error/occurrence data |
| Router | `lib/music_library_web/router.ex` | `/api/v1/errors` routes in API scope (Bearer token auth) |
| Auth | `lib/music_library_web/auth.ex` | `require_api_token/2` plug — Bearer token comparison |
### Pi Extension (TypeScript)
| Component | File | Status |
|---|---|---|
| Component | File | Status |
| --------------------- | ------------------------------------- | ------------------------------------------------------------------------------------------------- |
| prod-errors extension | `.pi/extensions/prod-errors/index.ts` | Tools: `fetch_production_errors`, `fetch_production_error`; Command: `/prod-errors` (TUI browser) |
| TUI ErrorBrowser | Same file, `ErrorBrowser` class | List view (no mute/resolve actions), Detail view (no mute/resolve actions) |
| TUI ErrorBrowser | Same file, `ErrorBrowser` class | List view (no mute/resolve actions), Detail view (no mute/resolve actions) |
### Gap Analysis
@@ -48,12 +49,14 @@ POST /api/v1/errors/:id/resolve → sets status = :resolved
```
**Elixir changes:**
- `MusicLibrary.Errors`: Add `mute_error/1`, `resolve_error/1` (or a shared private helper)
- `MusicLibraryWeb.ErrorController`: Add `mute/2` and `resolve/2` actions
- `MusicLibraryWeb.ErrorJSON`: Add `mute/1`, `resolve/1` render functions
- `MusicLibraryWeb.Router`: Add two POST routes in the API scope
**Pi extension changes:**
- Register `mute_production_error` tool → POSTs to `/api/v1/errors/:id/mute`
- Register `resolve_production_error` tool → POSTs to `/api/v1/errors/:id/resolve`
- Add keybindings to `/prod-errors` TUI:
@@ -62,6 +65,7 @@ POST /api/v1/errors/:id/resolve → sets status = :resolved
- Or use single keys: `x` for mute, `d` for resolve (avoiding conflict with existing `m`/`r` filter toggles)
**Pros:**
- Simplest approach — each endpoint does exactly one thing
- RESTful resource/action pattern used elsewhere in the app (e.g., `/collection/latest`)
- Easy to extend with unmute/unresolve later as additional endpoints
@@ -69,6 +73,7 @@ POST /api/v1/errors/:id/resolve → sets status = :resolved
- Easy to test independently
**Cons:**
- Two new routes instead of one
- If many more error actions are added, route count could grow
@@ -81,11 +86,13 @@ PATCH /api/v1/errors/:id body: {"muted": true} or {"status": "resolved"}
```
**Pros:**
- Single route for all error mutations
- Follows REST convention for partial updates
- Easily extensible to other fields
**Cons:**
- Parameter validation is more complex (must reject unknown fields, validate combinations)
- Tool semantics are less clear — the pi tool would need to construct the PATCH body
- PATCH semantics imply partial update; if both fields are sent, behavior must be defined
@@ -99,12 +106,14 @@ POST /api/v1/errors/:id/actions body: {"action": "mute"} or {"action": "resolv
```
**Pros:**
- Single route for all actions
- Easy to add new action types
- Clean separation between action specification and execution
- Tool semantics map cleanly (tool name = action)
**Cons:**
- Less standard REST pattern
- Requires action validation/dispatch layer
- No existing precedent in the codebase
@@ -125,16 +134,16 @@ Route A is the best fit for this project because:
## Architecture Impact
| Component | Impact |
|---|---|
| `MusicLibrary.Errors` | Add `mute_error/1`, `resolve_error/1` context functions |
| `MusicLibraryWeb.ErrorController` | Add `mute/2`, `resolve/2` actions |
| `MusicLibraryWeb.ErrorJSON` | Add render functions for success/error responses |
| `MusicLibraryWeb.Router` | Add two POST routes |
| `.pi/extensions/prod-errors/index.ts` | Add two tools, add TUI keybindings |
| `test/music_library_web/controllers/error_controller_test.exs` | Add tests for new endpoints |
| `test/music_library/errors_test.exs` | Add tests for new context functions (if separate test file exists) |
| `docs/architecture.md` | Update Routes section if it lists API routes |
| Component | Impact |
| -------------------------------------------------------------- | ------------------------------------------------------------------ |
| `MusicLibrary.Errors` | Add `mute_error/1`, `resolve_error/1` context functions |
| `MusicLibraryWeb.ErrorController` | Add `mute/2`, `resolve/2` actions |
| `MusicLibraryWeb.ErrorJSON` | Add render functions for success/error responses |
| `MusicLibraryWeb.Router` | Add two POST routes |
| `.pi/extensions/prod-errors/index.ts` | Add two tools, add TUI keybindings |
| `test/music_library_web/controllers/error_controller_test.exs` | Add tests for new endpoints |
| `test/music_library/errors_test.exs` | Add tests for new context functions (if separate test file exists) |
| `docs/architecture.md` | Update Routes section if it lists API routes |
No changes needed to: supervision tree, PubSub, schemas, migrations, Oban workers, LiveViews, external APIs.
@@ -156,10 +165,10 @@ No production infrastructure changes needed. The new endpoints are served by the
## Documentation Updates
| File | Change |
|---|---|
| `docs/architecture.md` | Update Routes section if API routes are enumerated there |
| README (if applicable) | N/A — API is internal tooling |
| File | Change |
| ------------------------------------- | -------------------------------------------------------------- |
| `docs/architecture.md` | Update Routes section if API routes are enumerated there |
| README (if applicable) | N/A — API is internal tooling |
| `.pi/extensions/prod-errors/index.ts` | Self-documenting through tool descriptions and prompt snippets |
## Testing