149 lines
3.5 KiB
Plaintext
149 lines
3.5 KiB
Plaintext
@startuml commit-workflow
|
|
!theme plain
|
|
title Git Commit Workflow with Automation
|
|
|
|
actor Developer
|
|
participant "git commit" as git
|
|
participant "pre-commit hook" as hook
|
|
participant "runner.py" as runner
|
|
participant "config.py" as config
|
|
participant "patcher.py" as patcher
|
|
participant "AI Providers" as ai
|
|
participant "Claude CLI" as claude
|
|
participant "Codex CLI" as codex
|
|
participant "Gemini CLI" as gemini
|
|
participant "workflow.py" as workflow
|
|
database ".git index" as index
|
|
|
|
Developer -> git: commit staged files
|
|
activate git
|
|
|
|
git -> hook: trigger pre-commit
|
|
activate hook
|
|
|
|
hook -> runner: python3 -m automation.runner
|
|
activate runner
|
|
|
|
runner -> config: Load .ai-rules.yml
|
|
activate config
|
|
config -> config: Find cascading rules
|
|
config -> runner: Return merged config
|
|
deactivate config
|
|
|
|
loop For each staged file
|
|
runner -> config: Get rule for file
|
|
config -> runner: Return rule & outputs
|
|
|
|
runner -> patcher: generate_output(source, target, instruction)
|
|
activate patcher
|
|
|
|
patcher -> patcher: Build prompt with\nsource diff + context
|
|
|
|
patcher -> ai: Try provider 1/3
|
|
activate ai
|
|
ai -> claude: Send prompt
|
|
activate claude
|
|
|
|
alt Claude produces diff
|
|
claude -> ai: Return unified diff\n(wrapped in markers)
|
|
ai -> patcher: Success with diff
|
|
deactivate claude
|
|
deactivate ai
|
|
patcher -> patcher: Extract & sanitize patch
|
|
patcher -> patcher: git apply --3way
|
|
patcher -> index: Stage generated file
|
|
patcher -> runner: Success
|
|
else Claude non-diff output
|
|
claude -> ai: Non-diff response
|
|
deactivate claude
|
|
ai -> codex: Try provider 2/3
|
|
activate codex
|
|
|
|
alt Codex succeeds
|
|
codex -> ai: Return diff (JSON parsed)
|
|
deactivate codex
|
|
deactivate ai
|
|
patcher -> patcher: Extract & sanitize
|
|
patcher -> index: Stage file
|
|
patcher -> runner: Success
|
|
else Codex fails (exit 1)
|
|
codex -> ai: Exit code 1
|
|
deactivate codex
|
|
ai -> gemini: Try provider 3/3
|
|
activate gemini
|
|
|
|
alt Gemini succeeds
|
|
gemini -> ai: Return diff
|
|
deactivate gemini
|
|
deactivate ai
|
|
patcher -> patcher: Extract & sanitize
|
|
patcher -> index: Stage file
|
|
patcher -> runner: Success
|
|
else All providers failed
|
|
gemini -> ai: Error/no diff
|
|
deactivate gemini
|
|
deactivate ai
|
|
patcher -> patcher: Log error to stderr
|
|
patcher -> runner: Skip this file
|
|
end
|
|
end
|
|
end
|
|
|
|
deactivate patcher
|
|
end
|
|
|
|
runner -> hook: Exit 0
|
|
deactivate runner
|
|
|
|
hook -> workflow: python3 -m automation.workflow --status
|
|
activate workflow
|
|
|
|
workflow -> workflow: Parse VOTE: lines\nfrom discussions
|
|
workflow -> workflow: Update .sum.md files
|
|
workflow -> index: Stage updated summaries
|
|
workflow -> hook: Exit 0
|
|
deactivate workflow
|
|
|
|
hook -> git: Exit 0 (continue commit)
|
|
deactivate hook
|
|
|
|
git -> index: Create commit
|
|
git -> Developer: Commit successful
|
|
deactivate git
|
|
|
|
note right of ai
|
|
**Multi-Provider Fallback Chain**
|
|
Configured in config/ai.yml:
|
|
1. claude -p (Claude CLI with subagent)
|
|
2. codex exec --model gpt-5 --json
|
|
3. gemini --model gemini-2.5-flash
|
|
|
|
Each provider tried until one succeeds.
|
|
Provides redundancy against:
|
|
- Rate limits
|
|
- API outages
|
|
- Non-diff responses
|
|
end note
|
|
|
|
note right of patcher
|
|
Saves debug artifacts to
|
|
.git/ai-rules-debug/
|
|
for troubleshooting:
|
|
- *.raw.out
|
|
- *.clean.diff
|
|
- *.sanitized.diff
|
|
- *.final.diff
|
|
end note
|
|
|
|
note right of workflow
|
|
Always exits 0
|
|
(non-blocking)
|
|
|
|
Extracts structured markers:
|
|
- **DECISION**: text
|
|
- **QUESTION**: text
|
|
- **ACTION**: @assignee text
|
|
end note
|
|
|
|
@enduml
|