@wolfx/oh-my-openagent 3.17.14 → 4.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.ja.md +153 -113
- package/README.ko.md +196 -149
- package/README.md +53 -50
- package/README.ru.md +92 -70
- package/README.zh-cn.md +112 -71
- package/dist/agents/agent-skill-resolution.d.ts +1 -0
- package/dist/agents/builtin-agents/available-skills.d.ts +1 -1
- package/dist/agents/builtin-agents/general-agents.d.ts +1 -0
- package/dist/agents/builtin-agents.d.ts +1 -1
- package/dist/agents/dynamic-agent-core-sections.d.ts +1 -0
- package/dist/agents/dynamic-agent-prompt-builder.d.ts +1 -1
- package/dist/agents/hephaestus/gpt-5-5.d.ts +0 -4
- package/dist/agents/types.d.ts +1 -0
- package/dist/config/index.d.ts +1 -1
- package/dist/config/schema/agent-names.d.ts +1 -0
- package/dist/config/schema/agent-overrides.d.ts +45 -0
- package/dist/config/schema/categories.d.ts +7 -1
- package/dist/config/schema/commands.d.ts +1 -0
- package/dist/config/schema/fallback-models.d.ts +5 -0
- package/dist/config/schema/hooks.d.ts +1 -0
- package/dist/config/schema/keyword-detector.d.ts +21 -0
- package/dist/config/schema/oh-my-opencode-config.d.ts +70 -0
- package/dist/config/schema/team-mode.d.ts +16 -0
- package/dist/config/schema.d.ts +2 -0
- package/dist/create-hooks.d.ts +3 -0
- package/dist/features/background-agent/manager.d.ts +3 -0
- package/dist/features/background-agent/types.d.ts +4 -0
- package/dist/features/boulder-state/storage.d.ts +1 -0
- package/dist/features/builtin-commands/commands.d.ts +1 -0
- package/dist/features/builtin-commands/templates/hyperplan.d.ts +1 -0
- package/dist/features/builtin-commands/templates/refactor.d.ts +1 -0
- package/dist/features/builtin-commands/templates/remove-ai-slops.d.ts +1 -0
- package/dist/features/builtin-commands/types.d.ts +1 -1
- package/dist/features/builtin-skills/skills/git-master-sections/commit-workflow.d.ts +1 -1
- package/dist/features/builtin-skills/skills/git-master-sections/history-search-workflow.d.ts +1 -1
- package/dist/features/builtin-skills/skills/git-master-sections/overview.d.ts +1 -1
- package/dist/features/builtin-skills/skills/git-master-sections/quick-reference.d.ts +1 -1
- package/dist/features/builtin-skills/skills/git-master-sections/rebase-workflow.d.ts +1 -1
- package/dist/features/builtin-skills/skills/index.d.ts +1 -0
- package/dist/features/builtin-skills/skills/team-mode.d.ts +2 -0
- package/dist/features/builtin-skills/skills.d.ts +1 -0
- package/dist/features/claude-code-plugin-loader/discovery.d.ts +1 -0
- package/dist/features/hook-message-injector/injector.d.ts +2 -2
- package/dist/features/opencode-skill-loader/loader.d.ts +2 -2
- package/dist/features/opencode-skill-loader/skill-resolution-options.d.ts +1 -0
- package/dist/features/team-mode/deps.d.ts +6 -0
- package/dist/features/team-mode/member-guidance.d.ts +2 -0
- package/dist/features/team-mode/member-parser.d.ts +16 -0
- package/dist/features/team-mode/member-session-resolution.d.ts +6 -0
- package/dist/features/team-mode/member-session-routing.d.ts +19 -0
- package/dist/features/team-mode/team-layout-tmux/close-team-member-pane.d.ts +4 -0
- package/dist/features/team-mode/team-layout-tmux/layout.d.ts +26 -6
- package/dist/features/team-mode/team-layout-tmux/rebalance-team-window.d.ts +9 -0
- package/dist/features/team-mode/team-layout-tmux/resolve-caller-tmux-session.d.ts +7 -0
- package/dist/features/team-mode/team-layout-tmux/sweep-stale-team-sessions.d.ts +8 -0
- package/dist/features/team-mode/team-mailbox/ack.d.ts +2 -0
- package/dist/features/team-mode/team-mailbox/inbox.d.ts +3 -0
- package/dist/features/team-mode/team-mailbox/index.d.ts +7 -0
- package/dist/features/team-mode/team-mailbox/poll.d.ts +10 -0
- package/dist/features/team-mode/team-mailbox/reservation.d.ts +11 -0
- package/dist/features/team-mode/team-mailbox/send.d.ts +27 -0
- package/dist/features/team-mode/team-registry/index.d.ts +3 -0
- package/dist/features/team-mode/team-registry/loader.d.ts +12 -0
- package/dist/features/team-mode/team-registry/paths.d.ts +13 -0
- package/dist/features/team-mode/team-registry/team-spec-input-normalizer.d.ts +6 -0
- package/dist/features/team-mode/team-registry/validator.d.ts +10 -0
- package/dist/features/team-mode/team-runtime/activate-team-layout.d.ts +4 -0
- package/dist/features/team-mode/team-runtime/cleanup-team-run-resources.d.ts +17 -0
- package/dist/features/team-mode/team-runtime/create.d.ts +25 -0
- package/dist/features/team-mode/team-runtime/delete-team.d.ts +16 -0
- package/dist/features/team-mode/team-runtime/index.d.ts +2 -0
- package/dist/features/team-mode/team-runtime/resolve-member-dependencies.d.ts +3 -0
- package/dist/features/team-mode/team-runtime/resolve-member.d.ts +17 -0
- package/dist/features/team-mode/team-runtime/shutdown-helpers.d.ts +11 -0
- package/dist/features/team-mode/team-runtime/shutdown-test-fixtures.d.ts +46 -0
- package/dist/features/team-mode/team-runtime/shutdown.d.ts +5 -0
- package/dist/features/team-mode/team-runtime/status.d.ts +36 -0
- package/dist/features/team-mode/team-session-registry.d.ts +11 -0
- package/dist/features/team-mode/team-state-store/index.d.ts +1 -0
- package/dist/features/team-mode/team-state-store/locks.d.ts +12 -0
- package/dist/features/team-mode/team-state-store/resume.d.ts +10 -0
- package/dist/features/team-mode/team-state-store/store.d.ts +21 -0
- package/dist/features/team-mode/team-tasklist/claim.d.ts +10 -0
- package/dist/features/team-mode/team-tasklist/dependencies.d.ts +2 -0
- package/dist/features/team-mode/team-tasklist/get.d.ts +3 -0
- package/dist/features/team-mode/team-tasklist/index.d.ts +6 -0
- package/dist/features/team-mode/team-tasklist/list.d.ts +8 -0
- package/dist/features/team-mode/team-tasklist/store.d.ts +3 -0
- package/dist/features/team-mode/team-tasklist/test-support.d.ts +9 -0
- package/dist/features/team-mode/team-tasklist/update.d.ts +9 -0
- package/dist/features/team-mode/tools/index.d.ts +1 -0
- package/dist/features/team-mode/tools/lifecycle-test-fixture.d.ts +188 -0
- package/dist/features/team-mode/tools/lifecycle.d.ts +37 -0
- package/dist/features/team-mode/tools/messaging.d.ts +31 -0
- package/dist/features/team-mode/tools/query.d.ts +16 -0
- package/dist/features/team-mode/tools/tasks.d.ts +18 -0
- package/dist/features/team-mode/types.d.ts +137 -5
- package/dist/features/tmux-subagent/action-executor-core.d.ts +1 -0
- package/dist/features/tmux-subagent/action-executor.d.ts +1 -0
- package/dist/features/tmux-subagent/attachable-session-status.d.ts +4 -0
- package/dist/features/tmux-subagent/manager.d.ts +32 -3
- package/dist/features/tmux-subagent/pane-state-querier.d.ts +10 -0
- package/dist/features/tmux-subagent/polling.d.ts +1 -0
- package/dist/hooks/atlas/atlas-hook.d.ts +1 -1
- package/dist/hooks/atlas/boulder-continuation-injector.d.ts +2 -3
- package/dist/hooks/atlas/recent-model-resolver.d.ts +9 -1
- package/dist/hooks/atlas/tool-execute-after.d.ts +2 -1
- package/dist/hooks/atlas/tool-execute-before.d.ts +1 -0
- package/dist/hooks/atlas/types.d.ts +8 -2
- package/dist/hooks/index.d.ts +3 -0
- package/dist/hooks/keyword-detector/constants.d.ts +6 -0
- package/dist/hooks/keyword-detector/detector.d.ts +5 -3
- package/dist/hooks/keyword-detector/hook.d.ts +2 -1
- package/dist/hooks/keyword-detector/hyperplan/default.d.ts +13 -0
- package/dist/hooks/keyword-detector/hyperplan/index.d.ts +1 -0
- package/dist/hooks/keyword-detector/team/default.d.ts +13 -0
- package/dist/hooks/keyword-detector/team/index.d.ts +1 -0
- package/dist/hooks/session-recovery/recover-tool-result-missing.d.ts +2 -2
- package/dist/hooks/team-mailbox-injector/hook.d.ts +31 -0
- package/dist/hooks/team-mailbox-injector/index.d.ts +2 -0
- package/dist/hooks/team-mode-status-injector/hook.d.ts +28 -0
- package/dist/hooks/team-mode-status-injector/index.d.ts +1 -0
- package/dist/hooks/team-session-events/team-idle-wake-hint.d.ts +38 -0
- package/dist/hooks/team-session-events/team-lead-orphan-handler.d.ts +12 -0
- package/dist/hooks/team-session-events/team-member-error-handler.d.ts +10 -0
- package/dist/hooks/team-session-events/team-member-status-handler.d.ts +10 -0
- package/dist/hooks/team-tool-gating/hook.d.ts +3 -0
- package/dist/hooks/team-tool-gating/index.d.ts +1 -0
- package/dist/hooks/write-existing-file-guard/hook.d.ts +6 -1
- package/dist/hooks/write-existing-file-guard/tool-execute-before-handler.d.ts +1 -0
- package/dist/index.js +89536 -80765
- package/dist/oh-my-opencode.schema.json +191 -47
- package/dist/plugin/hooks/create-core-hooks.d.ts +3 -0
- package/dist/plugin/hooks/create-tool-guard-hooks.d.ts +2 -1
- package/dist/plugin/hooks/create-transform-hooks.d.ts +3 -1
- package/dist/plugin/recent-synthetic-idles.d.ts +1 -0
- package/dist/plugin/tool-registry.d.ts +16 -0
- package/dist/shared/bun-spawn-shim.d.ts +40 -0
- package/dist/shared/project-discovery-dirs.d.ts +1 -0
- package/dist/shared/shell-env.d.ts +1 -0
- package/dist/shared/tmux/constants.d.ts +1 -1
- package/dist/shared/tmux/index.d.ts +1 -0
- package/dist/shared/tmux/runner.d.ts +13 -0
- package/dist/shared/tmux/tmux-utils/pane-replace.d.ts +1 -1
- package/dist/shared/tmux/tmux-utils/pane-spawn.d.ts +13 -1
- package/dist/shared/tmux/tmux-utils/session-spawn.d.ts +13 -1
- package/dist/shared/tmux/tmux-utils/spawn-process.d.ts +1 -1
- package/dist/shared/tmux/tmux-utils/stale-session-sweep.d.ts +9 -2
- package/dist/shared/tmux/tmux-utils/window-spawn.d.ts +13 -1
- package/dist/shared/tmux/tmux-utils.d.ts +1 -1
- package/dist/tools/delegate-task/openai-categories.d.ts +1 -0
- package/dist/tools/delegate-task/skill-resolver.d.ts +1 -0
- package/dist/tools/delegate-task/subagent-resolver.d.ts +5 -1
- package/dist/tools/delegate-task/types.d.ts +1 -0
- package/dist/tools/index.d.ts +1 -0
- package/dist/tools/look-at/missing-file-error.d.ts +2 -0
- package/dist/tools/skill/types.d.ts +2 -0
- package/package.json +3 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const GIT_MASTER_COMMIT_WORKFLOW_SECTION = "## PHASE 0: Parallel Context Gathering (MANDATORY FIRST STEP)\n\n<parallel_analysis>\n**Execute ALL of the following commands IN PARALLEL to minimize latency:**\n\n```bash\n# Group 1: Current state\ngit status\ngit diff --staged --stat\ngit diff --stat\n\n# Group 2: History context \ngit log -30 --oneline\ngit log -30 --pretty=format:\"%s\"\n\n# Group 3: Branch context\ngit branch --show-current\ngit merge-base HEAD main 2>/dev/null || git merge-base HEAD master 2>/dev/null\ngit rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo \"NO_UPSTREAM\"\ngit log --oneline $(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master 2>/dev/null)..HEAD 2>/dev/null\n```\n\n**Capture these data points simultaneously:**\n1. What files changed (staged vs unstaged)\n2. Recent 30 commit messages for style detection\n3. Branch position relative to main/master\n4. Whether branch has upstream tracking\n5. Commits that would go in PR (local only)\n</parallel_analysis>\n\n---\n\n## PHASE 1: Style Detection (BLOCKING - MUST OUTPUT BEFORE PROCEEDING)\n\n<style_detection>\n**THIS PHASE HAS MANDATORY OUTPUT** - You MUST print the analysis result before moving to Phase 2.\n\n### 1.1 Language Detection\n\n```\nCount from git log -30:\n- Korean characters: N commits\n- English only: M commits\n- Mixed: K commits\n\nDECISION:\n- If Korean >= 50% -> KOREAN\n- If English >= 50% -> ENGLISH \n- If Mixed -> Use MAJORITY language\n```\n\n### 1.2 Commit Style Classification\n\n| Style | Pattern | Example | Detection Regex |\n|-------|---------|---------|-----------------|\n| `SEMANTIC` | `type: message` or `type(scope): message` | `feat: add login` | `/^(feat\\|fix\\|chore\\|refactor\\|docs\\|test\\|ci\\|style\\|perf\\|build)(\\(.+\\))?:/` |\n| `PLAIN` | Just description, no prefix | `Add login feature` | No conventional prefix, >3 words |\n| `SENTENCE` | Full sentence style | `Implemented the new login flow` | Complete grammatical sentence |\n| `SHORT` | Minimal keywords | `format`, `lint` | 1-3 words only |\n\n**Detection Algorithm:**\n```\nsemantic_count = commits matching semantic regex\nplain_count = non-semantic commits with >3 words\nshort_count = commits with <=3 words\n\nIF semantic_count >= 15 (50%): STYLE = SEMANTIC\nELSE IF plain_count >= 15: STYLE = PLAIN \nELSE IF short_count >= 10: STYLE = SHORT\nELSE: STYLE = PLAIN (safe default)\n```\n\n### 1.3 MANDATORY OUTPUT (BLOCKING)\n\n**You MUST output this block before proceeding to Phase 2. NO EXCEPTIONS.**\n\n```\nSTYLE DETECTION RESULT\n======================\nAnalyzed: 30 commits from git log\n\nLanguage: [KOREAN | ENGLISH]\n - Korean commits: N (X%)\n - English commits: M (Y%)\n\nStyle: [SEMANTIC | PLAIN | SENTENCE | SHORT]\n - Semantic (feat:, fix:, etc): N (X%)\n - Plain: M (Y%)\n - Short: K (Z%)\n\nReference examples from repo:\n 1. \"actual commit message from log\"\n 2. \"actual commit message from log\"\n 3. \"actual commit message from log\"\n\nAll commits will follow: [LANGUAGE] + [STYLE]\n```\n\n**IF YOU SKIP THIS OUTPUT, YOUR COMMITS WILL BE WRONG. STOP AND REDO.**\n</style_detection>\n\n---\n\n## PHASE 2: Branch Context Analysis\n\n<branch_analysis>\n### 2.1 Determine Branch State\n\n```\nBRANCH_STATE:\n current_branch: <name>\n has_upstream: true | false\n commits_ahead: N # Local-only commits\n merge_base: <hash>\n \nREWRITE_SAFETY:\n - If has_upstream AND commits_ahead > 0 AND already pushed:\n -> WARN before force push\n - If no upstream OR all commits local:\n -> Safe for aggressive rewrite (fixup, reset, rebase)\n - If on main/master:\n -> NEVER rewrite, only new commits\n```\n\n### 2.2 History Rewrite Strategy Decision\n\n```\nIF current_branch == main OR current_branch == master:\n -> STRATEGY = NEW_COMMITS_ONLY\n -> Never fixup, never rebase\n\nELSE IF commits_ahead == 0:\n -> STRATEGY = NEW_COMMITS_ONLY\n -> No history to rewrite\n\nELSE IF all commits are local (not pushed):\n -> STRATEGY = AGGRESSIVE_REWRITE\n -> Fixup freely, reset if needed, rebase to clean\n\nELSE IF pushed but not merged:\n -> STRATEGY = CAREFUL_REWRITE \n -> Fixup OK but warn about force push\n```\n</branch_analysis>\n\n---\n\n## PHASE 3: Atomic Unit Planning (BLOCKING - MUST OUTPUT BEFORE PROCEEDING)\n\n<atomic_planning>\n**THIS PHASE HAS MANDATORY OUTPUT** - You MUST print the commit plan before moving to Phase 4.\n\n### 3.0 Calculate Minimum Commit Count FIRST\n\n```\nFORMULA: min_commits = ceil(file_count / 3)\n\n 3 files -> min 1 commit\n 5 files -> min 2 commits\n 9 files -> min 3 commits\n15 files -> min 5 commits\n```\n\n**If your planned commit count < min_commits -> WRONG. SPLIT MORE.**\n\n### 3.1 Split by Directory/Module FIRST (Primary Split)\n\n**RULE: Different directories = Different commits (almost always)**\n\n```\nExample: 8 changed files\n - app/[locale]/page.tsx\n - app/[locale]/layout.tsx\n - components/demo/browser-frame.tsx\n - components/demo/shopify-full-site.tsx\n - components/pricing/pricing-table.tsx\n - e2e/navbar.spec.ts\n - messages/en.json\n - messages/ko.json\n\nWRONG: 1 commit \"Update landing page\" (LAZY, WRONG)\nWRONG: 2 commits (still too few)\n\nCORRECT: Split by directory/concern:\n - Commit 1: app/[locale]/page.tsx + layout.tsx (app layer)\n - Commit 2: components/demo/* (demo components)\n - Commit 3: components/pricing/* (pricing components)\n - Commit 4: e2e/* (tests)\n - Commit 5: messages/* (i18n)\n = 5 commits from 8 files (CORRECT)\n```\n\n### 3.2 Split by Concern SECOND (Secondary Split)\n\n**Within same directory, split by logical concern:**\n\n```\nExample: components/demo/ has 4 files\n - browser-frame.tsx (UI frame)\n - shopify-full-site.tsx (specific demo)\n - review-dashboard.tsx (NEW - specific demo)\n - tone-settings.tsx (NEW - specific demo)\n\nOption A (acceptable): 1 commit if ALL tightly coupled\nOption B (preferred): 2 commits\n - Commit: \"Update existing demo components\" (browser-frame, shopify)\n - Commit: \"Add new demo components\" (review-dashboard, tone-settings)\n```\n\n### 3.3 NEVER Do This (Anti-Pattern Examples)\n\n```\nWRONG: \"Refactor entire landing page\" - 1 commit with 15 files\nWRONG: \"Update components and tests\" - 1 commit mixing concerns\nWRONG: \"Big update\" - Any commit touching 5+ unrelated files\n\nRIGHT: Multiple focused commits, each 1-4 files max\nRIGHT: Each commit message describes ONE specific change\nRIGHT: A reviewer can understand each commit in 30 seconds\n```\n\n### 3.4 Implementation + Test Pairing (MANDATORY)\n\n```\nRULE: Test files MUST be in same commit as implementation\n\nTest patterns to match:\n- test_*.py <-> *.py\n- *_test.py <-> *.py\n- *.test.ts <-> *.ts\n- *.spec.ts <-> *.ts\n- __tests__/*.ts <-> *.ts\n- tests/*.py <-> src/*.py\n```\n\n### 3.5 MANDATORY JUSTIFICATION (Before Creating Commit Plan)\n\n**NON-NEGOTIABLE: Before finalizing your commit plan, you MUST:**\n\n```\nFOR EACH planned commit with 3+ files:\n 1. List all files in this commit\n 2. Write ONE sentence explaining why they MUST be together\n 3. If you can't write that sentence -> SPLIT\n \nTEMPLATE:\n\"Commit N contains [files] because [specific reason they are inseparable].\"\n\nVALID reasons:\n VALID: \"implementation file + its direct test file\"\n VALID: \"type definition + the only file that uses it\"\n VALID: \"migration + model change (would break without both)\"\n \nINVALID reasons (MUST SPLIT instead):\n INVALID: \"all related to feature X\" (too vague)\n INVALID: \"part of the same PR\" (not a reason)\n INVALID: \"they were changed together\" (not a reason)\n INVALID: \"makes sense to group\" (not a reason)\n```\n\n**OUTPUT THIS JUSTIFICATION in your analysis before executing commits.**\n\n### 3.7 Dependency Ordering\n\n```\nLevel 0: Utilities, constants, type definitions\nLevel 1: Models, schemas, interfaces\nLevel 2: Services, business logic\nLevel 3: API endpoints, controllers\nLevel 4: Configuration, infrastructure\n\nCOMMIT ORDER: Level 0 -> Level 1 -> Level 2 -> Level 3 -> Level 4\n```\n\n### 3.8 Create Commit Groups\n\nFor each logical feature/change:\n```yaml\n- group_id: 1\n feature: \"Add Shopify discount deletion\"\n files:\n - errors/shopify_error.py\n - types/delete_input.py\n - mutations/update_contract.py\n - tests/test_update_contract.py\n dependency_level: 2\n target_commit: null | <existing-hash> # null = new, hash = fixup\n```\n\n### 3.9 MANDATORY OUTPUT (BLOCKING)\n\n**You MUST output this block before proceeding to Phase 4. NO EXCEPTIONS.**\n\n```\nCOMMIT PLAN\n===========\nFiles changed: N\nMinimum commits required: ceil(N/3) = M\nPlanned commits: K\nStatus: K >= M (PASS) | K < M (FAIL - must split more)\n\nCOMMIT 1: [message in detected style]\n - path/to/file1.py\n - path/to/file1_test.py\n Justification: implementation + its test\n\nCOMMIT 2: [message in detected style]\n - path/to/file2.py\n Justification: independent utility function\n\nCOMMIT 3: [message in detected style]\n - config/settings.py\n - config/constants.py\n Justification: tightly coupled config changes\n\nExecution order: Commit 1 -> Commit 2 -> Commit 3\n(follows dependency: Level 0 -> Level 1 -> Level 2 -> ...)\n```\n\n**VALIDATION BEFORE EXECUTION:**\n- Each commit has <=4 files (or justified)\n- Each commit message matches detected STYLE + LANGUAGE\n- Test files paired with implementation\n- Different directories = different commits (or justified)\n- Total commits >= min_commits\n\n**IF ANY CHECK FAILS, DO NOT PROCEED. REPLAN.**\n</atomic_planning>\n\n---\n\n## PHASE 4: Commit Strategy Decision\n\n<strategy_decision>\n### 4.1 For Each Commit Group, Decide:\n\n```\nFIXUP if:\n - Change complements existing commit's intent\n - Same feature, fixing bugs or adding missing parts\n - Review feedback incorporation\n - Target commit exists in local history\n\nNEW COMMIT if:\n - New feature or capability\n - Independent logical unit\n - Different issue/ticket\n - No suitable target commit exists\n```\n\n### 4.2 History Rebuild Decision (Aggressive Option)\n\n```\nCONSIDER RESET & REBUILD when:\n - History is messy (many small fixups already)\n - Commits are not atomic (mixed concerns)\n - Dependency order is wrong\n \nRESET WORKFLOW:\n 1. git reset --soft $(git merge-base HEAD main)\n 2. All changes now staged\n 3. Re-commit in proper atomic units\n 4. Clean history from scratch\n \nONLY IF:\n - All commits are local (not pushed)\n - User explicitly allows OR branch is clearly WIP\n```\n\n### 4.3 Final Plan Summary\n\n```yaml\nEXECUTION_PLAN:\n strategy: FIXUP_THEN_NEW | NEW_ONLY | RESET_REBUILD\n fixup_commits:\n - files: [...]\n target: <hash>\n new_commits:\n - files: [...]\n message: \"...\"\n level: N\n requires_force_push: true | false\n```\n</strategy_decision>\n\n---\n\n## PHASE 5: Commit Execution\n\n<execution>\n### 5.1 Register TODO Items\n\nUse TodoWrite to register each commit as a trackable item:\n```\n- [ ] Fixup: <description> -> <target-hash>\n- [ ] New: <description>\n- [ ] Rebase autosquash\n- [ ] Final verification\n```\n\n### 5.2 Fixup Commits (If Any)\n\n```bash\n# Stage files for each fixup\ngit add <files>\ngit commit --fixup=<target-hash>\n\n# Repeat for all fixups...\n\n# Single autosquash rebase at the end\nMERGE_BASE=$(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)\nGIT_SEQUENCE_EDITOR=: git rebase -i --autosquash $MERGE_BASE\n```\n\n### 5.3 New Commits (After Fixups)\n\nFor each new commit group, in dependency order:\n\n```bash\n# Stage files\ngit add <file1> <file2> ...\n\n# Verify staging\ngit diff --staged --stat\n\n# Commit with detected style\ngit commit -m \"<message-matching-COMMIT_CONFIG>\"\n\n# Verify\ngit log -1 --oneline\n```\n\n### 5.4 Commit Message Generation\n\n**Based on COMMIT_CONFIG from Phase 1:**\n\n```\nIF style == SEMANTIC AND language == KOREAN:\n -> \"feat: \uB85C\uADF8\uC778 \uAE30\uB2A5 \uCD94\uAC00\"\n \nIF style == SEMANTIC AND language == ENGLISH:\n -> \"feat: add login feature\"\n \nIF style == PLAIN AND language == KOREAN:\n -> \"\uB85C\uADF8\uC778 \uAE30\uB2A5 \uCD94\uAC00\"\n \nIF style == PLAIN AND language == ENGLISH:\n -> \"Add login feature\"\n \nIF style == SHORT:\n -> \"format\" / \"type fix\" / \"lint\"\n```\n\n**VALIDATION before each commit:**\n1. Does message match detected style?\n2. Does language match detected language?\n3. Is it similar to examples from git log?\n\nIf ANY check fails -> REWRITE message.\n```\n</execution>\n\n---\n\n## PHASE 6: Verification & Cleanup\n\n<verification>\n### 6.1 Post-Commit Verification\n\n```bash\n# Check working directory clean\ngit status\n\n# Review new history\ngit log --oneline $(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)..HEAD\n\n# Verify each commit is atomic\n# (mentally check: can each be reverted independently?)\n```\n\n### 6.2 Force Push Decision\n\n```\nIF fixup was used AND branch has upstream:\n -> Requires: git push --force-with-lease\n -> WARN user about force push implications\n \nIF only new commits:\n -> Regular: git push\n```\n\n### 6.3 Final Report\n\n```\nCOMMIT SUMMARY:\n Strategy: <what was done>\n Commits created: N\n Fixups merged: M\n \nHISTORY:\n <hash1> <message1>\n <hash2> <message2>\n ...\n\nNEXT STEPS:\n - git push [--force-with-lease]\n - Create PR if ready\n```\n</verification>";
|
|
1
|
+
export declare const GIT_MASTER_COMMIT_WORKFLOW_SECTION = "## PHASE 0: Parallel Context Gathering (MANDATORY FIRST STEP)\n\n<parallel_analysis>\n**Execute ALL of the following commands IN PARALLEL to minimize latency:**\n\n```bash\n# Group 1: Current state\ngit status\ngit diff --staged --stat\ngit diff --stat\n\n# Group 2: History context \ngit log -30 --oneline\ngit log -30 --pretty=format:\"%s\"\n\n# Group 3: Branch context\ngit branch --show-current\ngit merge-base HEAD main 2>/dev/null || git merge-base HEAD master 2>/dev/null\ngit rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo \"NO_UPSTREAM\"\ngit log --oneline $(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master 2>/dev/null)..HEAD 2>/dev/null\n```\n\n**Capture these data points simultaneously:**\n1. What files changed (staged vs unstaged)\n2. Recent 30 commit messages for style detection\n3. Branch position relative to main/master\n4. Whether branch has upstream tracking\n5. Commits that would go in PR (local only)\n</parallel_analysis>\n\n---\n\n## PHASE 1: Style Detection (BLOCKING - MUST OUTPUT BEFORE PROCEEDING)\n\n<style_detection>\n**THIS PHASE HAS MANDATORY OUTPUT** - You MUST print the analysis result before moving to Phase 2.\n\n### 1.1 Language Profile Detection\n\n```\nCount from git log -30:\n- Dominant language/script patterns: N commits\n- Secondary language/script patterns: M commits\n- Mixed/ambiguous: K commits\n\nDECISION:\n- Preserve the dominant repository language pattern in commit messages\n- If multiple languages are common, follow the nearest recent examples for the same module\n- Never restrict output to specific languages; support any language used by the repo (e.g., Japanese, Korean, English, etc.)\n```\n\n### 1.2 Commit Style Classification\n\n| Style | Pattern | Example | Detection Regex |\n|-------|---------|---------|-----------------|\n| `SEMANTIC` | `type: message` or `type(scope): message` | `feat: add login` | `/^(feat\\|fix\\|chore\\|refactor\\|docs\\|test\\|ci\\|style\\|perf\\|build)(\\(.+\\))?:/` |\n| `PLAIN` | Just description, no prefix | `Add login feature` | No conventional prefix, >3 words |\n| `SENTENCE` | Full sentence style | `Implemented the new login flow` | Complete grammatical sentence |\n| `SHORT` | Minimal keywords | `format`, `lint` | 1-3 words only |\n\n**Detection Algorithm:**\n```\nsemantic_count = commits matching semantic regex\nplain_count = non-semantic commits with >3 words\nshort_count = commits with <=3 words\n\nIF semantic_count >= 15 (50%): STYLE = SEMANTIC\nELSE IF plain_count >= 15: STYLE = PLAIN \nELSE IF short_count >= 10: STYLE = SHORT\nELSE: STYLE = PLAIN (safe default)\n```\n\n### 1.3 MANDATORY OUTPUT (BLOCKING)\n\n**You MUST output this block before proceeding to Phase 2. NO EXCEPTIONS.**\n\n```\nSTYLE DETECTION RESULT\n======================\nAnalyzed: 30 commits from git log\n\nLanguage profile: [DOMINANT_LANGUAGE_OR_SCRIPT]\n - Dominant pattern: N (X%)\n - Secondary pattern: M (Y%)\n\nStyle: [SEMANTIC | PLAIN | SENTENCE | SHORT]\n - Semantic (feat:, fix:, etc): N (X%)\n - Plain: M (Y%)\n - Short: K (Z%)\n\nReference examples from repo:\n 1. \"actual commit message from log\"\n 2. \"actual commit message from log\"\n 3. \"actual commit message from log\"\n\nAll commits will follow: [DOMINANT_LANGUAGE_OR_SCRIPT] + [STYLE]\n```\n\n**IF YOU SKIP THIS OUTPUT, YOUR COMMITS WILL BE WRONG. STOP AND REDO.**\n</style_detection>\n\n---\n\n## PHASE 2: Branch Context Analysis\n\n<branch_analysis>\n### 2.1 Determine Branch State\n\n```\nBRANCH_STATE:\n current_branch: <name>\n has_upstream: true | false\n commits_ahead: N # Local-only commits\n merge_base: <hash>\n \nREWRITE_SAFETY:\n - If has_upstream AND commits_ahead > 0 AND already pushed:\n -> WARN before force push\n - If no upstream OR all commits local:\n -> Safe for aggressive rewrite (fixup, reset, rebase)\n - If on main/master:\n -> NEVER rewrite, only new commits\n```\n\n### 2.2 History Rewrite Strategy Decision\n\n```\nIF current_branch == main OR current_branch == master:\n -> STRATEGY = NEW_COMMITS_ONLY\n -> Never fixup, never rebase\n\nELSE IF commits_ahead == 0:\n -> STRATEGY = NEW_COMMITS_ONLY\n -> No history to rewrite\n\nELSE IF all commits are local (not pushed):\n -> STRATEGY = AGGRESSIVE_REWRITE\n -> Fixup freely, reset if needed, rebase to clean\n\nELSE IF pushed but not merged:\n -> STRATEGY = CAREFUL_REWRITE \n -> Fixup OK but warn about force push\n```\n</branch_analysis>\n\n---\n\n## PHASE 3: Atomic Unit Planning (BLOCKING - MUST OUTPUT BEFORE PROCEEDING)\n\n<atomic_planning>\n**THIS PHASE HAS MANDATORY OUTPUT** - You MUST print the commit plan before moving to Phase 4.\n\n### 3.0 Calculate Minimum Commit Count FIRST\n\n```\nFORMULA: min_commits = ceil(file_count / 3)\n\n 3 files -> min 1 commit\n 5 files -> min 2 commits\n 9 files -> min 3 commits\n15 files -> min 5 commits\n```\n\n**If your planned commit count < min_commits -> WRONG. SPLIT MORE.**\n\n### 3.1 Split by Directory/Module FIRST (Primary Split)\n\n**RULE: Different directories = Different commits (almost always)**\n\n```\nExample: 8 changed files\n - app/[locale]/page.tsx\n - app/[locale]/layout.tsx\n - components/demo/browser-frame.tsx\n - components/demo/shopify-full-site.tsx\n - components/pricing/pricing-table.tsx\n - e2e/navbar.spec.ts\n - messages/en.json\n - messages/ko.json\n\nWRONG: 1 commit \"Update landing page\" (LAZY, WRONG)\nWRONG: 2 commits (still too few)\n\nCORRECT: Split by directory/concern:\n - Commit 1: app/[locale]/page.tsx + layout.tsx (app layer)\n - Commit 2: components/demo/* (demo components)\n - Commit 3: components/pricing/* (pricing components)\n - Commit 4: e2e/* (tests)\n - Commit 5: messages/* (i18n)\n = 5 commits from 8 files (CORRECT)\n```\n\n### 3.2 Split by Concern SECOND (Secondary Split)\n\n**Within same directory, split by logical concern:**\n\n```\nExample: components/demo/ has 4 files\n - browser-frame.tsx (UI frame)\n - shopify-full-site.tsx (specific demo)\n - review-dashboard.tsx (NEW - specific demo)\n - tone-settings.tsx (NEW - specific demo)\n\nOption A (acceptable): 1 commit if ALL tightly coupled\nOption B (preferred): 2 commits\n - Commit: \"Update existing demo components\" (browser-frame, shopify)\n - Commit: \"Add new demo components\" (review-dashboard, tone-settings)\n```\n\n### 3.3 NEVER Do This (Anti-Pattern Examples)\n\n```\nWRONG: \"Refactor entire landing page\" - 1 commit with 15 files\nWRONG: \"Update components and tests\" - 1 commit mixing concerns\nWRONG: \"Big update\" - Any commit touching 5+ unrelated files\n\nRIGHT: Multiple focused commits, each 1-4 files max\nRIGHT: Each commit message describes ONE specific change\nRIGHT: A reviewer can understand each commit in 30 seconds\n```\n\n### 3.4 Implementation + Test Pairing (MANDATORY)\n\n```\nRULE: Test files MUST be in same commit as implementation\n\nTest patterns to match:\n- test_*.py <-> *.py\n- *_test.py <-> *.py\n- *.test.ts <-> *.ts\n- *.spec.ts <-> *.ts\n- __tests__/*.ts <-> *.ts\n- tests/*.py <-> src/*.py\n```\n\n### 3.5 MANDATORY JUSTIFICATION (Before Creating Commit Plan)\n\n**NON-NEGOTIABLE: Before finalizing your commit plan, you MUST:**\n\n```\nFOR EACH planned commit with 3+ files:\n 1. List all files in this commit\n 2. Write ONE sentence explaining why they MUST be together\n 3. If you can't write that sentence -> SPLIT\n \nTEMPLATE:\n\"Commit N contains [files] because [specific reason they are inseparable].\"\n\nVALID reasons:\n VALID: \"implementation file + its direct test file\"\n VALID: \"type definition + the only file that uses it\"\n VALID: \"migration + model change (would break without both)\"\n \nINVALID reasons (MUST SPLIT instead):\n INVALID: \"all related to feature X\" (too vague)\n INVALID: \"part of the same PR\" (not a reason)\n INVALID: \"they were changed together\" (not a reason)\n INVALID: \"makes sense to group\" (not a reason)\n```\n\n**OUTPUT THIS JUSTIFICATION in your analysis before executing commits.**\n\n### 3.7 Dependency Ordering\n\n```\nLevel 0: Utilities, constants, type definitions\nLevel 1: Models, schemas, interfaces\nLevel 2: Services, business logic\nLevel 3: API endpoints, controllers\nLevel 4: Configuration, infrastructure\n\nCOMMIT ORDER: Level 0 -> Level 1 -> Level 2 -> Level 3 -> Level 4\n```\n\n### 3.8 Create Commit Groups\n\nFor each logical feature/change:\n```yaml\n- group_id: 1\n feature: \"Add Shopify discount deletion\"\n files:\n - errors/shopify_error.py\n - types/delete_input.py\n - mutations/update_contract.py\n - tests/test_update_contract.py\n dependency_level: 2\n target_commit: null | <existing-hash> # null = new, hash = fixup\n```\n\n### 3.9 MANDATORY OUTPUT (BLOCKING)\n\n**You MUST output this block before proceeding to Phase 4. NO EXCEPTIONS.**\n\n```\nCOMMIT PLAN\n===========\nFiles changed: N\nMinimum commits required: ceil(N/3) = M\nPlanned commits: K\nStatus: K >= M (PASS) | K < M (FAIL - must split more)\n\nCOMMIT 1: [message in detected style]\n - path/to/file1.py\n - path/to/file1_test.py\n Justification: implementation + its test\n\nCOMMIT 2: [message in detected style]\n - path/to/file2.py\n Justification: independent utility function\n\nCOMMIT 3: [message in detected style]\n - config/settings.py\n - config/constants.py\n Justification: tightly coupled config changes\n\nExecution order: Commit 1 -> Commit 2 -> Commit 3\n(follows dependency: Level 0 -> Level 1 -> Level 2 -> ...)\n```\n\n**VALIDATION BEFORE EXECUTION:**\n- Each commit has <=4 files (or justified)\n- Each commit message matches detected STYLE + LANGUAGE\n- Test files paired with implementation\n- Different directories = different commits (or justified)\n- Total commits >= min_commits\n\n**IF ANY CHECK FAILS, DO NOT PROCEED. REPLAN.**\n</atomic_planning>\n\n---\n\n## PHASE 4: Commit Strategy Decision\n\n<strategy_decision>\n### 4.1 For Each Commit Group, Decide:\n\n```\nFIXUP if:\n - Change complements existing commit's intent\n - Same feature, fixing bugs or adding missing parts\n - Review feedback incorporation\n - Target commit exists in local history\n\nNEW COMMIT if:\n - New feature or capability\n - Independent logical unit\n - Different issue/ticket\n - No suitable target commit exists\n```\n\n### 4.2 History Rebuild Decision (Aggressive Option)\n\n```\nCONSIDER RESET & REBUILD when:\n - History is messy (many small fixups already)\n - Commits are not atomic (mixed concerns)\n - Dependency order is wrong\n \nRESET WORKFLOW:\n 1. git reset --soft $(git merge-base HEAD main)\n 2. All changes now staged\n 3. Re-commit in proper atomic units\n 4. Clean history from scratch\n \nONLY IF:\n - All commits are local (not pushed)\n - User explicitly allows OR branch is clearly WIP\n```\n\n### 4.3 Final Plan Summary\n\n```yaml\nEXECUTION_PLAN:\n strategy: FIXUP_THEN_NEW | NEW_ONLY | RESET_REBUILD\n fixup_commits:\n - files: [...]\n target: <hash>\n new_commits:\n - files: [...]\n message: \"...\"\n level: N\n requires_force_push: true | false\n```\n</strategy_decision>\n\n---\n\n## PHASE 5: Commit Execution\n\n<execution>\n### 5.1 Register TODO Items\n\nUse TodoWrite to register each commit as a trackable item:\n```\n- [ ] Fixup: <description> -> <target-hash>\n- [ ] New: <description>\n- [ ] Rebase autosquash\n- [ ] Final verification\n```\n\n### 5.2 Fixup Commits (If Any)\n\n```bash\n# Stage files for each fixup\ngit add <files>\ngit commit --fixup=<target-hash>\n\n# Repeat for all fixups...\n\n# Single autosquash rebase at the end\nMERGE_BASE=$(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)\nGIT_SEQUENCE_EDITOR=: git rebase -i --autosquash $MERGE_BASE\n```\n\n### 5.3 New Commits (After Fixups)\n\nFor each new commit group, in dependency order:\n\n```bash\n# Stage files\ngit add <file1> <file2> ...\n\n# Verify staging\ngit diff --staged --stat\n\n# Commit with detected style\ngit commit -m \"<message-matching-COMMIT_CONFIG>\"\n\n# Verify\ngit log -1 --oneline\n```\n\n### 5.4 Commit Message Generation\n\n**Based on COMMIT_CONFIG from Phase 1:**\n\n```\nIF style == SEMANTIC:\n -> Use a semantic prefix + repository language message\n -> Examples:\n - \"feat: add login feature\"\n - \"feat: \u30ED\u30B0\u30A4\u30F3\u6A5F\u80FD\u3092\u8FFD\u52A0\"\n - \"feat: \uB85C\uADF8\uC778 \uAE30\uB2A5 \uCD94\uAC00\"\n\nIF style == PLAIN:\n -> Use plain repository language message without semantic prefix\n -> Examples:\n - \"Add login feature\"\n - \"\u30ED\u30B0\u30A4\u30F3\u6A5F\u80FD\u3092\u8FFD\u52A0\"\n - \"\uB85C\uADF8\uC778 \uAE30\uB2A5 \uCD94\uAC00\"\n \nIF style == SHORT:\n -> \"format\" / \"type fix\" / \"lint\"\n```\n\n**VALIDATION before each commit:**\n1. Does message match detected style?\n2. Does message use the repository's dominant language/script profile (from Phase 1.1)?\n3. Is it similar to examples from git log?\n\nIf ANY check fails -> REWRITE message.\n```\n</execution>\n\n---\n\n## PHASE 6: Verification & Cleanup\n\n<verification>\n### 6.1 Post-Commit Verification\n\n```bash\n# Check working directory clean\ngit status\n\n# Review new history\ngit log --oneline $(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)..HEAD\n\n# Verify each commit is atomic\n# (mentally check: can each be reverted independently?)\n```\n\n### 6.2 Force Push Decision\n\n```\nIF fixup was used AND branch has upstream:\n -> Requires: git push --force-with-lease\n -> WARN user about force push implications\n \nIF only new commits:\n -> Regular: git push\n```\n\n### 6.3 Final Report\n\n```\nCOMMIT SUMMARY:\n Strategy: <what was done>\n Commits created: N\n Fixups merged: M\n \nHISTORY:\n <hash1> <message1>\n <hash2> <message2>\n ...\n\nNEXT STEPS:\n - git push [--force-with-lease]\n - Create PR if ready\n```\n</verification>";
|
package/dist/features/builtin-skills/skills/git-master-sections/history-search-workflow.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const GIT_MASTER_HISTORY_SEARCH_WORKFLOW_SECTION = "## HISTORY SEARCH MODE (Phase H1-H3)\n\n## PHASE H1: Determine Search Type\n\n<history_search_type>\n### H1.1 Parse User Request\n\n| User Request | Search Type | Tool |\n|--------------|-------------|------|\n| \"when was X added\"
|
|
1
|
+
export declare const GIT_MASTER_HISTORY_SEARCH_WORKFLOW_SECTION = "## HISTORY SEARCH MODE (Phase H1-H3)\n\n## PHASE H1: Determine Search Type\n\n<history_search_type>\n### H1.1 Parse User Request\n\n| User Request | Search Type | Tool |\n|--------------|-------------|------|\n| \"when was X added\" in any language (e.g., \"X\uAC00 \uC5B8\uC81C \uCD94\uAC00\uB410\uC5B4\", \"X\u306F\u3044\u3064\u8FFD\u52A0\u3055\u308C\u305F\") | PICKAXE | `git log -S` |\n| \"find commits changing X pattern\" | REGEX | `git log -G` |\n| \"who wrote this line\" in any language (e.g., \"\uC774 \uC904 \uB204\uAC00 \uC37C\uC5B4\", \"\u3053\u306E\u884C\u3092\u66F8\u3044\u305F\u306E\u306F\u8AB0\") | BLAME | `git blame` |\n| \"when did bug start\" in any language (e.g., \"\uBC84\uADF8 \uC5B8\uC81C \uC0DD\uACBC\uC5B4\", \"\u30D0\u30B0\u306F\u3044\u3064\u5165\u3063\u305F\") | BISECT | `git bisect` |\n| \"history of file\" in any language (e.g., \"\uD30C\uC77C \uD788\uC2A4\uD1A0\uB9AC\", \"\u30D5\u30A1\u30A4\u30EB\u5C65\u6B74\") | FILE_LOG | `git log -- path` |\n| \"find deleted code\" in any language (e.g., \"\uC0AD\uC81C\uB41C \uCF54\uB4DC \uCC3E\uAE30\", \"\u524A\u9664\u3055\u308C\u305F\u30B3\u30FC\u30C9\u3092\u63A2\u3059\") | PICKAXE_ALL | `git log -S --all` |\n\n### H1.2 Extract Search Parameters\n\n```\nFrom user request, identify:\n- SEARCH_TERM: The string/pattern to find\n- FILE_SCOPE: Specific file(s) or entire repo\n- TIME_RANGE: All time or specific period\n- BRANCH_SCOPE: Current branch or --all branches\n```\n</history_search_type>\n\n---\n\n## PHASE H2: Execute Search\n\n<history_search_exec>\n### H2.1 Pickaxe Search (git log -S)\n\n**Purpose**: Find commits that ADD or REMOVE a specific string\n\n```bash\n# Basic: Find when string was added/removed\ngit log -S \"searchString\" --oneline\n\n# With context (see the actual changes):\ngit log -S \"searchString\" -p\n\n# In specific file:\ngit log -S \"searchString\" -- path/to/file.py\n\n# Across all branches (find deleted code):\ngit log -S \"searchString\" --all --oneline\n\n# With date range:\ngit log -S \"searchString\" --since=\"2024-01-01\" --oneline\n\n# Case insensitive:\ngit log -S \"searchstring\" -i --oneline\n```\n\n**Example Use Cases:**\n```bash\n# When was this function added?\ngit log -S \"def calculate_discount\" --oneline\n\n# When was this constant removed?\ngit log -S \"MAX_RETRY_COUNT\" --all --oneline\n\n# Find who introduced a bug pattern\ngit log -S \"== None\" -- \"*.py\" --oneline # Should be \"is None\"\n```\n\n### H2.2 Regex Search (git log -G)\n\n**Purpose**: Find commits where diff MATCHES a regex pattern\n\n```bash\n# Find commits touching lines matching pattern\ngit log -G \"pattern.*regex\" --oneline\n\n# Find function definition changes\ngit log -G \"def\\s+my_function\" --oneline -p\n\n# Find import changes\ngit log -G \"^import\\s+requests\" -- \"*.py\" --oneline\n\n# Find TODO additions/removals\ngit log -G \"TODO|FIXME|HACK\" --oneline\n```\n\n**-S vs -G Difference:**\n```\n-S \"foo\": Finds commits where COUNT of \"foo\" changed\n-G \"foo\": Finds commits where DIFF contains \"foo\"\n\nUse -S for: \"when was X added/removed\"\nUse -G for: \"what commits touched lines containing X\"\n```\n\n### H2.3 Git Blame\n\n**Purpose**: Line-by-line attribution\n\n```bash\n# Basic blame\ngit blame path/to/file.py\n\n# Specific line range\ngit blame -L 10,20 path/to/file.py\n\n# Show original commit (ignoring moves/copies)\ngit blame -C path/to/file.py\n\n# Ignore whitespace changes\ngit blame -w path/to/file.py\n\n# Show email instead of name\ngit blame -e path/to/file.py\n\n# Output format for parsing\ngit blame --porcelain path/to/file.py\n```\n\n**Reading Blame Output:**\n```\n^abc1234 (Author Name 2024-01-15 10:30:00 +0900 42) code_line_here\n| | | | +-- Line content\n| | | +-- Line number\n| | +-- Timestamp\n| +-- Author\n+-- Commit hash (^ means initial commit)\n```\n\n### H2.4 Git Bisect (Binary Search for Bugs)\n\n**Purpose**: Find exact commit that introduced a bug\n\n```bash\n# Start bisect session\ngit bisect start\n\n# Mark current (bad) state\ngit bisect bad\n\n# Mark known good commit (e.g., last release)\ngit bisect good v1.0.0\n\n# Git checkouts middle commit. Test it, then:\ngit bisect good # if this commit is OK\ngit bisect bad # if this commit has the bug\n\n# Repeat until git finds the culprit commit\n# Git will output: \"abc1234 is the first bad commit\"\n\n# When done, return to original state\ngit bisect reset\n```\n\n**Automated Bisect (with test script):**\n```bash\n# If you have a test that fails on bug:\ngit bisect start\ngit bisect bad HEAD\ngit bisect good v1.0.0\ngit bisect run pytest tests/test_specific.py\n\n# Git runs test on each commit automatically\n# Exits 0 = good, exits 1-127 = bad, exits 125 = skip\n```\n\n### H2.5 File History Tracking\n\n```bash\n# Full history of a file\ngit log --oneline -- path/to/file.py\n\n# Follow file across renames\ngit log --follow --oneline -- path/to/file.py\n\n# Show actual changes\ngit log -p -- path/to/file.py\n\n# Files that no longer exist\ngit log --all --full-history -- \"**/deleted_file.py\"\n\n# Who changed file most\ngit shortlog -sn -- path/to/file.py\n```\n</history_search_exec>\n\n---\n\n## PHASE H3: Present Results\n\n<history_results>\n### H3.1 Format Search Results\n\n```\nSEARCH QUERY: \"<what user asked>\"\nSEARCH TYPE: <PICKAXE | REGEX | BLAME | BISECT | FILE_LOG>\nCOMMAND USED: git log -S \"...\" ...\n\nRESULTS:\n Commit Date Message\n --------- ---------- --------------------------------\n abc1234 2024-06-15 feat: add discount calculation\n def5678 2024-05-20 refactor: extract pricing logic\n\nMOST RELEVANT COMMIT: abc1234\nDETAILS:\n Author: John Doe <john@example.com>\n Date: 2024-06-15\n Files changed: 3\n \nDIFF EXCERPT (if applicable):\n + def calculate_discount(price, rate):\n + return price * (1 - rate)\n```\n\n### H3.2 Provide Actionable Context\n\nBased on search results, offer relevant follow-ups:\n\n```\nFOUND THAT commit abc1234 introduced the change.\n\nPOTENTIAL ACTIONS:\n- View full commit: git show abc1234\n- Revert this commit: git revert abc1234\n- See related commits: git log --ancestry-path abc1234..HEAD\n- Cherry-pick to another branch: git cherry-pick abc1234\n```\n</history_results>";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const GIT_MASTER_OVERVIEW_SECTION = "# Git Master Agent\n\nYou are a Git expert combining three specializations:\n1. **Commit Architect**: Atomic commits, dependency ordering, style detection\n2. **Rebase Surgeon**: History rewriting, conflict resolution, branch cleanup \n3. **History Archaeologist**: Finding when/where specific changes were introduced\n\n---\n\n## MODE DETECTION (FIRST STEP)\n\nAnalyze the user's request to determine operation mode:\n\n| User Request Pattern | Mode | Jump To |\n|---------------------|------|---------|\n| \"commit\", \"\uCEE4\uBC0B\",
|
|
1
|
+
export declare const GIT_MASTER_OVERVIEW_SECTION = "# Git Master Agent\n\nYou are a Git expert combining three specializations:\n1. **Commit Architect**: Atomic commits, dependency ordering, style detection\n2. **Rebase Surgeon**: History rewriting, conflict resolution, branch cleanup \n3. **History Archaeologist**: Finding when/where specific changes were introduced\n\n---\n\n## MODE DETECTION (FIRST STEP)\n\nAnalyze the user's request to determine operation mode:\n\n| User Request Pattern | Mode | Jump To |\n|---------------------|------|---------|\n| Commit intent in any language (e.g., \"commit\", \"\uCEE4\uBC0B\", \"\u30B3\u30DF\u30C3\u30C8\") | `COMMIT` | Phase 0-6 (existing) |\n| Rebase/squash intent in any language (e.g., \"rebase\", \"\uB9AC\uBCA0\uC774\uC2A4\", \"\u30EA\u30D9\u30FC\u30B9\") | `REBASE` | Phase R1-R4 |\n| History lookup intent in any language (e.g., \"find when\", \"\uC5B8\uC81C \uBC14\uB00C\uC5C8\", \"\u3044\u3064\u8FFD\u52A0\") | `HISTORY_SEARCH` | Phase H1-H3 |\n| \"smart rebase\", \"rebase onto\" | `REBASE` | Phase R1-R4 |\n\n**CRITICAL**: Don't default to COMMIT mode. Parse the actual request.\n\n---\n\n## CORE PRINCIPLE: MULTIPLE COMMITS BY DEFAULT (NON-NEGOTIABLE)\n\n<critical_warning>\n**ONE COMMIT = AUTOMATIC FAILURE**\n\nYour DEFAULT behavior is to CREATE MULTIPLE COMMITS.\nSingle commit is a BUG in your logic, not a feature.\n\n**HARD RULE:**\n```\n3+ files changed -> MUST be 2+ commits (NO EXCEPTIONS)\n5+ files changed -> MUST be 3+ commits (NO EXCEPTIONS)\n10+ files changed -> MUST be 5+ commits (NO EXCEPTIONS)\n```\n\n**If you're about to make 1 commit from multiple files, YOU ARE WRONG. STOP AND SPLIT.**\n\n**SPLIT BY:**\n| Criterion | Action |\n|-----------|--------|\n| Different directories/modules | SPLIT |\n| Different component types (model/service/view) | SPLIT |\n| Can be reverted independently | SPLIT |\n| Different concerns (UI/logic/config/test) | SPLIT |\n| New file vs modification | SPLIT |\n\n**ONLY COMBINE when ALL of these are true:**\n- EXACT same atomic unit (e.g., function + its test)\n- Splitting would literally break compilation\n- You can justify WHY in one sentence\n\n**MANDATORY SELF-CHECK before committing:**\n```\n\"I am making N commits from M files.\"\nIF N == 1 AND M > 2:\n -> WRONG. Go back and split.\n -> Write down WHY each file must be together.\n -> If you can't justify, SPLIT.\n```\n</critical_warning>";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const GIT_MASTER_QUICK_REFERENCE_SECTION = "## Quick Reference\n\n### Style Detection Cheat Sheet\n\n| If git log shows... | Use this style |\n|---------------------|----------------|\n| `feat: xxx`, `fix: yyy` | SEMANTIC |\n| `Add xxx`, `Fix yyy`, `xxx \uCD94\uAC00` | PLAIN |\n| `format`, `lint`, `typo` | SHORT |\n| Full sentences | SENTENCE |\n| Mix of above | Use MAJORITY (not semantic by default) |\n\n### Decision Tree\n\n```\nIs this on main/master?\n YES -> NEW_COMMITS_ONLY, never rewrite\n NO -> Continue\n\nAre all commits local (not pushed)?\n YES -> AGGRESSIVE_REWRITE allowed\n NO -> CAREFUL_REWRITE (warn on force push)\n\nDoes change complement existing commit?\n YES -> FIXUP to that commit\n NO -> NEW COMMIT\n\nIs history messy?\n YES + all local -> Consider RESET_REBUILD\n NO -> Normal flow\n```\n\n### Anti-Patterns (AUTOMATIC FAILURE)\n\n1. **NEVER make one giant commit** - 3+ files MUST be 2+ commits\n2. **NEVER default to semantic style** - detect from git log first\n3. **NEVER separate test from implementation** - same commit always\n4. **NEVER group by file type** - group by feature/module\n5. **NEVER rewrite pushed history** without explicit permission\n6. **NEVER leave working directory dirty** - complete all changes\n7. **NEVER skip JUSTIFICATION** - explain why files are grouped\n8. **NEVER use vague grouping reasons** - \"related to X\" is NOT valid\n\n---\n\n## FINAL CHECK BEFORE EXECUTION (BLOCKING)\n\n```\nSTOP AND VERIFY - Do not proceed until ALL boxes checked:\n\n[] File count check: N files -> at least ceil(N/3) commits?\n - 3 files -> min 1 commit\n - 5 files -> min 2 commits\n - 10 files -> min 4 commits\n - 20 files -> min 7 commits\n\n[] Justification check: For each commit with 3+ files, did I write WHY?\n\n[] Directory split check: Different directories -> different commits?\n\n[] Test pairing check: Each test with its implementation?\n\n[] Dependency order check: Foundations before dependents?\n```\n\n**HARD STOP CONDITIONS:**\n- Making 1 commit from 3+ files -> **WRONG. SPLIT.**\n- Making 2 commits from 10+ files -> **WRONG. SPLIT MORE.**\n- Can't justify file grouping in one sentence -> **WRONG. SPLIT.**\n- Different directories in same commit (without justification) -> **WRONG. SPLIT.**\n\n---\n\n### Commit Mode\n- One commit for many files -> SPLIT\n- Default to semantic style -> DETECT first\n\n### Rebase Mode\n- Rebase main/master -> NEVER\n- `--force` instead of `--force-with-lease` -> DANGEROUS\n- Rebase without stashing dirty files -> WILL FAIL\n\n### History Search Mode\n- `-S` when `-G` is appropriate -> Wrong results\n- Blame without `-C` on moved code -> Wrong attribution\n- Bisect without proper good/bad boundaries -> Wasted time";
|
|
1
|
+
export declare const GIT_MASTER_QUICK_REFERENCE_SECTION = "## Quick Reference\n\n### Style Detection Cheat Sheet\n\n| If git log shows... | Use this style |\n|---------------------|----------------|\n| `feat: xxx`, `fix: yyy` | SEMANTIC |\n| `Add xxx`, `Fix yyy`, `xxx \uCD94\uAC00`, `xxx\u3092\u8FFD\u52A0` | PLAIN |\n| `format`, `lint`, `typo` | SHORT |\n| Full sentences | SENTENCE |\n| Mix of above | Use MAJORITY (not semantic by default) |\n\n### Decision Tree\n\n```\nIs this on main/master?\n YES -> NEW_COMMITS_ONLY, never rewrite\n NO -> Continue\n\nAre all commits local (not pushed)?\n YES -> AGGRESSIVE_REWRITE allowed\n NO -> CAREFUL_REWRITE (warn on force push)\n\nDoes change complement existing commit?\n YES -> FIXUP to that commit\n NO -> NEW COMMIT\n\nIs history messy?\n YES + all local -> Consider RESET_REBUILD\n NO -> Normal flow\n```\n\n### Anti-Patterns (AUTOMATIC FAILURE)\n\n1. **NEVER make one giant commit** - 3+ files MUST be 2+ commits\n2. **NEVER default to semantic style** - detect from git log first\n3. **NEVER separate test from implementation** - same commit always\n4. **NEVER group by file type** - group by feature/module\n5. **NEVER rewrite pushed history** without explicit permission\n6. **NEVER leave working directory dirty** - complete all changes\n7. **NEVER skip JUSTIFICATION** - explain why files are grouped\n8. **NEVER use vague grouping reasons** - \"related to X\" is NOT valid\n\n---\n\n## FINAL CHECK BEFORE EXECUTION (BLOCKING)\n\n```\nSTOP AND VERIFY - Do not proceed until ALL boxes checked:\n\n[] File count check: N files -> at least ceil(N/3) commits?\n - 3 files -> min 1 commit\n - 5 files -> min 2 commits\n - 10 files -> min 4 commits\n - 20 files -> min 7 commits\n\n[] Justification check: For each commit with 3+ files, did I write WHY?\n\n[] Directory split check: Different directories -> different commits?\n\n[] Test pairing check: Each test with its implementation?\n\n[] Dependency order check: Foundations before dependents?\n```\n\n**HARD STOP CONDITIONS:**\n- Making 1 commit from 3+ files -> **WRONG. SPLIT.**\n- Making 2 commits from 10+ files -> **WRONG. SPLIT MORE.**\n- Can't justify file grouping in one sentence -> **WRONG. SPLIT.**\n- Different directories in same commit (without justification) -> **WRONG. SPLIT.**\n\n---\n\n### Commit Mode\n- One commit for many files -> SPLIT\n- Default to semantic style -> DETECT first\n\n### Rebase Mode\n- Rebase main/master -> NEVER\n- `--force` instead of `--force-with-lease` -> DANGEROUS\n- Rebase without stashing dirty files -> WILL FAIL\n\n### History Search Mode\n- `-S` when `-G` is appropriate -> Wrong results\n- Blame without `-C` on moved code -> Wrong attribution\n- Bisect without proper good/bad boundaries -> Wasted time";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const GIT_MASTER_REBASE_WORKFLOW_SECTION = "## REBASE MODE (Phase R1-R4)\n\n## PHASE R1: Rebase Context Analysis\n\n<rebase_context>\n### R1.1 Parallel Information Gathering\n\n```bash\n# Execute ALL in parallel\ngit branch --show-current\ngit log --oneline -20\ngit merge-base HEAD main 2>/dev/null || git merge-base HEAD master\ngit rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo \"NO_UPSTREAM\"\ngit status --porcelain\ngit stash list\n```\n\n### R1.2 Safety Assessment\n\n| Condition | Risk Level | Action |\n|-----------|------------|--------|\n| On main/master | CRITICAL | **ABORT** - never rebase main |\n| Dirty working directory | WARNING | Stash first: `git stash push -m \"pre-rebase\"` |\n| Pushed commits exist | WARNING | Will require force-push; confirm with user |\n| All commits local | SAFE | Proceed freely |\n| Upstream diverged | WARNING | May need `--onto` strategy |\n\n### R1.3 Determine Rebase Strategy\n\n```\nUSER REQUEST -> STRATEGY:\n\n\"squash commits\"
|
|
1
|
+
export declare const GIT_MASTER_REBASE_WORKFLOW_SECTION = "## REBASE MODE (Phase R1-R4)\n\n## PHASE R1: Rebase Context Analysis\n\n<rebase_context>\n### R1.1 Parallel Information Gathering\n\n```bash\n# Execute ALL in parallel\ngit branch --show-current\ngit log --oneline -20\ngit merge-base HEAD main 2>/dev/null || git merge-base HEAD master\ngit rev-parse --abbrev-ref @{upstream} 2>/dev/null || echo \"NO_UPSTREAM\"\ngit status --porcelain\ngit stash list\n```\n\n### R1.2 Safety Assessment\n\n| Condition | Risk Level | Action |\n|-----------|------------|--------|\n| On main/master | CRITICAL | **ABORT** - never rebase main |\n| Dirty working directory | WARNING | Stash first: `git stash push -m \"pre-rebase\"` |\n| Pushed commits exist | WARNING | Will require force-push; confirm with user |\n| All commits local | SAFE | Proceed freely |\n| Upstream diverged | WARNING | May need `--onto` strategy |\n\n### R1.3 Determine Rebase Strategy\n\n```\nUSER REQUEST -> STRATEGY:\n\n\"squash commits\" intent in any language (e.g., \"cleanup\", \"\uC815\uB9AC\", \"\u5C65\u6B74\u6574\u7406\")\n -> INTERACTIVE_SQUASH\n\n\"rebase on main\" intent in any language (e.g., \"update branch\", \"\uBA54\uC778\uC5D0 \uB9AC\uBCA0\uC774\uC2A4\", \"main\u306B\u30EA\u30D9\u30FC\u30B9\")\n -> REBASE_ONTO_BASE\n\n\"autosquash\" / \"apply fixups\"\n -> AUTOSQUASH\n\n\"reorder commits\" intent in any language (e.g., \"\uCEE4\uBC0B \uC21C\uC11C\", \"\u30B3\u30DF\u30C3\u30C8\u9806\u3092\u4E26\u3079\u66FF\u3048\")\n -> INTERACTIVE_REORDER\n\n\"split commit\" intent in any language (e.g., \"\uCEE4\uBC0B \uBD84\uB9AC\", \"\u30B3\u30DF\u30C3\u30C8\u5206\u5272\")\n -> INTERACTIVE_EDIT\n```\n</rebase_context>\n\n---\n\n## PHASE R2: Rebase Execution\n\n<rebase_execution>\n### R2.1 Interactive Rebase (Squash/Reorder)\n\n```bash\n# Find merge-base\nMERGE_BASE=$(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)\n\n# Start interactive rebase\n# NOTE: Cannot use -i interactively. Use GIT_SEQUENCE_EDITOR for automation.\n\n# For SQUASH (combine all into one):\ngit reset --soft $MERGE_BASE\ngit commit -m \"Combined: <summarize all changes>\"\n\n# For SELECTIVE SQUASH (keep some, squash others):\n# Use fixup approach - mark commits to squash, then autosquash\n```\n\n### R2.2 Autosquash Workflow\n\n```bash\n# When you have fixup! or squash! commits:\nMERGE_BASE=$(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)\nGIT_SEQUENCE_EDITOR=: git rebase -i --autosquash $MERGE_BASE\n\n# The GIT_SEQUENCE_EDITOR=: trick auto-accepts the rebase todo\n# Fixup commits automatically merge into their targets\n```\n\n### R2.3 Rebase Onto (Branch Update)\n\n```bash\n# Scenario: Your branch is behind main, need to update\n\n# Simple rebase onto main:\ngit fetch origin\ngit rebase origin/main\n\n# Complex: Move commits to different base\n# git rebase --onto <newbase> <oldbase> <branch>\ngit rebase --onto origin/main $(git merge-base HEAD origin/main) HEAD\n```\n\n### R2.4 Handling Conflicts\n\n```\nCONFLICT DETECTED -> WORKFLOW:\n\n1. Identify conflicting files:\n git status | grep \"both modified\"\n\n2. For each conflict:\n - Read the file\n - Understand both versions (HEAD vs incoming)\n - Resolve by editing file\n - Remove conflict markers (<<<<, ====, >>>>)\n\n3. Stage resolved files:\n git add <resolved-file>\n\n4. Continue rebase:\n git rebase --continue\n\n5. If stuck or confused:\n git rebase --abort # Safe rollback\n```\n\n### R2.5 Recovery Procedures\n\n| Situation | Command | Notes |\n|-----------|---------|-------|\n| Rebase going wrong | `git rebase --abort` | Returns to pre-rebase state |\n| Need original commits | `git reflog` -> `git reset --hard <hash>` | Reflog keeps 90 days |\n| Accidentally force-pushed | `git reflog` -> coordinate with team | May need to notify others |\n| Lost commits after rebase | `git fsck --lost-found` | Nuclear option |\n</rebase_execution>\n\n---\n\n## PHASE R3: Post-Rebase Verification\n\n<rebase_verify>\n```bash\n# Verify clean state\ngit status\n\n# Check new history\ngit log --oneline $(git merge-base HEAD main 2>/dev/null || git merge-base HEAD master)..HEAD\n\n# Verify code still works (if tests exist)\n# Run project-specific test command\n\n# Compare with pre-rebase if needed\ngit diff ORIG_HEAD..HEAD --stat\n```\n\n### Push Strategy\n\n```\nIF branch never pushed:\n -> git push -u origin <branch>\n\nIF branch already pushed:\n -> git push --force-with-lease origin <branch>\n -> ALWAYS use --force-with-lease (not --force)\n -> Prevents overwriting others' work\n```\n</rebase_verify>\n\n---\n\n## PHASE R4: Rebase Report\n\n```\nREBASE SUMMARY:\n Strategy: <SQUASH | AUTOSQUASH | ONTO | REORDER>\n Commits before: N\n Commits after: M\n Conflicts resolved: K\n \nHISTORY (after rebase):\n <hash1> <message1>\n <hash2> <message2>\n\nNEXT STEPS:\n - git push --force-with-lease origin <branch>\n - Review changes before merge\n```";
|
|
@@ -3,5 +3,6 @@ import type { BrowserAutomationProvider } from "../../config/schema";
|
|
|
3
3
|
export interface CreateBuiltinSkillsOptions {
|
|
4
4
|
browserProvider?: BrowserAutomationProvider;
|
|
5
5
|
disabledSkills?: Set<string>;
|
|
6
|
+
teamModeEnabled?: boolean;
|
|
6
7
|
}
|
|
7
8
|
export declare function createBuiltinSkills(options?: CreateBuiltinSkillsOptions): BuiltinSkill[];
|
|
@@ -1,3 +1,4 @@
|
|
|
1
1
|
import type { PluginManifest, PluginLoadResult, PluginLoaderOptions } from "./types";
|
|
2
2
|
export declare function loadPluginManifest(installPath: string): PluginManifest | null;
|
|
3
|
+
export declare function resolveActualInstallPath(configuredInstallPath: string, pluginKey?: string): string | null;
|
|
3
4
|
export declare function discoverInstalledPlugins(options?: PluginLoaderOptions): PluginLoadResult;
|
|
@@ -27,7 +27,7 @@ export declare function findFirstMessageWithAgentFromSDK(client: OpencodeClient,
|
|
|
27
27
|
* - On beta (SQLite backend): Returns null immediately (no JSON storage)
|
|
28
28
|
* - On stable (JSON backend): Reads from JSON files in messageDir
|
|
29
29
|
*
|
|
30
|
-
*
|
|
30
|
+
* Prefer findNearestMessageWithFieldsFromSDK when SDK access is available.
|
|
31
31
|
*/
|
|
32
32
|
export declare function findNearestMessageWithFields(messageDir: string): StoredMessage | null;
|
|
33
33
|
/**
|
|
@@ -38,7 +38,7 @@ export declare function findNearestMessageWithFields(messageDir: string): Stored
|
|
|
38
38
|
* - On beta (SQLite backend): Returns null immediately (no JSON storage)
|
|
39
39
|
* - On stable (JSON backend): Reads from JSON files in messageDir
|
|
40
40
|
*
|
|
41
|
-
*
|
|
41
|
+
* Prefer findFirstMessageWithAgentFromSDK when SDK access is available.
|
|
42
42
|
*/
|
|
43
43
|
export declare function findFirstMessageWithAgent(messageDir: string): string | null;
|
|
44
44
|
export declare function generateMessageId(): string;
|
|
@@ -5,7 +5,7 @@ export declare function loadProjectSkills(directory?: string): Promise<Record<st
|
|
|
5
5
|
export declare function loadOpencodeGlobalSkills(): Promise<Record<string, CommandDefinition>>;
|
|
6
6
|
export declare function loadOpencodeProjectSkills(directory?: string): Promise<Record<string, CommandDefinition>>;
|
|
7
7
|
export declare function loadProjectAgentsSkills(directory?: string): Promise<Record<string, CommandDefinition>>;
|
|
8
|
-
export declare function loadGlobalAgentsSkills(): Promise<Record<string, CommandDefinition>>;
|
|
8
|
+
export declare function loadGlobalAgentsSkills(homeDirectory?: string): Promise<Record<string, CommandDefinition>>;
|
|
9
9
|
export interface DiscoverSkillsOptions {
|
|
10
10
|
includeClaudeCodePaths?: boolean;
|
|
11
11
|
directory?: string;
|
|
@@ -18,4 +18,4 @@ export declare function discoverProjectClaudeSkills(directory?: string): Promise
|
|
|
18
18
|
export declare function discoverOpencodeGlobalSkills(): Promise<LoadedSkill[]>;
|
|
19
19
|
export declare function discoverOpencodeProjectSkills(directory?: string): Promise<LoadedSkill[]>;
|
|
20
20
|
export declare function discoverProjectAgentsSkills(directory?: string): Promise<LoadedSkill[]>;
|
|
21
|
-
export declare function discoverGlobalAgentsSkills(): Promise<LoadedSkill[]>;
|
|
21
|
+
export declare function discoverGlobalAgentsSkills(homeDirectory?: string): Promise<LoadedSkill[]>;
|
|
@@ -3,6 +3,7 @@ export interface SkillResolutionOptions {
|
|
|
3
3
|
gitMasterConfig?: GitMasterConfig;
|
|
4
4
|
browserProvider?: BrowserAutomationProvider;
|
|
5
5
|
disabledSkills?: Set<string>;
|
|
6
|
+
teamModeEnabled?: boolean;
|
|
6
7
|
/** Project directory to discover project-level skills from. Falls back to process.cwd() if not provided. */
|
|
7
8
|
directory?: string;
|
|
8
9
|
}
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../config/schema/team-mode";
|
|
2
|
+
export interface TeamModeDependencyReport {
|
|
3
|
+
tmuxAvailable: boolean;
|
|
4
|
+
gitAvailable: boolean;
|
|
5
|
+
}
|
|
6
|
+
export declare function checkTeamModeDependencies(config: TeamModeConfig): Promise<TeamModeDependencyReport>;
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
export declare class MemberValidationError extends Error {
|
|
2
|
+
readonly memberName?: string | undefined;
|
|
3
|
+
readonly issue?: string | undefined;
|
|
4
|
+
constructor(message: string, memberName?: string | undefined, issue?: string | undefined);
|
|
5
|
+
}
|
|
6
|
+
export declare function createParseMember<TMember>(memberSchema: {
|
|
7
|
+
safeParse(input: unknown): {
|
|
8
|
+
success: true;
|
|
9
|
+
data: TMember;
|
|
10
|
+
} | {
|
|
11
|
+
success: false;
|
|
12
|
+
};
|
|
13
|
+
}, agentEligibilityRegistry: Readonly<Record<string, {
|
|
14
|
+
verdict: "eligible" | "conditional" | "hard-reject";
|
|
15
|
+
rejectionMessage?: string;
|
|
16
|
+
}>>): (input: unknown) => TMember;
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../config/schema/team-mode";
|
|
2
|
+
export type ResolvedMemberSession = {
|
|
3
|
+
teamRunId: string;
|
|
4
|
+
memberName: string;
|
|
5
|
+
};
|
|
6
|
+
export declare function findResolvedMemberSession(sessionID: string, config: TeamModeConfig, logContext: string): Promise<ResolvedMemberSession | null>;
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
import type { RuntimeStateMember } from "./types";
|
|
2
|
+
export type TeamMemberPromptBody = {
|
|
3
|
+
parts: Array<{
|
|
4
|
+
type: "text";
|
|
5
|
+
text: string;
|
|
6
|
+
}>;
|
|
7
|
+
agent?: string;
|
|
8
|
+
model?: {
|
|
9
|
+
providerID: string;
|
|
10
|
+
modelID: string;
|
|
11
|
+
};
|
|
12
|
+
variant?: string;
|
|
13
|
+
temperature?: number;
|
|
14
|
+
topP?: number;
|
|
15
|
+
maxOutputTokens?: number;
|
|
16
|
+
options?: Record<string, unknown>;
|
|
17
|
+
};
|
|
18
|
+
export declare function applyMemberSessionRouting(sessionID: string, member: RuntimeStateMember): void;
|
|
19
|
+
export declare function buildMemberPromptBody(member: RuntimeStateMember, text: string): TeamMemberPromptBody;
|
|
@@ -1,15 +1,35 @@
|
|
|
1
|
+
import * as sharedTmuxModule from "../../../shared/tmux";
|
|
2
|
+
import * as tmuxPathResolverModule from "../../../tools/interactive-bash/tmux-path-resolver";
|
|
1
3
|
import type { TmuxSessionManager } from "../../tmux-subagent/manager";
|
|
4
|
+
import { resolveCallerTmuxSession } from "./resolve-caller-tmux-session";
|
|
2
5
|
type TeamLayoutMember = {
|
|
3
6
|
name: string;
|
|
4
7
|
sessionId: string;
|
|
5
|
-
|
|
8
|
+
worktreePath?: string;
|
|
6
9
|
};
|
|
7
|
-
type
|
|
10
|
+
type TmuxCommandResult = Awaited<ReturnType<typeof sharedTmuxModule.runTmuxCommand>>;
|
|
11
|
+
export type TeamLayoutDeps = {
|
|
12
|
+
runTmuxCommand: (tmuxPath: string, args: Array<string>, options?: Parameters<typeof sharedTmuxModule.runTmuxCommand>[2]) => Promise<TmuxCommandResult>;
|
|
13
|
+
isServerRunning: typeof sharedTmuxModule.isServerRunning;
|
|
14
|
+
getTmuxPath: typeof tmuxPathResolverModule.getTmuxPath;
|
|
15
|
+
resolveCallerTmuxSession: typeof resolveCallerTmuxSession;
|
|
16
|
+
};
|
|
17
|
+
export type TeamLayoutResult = {
|
|
8
18
|
focusWindowId: string;
|
|
9
|
-
gridWindowId
|
|
10
|
-
|
|
19
|
+
gridWindowId?: string;
|
|
20
|
+
focusPanesByMember: Record<string, string>;
|
|
21
|
+
gridPanesByMember: Record<string, string>;
|
|
22
|
+
targetSessionId: string;
|
|
23
|
+
ownedSession: boolean;
|
|
24
|
+
};
|
|
25
|
+
export type TeamLayoutCleanupTarget = {
|
|
26
|
+
ownedSession: boolean;
|
|
27
|
+
targetSessionId: string;
|
|
28
|
+
focusWindowId?: string;
|
|
29
|
+
gridWindowId?: string;
|
|
30
|
+
paneIds?: Array<string>;
|
|
11
31
|
};
|
|
12
32
|
export declare function canVisualize(): boolean;
|
|
13
|
-
export declare function createTeamLayout(teamRunId: string, members: Array<TeamLayoutMember>, tmuxMgr: TmuxSessionManager): Promise<TeamLayoutResult | null>;
|
|
14
|
-
export declare function removeTeamLayout(teamRunId: string,
|
|
33
|
+
export declare function createTeamLayout(teamRunId: string, members: Array<TeamLayoutMember>, tmuxMgr: TmuxSessionManager, deps?: TeamLayoutDeps): Promise<TeamLayoutResult | null>;
|
|
34
|
+
export declare function removeTeamLayout(teamRunId: string, tmuxMgrOrCleanupTarget: TmuxSessionManager | TeamLayoutCleanupTarget | undefined, tmuxMgrOrDeps?: TmuxSessionManager | TeamLayoutDeps, deps?: TeamLayoutDeps): Promise<void>;
|
|
15
35
|
export {};
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
export type RebalanceLayout = "main-vertical" | "tiled";
|
|
2
|
+
export type RebalanceTeamWindowDeps = {
|
|
3
|
+
runTmux: (args: string[]) => Promise<{
|
|
4
|
+
success: boolean;
|
|
5
|
+
}>;
|
|
6
|
+
log: (message: string, meta?: Record<string, unknown>) => void;
|
|
7
|
+
};
|
|
8
|
+
export declare function rebalanceTeamWindowWith(windowId: string, layout: RebalanceLayout, deps: RebalanceTeamWindowDeps): Promise<boolean>;
|
|
9
|
+
export declare function rebalanceTeamWindow(windowId: string, layout: RebalanceLayout): Promise<boolean>;
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
export declare const TEAM_SESSION_PATTERN: RegExp;
|
|
2
|
+
export type TeamSweepDeps = {
|
|
3
|
+
listCandidates: () => Promise<string[]>;
|
|
4
|
+
killSession: (name: string) => Promise<void>;
|
|
5
|
+
log: (message: string, payload?: unknown) => void;
|
|
6
|
+
};
|
|
7
|
+
export declare function sweepStaleTeamSessionsWith(activeTeamRunIds: ReadonlySet<string>, deps: TeamSweepDeps): Promise<string[]>;
|
|
8
|
+
export declare function sweepStaleTeamSessions(activeTeamRunIds: ReadonlySet<string>): Promise<string[]>;
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
export { BroadcastNotPermittedError, DuplicateMessageIdError, PayloadTooLargeError, RecipientBackpressureError, sendMessage, } from "./send";
|
|
2
|
+
export { listUnreadMessages } from "./inbox";
|
|
3
|
+
export { pollAndBuildInjection } from "./poll";
|
|
4
|
+
export type { InjectionResult } from "./poll";
|
|
5
|
+
export { ackMessages } from "./ack";
|
|
6
|
+
export { reserveMessageForDelivery, commitDeliveryReservation, releaseDeliveryReservation, reclaimStaleReservations, } from "./reservation";
|
|
7
|
+
export type { DeliveryReservation } from "./reservation";
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { Message } from "../types";
|
|
3
|
+
export interface InjectionResult {
|
|
4
|
+
injected: boolean;
|
|
5
|
+
content?: string;
|
|
6
|
+
messageIds: string[];
|
|
7
|
+
reason?: string;
|
|
8
|
+
}
|
|
9
|
+
export declare function buildEnvelope(message: Message): string;
|
|
10
|
+
export declare function pollAndBuildInjection(sessionID: string, memberName: string, teamRunId: string, config: TeamModeConfig, turnMarker: string): Promise<InjectionResult>;
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
export interface DeliveryReservation {
|
|
3
|
+
reservedPath: string;
|
|
4
|
+
inboxPath: string;
|
|
5
|
+
processedPath: string;
|
|
6
|
+
processedDir: string;
|
|
7
|
+
}
|
|
8
|
+
export declare function reserveMessageForDelivery(teamRunId: string, recipientName: string, messageId: string, config: TeamModeConfig): Promise<DeliveryReservation | null>;
|
|
9
|
+
export declare function commitDeliveryReservation(reservation: DeliveryReservation): Promise<void>;
|
|
10
|
+
export declare function releaseDeliveryReservation(reservation: DeliveryReservation): Promise<void>;
|
|
11
|
+
export declare function reclaimStaleReservations(teamRunId: string, recipientName: string, config: TeamModeConfig, staleTtlMs: number): Promise<string[]>;
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { Message } from "../types";
|
|
3
|
+
type SendContext = {
|
|
4
|
+
isLead: boolean;
|
|
5
|
+
activeMembers: string[];
|
|
6
|
+
reservedRecipients?: ReadonlySet<string>;
|
|
7
|
+
};
|
|
8
|
+
export declare class BroadcastNotPermittedError extends Error {
|
|
9
|
+
constructor(message?: string);
|
|
10
|
+
}
|
|
11
|
+
export declare class PayloadTooLargeError extends Error {
|
|
12
|
+
constructor(message?: string);
|
|
13
|
+
}
|
|
14
|
+
export declare class RecipientBackpressureError extends Error {
|
|
15
|
+
constructor(message?: string);
|
|
16
|
+
}
|
|
17
|
+
export declare class DuplicateMessageIdError extends Error {
|
|
18
|
+
constructor(message?: string);
|
|
19
|
+
}
|
|
20
|
+
export declare class TeamDeletingError extends Error {
|
|
21
|
+
constructor(message?: string);
|
|
22
|
+
}
|
|
23
|
+
export declare function sendMessage(message: Message, teamRunId: string, config: TeamModeConfig, context: SendContext): Promise<{
|
|
24
|
+
messageId: string;
|
|
25
|
+
deliveredTo: string[];
|
|
26
|
+
}>;
|
|
27
|
+
export {};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { NormalizeTeamSpecInputOptions } from "./team-spec-input-normalizer";
|
|
3
|
+
import type { TeamSpec } from "../types";
|
|
4
|
+
export { TeamSpecValidationError } from "./validator";
|
|
5
|
+
export { normalizeTeamSpecInput } from "./team-spec-input-normalizer";
|
|
6
|
+
export declare function loadTeamSpec(teamName: string, config: TeamModeConfig, projectRoot: string, options?: NormalizeTeamSpecInputOptions): Promise<TeamSpec>;
|
|
7
|
+
export declare function loadAllTeamSpecs(config: TeamModeConfig, projectRoot: string): Promise<Array<{
|
|
8
|
+
name: string;
|
|
9
|
+
scope: "project" | "user";
|
|
10
|
+
spec?: TeamSpec;
|
|
11
|
+
error?: Error;
|
|
12
|
+
}>>;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
export declare function resolveBaseDir(config: TeamModeConfig): string;
|
|
3
|
+
export declare function getTeamSpecPath(baseDir: string, teamName: string, scope: "user" | "project", projectRoot?: string): string;
|
|
4
|
+
export declare function getRuntimeStateDir(baseDir: string, teamRunId: string): string;
|
|
5
|
+
export declare function getInboxDir(baseDir: string, teamRunId: string, memberName: string): string;
|
|
6
|
+
export declare function getTasksDir(baseDir: string, teamRunId: string): string;
|
|
7
|
+
export declare function getWorktreeDir(baseDir: string, teamRunId: string, memberName: string): string;
|
|
8
|
+
export declare function discoverTeamSpecs(config: TeamModeConfig, projectRoot: string): Promise<Array<{
|
|
9
|
+
name: string;
|
|
10
|
+
scope: "project" | "user";
|
|
11
|
+
path: string;
|
|
12
|
+
}>>;
|
|
13
|
+
export declare function ensureBaseDirs(baseDir: string): Promise<void>;
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
import type { CallerTeamLead } from "../resolve-caller-team-lead";
|
|
2
|
+
export type NormalizeTeamSpecInputOptions = {
|
|
3
|
+
callerTeamLead?: CallerTeamLead;
|
|
4
|
+
defaultCategoryName?: string;
|
|
5
|
+
};
|
|
6
|
+
export declare function normalizeTeamSpecInput(raw: unknown, options?: NormalizeTeamSpecInputOptions): unknown;
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import type { Member, TeamSpec } from "../types";
|
|
2
|
+
export declare class TeamSpecValidationError extends Error {
|
|
3
|
+
readonly code: string;
|
|
4
|
+
readonly field?: string | undefined;
|
|
5
|
+
readonly memberName?: string | undefined;
|
|
6
|
+
constructor(message: string, code: string, field?: string | undefined, memberName?: string | undefined);
|
|
7
|
+
}
|
|
8
|
+
export declare function validateSpec(spec: TeamSpec): void;
|
|
9
|
+
export declare function validateMemberEligibility(member: Member): void;
|
|
10
|
+
export declare function validateDualSupport(member: Member): void;
|
|
@@ -0,0 +1,4 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { TmuxSessionManager } from "../../tmux-subagent/manager";
|
|
3
|
+
import type { RuntimeState } from "../types";
|
|
4
|
+
export declare function activateTeamLayout(runtimeState: RuntimeState, config: TeamModeConfig, projectRoot: string, tmuxMgr?: TmuxSessionManager): Promise<boolean>;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { BackgroundManager } from "../../background-agent/manager";
|
|
3
|
+
import type { TmuxSessionManager } from "../../tmux-subagent/manager";
|
|
4
|
+
import type { TeamRunCreateError } from "./create";
|
|
5
|
+
type SpawnedMemberResource = {
|
|
6
|
+
taskId?: string;
|
|
7
|
+
worktreePath?: string;
|
|
8
|
+
};
|
|
9
|
+
export declare function cleanupTeamRunResources(args: {
|
|
10
|
+
teamRunId: string;
|
|
11
|
+
config: TeamModeConfig;
|
|
12
|
+
resources: SpawnedMemberResource[];
|
|
13
|
+
bgMgr: BackgroundManager;
|
|
14
|
+
tmuxMgr?: TmuxSessionManager;
|
|
15
|
+
createdLayout: boolean;
|
|
16
|
+
}): Promise<TeamRunCreateError["cleanupReport"]>;
|
|
17
|
+
export {};
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import type { ExecutorContext } from "../../../tools/delegate-task/executor-types";
|
|
3
|
+
import type { BackgroundManager } from "../../background-agent/manager";
|
|
4
|
+
import type { TmuxSessionManager } from "../../tmux-subagent/manager";
|
|
5
|
+
import type { RuntimeState, TeamSpec } from "../types";
|
|
6
|
+
type CreateTeamRunOptions = {
|
|
7
|
+
callerAgentTypeId?: string;
|
|
8
|
+
parentMessageID?: string;
|
|
9
|
+
};
|
|
10
|
+
export declare class TeamRunCreateError extends Error {
|
|
11
|
+
readonly cleanupReport: {
|
|
12
|
+
cancelledTaskIds: string[];
|
|
13
|
+
removedLayout: boolean;
|
|
14
|
+
removedWorktrees: string[];
|
|
15
|
+
errors: string[];
|
|
16
|
+
};
|
|
17
|
+
constructor(message: string, cleanupReport: {
|
|
18
|
+
cancelledTaskIds: string[];
|
|
19
|
+
removedLayout: boolean;
|
|
20
|
+
removedWorktrees: string[];
|
|
21
|
+
errors: string[];
|
|
22
|
+
}, cause: Error);
|
|
23
|
+
}
|
|
24
|
+
export declare function createTeamRun(spec: TeamSpec, leadSessionId: string, ctx: ExecutorContext, config: TeamModeConfig, bgMgr: BackgroundManager, tmuxMgr?: TmuxSessionManager, options?: CreateTeamRunOptions): Promise<RuntimeState>;
|
|
25
|
+
export {};
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import type { TeamModeConfig } from "../../../config/schema/team-mode";
|
|
2
|
+
import { log } from "../../../shared/logger";
|
|
3
|
+
import type { BackgroundManager } from "../../background-agent/manager";
|
|
4
|
+
import type { TmuxSessionManager } from "../../tmux-subagent/manager";
|
|
5
|
+
import { canVisualize, removeTeamLayout } from "../team-layout-tmux/layout";
|
|
6
|
+
export type DeleteTeamDeps = {
|
|
7
|
+
canVisualize: typeof canVisualize;
|
|
8
|
+
removeTeamLayout: typeof removeTeamLayout;
|
|
9
|
+
log: typeof log;
|
|
10
|
+
};
|
|
11
|
+
export declare function deleteTeam(teamRunId: string, config: TeamModeConfig, tmuxMgr?: TmuxSessionManager, bgMgr?: BackgroundManager, options?: {
|
|
12
|
+
force?: boolean;
|
|
13
|
+
}, deps?: DeleteTeamDeps): Promise<{
|
|
14
|
+
removedWorktrees: string[];
|
|
15
|
+
removedLayout: boolean;
|
|
16
|
+
}>;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import type { FallbackEntry } from "../../../shared/model-requirements";
|
|
2
|
+
import type { DelegatedModelConfig } from "../../../shared/model-resolution-types";
|
|
3
|
+
import type { ExecutorContext } from "../../../tools/delegate-task/executor-types";
|
|
4
|
+
import type { Member } from "../types";
|
|
5
|
+
export declare class TeamMemberResolutionError extends Error {
|
|
6
|
+
readonly memberName: string;
|
|
7
|
+
readonly cause: Error;
|
|
8
|
+
constructor(memberName: string, cause: Error);
|
|
9
|
+
}
|
|
10
|
+
export interface ResolvedMember {
|
|
11
|
+
memberName: string;
|
|
12
|
+
agentToUse: string;
|
|
13
|
+
model: DelegatedModelConfig | undefined;
|
|
14
|
+
fallbackChain: FallbackEntry[] | undefined;
|
|
15
|
+
systemContent: string;
|
|
16
|
+
}
|
|
17
|
+
export declare function resolveMember(member: Member, ctx: ExecutorContext, categoryExamples: string, parentAgent?: string): Promise<ResolvedMember>;
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import type { Message, RuntimeState } from "../types";
|
|
2
|
+
export declare const DELETABLE_MEMBER_STATUSES: Set<"pending" | "completed" | "running" | "idle" | "shutdown_approved" | "errored">;
|
|
3
|
+
export declare function createShutdownMessage(from: string, to: string, kind: Message["kind"], body: string): Message;
|
|
4
|
+
export declare function getRuntimeMember(runtimeState: RuntimeState, memberName: string): RuntimeState["members"][number];
|
|
5
|
+
export declare function getLeadMemberName(runtimeState: RuntimeState): string;
|
|
6
|
+
export declare function createSendContext(runtimeState: RuntimeState, senderName: string): {
|
|
7
|
+
isLead: boolean;
|
|
8
|
+
activeMembers: string[];
|
|
9
|
+
};
|
|
10
|
+
export declare function findLatestShutdownRequestIndex(runtimeState: RuntimeState, memberName: string, requesterName?: string): number;
|
|
11
|
+
export declare function removeWorktrees(memberPaths: Array<string | undefined>): Promise<string[]>;
|