Review: Admin panel: lead/client management UI

review-1187-2026-05-09 Review

review needs-refinement

Verdict: NEEDS_REFINEMENT

Template Completeness

  • [x] Type -- Feature
  • [x] Lineage -- Standalone
  • [x] Repo -- ldraney/pal-enterprises
  • [x] User Story -- present and well-formed
  • [x] Context -- present, references convention-client-project-structure
  • [x] File Targets -- present but inaccurate (see below)
  • [x] Acceptance Criteria -- present, 6 criteria
  • [x] Test Expectations -- present
  • [x] Constraints -- present but contains conflicting guidance
  • [x] Checklist -- present
  • [x] Related -- present

Traceability

  • [x] story:sso-gateway label -- present on board item
  • [ ] story note MISSING -- [SCOPE] No project-pal-enterprises project page exists in pal-e-docs. Create project page with user-stories section containing sso-gateway story entry.
  • [x] arch:rails-app label -- present on board item
  • [ ] arch note MISSING -- [SCOPE] No arch-rails-app architecture note exists in pal-e-docs. Create architecture note arch-rails-app.
  • [x] Forgejo issue -- ldraney/pal-enterprises#9, state: open
  • [ ] convention-client-project-structure MISSING -- [SCOPE] Issue lineage references this convention but it does not exist in pal-e-docs. Create convention note or update lineage.

File Targets

  • [ ] app/controllers/admin_controller.rb -- ISSUE: File does NOT exist. Issue claims it "already exists in the scaffold" but the controllers directory only contains: application_controller.rb, concerns/, contacts_controller.rb, dashboard_controller.rb, pages_controller.rb, sessions_controller.rb. Should say "create" not "modify."
  • [ ] app/views/admin/ -- ISSUE: Directory does NOT exist. Only these view dirs exist: contacts, dashboard, layouts, pages, pwa, sessions. Should say "create" not "modify."
  • [x] config/routes.rb -- verified: exists, currently has no admin routes. Modification is correct.
  • [x] app/controllers/dashboard_controller.rb -- verified: exists, correctly listed under "do not touch."

Repo Placement

OK. Issue is filed on ldraney/pal-enterprises and the work targets that repo. However, the "promote lead to client" AC requires Keycloak admin API calls, which may involve configuration in pal-e-deployments (Keycloak realm config). This cross-repo dependency is not documented.

Dependencies

  • Database schema gap (undocumented) -- The Lead model currently has only: name, email, message, timestamps. There is no status field (for pipeline tracking: new/pending/promoted), no business_name field, no logo field. The AC references "business name, name, logo, email" but the model lacks business_name and logo columns. A migration is required.
  • No Client model (undocumented) -- The AC says "view all active clients with status" but there is no Client model. Either Lead needs a status enum for promotion, or a separate Client model/table is needed. This architectural decision is not scoped.
  • No role-checking infrastructure (undocumented) -- ApplicationController has require_login but no require_owner or role-checking method. The session stores roles from Keycloak but nothing consumes them. A require_owner before_action needs to be built.
  • Keycloak admin API integration (undocumented) -- AC: "lead promotion creates Keycloak user." No Keycloak admin API client exists in the codebase. This requires: Keycloak admin credentials (env vars), an HTTP client for the admin REST API, and realm-level user creation logic. This is a significant new capability.
  • Board item #1188 (Remove Tailwind) -- in backlog. Not a blocker, but Constraints section says "Follow existing Rails patterns (Hotwire/Turbo, Tailwind)" which will conflict if #1188 lands first.
  • Board item #1181 (Phase 4: Dashboard with tool grid) -- in backlog. The admin panel is separate from the dashboard, but both need auth. No conflict, but should be sequenced.

Acceptance Criteria

6 acceptance criteria. Testability assessment:
  • "/admin shows leads pipeline" -- testable via integration test, but what does "pipeline" mean? Need to define states (new/pending review/promoted).
  • "Owner can view lead details (business name, name, logo, email)" -- Lead model lacks business_name and logo fields. Not implementable without migration.
  • "Owner can promote a lead to client (triggers Keycloak user creation)" -- requires Keycloak admin API integration that does not exist. Not implementable without new infrastructure.
  • "Owner can view all active clients with status" -- No Client model exists. Not implementable without model creation.
  • "Only owner role can access /admin -- clients get 403" -- testable but requires new role-checking method.
  • "Per-client links to their -docs and -admin surfaces visible" -- requires knowing the URL pattern for client surfaces. How does the system know a client's surface URLs? Undocumented.

Blast Radius

Low blast radius to existing code -- this is additive (new controller, new views, new routes). However:
  • The Lead model is shared with ContactsController. Adding status/fields to Lead affects the contact form flow.
  • ApplicationController changes (adding require_owner) are cross-cutting and will be used by other controllers later.
  • Keycloak admin API credentials will need to be added to deployment configs (pal-e-deployments).

Decomposition Assessment

NEEDS DECOMPOSITION -- This ticket violates the 5-minute rule on multiple counts:
  • 6 acceptance criteria (threshold: 5)
  • Requires new database migration (Lead fields + possibly Client model)
  • Requires new infrastructure (Keycloak admin API client)
  • Requires new auth infrastructure (role-checking)
  • Estimated agent work: 15-20 minutes across 4 distinct concerns
Suggested decomposition:
  • Sub-ticket 1: Lead model expansion + admin scaffold -- Add status/business_name/logo fields to Lead, create AdminController with require_owner, add /admin route, basic lead list view.
  • Sub-ticket 2: Role-based access control -- Add require_owner to ApplicationController, owner role check against Keycloak roles in session, 403 for non-owners.
  • Sub-ticket 3: Lead detail views + pipeline UI -- Lead show/edit views, pipeline state management (new/pending/promoted).
  • Sub-ticket 4: Keycloak user creation on promote -- Keycloak admin API client, promote action that creates realm user, Client model or status update.

Recommendation

  • [BODY] Fix file targets: admin_controller.rb and app/views/admin/ do not exist -- change "modify" to "create."
  • [BODY] Add missing Lead fields to File Targets: migration needed for business_name, logo, status columns on leads table.
  • [BODY] Document Keycloak admin API dependency: add to Context and Constraints that a new Keycloak admin HTTP client is required, plus KEYCLOAK_ADMIN_USER/KEYCLOAK_ADMIN_PASSWORD env vars.
  • [BODY] Remove or qualify Tailwind constraint: board item #1188 plans to remove Tailwind. Change constraint to "Follow existing Rails patterns (Hotwire/Turbo)" or note Tailwind may be replaced.
  • [BODY] Define "per-client links" data source: how does the system know a client's -docs and -admin URLs? This needs to be specified (convention-based from business name? stored in Client model?).
  • [SCOPE] Create project-pal-enterprises project page in pal-e-docs with user-stories section.
  • [SCOPE] Create arch-rails-app architecture note in pal-e-docs.
  • [SCOPE] Create or verify convention-client-project-structure in pal-e-docs (referenced in issue lineage but does not exist).
  • [DECOMPOSE] 6 AC across 4 concerns (model, auth, views, Keycloak API). Route to skill-decompose-ticket for sub-board creation.