| name | project-issues |
| description | Track, manage, and fix issues across all projects (full lifecycle, strict format) |
| version | 5.0.0 |
| author | potato |
| triggers | {"patterns":["issue:","bug:","improvement:","记一下这个bug","记一下这个问题","这个需要改进","需要fix","需要修","发现一个问题","有个bug","要改进","项目问题","fix ISS-","close ISS-","ISS-\\d+ closed","ISS-\\d+ wontfix","ISS-\\d+ blocked","show all issues","所有.*issue","issue dashboard","audit issues","lint issues","rebuild issues index"],"keywords":["issue","bug report","improvement needed","需要改","记个issue","fix","fix issue","修复","close","wontfix","dashboard","audit"]} |
| tags | ["productivity","project-management","quality"] |
| priority | 70 |
| always_load | false |
| max_body_size | 4096 |
SKILL: Project Issue Tracker (v5)
Capture bugs, improvements, and issues with strict file format enforcement. Every issue is a self-contained directory with a canonical issue.md whose YAML frontmatter is the single source of truth. The aggregate issues-index.md is a derived view, regenerated from frontmatter — never hand-edited.
Why v5 (vs v4)
v4 designed a centralized issues-index.md model where the index was the source of truth and ISS-NNN/ directories were optional workrooms. In practice this collapsed: issues drifted into issue.md / README.md / ISSUE.md / bare .md files; status lines used 5 different formats; the index fell out of sync (rustclaw index has 6 entries vs 27 actual issues, with stale statuses).
v5 inverts the model:
- Source of truth:
ISS-NNN/issue.md with strict YAML frontmatter
- Derived view:
issues-index.md is auto-rebuilt from frontmatter (a script — never written by hand)
- One file name:
issue.md. Not README.md, not ISSUE.md, not ISS-NNN.md
- One directory layout: every issue gets
ISS-NNN/ (no more bare .md files at issues root)
- Lint command to detect drift
Philosophy
使用项目的过程中总会发现问题——bug、性能瓶颈、UX 改进、缺失功能。这些发现如果散落在 daily log、engram、随机文件里,以后根本找不到。
每个项目在 .gid/issues/ 下统一管理所有 issue,遵守 v5 strict format。
Directory Structure (STRICT)
{project_root}/
├── .gid/
│ ├── docs/
│ │ └── issues-index.md ← AUTO-GENERATED. Do not hand-edit.
│ └── issues/
│ ├── ISS-001/ ← REQUIRED: directory, NOT a bare .md file
│ │ ├── issue.md ← REQUIRED: canonical name. Frontmatter = source of truth.
│ │ ├── design.md ← OPTIONAL: when fix needs design
│ │ ├── reviews/ ← OPTIONAL: review findings
│ │ └── ... ← any other artifacts
│ ├── ISS-002/
│ │ └── issue.md
│ └── ISS-NNN/
│ └── issue.md
Hard rules (lint will fail otherwise)
- Every issue MUST be a directory named
ISS-NNN (zero-padded to 3 digits, no suffix)
- ❌
ISS-022-migrate-start-ritual.md (bare file)
- ❌
ISS-22/ (not zero-padded)
- ✅
ISS-022/
- Every issue directory MUST contain
issue.md (lowercase, exact name)
- ❌
ISS-007/README.md
- ❌
ISS-014/ISSUE.md
- ✅
ISS-007/issue.md
issue.md MUST start with YAML frontmatter (see schema below)
issues-index.md MUST NOT be hand-edited — it's regenerated by Step F: Rebuild Index
Pure-doc directories (NOT issues)
Some legacy ISS-NNN/ dirs (e.g., rustclaw ISS-002, ISS-004, ISS-006) contain only design/reference docs with no issue.md. These are archives, not issues. Migration:
- If superseded → write a stub
issue.md with status: superseded pointing to the archive docs
- Never leave a directory under
.gid/issues/ without an issue.md
YAML Frontmatter Schema (STRICT)
Every issue.md MUST start with this frontmatter. Fields are validated by lint.
---
id: ISS-007
title: "Engram memory recall quality — three bugs"
type: bug
priority: P1
status: open
created: 2026-04-15
reporter: potato
component: "src/agent.rs, engramai/recall"
closed: 2026-04-25
commits:
- rustclaw:b10c9f9c8d7e6f5a4b3c2d1e0f9a8b7c6d5e4f3a
- gid-rs:6e5782b0a1b2c3d4e5f6a7b8c9d0e1f2a3b4c5d6
blocked_by:
- engram:ISS-032
wontfix_reason: "Superseded by ISS-021 design"
superseded_by: ISS-029
related: [ISS-005, ISS-008]
tags: [memory, recall]
---
Body structure (after frontmatter)
# {title}
## Problem
{Clear problem statement. For bugs: include reproduction steps. For improvements: state current vs desired behavior.}
## Context
{Why it matters. Where it was discovered.}
## Proposed Solution
{If known. Otherwise "TBD — needs analysis".}
## Resolution ← Required when status == closed
{One-paragraph summary of what was actually fixed and how.}
The body is human-readable detail. The frontmatter is the contract — lint and index rebuild only read frontmatter.
Storage Location
{project_root}/.gid/issues/ISS-NNN/issue.md
Project paths resolved via .gid/projects.yml. Fallback list in MEMORY.md → "Canonical Project Roots". If unknown, ask potato.
⚠️ NEVER create the project root directory. .gid/issues/ISS-NNN/ may be created; the project root must already exist.
Pipeline
Step 1: Identify project & next number
- Determine project from potato's message (ask if ambiguous).
- Resolve project path via
.gid/projects.yml or fallback list.
- List
.gid/issues/ISS-* directories. Next number = max + 1, zero-padded to 3 digits.
- Create
.gid/issues/ISS-{NNN}/ directory.
Step 2: Write issue.md
Use the frontmatter schema above. Required fields for a new issue:
id, title, type, priority, status: open, created, reporter
component (strongly recommended)
Body: at minimum ## Problem and ## Context.
Step 3: Cross-record
- Daily log (
memory/YYYY-MM-DD.md):
## Issue Recorded: {project} ISS-NNN
- {one-line description}
- {project_path}/.gid/issues/ISS-NNN/issue.md
- Engram:
engram_store(type=factual, importance=0.5,
content="{project} ISS-NNN: {title}. Type={type}, Priority={priority}")
Step 4: Rebuild index (Step F below)
Always rebuild after creating/closing/changing status.
Step 5: Reply to potato
🐛 **Issue Recorded: {project} ISS-{NNN}**
Type: {type} | Priority: {priority}
{one-line description}
📂 {project_path}/.gid/issues/ISS-NNN/issue.md
Lifecycle Operations
Step A: Status change
Triggers: close ISS-NNN, ISS-NNN wontfix, ISS-NNN blocked by ..., etc.
- Locate
ISS-NNN/issue.md, parse frontmatter.
- Update frontmatter fields per the transition:
| Transition | Required field updates |
|---|
→ in_progress | status: in_progress |
→ closed | status: closed, closed: <today>, commits: [<repo>:<hash>, ...] (≥1) |
→ wontfix | status: wontfix, closed: <today>, wontfix_reason: "..." |
→ blocked | status: blocked, blocked_by: [<ref>, ...] |
→ superseded | status: superseded, closed: <today>, superseded_by: ISS-XXX |
| priority change | priority: P? |
- Critical: When closing, you MUST collect commit hashes:
cd {project_root} && git log -10 --format="%H %s" | grep -i "ISS-NNN"
If no matching commits found → ask potato for the commit hash(es). Never close without commits: filled.
- Optionally append a
## Resolution section to the body.
- Rebuild index (Step F).
- Daily log + engram store the transition.
Step B: Dashboard
Triggers: show all issues, issue dashboard, 所有.*issue
- Read
.gid/projects.yml (or fallback list).
- For each project, read
.gid/issues/ISS-*/issue.md, parse frontmatter.
- Group by
priority, filter by status (default: open + in_progress + blocked + last-7-days closed).
- Output as Telegram bullet list.
- If frontmatter parse fails for any issue → list it under "⚠️ Malformed (run lint)".
Step C: Fix Workflow (fix ISS-NNN)
End-to-end fix: analyze → fix → commit → verify → close. Skill-based (not ritual) — keeps full session context.
C1: Understand
- Locate issue, read frontmatter + body.
- If
status not in {open, in_progress} → tell potato + STOP.
- Set
status: in_progress (prevents heartbeat retrigger).
- Locate code via
search_files / gid_query_impact.
- Notify potato:
🔧 Starting fix for {project} ISS-NNN — Priority {priority}.
C2: Implement
- Read source, identify root cause (not symptom).
- Apply minimal root-fix via
edit_file. Don't drive-by refactor.
- Complex (multi-file, architecture) →
spawn_specialist (builder).
-
5 files changed → pause, list changes, ask potato.
- Commit:
cd {project_root} && git add -A && git commit -m "fix({project}): ISS-NNN {brief}"
Commit failure → STOP + tell potato.
C3: Verify
- Read
verify_command from .gid/config.yml. Defaults by language:
Cargo.toml → cargo test
package.json → npm test
pyproject.toml → pytest
go.mod → go test ./...
- Run.
- Pass → C4. Fail → revert
status to open, keep code, notify potato + STOP.
C4: Close (frontmatter + commits MANDATORY)
commit_hash=$(git -C {project_root} log -1 --format=%H)
- Edit
issue.md frontmatter:
status: closed
closed: <today>
commits: [<project>:<commit_hash>] (cross-project: list multiple)
- Append
## Resolution section to body with one-paragraph summary.
- Rebuild index (Step F).
C5: Record
- Daily log:
## Issue Closed: {project} ISS-NNN
- **Title**: {title}
- **Commit**: {hash}
- **Resolution**: {summary}
- Engram:
importance=0.6 (P0 → 0.8).
- Notify:
✅ {project} ISS-NNN fixed and closed — {summary}\nCommit: {hash_short}.
Fix failure handling
| Step | Failure | Action |
|---|
| C1 | Issue missing / already closed | STOP + notify |
| C2 | Cannot identify root cause | STOP + notify + suggest manual |
| C2 | Commit fails | STOP + notify |
| C3 | Tests fail | Keep code, revert status to open, notify, STOP |
| C4 | Frontmatter edit fails | Notify, ask manual fix |
| C4 | Cannot determine commit hash | Notify potato — DO NOT close without commits |
| C5 | Daily log / engram fail | Consider fix successful, notify |
All failures → daily log.
Step D: Lint (audit issues / lint issues)
Validate every issue against the strict format. Run before any rebuild.
Checks per issue:
- ❌ Bare
.md file at issues root (must be a directory)
- ❌ Directory name not matching
^ISS-\d{3}$
- ❌ Missing
issue.md in directory
- ❌
issue.md missing YAML frontmatter
- ❌ Required field missing:
id, title, type, priority, status, created, reporter
- ❌
id doesn't match directory name
- ❌ Field has invalid value (e.g.,
type: foo, priority: P5)
- ❌
status: closed but closed date missing
- ❌
status: closed but commits missing or empty
- ❌
status: blocked but blocked_by missing
- ❌
status: wontfix but wontfix_reason missing
- ❌
status: superseded but superseded_by missing
- ⚠️
closed date earlier than created
- ⚠️ Body missing
## Problem section
Output format:
## Lint Report: {project} (.gid/issues/)
### ❌ Errors (must fix)
- ISS-007: missing `commits` field (status=closed)
- ISS-014: directory has `ISSUE.md` not `issue.md`
### ⚠️ Warnings
- ISS-021: closed date (2026-04-22) before created date (2026-04-23)
### ✅ Compliant
- 18/27 issues pass strict format
On lint failures: notify potato. Offer to migrate. Never auto-fix without confirmation — issues are project history.
Step E: Migration helper
When potato approves migrating malformed issues:
- Bare
.md → directory:
mkdir -p ISS-022/
git mv ISS-022-migrate-start-ritual-to-workunit.md ISS-022/issue.md
- Wrong filename →
issue.md:
git mv ISS-007/README.md ISS-007/issue.md
- Missing frontmatter: parse existing free-form Status/Priority lines, generate frontmatter, prepend to file. Show diff to potato before writing.
- Pure-doc directories (no
issue.md, only design archives): write a stub issue.md with status: superseded or status: closed and a body pointing to the archive files.
Step F: Rebuild Index (rebuild issues index)
issues-index.md is derived — generated by scanning all ISS-NNN/issue.md frontmatter.
Algorithm:
- Find all
.gid/issues/ISS-*/issue.md.
- Parse frontmatter from each.
- Group by status: open / in_progress / blocked / closed / wontfix / superseded.
- Within each group, sort by priority (P0 first), then by id.
- Write
.gid/docs/issues-index.md with header:
# Issues: {project_name}
> AUTO-GENERATED by project-issues skill v5. DO NOT EDIT BY HAND.
> Source: .gid/issues/ISS-NNN/issue.md frontmatter.
> Last rebuilt: {YYYY-MM-DD HH:MM}
- For each issue, emit a one-block summary:
## ISS-007 [bug] [P1] [open]
**Title**: Engram memory recall quality — three bugs
**Created**: 2026-04-15 | **Reporter**: potato
**Component**: src/agent.rs, engramai/recall
**Path**: `.gid/issues/ISS-007/issue.md`
{if closed}**Closed**: 2026-04-25 | **Commits**: rustclaw:b10c9f9, gid-rs:6e5782b
{if blocked}**Blocked by**: engram:ISS-032
- Optionally append a stats footer (counts by status/priority).
This step runs automatically after: Step 2 (new issue), Step A (status change), Step C4 (close).
主动记录
RustClaw 不只是被动记录。在以下场景主动创建 issue:
- 开发过程中发现代码问题但不在当前任务范围
- 使用 engram/gid 等工具时遇到不理想的行为
- review 代码或文档时发现需要改进的地方
- 心跳检查时发现某个功能异常
主动记录时,reporter: RustClaw,body 简要说明发现场景。
Rules (Hard)
- One issue, one thing. Don't pack multiple problems into one ISS.
- Frontmatter is the contract. Body is for humans; tools only read frontmatter.
- Never delete closed issues. They're project history. Status flips, content stays.
- Numbers never reuse. Even after delete (don't delete).
- Never hand-edit
issues-index.md. Always Step F.
issue.md is the only canonical filename. Not README.md, not ISSUE.md.
- Closing requires commits. No
commits field → not closed.
- One issue = one directory. No bare
.md files at .gid/issues/ root.
- ISS-XXX docs go in
.gid/issues/ISS-XXX/. Not in project root, not in docs/.
Quick Reference: Common Commands
| Trigger | Action |
|---|
bug: ... / improvement: ... | Pipeline Steps 1–5 (create new issue) |
fix ISS-NNN | Step C (full fix workflow) |
close ISS-NNN | Step A (collect commits, update frontmatter, rebuild index) |
ISS-NNN wontfix | Step A with wontfix_reason prompt |
ISS-NNN blocked by X | Step A with blocked_by |
show all issues / issue dashboard | Step B |
audit issues / lint issues | Step D |
rebuild issues index | Step F |
migrate ISS-NNN | Step E (offer migration plan) |
Migration Note (v4 → v5)
Existing projects (rustclaw has 27 issues, mostly v4 format) need a one-time migration:
- Run
audit issues on each project — get the lint report.
- For each error, ask potato to confirm before applying Step E migration.
- After all issues migrated, run
rebuild issues index to regenerate issues-index.md.
Do this incrementally, not all-at-once. Issues are history; mass-edits risk losing nuance.