Dashboard issue actions + pooled project store#8
Merged
Conversation
POST /issues/{id}/close moves a done issue to the Closed column (a plain
setIssueStatus; the board's polling SSE feed carries the change).
POST /issues/{id}/stop cancels an in-flight run: the run coroutine handle is
now kept in $active (was a bare bool), so stop() can cancel() it and drop the
issue back to Open. 409 when no run is active.
Also: add the run-app skill documenting how to launch the server + UI, and
ignore local .claude settings.
artifactRecords now walks the run tracking open step spans, so every artifact record carries the innermost step name — the dashboard shows which step emitted which artifact.
POST /issues/{id}/delete cancels any in-flight run, then marks the issue
Deleted (a new IssueStatus case) — the row, its runs and trace stay in the db
but allIssues() hides Deleted, so the board no longer shows it.
issuesStream now emits an 'issue-removed' event for an id that vanished from the
snapshot set, so clients drop a deleted (or otherwise gone) card live instead of
keeping it until reconnect.
…te handle split The Server hand-rolled connection lifecycle — a cached read handle plus a fresh storeFor() per run — to keep a run's writes off the shared connection. That put a database concern in the HTTP layer and leaked it as two ways to get a store, one of which createIssue picked wrong. TrueAsync's PDO pool already provides exactly this: it hands each coroutine its own connection and keeps it pinned across awaits, so one shared handle is safe for concurrent reads and writes and INSERT + lastInsertId() stays correct. - ProjectStore::open() enables the pool (ATTR_POOL_*) + WAL; busy timeout moves to ATTR_TIMEOUT so it applies to every pooled connection, not just the first - collapse Server readStore()/storeFor()/$readStores into one cached store() - extract ProjectStoreInterface; runner and frontends depend on it, not the concrete store - createIssue: 404 for an unknown project (was an uncaught 500); status read from the issue - move a docblock that had drifted onto stop() back onto answer(); drop a stray blank line - tests: concurrent-coroutine pool safety; Artifact content-type sniffing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Dashboard issue-management endpoints, richer trace/artifact metadata, and a storage refactor that retires the hand-rolled connection handling.
Endpoints
issue-removedso clients drop the cardartifact-fileread, path-confined to the project folderTrace / artifacts
Storage refactor
ProjectStore::open()enables TrueAsync's PDO connection pool + WAL; busy timeout viaATTR_TIMEOUTso it covers every pooled connectionServer::readStore()/storeFor()into one cachedstore()— the pool gives each coroutine its own connection, so a run's writes and the dashboard's reads share one handle safelyProjectStoreInterface; the runner and frontends depend on itcreateIssue: 404 for an unknown project (was an uncaught 500)Tests
QA: php-cs-fixer, PHPStan level 8, full suite (212 tests) all green.