Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
dee3c32a5c | ||
|
|
968db75c69 |
@@ -1,18 +0,0 @@
|
|||||||
name: Monitor Agent Loop
|
|
||||||
|
|
||||||
on:
|
|
||||||
schedule:
|
|
||||||
- cron: '0 */2 * * *' # every 2 hours
|
|
||||||
workflow_dispatch:
|
|
||||||
|
|
||||||
jobs:
|
|
||||||
monitor:
|
|
||||||
name: Check Agent Loop Health
|
|
||||||
runs-on: ubuntu-latest
|
|
||||||
timeout-minutes: 5
|
|
||||||
|
|
||||||
steps:
|
|
||||||
- uses: actions/checkout@v4
|
|
||||||
|
|
||||||
- name: Check agent loop heartbeat
|
|
||||||
run: python3 scripts/agent_loop.py monitor
|
|
||||||
@@ -8,46 +8,41 @@ CLI tool `fgj` is available to query issues/PRs/actions.
|
|||||||
|
|
||||||
## Issue Label Workflow
|
## Issue Label Workflow
|
||||||
|
|
||||||
We use issues, follow this label state machine:
|
Automation is handled by [agentloop](https://github.com/guettli/agentloop) running every 5 minutes via cron. Add a label to trigger an agent:
|
||||||
|
|
||||||
- **State/ToPlan** — Issue needs a plan written by an agent before implementation
|
| Label | Trigger | Outcome |
|
||||||
- **State/Planned** — Plan has been posted as a comment; awaiting human review
|
|---|---|---|
|
||||||
- **State/Ready** — Issue is approved and ready for implementation
|
| `loop/plan` | Planning agent reads the issue and writes an implementation plan as a comment | Issue moves to `loop/plan-done` |
|
||||||
- **State/InProgress** — Set while an agent (or human) is actively working
|
| `loop/code` | Coding agent implements the change, creates a branch + PR | Issue moves to `loop/code-done` |
|
||||||
- **State/Question** — Agent hit a blocker or needs clarification
|
|
||||||
|
|
||||||
Full lifecycle:
|
**State machine:**
|
||||||
|
|
||||||
```
|
```
|
||||||
State/ToPlan → State/Planned (automated: agent_loop.py runs a planning agent)
|
loop/plan → loop/plan-in-progress → loop/plan-done
|
||||||
State/Planned → State/Ready (manual: human reviews the plan and approves)
|
↘ NeedSupervisor (on failure)
|
||||||
State/Ready → State/InProgress (automated: agent_loop.py before starting implementation)
|
|
||||||
State/InProgress → closed (automated: after PR is merged and CI passes)
|
loop/code → loop/code-in-progress → loop/code-done
|
||||||
any state → State/Question (automated or manual: when blocked)
|
↘ NeedSupervisor (on failure)
|
||||||
```
|
```
|
||||||
|
|
||||||
List open issues ready to pick up:
|
**Rules:**
|
||||||
|
|
||||||
|
- Only issues authored by allowed users are picked up (guettli, guettlibot, guettlibot2, forgejo-actions).
|
||||||
|
- An issue with `NeedSupervisor` needs human attention — investigate, fix, then re-label.
|
||||||
|
- The coding agent opens a PR but does NOT close the issue. A human reviews the PR and closes the issue after merging.
|
||||||
|
- Planning agents only post a comment — they do NOT write code or open PRs.
|
||||||
|
- `loop/*` labels are managed by agentloop — do not set them manually while an agent is active.
|
||||||
|
|
||||||
|
**Typical lifecycle for a new feature:**
|
||||||
|
|
||||||
```bash
|
|
||||||
fgj issue list --json --state open | jq '[.[] | select(.labels[].name == "State/Ready")] | .[] | {number, title, html_url}'
|
|
||||||
```
|
```
|
||||||
|
1. Create issue
|
||||||
Rules:
|
2. Add label loop/plan → agent writes plan as comment
|
||||||
|
3. Review plan, request changes or approve
|
||||||
- Never start implementation on an issue without `State/Ready`
|
4. Add label loop/code → agent implements + opens PR
|
||||||
- Planning agents only post a plan comment — they do NOT write code or open PRs
|
5. Review PR, merge
|
||||||
- After `State/Planned`, a human must review the plan and manually add `State/Ready`
|
6. Close issue
|
||||||
- When working via the agent loop: label transitions are set automatically
|
```
|
||||||
by `agent_loop.py` — do **not** set them yourself.
|
|
||||||
- When working manually: switch to `State/InProgress` as your **first action**:
|
|
||||||
```bash
|
|
||||||
fgj issue edit <NUMBER> --remove-label "State/Ready" --add-label "State/InProgress"
|
|
||||||
```
|
|
||||||
- If blocked, replace current state label with `State/Question` and leave a comment explaining the blocker
|
|
||||||
- When done and CI is green, close the issue:
|
|
||||||
```bash
|
|
||||||
fgj issue close <NUMBER>
|
|
||||||
```
|
|
||||||
|
|
||||||
## Code conventions
|
## Code conventions
|
||||||
|
|
||||||
|
|||||||
@@ -156,6 +156,7 @@ class EmailRepositoryImpl implements EmailRepository {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (threadEmails.isEmpty) return;
|
||||||
final latest = threadEmails.last;
|
final latest = threadEmails.last;
|
||||||
|
|
||||||
// Collect unique participants across the whole thread.
|
// Collect unique participants across the whole thread.
|
||||||
|
|||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user