diff --git a/.claude-plugin/marketplace.json b/.claude-plugin/marketplace.json index 02f225e..5c06dc8 100644 --- a/.claude-plugin/marketplace.json +++ b/.claude-plugin/marketplace.json @@ -12,7 +12,7 @@ "name": "projectstore", "displayName": "projectstore", "description": "๐Ÿ“š Your project's knowledge base, written by your AI agent โ€” ADRs ยท epics ยท stories ยท runbooks ยท research. An Obsidian-friendly markdown vault, agent-maintained, you approve every write. Like Karpathy's LLM Wiki, but for engineering project artifacts.", - "version": "0.11.0", + "version": "0.12.0", "author": { "name": "Evgenii Konev", "email": "ekonev@smartandpoint.com", diff --git a/.claude-plugin/plugin.json b/.claude-plugin/plugin.json index f3b8b83..b43f8f6 100644 --- a/.claude-plugin/plugin.json +++ b/.claude-plugin/plugin.json @@ -1,7 +1,7 @@ { "name": "projectstore", "displayName": "projectstore", - "version": "0.11.0", + "version": "0.12.0", "description": "Opinionated project-management paradigms (ADR / epics / stories / kanban / runbooks) for agentic development. Markdown-first, git-portable, human-readable.", "author": { "name": "Evgenii Konev @ SmartAndPoint", diff --git a/README.md b/README.md index 58bf7df..ff80dc2 100644 --- a/README.md +++ b/README.md @@ -158,7 +158,7 @@ PreCompact [...pre-compact.mjs] completed successfully: { The packet contains the vault path, the command list, the last 15 vault touches, and the newest in-flight ADR / epic / story / research. The post-compact agent picks up drafting from where the previous one left off, no manual rehydration. -## What's in the box (v0.11) +## What's in the box (v0.12) - **14 commands** โ€” `bind`, `scaffold`, `status`, `adr`, `epic`, `story`, `kanban`, `research`, `concept`, `meeting`, `runbook`, `search`, `review`, `statusline` - **3 passive skills** โ€” `decision-detector`, `story-completion`, `peer-reviewer`. They suggest commands; they never write directly. @@ -222,7 +222,8 @@ So in a projectstore project you keep your full [oh-my-claudecode](https://githu | Version | What ships | Status | |---|---|---| -| **v0.11** | Status line install simplified โ€” opt-in flag + self-healing SessionStart wiring | โœ… current | +| **v0.12** | Status line shows full epic & story titles (from frontmatter, not the filename) | โœ… current | +| v0.11 | Status line install simplified โ€” opt-in flag + self-healing SessionStart wiring | โœ… | | v0.10 | Status line โ€” current epic & story in the HUD, composes with an existing status line | โœ… | | v0.9 | Bundled review agents (`projectstore-critic`, `code-planner`, `code-reviewer`) | โœ… | | v0.8 | Russian (`ru`) templates | โœ… | diff --git a/scripts/statusline.mjs b/scripts/statusline.mjs index 0509748..fc8c7f3 100644 --- a/scripts/statusline.mjs +++ b/scripts/statusline.mjs @@ -129,15 +129,27 @@ function bookSegment(cfg, input) { } } - let seg = BOOK + epicId; + // Prefer the human `title:` from each artifact's frontmatter over the raw + // id / filename slug (fall back to those when a title is missing/unreadable). + let epicTitle = null; + try { + const { data } = parseFrontmatter( + readFileSync(join(vault, "epics", epicId, "epic.md"), "utf8"), + ); + if (data.title) epicTitle = String(data.title); + } catch {} + let seg = BOOK + (epicTitle || epicId); + if (storyFile) { - const label = storyFile.replace(/\.md$/, ""); let status = null; + let storyTitle = null; try { const { data } = parseFrontmatter(readFileSync(storyPath, "utf8")); if (data.status) status = String(data.status).toLowerCase(); + if (data.title) storyTitle = String(data.title); } catch {} - seg += ARROW + label + (status ? ` (${status})` : ""); + const storyLabel = storyTitle || storyFile.replace(/\.md$/, ""); + seg += ARROW + storyLabel + (status ? ` (${status})` : ""); } return seg; }