Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions .agent/hooks/branch-guard.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -38,11 +38,11 @@ function isArtifactPath(targetFile, repoRoot) {
function inspectFileWrite(targetFile, currentBranch, blockedBranches, repoRoot) {
if (isArtifactPath(targetFile, repoRoot)) return { allow: true };

if (blockedBranches.includes(currentBranch)) {
return {
allow: false,
reason: `[Rule 0 Violation S-04] Direct modification to '${targetFile}' on '${currentBranch}' is blocked. Cut a dedicated feature branch first.`
};
const isEpic = currentBranch.startsWith('epic/');
if (blockedBranches.includes(currentBranch) || isEpic) {
const code = isEpic ? 'Rule 0.1 Violation E-04' : 'Rule 0 Violation S-04';
const msg = isEpic ? 'Direct write on epic branch blocked. Cut a child branch first.' : 'Direct write on protected branch blocked. Cut a feature branch first.';
return { allow: false, reason: `[${code}] ${msg}` };
}
return { allow: true };
}
Expand Down
7 changes: 4 additions & 3 deletions .agent/hooks/plan-guard.mjs
Original file line number Diff line number Diff line change
Expand Up @@ -79,10 +79,11 @@ function inspectCommand(commandLine, currentBranch, blockedBranches) {
};
}

if (blockedBranches.includes(currentBranch)) {
if (blockedBranches.includes(currentBranch) || currentBranch.startsWith('epic/')) {
const code = currentBranch.startsWith('epic/') ? 'Rule 0.1 Violation E-01' : 'Rule 0 Violation S-01';
return {
allow: false,
reason: `[Rule 0 Violation S-01] Direct 'git commit' on protected branch '${currentBranch}' is blocked. Cut a dedicated feature branch first.`
reason: `[${code}] Direct 'git commit' on protected branch '${currentBranch}' is blocked. Cut a dedicated child feature branch first.`
};
}
}
Expand All @@ -106,7 +107,7 @@ function inspectCommand(commandLine, currentBranch, blockedBranches) {
}
}

if (subcommand === 'merge' && blockedBranches.includes(currentBranch)) {
if (subcommand === 'merge' && (blockedBranches.includes(currentBranch) || currentBranch.startsWith('epic/'))) {
return { allow: false, reason: `[Rule 0 Violation S-01] Direct 'git merge' on protected branch '${currentBranch}' is blocked. Merge via PR at Gate 3.5.` };
}
}
Expand Down
15 changes: 15 additions & 0 deletions .agent/hooks/post-merge-dual-sync.sh
Original file line number Diff line number Diff line change
Expand Up @@ -83,4 +83,19 @@ else
echo "ℹ️ Issue #$ISSUE_MATCH does not carry 'source:crashlytics'. Dual-sync skipped."
fi

# 4. Dynamic Base Branch Synchronization
if [ -n "$PR_NUMBER" ]; then
TARGET_BASE=$(gh pr view "$PR_NUMBER" --json baseRefName --jq '.baseRefName' 2>/dev/null || echo "main")
HEAD_BRANCH=$(gh pr view "$PR_NUMBER" --json headRefName --jq '.headRefName' 2>/dev/null || echo "")
if [ -n "$TARGET_BASE" ]; then
echo "🌿 Synchronizing base branch: $TARGET_BASE..."
git checkout "$TARGET_BASE" 2>/dev/null || true
git pull origin "$TARGET_BASE" 2>/dev/null || true
if [ -n "$HEAD_BRANCH" ] && [ "$HEAD_BRANCH" != "$TARGET_BASE" ]; then
git branch -d "$HEAD_BRANCH" 2>/dev/null || true
fi
git fetch --prune 2>/dev/null || true
fi
fi

exit 0
8 changes: 7 additions & 1 deletion .agent/hooks/pre-invocation-anchor.sh
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,15 @@ if [ -f "kernel.config.json" ]; then
fi

if [ -n "$BRANCH" ] && [ "$BRANCH" != "$DEF" ] && [ "$BRANCH" != "main" ] && [ "$BRANCH" != "master" ]; then
cat <<EOF
if [[ "$BRANCH" =~ ^epic/ ]]; then
cat <<EOF
{"injectSteps":[{"ephemeralMessage":"[SYSTEM CONTEXT: Active branch: '$BRANCH' (Epic Integration Branch). Direct commits forbidden. Child tasks branch from and merge into this epic branch.]"}]}
EOF
else
cat <<EOF
{"injectSteps":[{"ephemeralMessage":"[SYSTEM CONTEXT: Active branch: '$BRANCH' | State: Code / PR Review Loop. Apply all fixes or test feedback directly on this branch. Do NOT create a new issue or branch.]"}]}
EOF
fi
else
echo '{"injectSteps":[]}'
fi
22 changes: 8 additions & 14 deletions .agent/personas/p1-product-planner.md
Original file line number Diff line number Diff line change
Expand Up @@ -54,21 +54,15 @@ Before creating any work item:
- **Closed issue = regression** β†’ create new issue referencing `Regression of #<id>`.
- **No match** β†’ proceed to sealed issue creation.

### 2. Sealed Issue Creation
Issues are immutable upon creation (**Rule A β€” Append-Only**).
```json
{
"owner": "<owner>", "repo": "<repo>",
"title": "<type>(<scope>): <imperative description>",
"body": "<initial brief + placeholder for 4-Pillar Spec>",
"assignees": ["<owner>"],
"labels": ["<type_label>", "source:<origin>"]
}
```
Set at creation and assigned on GitHub Projects v2:
### 2. Just-In-Time (JIT) Issue Sealing
Specifications are elaborated locally in `implementation_plan.md` (`issue: null`).
Upon human written approval at Gate 1.4, P1 orchestrates atomic issue sealing via `./scripts/seal-issue.sh --from-plan`.
Native flags and Project v2 metadata:
- **Priority**: `P0` (Blocker/Fatal) Β· `P1` (Major) Β· `P2` (Minor)
- **Estimate** (co-owned with P4): Numeric estimate in days or story points
- **Status**: `Backlog`
- **Estimate** (co-owned with P4): Numeric estimate in days or points
- **Parent**: `--parent <epic_id>` if child task
- **Milestone**: `--milestone "<milestone_name>"`
- **Status**: `Ready`

### 3. Milestone & Cycle Scoping
- Create and scope GitHub Milestones (release boundaries).
Expand Down
5 changes: 3 additions & 2 deletions .agent/personas/p4-system-architect.md
Original file line number Diff line number Diff line change
Expand Up @@ -71,8 +71,9 @@ Assign numeric `Estimate` (days or story points, co-owned with P1).
### 5. Architectural Split Mandate (Epic Gating)
When Size is `L` or `XL`:
- **Reject Monolithic PRs**: Strictly forbid single large branches or PRs.
- **Decomposition DAG**: Produce a topological DAG of atomic child issues (< 300 diff lines each) referencing `parent: #<id>` via `.agent/templates/epic-spec.md`.
- Enforce trunk-based sequential delivery with `skip-release` for intermediate child PRs.
- **Epic Branch Isolation**: Establish integration branch `epic/issue-<id>-<slug>`.
- **Decomposition DAG**: Produce a topological DAG of atomic child tasks (< 300 diff lines each) referencing `parent: #<id>` via `.agent/templates/epic-spec.md`.
- Enforce sequential child PR delivery targeting `epic/**` with `skip-release` before a consolidated release PR to `main`.

### 6. Infrastructure Lock Protocol
Flag conflicts on shared infrastructure files: `AppDatabase.kt`, `firestore.rules`, `res/values/strings.xml`. Block concurrent branches and require sequential merge.
Expand Down
72 changes: 32 additions & 40 deletions .agent/rules/agent-lifecycle.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,60 +41,53 @@ Every task follows a strict **3-Phase Deterministic Lifecycle** executed by 6 En

## 2. Phase 1 Β· Inception & Scoping (Personas 1–4)

### Step 1.0 Β· Sealed Issue Creation (P1 β€” Product Planner)
**Absolute rule**: no branch, no file edit, no PR without a prior GitHub Issue.

Anti-duplication first: `GitHubMCP:search_issues` β†’ `{ "query": "repo:<owner>/<repo> is:issue <keywords>" }`

If no duplicate, create sealed issue via `GitHubMCP:create_issue` with title `<type>(<scope>): <title>`, assign `@me`, and retrieve `<id>`.
Conversation naming: `[#<id>] <type>(<scope>): <title>`

Kanban attachment:
```bash
gh project item-add <PROJECT> --owner @me --url "https://github.com/<owner>/<repo>/issues/<id>"
gh project item-edit <PROJECT> --owner @me --url "..." --field "Status" --value "Backlog"
```
### Step 1.0 Β· Anti-Duplication & Local Inception (P1 & P4)
**Rule 0 (JIT Issue-First)**: Zero code, branch, or premature GitHub issues before Gate 1.4.
- Anti-duplication first: `GitHubMCP:search_issues` β†’ `{ "query": "repo:<owner>/<repo> is:issue <keywords>" }`
- P1 & P4 elaborate specification locally in `implementation_plan.md` artifact (`issue: null`, `RequestFeedback: true`).
- P4 consolidates `Size` (XS–XL) and `Estimate` into Pillar 3 before sealing.

### Step 1.1 Β· Rule A β€” Issue & Branch Immutability (Append-Only)

> [!CAUTION]
> **Issue title and initial body are permanently sealed upon creation (READ-ONLY).**

- `GitHubMCP:update_issue` targeting `title` or `body` is **strictly forbidden**.
- `GitHubMCP:update_issue` targeting `title` or `body` is strictly forbidden.
- Branch type is immutable: a `feat/issue-<id>-*` stays `feat/` even if Phase 2 reveals bugs.
- Never rename a branch mid-flight. Scope revisions/corrections MUST use `GitHubMCP:add_issue_comment`.
- Scope revisions/corrections MUST use `GitHubMCP:add_issue_comment`.

### Step 1.2 Β· 4-Pillar Spec Orchestration (P1 orchestrates P2–P4)
Each persona contributes to the canonical 4-Pillar Spec posted via `GitHubMCP:add_issue_comment`:

- **P1 Product Planner** β†’ User Story (Gherkin) & 3-State Access Matrix (Guest/Solo/Duo).
- **P2 Design Lead** β†’ Pillar 1: Material 3 tokens, WCAG 2.1 AAA, 4-state UI matrix, Roborazzi expectations (or explicit `N/A β€” No visual/UI changes`).
- **P2 Design Lead** β†’ Pillar 1: Material 3 tokens, WCAG 2.1 AAA, 4-state UI matrix, Roborazzi expectations (or `N/A β€” No visual/UI changes`).
- **P3 Privacy & Data Lead** β†’ Pillar 2: Zero-PII telemetry, value bucketing, GDPR/AI Act compliance.
- **P4 System Architect** β†’ Pillar 3: Room schema/DDL, Firestore rules delta, Clean MVI, infra locks (`AppDatabase.kt`, `firestore.rules`, `strings.xml`), Size & Estimate.
- **P4 System Architect** β†’ Pillar 3: Room schema/DDL, Firestore rules delta, Clean MVI, infra locks, Size & Estimate.

### Step 1.3 Β· Dual-Write Pattern & Gate 1.4 Approval (Rule 1.5)
- **Canonical Remote Truth**: The sealed GitHub issue and its 4-Pillar comment serve as the authoritative project contract.
- **Local IDE Mirror**: To harmonize with Antigravity IDE native planning capabilities, the Orchestrator mirrors the 4-Pillar spec locally into the `implementation_plan.md` artifact (`RequestFeedback: true`, `UserFacing: true`).
- **Gate 1.4 Hard Stop**: **STOP AND WAIT**. The agent must not create any git branch or edit any source file until the user provides explicit approval.
- Post-approval: Kanban status transitions to `Ready`.
### Step 1.3 Β· Gate 1.4 Approval & JIT Sealing (Rule 1.5)
- **Gate 1.4 Hard Stop**: **STOP AND WAIT**. Zero branches, code edits, or remote issue creation before explicit user approval.
- **JIT Sealing via CLI**: Upon user approval, execute:
`./scripts/seal-issue.sh --from-plan [path_to_plan]`
This creates the GitHub issue, applies native flags (`--milestone`, `--parent`), attaches Project v2 metadata (`Priority`, `Size`, `Estimate`, `Status: Ready`), and initializes `epic/**` branch if Epic.

### Step 1.4 Β· Hand-off to Persona 5
Phase 1 is complete. Dedicated branch creation and all source edits begin exclusively in Phase 2.
Phase 1 is complete. Dedicated branch creation and source edits begin exclusively in Phase 2.

---

## 3. Phase 2 Β· Construction & Isolation (Persona 5)

### Step 2.1 Β· Dedicated Branch Creation (Branch-First Isolation & WIP = 1)
**WIP = 1 Pre-check**: `gh pr list --state open` must be empty. If an open PR exists, STOP until it merges.
Base branch resolution:
- Standalone / Epic: branched from `main`.
- Epic Child Task: branched from active parent branch (`epic/issue-<epic_id>-<slug>`).

```bash
git checkout main && git pull origin main
git checkout <base_branch> && git pull origin <base_branch>
git checkout -b <type>/issue-<id>-<short-kebab-slug>
```
Or remotely via `GitHubMCP:create_branch` with `from_branch: "main"`. Kanban β†’ `In Progress`.
Kanban status transitions to `In Progress`.

**FORBIDDEN**: any file edit on `main` or starting while another PR is open.
**FORBIDDEN**: any file edit on `main` or `epic/*` or starting while another PR is open.

### Step 2.2 Β· Native Implementation
- **Clean MVI**: `data/model` β†’ `data/repository` β†’ `ui/viewmodel` (StateFlow) β†’ `ui/components` (Compose).
Expand All @@ -105,7 +98,7 @@ Or remotely via `GitHubMCP:create_branch` with `from_branch: "main"`. Kanban β†’

### Step 2.3 Β· Atomic Commits on Dedicated Branch
Format: `<type>(<scope>): <present-tense description>`
Push exclusively to `<type>/issue-<id>-<slug>`. Zero commits on `main`.
Push exclusively to `<type>/issue-<id>-<slug>`. Zero commits on `main` or `epic/*`.

### Step 2.4 Β· Hand-off to Persona 6
Phase 2 complete. Delivery and observability sync begin in Phase 3.
Expand All @@ -126,32 +119,31 @@ Anti-duplicate & WIP check: `gh pr list --state open`

If no open PR:
```bash
git fetch origin main && git rebase origin/main
git fetch origin <base_branch> && git rebase origin/<base_branch>
git push -u origin <type>/issue-<id>-<slug>
gh pr create --base main --head <type>/issue-<id>-<slug> \
gh pr create --base <base_branch> --head <type>/issue-<id>-<slug> \
--title "<type>(<scope>): <title>" --body-file ./walkthrough.md
```
- Assign to `@me`. Attach to "Project Kanban" β†’ `In Review`.
- PR targets `epic/**` with `skip-release` for intermediate child PRs; `main` for standalone or consolidated Epic release PRs.
- Assign to `@me`. Never add PRs directly to Project board (board hygiene).
- PR body hosts **exclusively** the Walkthrough (`Closes #<id>`, files, test proofs, Roborazzi snapshots).
- **STOP & WAIT FOR USER APPROVAL**.
- **STOP & WAIT FOR USER APPROVAL (Gate 3.5)**.

### Step 3.3 Β· Zero Auto-Merge Rule

> [!CAUTION]
> The agent NEVER merges a PR autonomously. Present the PR link and stop. Merge only after the user says *"Tu peux merger"* or equivalent.

### Step 3.4 Β· Post-Merge Branch Cleanup
### Step 3.4 Β· Post-Merge Branch Cleanup & Dynamic Sync

> [!IMPORTANT]
> Mandatory remote branch deletion. Never leave orphan branches on `origin`.
> Mandatory remote branch deletion and base synchronization via post-merge hook.

Run the post-merge hook:
```bash
git checkout main && git pull origin main
git branch -d <type>/issue-<id>-<slug>
git push origin --delete <type>/issue-<id>-<slug>
git fetch --prune
./.agent/hooks/post-merge-dual-sync.sh <pr_number>
```
Issue auto-closed by `Closes #<id>`. Kanban β†’ `Done`.
This hook dynamically switches to the target base branch (`epic/**` or `main`), pulls latest, and cleans local/remote branches. Issue auto-closed by `Closes #<id>`. Kanban β†’ `Done`.

### Step 3.5 Β· Crashlytics Dual-Sync Closure (P6 β€” mandatory for `source:crashlytics`)

Expand Down
54 changes: 24 additions & 30 deletions .agent/rules/backlog-planner.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,21 +42,24 @@ Configured on GitHub Projects v2 board. Revisions require an `add_issue_comment`

## 4. The 10 Golden Rules of Backlog Governance

### 🚨 Rule 0 · No Branch or Code Without a GitHub Issue
### 🚨 Rule 0 · JIT Issue Sealing (Gate 1.4 Hand-off)
Every task (feature, bug, refactor, chore, docs) requires:
1. A GitHub Issue created **before** any development starts.
2. A dedicated `<type>/issue-<id>-<slug>` branch cut from up-to-date `main`.
3. A 1:1 PR closing the issue (`Closes #<id>`).
1. Inception and 4-Pillars elaborated locally in `implementation_plan.md` (`issue: null`).
2. Sizing and estimation consolidated in Pillar 3 before Gate 1.4.
3. Sealing via `./scripts/seal-issue.sh --from-plan` exclusively **after** user approval at Gate 1.4.
4. Dedicated branch `<type>/issue-<id>-<slug>` cut from `main` or active Epic branch.
5. A 1:1 PR closing the issue (`Closes #<id>`).

> β›” **FORBIDDEN**: coding on `main`, creating a branch/PR without an Issue number.
> β›” **FORBIDDEN**: coding on `main` or `epic/*`, creating a branch or premature GitHub stubs before Gate 1.4.

---

### πŸ›οΈ Rule 0.1 Β· Epic Gating (Size: L / XL)
### πŸ›οΈ Rule 0.1 Β· Epic Branch Isolation Protocol (Size: L / XL)
Issues rated `Size: L` or `Size: XL` (or `Estimate >= 3d`) are classified as **Epics**.
- **Zero Branch Guardrail**: Never branch or commit directly on an Epic issue.
- **Sequential Decomposition**: P1 & P4 decompose Epics into atomic child issues (< 300 diff lines) referencing the parent (`parent: #<id>`), merged sequentially to `main` (Trunk-Based) using [`.agent/templates/epic-spec.md`](../templates/epic-spec.md).
- **Silent Merges (`skip-release`)**: Intermediate child PRs carry `skip-release`.
- **Integration Branch**: Upon sealing, an isolated branch `epic/issue-<id>-<slug>` is created from `origin/main`.
- **Zero Direct Commits**: Committing or merging directly on `epic/**` is strictly forbidden.
- **Sequential Child Tasks**: Decomposed into atomic child tasks (< 300 diff lines) with native `--parent <epic_id>`. Each child task runs its own JIT Inception, branches from and merges into `epic/**` with `skip-release`.
- **Consolidated Release**: Once all child tasks merge into `epic/**`, a final PR targets `main`, closing the parent Epic and child issues.

---

Expand Down Expand Up @@ -85,30 +88,26 @@ Every Issue and PR must be assigned to `@me` at creation. No unowned tickets.

---

### πŸ“‹ Rule 3 Β· Kanban Attachment & Milestone Linking
**At `Backlog` creation**: Attach to project board and assign Priority, Size, Estimate, Status.
**At `Ready` transition**: Link active Cycle and target Milestone:
```bash
gh issue edit <id> --milestone "<Milestone>"
gh project item-edit <PROJECT> --owner @me --url "..." --field "Status" --value "Ready"
```
### πŸ“‹ Rule 3 Β· Kanban Attachment & Native Metadata
Native metadata (`Priority`, `Size`, `Estimate`, `Status`) is managed on Project v2 via `sync-project-metadata.mjs` or `seal-issue.sh`. Narrative metadata is never mixed into issue bodies.
Column lifecycle: `Backlog` β†’ `Ready` β†’ `In Progress` β†’ `In Review` β†’ `Done`.

---

### πŸ“ Rule 4 Β· Issue vs PR Separation & Dual-Write Pattern
- **Issue**: hosts canonical 4-Pillar Plan via comment ([`.agent/templates/4-pillar-spec.md`](../templates/4-pillar-spec.md)).
- **Issue**: hosts canonical 4-Pillar Plan ([`.agent/templates/4-pillar-spec.md`](../templates/4-pillar-spec.md)).
- **Dual-Write**: spec is mirrored to local `implementation_plan.md` artifact at Gate 1.4 for Antigravity IDE harmony.
- **PR**: hosts exclusively the Walkthrough ([`.agent/templates/pr-walkthrough.md`](../templates/pr-walkthrough.md)). Zero heredocs.

---

### 🌿 Rule 5 · Branch-First Isolation
Cut branch from `main` or `epic/issue-<epic_id>-<slug>`:
```bash
git checkout main && git pull origin main
git checkout <base_branch> && git pull origin <base_branch>
git checkout -b <type>/issue-<id>-<slug>
```
**FORBIDDEN**: editing files on `main` or any generic branch before this sequence.
**FORBIDDEN**: editing files on `main` or `epic/*` before cutting the branch.

---

Expand Down Expand Up @@ -163,26 +162,21 @@ All specifications adhere to [`.agent/templates/4-pillar-spec.md`](../templates/

---

## 5. Inception Workflow (Chat-to-Issue)
## 5. Inception Workflow (JIT Sealing)

```
User Request
β”‚
β–Ό P1: Anti-duplication (GitHubMCP:search_issues)
β”‚
β–Ό P1: Create sealed Issue + assign Priority/Estimate + link Milestone
β”‚
β–Ό P1: Kanban attachment (Backlog)
β”‚
β”œβ”€β–Ά P2: Pillar 1 comment (Design Spec)
β”œβ”€β–Ά P3: Pillar 2 comment (Data & Privacy Spec)
└─▢ P4: Pillar 3 comment (Technical Blueprint) + assign Size/Estimate
β–Ό P1/P4: Local 4-Pillars (implementation_plan.md, issue: null)
β”‚
β–Ό P1: Cycle & Milestone linking β†’ Kanban to Ready
β–Ό Gate 1.4: Strict halt for human written approval
β”‚
β–Ό User explicit approval (Rule 1.5 of agent-lifecycle.md)
β–Ό JIT Sealing: ./scripts/seal-issue.sh --from-plan
β”‚ (Native Milestone, Parent, Projects v2 Priority/Size/Estimate)
β”‚
β–Ό Hand-off to Personas 5 & 6 (git-workflow.md)
β–Ό Hand-off to P5 (Branch cut, WIP=1) & P6
```

---
Expand Down
Loading
Loading