Skip to content

Chat action-dispatch: portfolio queue release/requeue #6520

Description

@JSONbored

Context

apps/loopover-miner-ui/src/routes/portfolio.tsx's "Queue actions" section (lines ~97-162) already
lets an operator release or requeue a portfolio-queue item from a table of buttons. Those buttons call
apps/loopover-miner-ui/src/lib/portfolio-queue-actions.ts, which POSTs to the existing
/api/portfolio-queue/release and /api/portfolio-queue/requeue endpoints. This is a real, shipped,
working write path against miner_portfolio_queue — nothing about the endpoints or their request/response
shape is changing.

The miner-chat design synthesis decided v1 chat is action-capable for three narrow action families —
discover/attempt, portfolio release/requeue, and governor pause/resume — but only by calling the
exact same endpoints the existing buttons already call, routed through a shared, chokepoint-routed
dispatch layer built by the chat action-dispatch scaffolding issue. That layer is what actually talks to
the Governor chokepoint / PreToolUse deny-hook path (packages/loopover-engine/src/governor/chokepoint.ts,
packages/loopover-miner/lib/governor-chokepoint.js, packages/loopover-miner/lib/pretooluse-hook.js) that
every other local AMS write already goes through — this issue does not implement or modify that routing
itself, it registers into it.

This issue is the portfolio-queue slice of that work: make the chat tool-calling surface resolve a
release/requeue request out of a chat message, dispatch it through the scaffolding issue's shared layer
(which in turn calls lib/portfolio-queue-actions.ts, unchanged), and render the outcome as a message in
the chat message list built by the chat message-list issue. The safety case (why a locally-autonomous
miner chat can be action-capable in v1 at all, not read-only) was already decided by the synthesis and is
not open here — this issue is pure wiring against an already-resolved design.

⚠️ Read this before starting. This issue does not add a new API endpoint, a new fetch/HTTP call, or
a new request-building module for portfolio-queue writes. The one and only write path is
apps/loopover-miner-ui/src/lib/portfolio-queue-actions.ts calling POST /api/portfolio-queue/release
and POST /api/portfolio-queue/requeue — the exact same calls routes/portfolio.tsx's existing buttons
already make. Your job is to get the chat surface to invoke that same module through the chat
action-dispatch scaffolding issue's dispatch layer, not to build a second way to reach those endpoints.
A PR that adds a parallel fetch call, a new API route, a duplicated request helper under a chat-specific
path, or any other second write path — even one that happens to hit the same two URLs — does not
resolve this issue and will be closed.

Requirements

  • The only two callable actions this issue adds are release and requeue, and each MUST call
    apps/loopover-miner-ui/src/lib/portfolio-queue-actions.ts's existing release/requeue functions
    unmodified — no new fetch/POST logic, no new file that re-implements the same request.
  • Every chat-triggered release/requeue call MUST be dispatched through the shared dispatch layer built by
    the chat action-dispatch scaffolding issue (the chokepoint-routed layer). Calling the endpoint or
    lib/portfolio-queue-actions.ts directly from new chat-only code, bypassing that layer, does not satisfy
    this issue even if it produces an identical HTTP call.
  • Do not add a new API route, a new server/worker handler, or any variant of /api/portfolio-queue/*
    beyond the two that already exist (release, requeue).
  • Do not duplicate lib/portfolio-queue-actions.ts's request logic in a new file under a chat-specific
    directory (e.g. no lib/chat-portfolio-actions.ts reimplementing the same POST) — import and call the
    existing module's exports directly.
  • Chat text must resolve to one of the two known actions plus a validated target (the repo/identifier the
    action applies to) before the dispatch layer is called. A malformed or ambiguous instruction (no
    resolvable target, or an action word that isn't release/requeue) must produce a "couldn't determine…"
    message in the chat log and must never fall through to a best-guess dispatch call.
  • The result of a dispatched call — success payload or error — renders as an entry inline in the chat
    message list component built by the chat message-list issue. Not a toast, not a separate panel, not
    console-only output.
  • Action-dispatch as a whole stays behind the config flag introduced by the chat action-dispatch
    scaffolding issue, default off. This issue must not flip that default and must not introduce a second,
    portfolio-queue-specific flag.
  • No new or duplicated miner_portfolio_queue write path, migration, or schema change of any kind — this
    issue is presentation/dispatch-registration only, the data layer (packages/loopover-miner/lib/portfolio-queue.js)
    is untouched.

Deliverables

  • Register release and requeue as callable actions in the chat action-dispatch scaffolding's
    dispatch layer, each thin-wrapping apps/loopover-miner-ui/src/lib/portfolio-queue-actions.ts's
    existing functions.
  • Chat-message-to-action resolution for the two portfolio-queue actions (parsing an action word and a
    target repo/identifier out of the user's chat text), with an explicit unresolvable/ambiguous-request
    path that never reaches the dispatch layer.
  • A message-list entry (new entry type, or reuse of a generic "action result" entry type if the chat
    message-list issue already ships one) that renders the dispatched call's success/error result inline,
    including which repo/identifier was acted on.
  • Tests covering: successful release dispatch, successful requeue dispatch, an endpoint error surfaced
    verbatim in the message list, and an unresolvable/ambiguous chat instruction that is rejected before
    the dispatch layer is invoked.

Test Coverage Requirements

All of this issue's changes land under apps/loopover-miner-ui/src/**, which is outside Codecov's
coverage.include
— only src/** (the ORB Worker app) is measured for the 99% patch-coverage gate per
this repo's contributing skill. Codecov will not block or numerically measure this PR. That does not lower
the bar: write full unit tests for the action-registration, chat-text-to-action resolution, and
message-list-render logic (including both the resolved and unresolvable/ambiguous branches, and both the
success and error-response branches of each dispatched call), and run the local npm run test:ci gate
(which does execute apps/** tests, just not under Codecov) before opening the PR. Untested logic here is
a real regression risk even though no automated coverage percentage enforces it.

Expected Outcome

A user typing something like "release the queued item for org/repo" or "requeue org/repo" in the miner
chat rail resolves to a real release/requeue dispatch call, routed through the shared chokepoint-routed
dispatch layer, hitting the exact same /api/portfolio-queue/{release,requeue} endpoints
routes/portfolio.tsx's existing buttons already call — and the chat message list shows an inline
confirmation or error for that call. There is exactly one write path into miner_portfolio_queue from the
UI layer (buttons and chat both funnel through lib/portfolio-queue-actions.ts), not two.

Links & Resources

  • apps/loopover-miner-ui/src/lib/portfolio-queue-actions.ts — the endpoint-calling module this issue must
    reuse as-is.
  • apps/loopover-miner-ui/src/routes/portfolio.tsx (lines ~97-162) — the existing "Queue actions"
    release/requeue table and button wiring; the behavioral reference for what chat must reproduce through
    the dispatch layer.
  • packages/loopover-engine/src/governor/chokepoint.ts, packages/loopover-miner/lib/governor-chokepoint.js,
    packages/loopover-miner/lib/pretooluse-hook.js — the fail-closed local-write safety path the shared
    dispatch layer routes through; background only, this issue does not modify these files.
  • The chat action-dispatch scaffolding issue — supplies the shared, chokepoint-routed dispatch layer this
    issue's actions register into. Blocked-by.
  • The chat message-list issue — supplies the message-list surface this issue renders confirmations into.
    Blocked-by.
  • The discover/attempt action-dispatch issue and the governor pause/resume action-dispatch issue — sibling
    action-family issues under the same scaffolding; useful for keeping action-registration conventions
    consistent, not a hard dependency.
  • Issue Spec: conversational chat interface for loopover (Lovable/Cursor-style) #6230 (the separate maintainer-chat scope) is explicitly unrelated to this issue — do not touch
    anything under its surface.

Metadata

Metadata

Assignees

No one assigned

    Labels

    gittensor:featureGittensor-scored feature linked to a feature issue — scores a 0.25x multiplier.help wantedExtra attention is needed

    Projects

    Status
    Done

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions