Open Issue by ID (Cmd+K I): open any issue in the browser#1123
Conversation
Architect Integration ReviewVerified the implementation independently against PR head; clean. Command + keybinding
Behaviour & deviations from the issue bodyTwo deviations from the original issue body, both dev-gate-approved per the commit log; both defensible:
Forge-side changes
Mergeability + CI
RecommendationAPPROVE for the pr gate. Implementation is clean, test coverage is comprehensive, the two deviations are defensible improvements over the original issue body. Architect integration review |
PIR Review:
codev.openIssueById+Cmd+K I(open any issue in the browser)Fixes #1096
Summary
Adds
codev.openIssueById("Codev: Open Issue by ID...", bound toCmd+K I/Ctrl+K I): prompt for an issue id, fetch it live via the forge contract, andopen its page in the browser. This is the deliberate counterpart to the
backlog / "View Issue" family (which preview in-editor) — direct,
keyboard-driven access to any issue by id, including closed/archived ones and
ids already claimed by a builder (which the backlog filters out). To support it,
the
issue-viewforge concept now carries the issue's browserurl. Also foldsin a small palette-clarity fix: the webview-panel command was retitled "Codev:
Open Backlog Search Panel" to stop colliding with the "Codev: Search Backlog..."
Quick Pick.
Naming note: the issue proposed
openIssueByNumber; the shipped command isopenIssueById("ID") per architect direction — "ID" is forge-neutral (GitLabiid, Linear/Jira identifiers aren't bare numbers) and matches the extension'sexisting
issueIdvocabulary. The porch slug / plan filename keep…openissuebynumber(porch-managed, derived from the issue title).Files Changed
packages/vscode/src/commands/open-issue-by-id.ts(+81 / -0) — new:parseIssueId+openIssueByIdpackages/vscode/src/__tests__/open-issue-by-id.test.ts(+125 / -0) — new: parser + handler-routing testspackages/vscode/src/extension.ts(+2) — import + command registrationpackages/vscode/package.json(+11 / -1) — command, keybinding, panel title renamepackages/types/src/api.ts(+9) — optionalIssueView.urlpackages/codev/src/lib/forge-contracts.ts(+8) — optionalIssueViewResult.urlpackages/codev/scripts/forge/github/issue-view.sh(+2 / -2) — emiturlpackages/codev/scripts/forge/gitlab/issue-view.sh(+4 / -1) — mapweb_url→urlpackages/codev/scripts/forge/gitea/issue-view.sh(+4 / -1) — maphtml_url→urlpackages/codev/scripts/forge/linear/issue-view.sh(+4 / -2) — addurlto query + mapcodev/resources/lessons-learned.md(+1) — COLD lesson on per-forge field divergencecodev/plans/1096-vscode-codev-openissuebynumber.md— plan (with mid-flight revisions)codev/state/pir-1096_thread.md— builder threadCommits
2a423a6e[PIR vscode: codev.openIssueByNumber quick-action + Cmd+K I keybinding for direct issue access #1096] Add codev.openIssueById command + Cmd+K I, disambiguate panel titlea0b76d1e[PIR vscode: codev.openIssueByNumber quick-action + Cmd+K I keybinding for direct issue access #1096] Open Issue by ID opens in browser; thread url through issue-view fetch184ec314[PIR vscode: codev.openIssueByNumber quick-action + Cmd+K I keybinding for direct issue access #1096] Clarify url contract doc: browser URL + per-forge source field73421def[PIR vscode: codev.openIssueByNumber quick-action + Cmd+K I keybinding for direct issue access #1096] Emit issue url from gitlab/gitea/linear issue-view scripts too(Plan-draft and porch-transition commits omitted.)
Test Results
npm run build: ✓ passnpm test: ✓ pass — vscode unit suite 530/530 (14 new inopen-issue-by-id.test.ts); codev package suite green via porch'stestscheckdev-approvalgate. Note the GitHub browser-open path requires the running Tower to serve the updatedissue-viewscript (rebuild + restart Tower), since the live/api/issuewas confirmed returningurl: nullon the stale global build during testing.Architecture Updates
No
arch.md/arch-critical.mdchange. The one non-obvious fact — that theurlcarried byissue-viewmaps to a different field per forge (GitHuburl,GitLab
web_url, Giteahtml_url, Linearurl) — is documented inline at thecontract (
IssueView/IssueViewResultdoc-comments), which is where afuture forge-script author will look, rather than in the architecture reference.
No module boundaries, invariants, or system shape changed.
Lessons Learned Updates
Added one COLD entry to
lessons-learned.md(Architecture),[From #1096]: alogical field crossing the forge-concept boundary maps to a different provider
field per forge, some are footguns (Gitea
url= API endpoint, not the browserpage), so verify each against its own API docs and keep the contract field
optional so non-emitting forges degrade rather than break — plus the honest-verification
corollary (validate untestable forge transforms against sample payloads and say
so). Not hot-tier: it's a forge-scripting recipe, not a behavior-changing
cross-cutting rule. It extends the existing #920 / #909 forge-concept lessons.
Things to Look At During PR Review
runtime-testable in this environment. The gitlab/gitea/linear
issue-viewedits were verified two ways — field names against each forge's API docs, and
each
jqtransform against a representative sample payload (correcturlextracted, other fields preserved, Gitea's
html_url-over-urlfallbackexercised) — but not against a live
glab/tea/Linear instance. Areviewer with those forges should sanity-check.
gitea/issue-view.shmapshtml_url(browser), not theraw
url(API endpoint). Confirm thejq '.url = (.html_url // .url)'choice.the change only adds/remaps
urland deliberately leaves their existingbody/state/comments handling alone (a separate, pre-existing concern).
openIssueByIdopens the browser when thefetch returns a
url, and falls back tocodev.viewBacklogIssue(in-editor)when it doesn't — so a forge without
urlstill works, degraded.codev.openBacklogSearch's command id and itsview/title🔍 binding are untouched — only the display title changed.How to Test Locally
pir-1096→ Review Difffrom the worktree root,
pnpm build && pnpm -w run local-install(rebuilds + restarts Tower with the newissue-viewscript), then reload the VSCode window.Cmd+K I→1096and#1096→ both open the GitHub issue page in the browser.Cmd+Shift+P→ "Search Backlog" shows two distinct entries ("Codev: Search Backlog..." vs "Codev: Open Backlog Search Panel"); the 🔍 Backlog title-bar icon still opens the panel.codev.searchBacklog,codev.viewBacklogIssue,codev.openBacklogIssueunaffected.