feat: m-agent-origin-milestone-creation-sync task files - PLAN/CODE_REVIEW for cloud-G07/G08
This commit is contained in:
parent
d80abe8357
commit
15d24b6767
8 changed files with 1609 additions and 0 deletions
|
|
@ -0,0 +1,139 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/01_scan_create_ledger plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Code Review Reference - API
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — READ FIRST] Filling in this file is the mandatory final step of implementation.**
|
||||||
|
> The task is NOT complete until every implementation-owned section below is filled in.
|
||||||
|
> Complete the `구현 체크리스트`; the final checklist item is mandatory before saving.
|
||||||
|
> Fill implementation-owned sections, then stop with active files in place and report ready for review.
|
||||||
|
> If implementation is blocked by a selected Milestone `구현 잠금 > 결정 필요` item, fill `사용자 리뷰 요청` with linked evidence and stop with active files in place; code-review decides whether to write `USER_REVIEW.md`. Environment/secret/service blockers, generic scope changes, repeated failures, and evidence gaps that a follow-up agent can close are normal follow-up issues, not user-review blockers by themselves.
|
||||||
|
> Do not ask the user directly, present choices in chat, or call `request_user_input` during implementation; record only Milestone lock decisions in `사용자 리뷰 요청` and stop for code-review.
|
||||||
|
> Finalization (`코드리뷰 결과`, log rename, `complete.log`, archive moves, `코드리뷰 전용 체크리스트`) is review-agent-only, even after compaction/resume.
|
||||||
|
> Follow the ownership table at the bottom of this file for which sections you own.
|
||||||
|
|
||||||
|
## 개요
|
||||||
|
|
||||||
|
date=2026-07-02
|
||||||
|
task=m-agent-origin-milestone-creation-sync/01_scan_create_ledger, plan=0, tag=API
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `scan-diff`: Gito webhook의 `before..after` 변경 목록을 wakeup 힌트로 사용하되, `after` SHA 검증 뒤 active Milestone diff와 전체 active index를 함께 스캔한다.
|
||||||
|
- `missing-create`: provider identity가 없는 active Milestone을 agent-origin 생성 후보로 판별하고 Plane work item을 생성한다.
|
||||||
|
- `identity-ledger`: 생성된 Plane work item id를 `roadmap_sync_identities`에 filename slug 기준으로 upsert하고 revision/idempotency conflict를 구분한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 이 파일을 읽는 리뷰 에이전트에게
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 아래 종결 절차는 코드리뷰 에이전트 전용이다. 구현 에이전트는 이 섹션을 실행하지 않는다.
|
||||||
|
|
||||||
|
각 항목의 구현을 실제 소스 파일과 대조하고, `검증 결과` 섹션의 출력이 코드와 일치하는지 확인하세요.
|
||||||
|
리뷰 완료는 아래 순서까지 끝난 상태를 의미합니다.
|
||||||
|
|
||||||
|
1. 판정을 append한다.
|
||||||
|
2. `CODE_REVIEW-cloud-G07.md` -> `code_review_cloud_G07_N.log`, `PLAN-cloud-G07.md` -> `plan_cloud_G07_M.log`로 아카이브한다.
|
||||||
|
3. PASS이면 `complete.log` 작성 후 active task 디렉터리를 `agent-task/archive/YYYY/MM/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/`로 이동한다. WARN/FAIL이면 user-review gate를 확인한 뒤 다음 active plan/review 파일 또는 `USER_REVIEW.md`를 작성한다.
|
||||||
|
4. PASS이고 task group이 `m-agent-origin-milestone-creation-sync`이면 완료 이벤트 메타데이터를 보고한다. roadmap 상태 체크와 `update-roadmap` 호출은 런타임 책임이다.
|
||||||
|
5. 적용 가능한 `코드리뷰 전용 체크리스트` 항목을 최종 `.log` 위치에서 체크한 뒤 보고한다.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 구현 항목별 완료 여부
|
||||||
|
|
||||||
|
| 항목 | 완료 여부 |
|
||||||
|
|------|---------|
|
||||||
|
| [API-1] Scan Hint And Revision Gate | [ ] |
|
||||||
|
| [API-2] Missing Create And Ledger Idempotency | [ ] |
|
||||||
|
| [API-3] Review Stub Completion | [ ] |
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `scan-diff` 경로에서 Gito `changed_files`/`before..after`는 wakeup hint로만 보존하고, `after` SHA fetch/verify와 active Milestone scan 없이는 enqueue하지 않는다. 검증: `changed_files`만 신뢰하지 않고 `origin/develop`의 `after` SHA가 일치할 때만 sync job이 enqueue된다.
|
||||||
|
- [ ] `missing-create` 경로에서 identity-less active Milestone이 Plane create 후보가 되고, 같은 milestone slug와 revision 재처리에서 duplicate create가 발생하지 않도록 ledger/idempotency 테스트를 보강한다. 검증: 같은 milestone slug와 revision을 재처리해도 중복 Plane work item을 만들지 않는다.
|
||||||
|
- [ ] `identity-ledger` 경로에서 filename slug 기준 upsert와 provider work item conflict가 provider mutation 없이 `conflict`로 구분되는지 pipeline/storage 테스트를 보강한다. 검증: 기존 slug가 다른 provider work item에 묶여 있으면 provider mutation 없이 conflict로 멈춘다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## 코드리뷰 전용 체크리스트
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 이 체크리스트는 코드리뷰 에이전트만 사용한다.
|
||||||
|
> 구현 에이전트는 이 섹션을 수정하거나 체크하지 않는다.
|
||||||
|
|
||||||
|
- [ ] `코드리뷰 결과`에 `PASS`, `WARN`, `FAIL` 중 하나의 판정을 append한다.
|
||||||
|
- [ ] 판정과 `차원별 평가`, Required/Suggested/Nit 분류가 서로 일치한다.
|
||||||
|
- [ ] active `CODE_REVIEW-*-G??.md`를 `code_review_cloud_G07_N.log`로 아카이브한다.
|
||||||
|
- [ ] active `PLAN-*-G??.md`를 `plan_cloud_G07_M.log`로 아카이브한다.
|
||||||
|
- [ ] `.gitignore`의 Agent-Ops 관리 block이 `agent-task/**/*.md`와 `agent-task/**/*.log`를 unignore하고 `agent-roadmap/current.md`를 ignore하는지 확인한다.
|
||||||
|
- [ ] PASS이면 `agent-ops/skills/common/code-review/templates/complete-log-template.md` 기준으로 `complete.log`를 작성하고 active `.md` 파일을 남기지 않는다.
|
||||||
|
- [ ] PASS이면 active task 디렉터리 `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/`를 `agent-task/archive/YYYY/MM/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/`로 이동하고 최종 archive 경로에서 이 체크리스트를 갱신한다.
|
||||||
|
- [ ] PASS이고 task group이 `m-<milestone-slug>`이면 런타임이 읽을 완료 이벤트 메타데이터를 보고하고, roadmap 수정이나 `update-roadmap` 직접 호출을 하지 않는다.
|
||||||
|
- [ ] PASS split 작업이면 이동 후 빈 active parent `agent-task/m-agent-origin-milestone-creation-sync/`를 제거하거나, 남은 sibling/file이 있어 유지했다고 확인한다.
|
||||||
|
- [ ] WARN/FAIL이고 user-review gate가 트리거되지 않았으면 다음 active `PLAN-{build_lane}-GNN.md`와 `CODE_REVIEW-{review_lane}-GNN.md`를 작성하고 `complete.log`를 작성하지 않는다.
|
||||||
|
- [ ] USER_REVIEW이면 `agent-ops/skills/common/code-review/templates/user-review-template.md` 기준으로 `USER_REVIEW.md`를 작성하고 active `PLAN-*.md`, `CODE_REVIEW-*.md`, `complete.log`를 남기지 않는다.
|
||||||
|
- [ ] USER_REVIEW가 연결된 Milestone 결정으로 완료/PASS 해소되면 `USER_REVIEW.md`를 해소 상태로 갱신하고 `complete.log`를 작성한 뒤 task directory를 archive로 이동한다.
|
||||||
|
|
||||||
|
## 계획 대비 변경 사항
|
||||||
|
|
||||||
|
_구현 에이전트가 계획과 다르게 구현한 부분을 이유와 함께 기록한다._
|
||||||
|
|
||||||
|
## 주요 설계 결정
|
||||||
|
|
||||||
|
_구현 에이전트가 주요 설계 결정 사항을 기록한다._
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청
|
||||||
|
|
||||||
|
_기본값은 `없음`이다. 구현 중 새 결정이 필요해 보여도 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. 이 섹션은 선택된 Milestone `구현 잠금 > 결정 필요` 항목이 실구현을 차단할 때만 채운다. 외부 환경/secret/서비스 준비, 검증 증거 공백, 반복 실패, 일반 범위 조정은 사용자 리뷰 요청이 아니며 `검증 결과`, `계획 대비 변경 사항`, 또는 code-review의 일반 follow-up plan으로 처리한다._
|
||||||
|
|
||||||
|
- 상태: 없음
|
||||||
|
- 사유 유형: 없음
|
||||||
|
- 연결 대상: 없음
|
||||||
|
- 결정 필요: 없음
|
||||||
|
- 차단 근거: 없음
|
||||||
|
- 실행한 검증/명령: 없음
|
||||||
|
- 자동 후속 불가 이유: 없음
|
||||||
|
- 재개 조건: 없음
|
||||||
|
|
||||||
|
## 리뷰어를 위한 체크포인트
|
||||||
|
|
||||||
|
- `changed_files` is hint-only; no provider mutation occurs before `after` SHA verification.
|
||||||
|
- Missing-create duplicate retry does not call Plane create twice.
|
||||||
|
- Provider work item/slug conflicts produce `SyncActionConflict` without further provider mutation.
|
||||||
|
|
||||||
|
## 검증 결과
|
||||||
|
|
||||||
|
_구현 에이전트가 각 중간 검증 및 최종 검증 명령 실행 후 출력을 여기에 붙여 넣는다._
|
||||||
|
|
||||||
|
필수 규칙:
|
||||||
|
- 검증 명령은 고정된 계약이다. 임의로 대체하지 않는다.
|
||||||
|
- 대체가 필요하면 `계획 대비 변경 사항`에 이유와 대체 명령을 기록한다.
|
||||||
|
- `검증 결과`에는 실제 stdout/stderr를 붙여 넣는다.
|
||||||
|
|
||||||
|
### API-1 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/http ./internal/gitoevents ./internal/gitosync
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-2 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/roadmapsyncpipeline ./internal/storage ./internal/gitosync
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 최종 검증
|
||||||
|
```sh
|
||||||
|
$ git diff --check
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go test -count=1 ./internal/http ./internal/gitoevents ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go vet ./internal/http ./internal/gitoevents ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — BEFORE SAVING] Have you filled in every implementation-owned section: completion table, implementation checklist, changes from plan, design decisions, and verification output?**
|
||||||
|
> If anything is blank, go back and fill it in before saving this file.
|
||||||
|
> Leave review-agent-only sections unchanged.
|
||||||
|
|
@ -0,0 +1,280 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/01_scan_create_ledger plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Plan - API
|
||||||
|
|
||||||
|
## 이 파일을 읽는 구현 에이전트에게
|
||||||
|
|
||||||
|
구현 후 active `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 반드시 실제 구현 내용과 검증 출력으로 채운다. 검증을 실행하고, active 파일은 그대로 둔 뒤 리뷰 준비를 보고한다. 최종 판정, log rename, `complete.log`, archive 이동은 code-review 스킬 전용이다.
|
||||||
|
|
||||||
|
선택된 Milestone의 `구현 잠금 > 결정 필요` 항목이 실구현을 막을 때만 review stub의 `사용자 리뷰 요청` 섹션을 채우고 멈춘다. 구현 중 사용자에게 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. 환경, secret, 외부 서비스, 검증 evidence 공백은 사용자 리뷰 요청이 아니라 검증 결과나 follow-up 대상이다.
|
||||||
|
|
||||||
|
## 배경
|
||||||
|
|
||||||
|
Agent-origin push는 Gito `branch.updated`를 wakeup으로 받지만, Plane mutation 전에 `after` revision을 fetch/scan해서 active Milestone 상태를 다시 확인해야 한다. 현재 scanner, bridge, pipeline은 부분 구현되어 있으나 `before..after` diff hint와 전체 active index의 결합, missing-create idempotency, identity conflict evidence를 하나의 완료 단위로 고정해야 한다.
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청 흐름
|
||||||
|
|
||||||
|
사용자 리뷰 요청은 선택된 Milestone lock decision만 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 직접 사용자 prompt는 금지이며, code-review가 정당성을 검증하고 실제 `USER_REVIEW.md` 작성을 소유한다.
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `scan-diff`: Gito webhook의 `before..after` 변경 목록을 wakeup 힌트로 사용하되, `after` SHA 검증 뒤 active Milestone diff와 전체 active index를 함께 스캔한다.
|
||||||
|
- `missing-create`: provider identity가 없는 active Milestone을 agent-origin 생성 후보로 판별하고 Plane work item을 생성한다.
|
||||||
|
- `identity-ledger`: 생성된 Plane work item id를 `roadmap_sync_identities`에 filename slug 기준으로 upsert하고 revision/idempotency conflict를 구분한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 분석 결과
|
||||||
|
|
||||||
|
### 읽은 파일
|
||||||
|
|
||||||
|
- `agent-roadmap/current.md`
|
||||||
|
- `agent-roadmap/phase/agent-ops-mcp-control-plane/PHASE.md`
|
||||||
|
- `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- `agent-contract/index.md`
|
||||||
|
- `agent-contract/outer/gito-branch-webhook-consumer-v1.md`
|
||||||
|
- `agent-test/local/rules.md`
|
||||||
|
- `agent-test/local/core-smoke.md`
|
||||||
|
- `agent-test/local/workspace-ops-smoke.md`
|
||||||
|
- `services/core/internal/gitoevents/events.go`
|
||||||
|
- `services/core/internal/gitoevents/events_test.go`
|
||||||
|
- `services/core/internal/gitosync/scanner.go`
|
||||||
|
- `services/core/internal/gitosync/scanner_test.go`
|
||||||
|
- `services/core/internal/gitosync/bridge.go`
|
||||||
|
- `services/core/internal/gitosync/bridge_test.go`
|
||||||
|
- `services/core/internal/gitosync/runner.go`
|
||||||
|
- `services/core/internal/gitosync/runner_test.go`
|
||||||
|
- `services/core/internal/roadmapsync/identity.go`
|
||||||
|
- `services/core/internal/roadmapsync/milestone_parser.go`
|
||||||
|
- `services/core/internal/roadmapsync/develop_match.go`
|
||||||
|
- `services/core/internal/roadmapsync/develop_match_test.go`
|
||||||
|
- `services/core/internal/roadmapsync/retry.go`
|
||||||
|
- `services/core/internal/roadmapsync/retry_test.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service_test.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_identities.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_identities_test.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps_test.go`
|
||||||
|
- `services/core/internal/adapters/plane/client.go`
|
||||||
|
- `services/core/internal/adapters/plane/client_test.go`
|
||||||
|
- `services/core/internal/workitem/provider.go`
|
||||||
|
- `services/core/internal/http/gito_webhook.go`
|
||||||
|
- `services/core/internal/http/gito_webhook_test.go`
|
||||||
|
- `services/core/internal/config/config.go`
|
||||||
|
- `services/core/internal/config/config_test.go`
|
||||||
|
- `services/core/internal/scheduler/roadmap_sync_jobs.go`
|
||||||
|
- `services/core/internal/scheduler/jobs.go`
|
||||||
|
- `services/core/queries/roadmap_sync_identities.sql`
|
||||||
|
- `services/core/queries/roadmap_sync_steps.sql`
|
||||||
|
- `services/core/migrations/00006_create_roadmap_sync_identities.sql`
|
||||||
|
- `services/core/migrations/00007_create_roadmap_sync_steps.sql`
|
||||||
|
- `services/core/migrations/00009_add_roadmap_sync_milestone_id.sql`
|
||||||
|
|
||||||
|
### SDD 기준
|
||||||
|
|
||||||
|
- SDD: `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- 상태: `[승인됨]`, SDD 잠금 해제, 사용자 리뷰 없음.
|
||||||
|
- Targeted scenarios: S01=`scan-diff`, S02=`missing-create`, S03=`identity-ledger`.
|
||||||
|
- Evidence Map rows: S01 requires gitosync scanner/bridge unit and webhook handler tests; S02 requires roadmapsyncpipeline missing-create idempotency test; S03 requires storage identity conflict/upsert test.
|
||||||
|
- 구현 checklist는 `changed_files` 단독 신뢰 금지, `after` SHA verification, missing identity create idempotency, slug/provider conflict evidence 순서로 역산한다.
|
||||||
|
|
||||||
|
### 테스트 환경 규칙
|
||||||
|
|
||||||
|
- test_env: `local`.
|
||||||
|
- `agent-test/local/rules.md` present/read.
|
||||||
|
- Matched profiles read: `agent-test/local/core-smoke.md`, `agent-test/local/workspace-ops-smoke.md`.
|
||||||
|
- 적용 명령: `git diff --check`, `cd services/core && go test ./...`, 필요 시 `cd services/core && go vet ./...`.
|
||||||
|
- Current preflight: repo root `/config/workspace/nomadcode`, branch `main`, HEAD `d80abe83579dd0d6fbc86b1a74c83db6d18c756d`, `go version go1.26.2 linux/arm64`, `git version 2.43.0`.
|
||||||
|
- 원격 runner 검증이 필요하면 `toki@toki-labs.com:$HOME/agent-work/nomadcode`를 현재 변경과 동기화한 뒤 같은 명령을 실행한다. 현재 계획 작성 시에는 local checkout에서 `git diff --check`, focused `go test`, `go vet`를 PASS로 확인했다.
|
||||||
|
|
||||||
|
### 테스트 커버리지 공백
|
||||||
|
|
||||||
|
- `scan-diff`: existing scanner tests cover `after` mismatch, active index, archive exclusion, duplicate active slug. Gap: event `changed_files` or `before..after` hint is not carried through HTTP handler/scanner as an explicit relevance hint.
|
||||||
|
- `missing-create`: bridge and pipeline tests cover identity-less docs, Plane create, and create result ledger upsert. Gap: same slug+same revision duplicate retry should assert no duplicate create after ledger exists.
|
||||||
|
- `identity-ledger`: storage tests cover slug upsert and provider-work-item unique conflict. Gap: pipeline should expose conflict/not-ready reason without provider mutation for existing slug bound to a different provider item.
|
||||||
|
|
||||||
|
### 심볼 참조
|
||||||
|
|
||||||
|
- No renamed or removed symbols planned in this subtask. New fields or helper symbols must be grepped before use.
|
||||||
|
|
||||||
|
### 분할 판단
|
||||||
|
|
||||||
|
- Split decision policy evaluated before file selection.
|
||||||
|
- Shared task group: `agent-task/m-agent-origin-milestone-creation-sync/`.
|
||||||
|
- Sibling subtasks:
|
||||||
|
- `01_scan_create_ledger`: independent foundation for S01-S03.
|
||||||
|
- `02+01_identity_backfill`: depends on 01 because it needs created identity rows and work item ids.
|
||||||
|
- `03+01,02_self_loop_update_conflict`: depends on 01 and 02 because self-loop is meaningful after backfill.
|
||||||
|
- `04+01,02,03_field_smoke`: depends on all prior subtasks.
|
||||||
|
- This plan is the first independent subtask; no predecessor completion is required.
|
||||||
|
|
||||||
|
### 범위 결정 근거
|
||||||
|
|
||||||
|
- Exclude identity backfill commit/push, self-loop no-op, provider identity update projection, conflict policy hardening, and field smoke. Those are separate dependent plans.
|
||||||
|
- Exclude Plane `Todo -> In Progress` lifecycle and child ticket sync per Milestone 범위 제외.
|
||||||
|
|
||||||
|
### 빌드 등급
|
||||||
|
|
||||||
|
- `cloud-G07`: core/provider/DB/webhook behavior spans multiple packages and external contract semantics; local tests are strong, but a wrong implementation could pass unit tests while violating Gito/Plane sync promises.
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `scan-diff` 경로에서 Gito `changed_files`/`before..after`는 wakeup hint로만 보존하고, `after` SHA fetch/verify와 active Milestone scan 없이는 enqueue하지 않는다. 검증: `changed_files`만 신뢰하지 않고 `origin/develop`의 `after` SHA가 일치할 때만 sync job이 enqueue된다.
|
||||||
|
- [ ] `missing-create` 경로에서 identity-less active Milestone이 Plane create 후보가 되고, 같은 milestone slug와 revision 재처리에서 duplicate create가 발생하지 않도록 ledger/idempotency 테스트를 보강한다. 검증: 같은 milestone slug와 revision을 재처리해도 중복 Plane work item을 만들지 않는다.
|
||||||
|
- [ ] `identity-ledger` 경로에서 filename slug 기준 upsert와 provider work item conflict가 provider mutation 없이 `conflict`로 구분되는지 pipeline/storage 테스트를 보강한다. 검증: 기존 slug가 다른 provider work item에 묶여 있으면 provider mutation 없이 conflict로 멈춘다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## [API-1] Scan Hint And Revision Gate
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
`services/core/internal/http/gito_webhook.go:22`의 HTTP event shape는 `changed_files`를 handler seam으로 전달하지 않고, `services/core/internal/gitosync/scanner.go:133`은 전체 active/archive tree만 읽는다. SDD S01은 `before..after` 변경 목록을 wakeup hint로 보존하되 `after` 검증 뒤 scan해야 한다.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
HTTP/proto-socket event에서 이미 존재하는 `gitoevents.ChangedFile` 형태를 bridge/scanner 입력까지 유지하고, scanner는 hint를 로그/결정 근거로만 사용한다. enqueue 여부는 계속 `git fetch`, `git rev-parse refs/remotes/<remote>/<branch>`, target revision active index scan 결과로만 결정한다.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// services/core/internal/http/gito_webhook.go:22
|
||||||
|
type GitoBranchUpdatedEvent struct {
|
||||||
|
RepoID string
|
||||||
|
Branch string
|
||||||
|
Before string
|
||||||
|
After string
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
type GitoBranchUpdatedEvent struct {
|
||||||
|
RepoID string
|
||||||
|
Branch string
|
||||||
|
Before string
|
||||||
|
After string
|
||||||
|
ChangedFiles []gitoevents.ChangedFile
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/http/gito_webhook.go`: validated `changed_files`를 typed event로 전달한다.
|
||||||
|
- [ ] `services/core/internal/http/gito_webhook_test.go`: changed_files가 handler로 전달되고 malformed shape는 400인 테스트를 유지/보강한다.
|
||||||
|
- [ ] `services/core/internal/gitosync/scanner.go`: hint와 full active scan의 책임을 주석/결과 타입에 명시한다.
|
||||||
|
- [ ] `services/core/internal/gitosync/scanner_test.go`: hint가 비어 있거나 다른 파일만 있어도 after verified active index가 source of truth임을 테스트한다.
|
||||||
|
- [ ] `services/core/internal/gitosync/runner_test.go`: wire event changed_files가 scanner로 유지되는 assertion을 추가한다.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S01. Add or update tests named around `ChangedFilesAreHintOnly` in HTTP/gitosync packages.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/http ./internal/gitoevents ./internal/gitosync
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS, no duplicate enqueue when `after` is not verified.
|
||||||
|
|
||||||
|
## [API-2] Missing Create And Ledger Idempotency
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
`services/core/internal/gitosync/bridge.go:137` builds missing-create jobs, and `services/core/internal/roadmapsyncpipeline/service.go:158` creates Plane work items when no existing identity row exists. The existing path needs explicit same-slug/same-revision duplicate retry coverage and conflict evidence for S02/S03.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Keep the existing missing-create branch, but make tests assert that a persisted slug identity prevents a second create and that provider-work-item unique conflicts return `SyncActionConflict` before any additional provider mutation.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// services/core/internal/roadmapsyncpipeline/service.go:158
|
||||||
|
} else if in.Expected.WorkItemID == "" && in.Ref.ID == "" {
|
||||||
|
creator, ok := s.provider.(workitem.Creator)
|
||||||
|
...
|
||||||
|
createRes, err := creator.CreateWorkItem(ctx, workitem.CreateInput{...})
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// same branch, but covered by an existing-row retry test:
|
||||||
|
// found=true with completed develop_matched must not call CreateWorkItem again.
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: add duplicate retry test for missing-create existing identity.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: assert conflict result does not call create/body/status after upsert conflict.
|
||||||
|
- [ ] `services/core/internal/storage/roadmap_sync_identities_test.go`: keep provider work item unique conflict coverage aligned with slug upsert.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S02/S03. No production behavior change is needed if existing code already satisfies the tests; if a test fails, fix the minimal production path.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/roadmapsyncpipeline ./internal/storage ./internal/gitosync
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; fake provider `CreateWorkItem` call count stays one across duplicate retry.
|
||||||
|
|
||||||
|
## [API-3] Review Stub Completion
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
Roadmap completion requires review evidence copied from active `CODE_REVIEW-*-G??.md`; implementation is incomplete until the review stub is filled.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Fill completion table, checklist, plan deviations, design decisions, and exact command outputs in `CODE_REVIEW-cloud-G07.md`.
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/CODE_REVIEW-cloud-G07.md`: fill implementation-owned sections only.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
No test file; this is required implementation evidence.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: no output.
|
||||||
|
|
||||||
|
## 수정 파일 요약
|
||||||
|
|
||||||
|
| 파일 | 항목 |
|
||||||
|
|------|------|
|
||||||
|
| `services/core/internal/http/gito_webhook.go` | API-1 |
|
||||||
|
| `services/core/internal/http/gito_webhook_test.go` | API-1 |
|
||||||
|
| `services/core/internal/gitosync/scanner.go` | API-1 |
|
||||||
|
| `services/core/internal/gitosync/scanner_test.go` | API-1 |
|
||||||
|
| `services/core/internal/gitosync/runner_test.go` | API-1 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service.go` | API-2 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service_test.go` | API-2 |
|
||||||
|
| `services/core/internal/storage/roadmap_sync_identities_test.go` | API-2 |
|
||||||
|
| `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/CODE_REVIEW-cloud-G07.md` | API-3 |
|
||||||
|
|
||||||
|
## 최종 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
cd services/core && go test -count=1 ./internal/http ./internal/gitoevents ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
cd services/core && go vet ./internal/http ./internal/gitoevents ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: all commands exit 0. Fresh `-count=1` is required for Go tests; cached output is not acceptable for this plan.
|
||||||
|
|
||||||
|
모든 코드 변경 완료 후 반드시 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채운다. 이 파일 작성이 구현의 마지막 단계다.
|
||||||
|
|
@ -0,0 +1,127 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/02+01_identity_backfill plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Code Review Reference - API
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — READ FIRST] Filling in this file is the mandatory final step of implementation.**
|
||||||
|
> The task is NOT complete until every implementation-owned section below is filled in.
|
||||||
|
> Complete the `구현 체크리스트`; the final checklist item is mandatory before saving.
|
||||||
|
> Fill implementation-owned sections, then stop with active files in place and report ready for review.
|
||||||
|
> If implementation is blocked by a selected Milestone `구현 잠금 > 결정 필요` item, fill `사용자 리뷰 요청` with linked evidence and stop with active files in place; code-review decides whether to write `USER_REVIEW.md`.
|
||||||
|
> Do not ask the user directly, present choices in chat, or call `request_user_input` during implementation.
|
||||||
|
> Finalization (`코드리뷰 결과`, log rename, `complete.log`, archive moves, `코드리뷰 전용 체크리스트`) is review-agent-only.
|
||||||
|
|
||||||
|
## 개요
|
||||||
|
|
||||||
|
date=2026-07-02
|
||||||
|
task=m-agent-origin-milestone-creation-sync/02+01_identity_backfill, plan=0, tag=API
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `identity-backfill`: Plane 생성 직후 Milestone markdown에 `Provider identity` block을 주입하고 Core-authored backfill commit을 `develop`에 push한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 이 파일을 읽는 리뷰 에이전트에게
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 아래 종결 절차는 코드리뷰 에이전트 전용이다. 구현 에이전트는 이 섹션을 실행하지 않는다.
|
||||||
|
|
||||||
|
각 항목의 구현을 실제 소스 파일과 대조하고, `검증 결과` 섹션의 출력이 코드와 일치하는지 확인하세요.
|
||||||
|
리뷰 완료는 판정 append, active 파일 log archive, PASS 시 `complete.log` 작성과 task directory archive까지 끝난 상태를 의미합니다.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 구현 항목별 완료 여부
|
||||||
|
|
||||||
|
| 항목 | 완료 여부 |
|
||||||
|
|------|---------|
|
||||||
|
| [API-1] Durable Backfill Step | [ ] |
|
||||||
|
| [API-2] Identity Backfill Writer And Commit Scope | [ ] |
|
||||||
|
| [API-3] Scheduler Wiring And Review Evidence | [ ] |
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `identity-backfill` step을 storage/domain ordered step set에 추가하고 DB check constraint migration/query tests를 갱신한다.
|
||||||
|
- [ ] missing-create Plane create + identity upsert 직후 Milestone markdown에 `Provider identity` block을 주입하는 pipeline seam을 추가한다.
|
||||||
|
- [ ] backfill writer가 identity block 외 unrelated roadmap 변경을 commit하지 않는 git scope check를 구현/테스트한다. 검증: backfill commit에는 identity block 외의 unrelated roadmap 변경이 포함되지 않는다.
|
||||||
|
- [ ] push 성공 뒤에만 `identity_backfilled` ledger step을 mark하고, 실패 시 retry가 create를 반복하지 않고 backfill부터 재개하게 한다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## 코드리뷰 전용 체크리스트
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 이 체크리스트는 코드리뷰 에이전트만 사용한다.
|
||||||
|
|
||||||
|
- [ ] `코드리뷰 결과`에 `PASS`, `WARN`, `FAIL` 중 하나의 판정을 append한다.
|
||||||
|
- [ ] 판정과 `차원별 평가`, Required/Suggested/Nit 분류가 서로 일치한다.
|
||||||
|
- [ ] active `CODE_REVIEW-*-G??.md`를 `code_review_cloud_G08_N.log`로 아카이브한다.
|
||||||
|
- [ ] active `PLAN-*-G??.md`를 `plan_cloud_G08_M.log`로 아카이브한다.
|
||||||
|
- [ ] `.gitignore`의 Agent-Ops 관리 block이 `agent-task/**/*.md`와 `agent-task/**/*.log`를 unignore하고 `agent-roadmap/current.md`를 ignore하는지 확인한다.
|
||||||
|
- [ ] PASS이면 `complete.log`를 작성하고 active `.md` 파일을 남기지 않는다.
|
||||||
|
- [ ] PASS이면 active task 디렉터리를 `agent-task/archive/YYYY/MM/m-agent-origin-milestone-creation-sync/02+01_identity_backfill/`로 이동한다.
|
||||||
|
- [ ] PASS이고 task group이 `m-<milestone-slug>`이면 런타임이 읽을 완료 이벤트 메타데이터를 보고하고, roadmap 수정이나 `update-roadmap` 직접 호출을 하지 않는다.
|
||||||
|
- [ ] PASS split 작업이면 이동 후 빈 active parent를 제거하거나, 남은 sibling/file이 있어 유지했다고 확인한다.
|
||||||
|
- [ ] WARN/FAIL이면 다음 active plan/review 파일 또는 `USER_REVIEW.md`를 작성하고 `complete.log`를 작성하지 않는다.
|
||||||
|
|
||||||
|
## 계획 대비 변경 사항
|
||||||
|
|
||||||
|
_구현 에이전트가 계획과 다르게 구현한 부분을 이유와 함께 기록한다._
|
||||||
|
|
||||||
|
## 주요 설계 결정
|
||||||
|
|
||||||
|
_구현 에이전트가 주요 설계 결정 사항을 기록한다._
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청
|
||||||
|
|
||||||
|
_기본값은 `없음`이다. 구현 중 새 결정이 필요해 보여도 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. 이 섹션은 선택된 Milestone `구현 잠금 > 결정 필요` 항목이 실구현을 차단할 때만 채운다. 외부 환경/secret/서비스 준비, 검증 증거 공백, 반복 실패, 일반 범위 조정은 사용자 리뷰 요청이 아니며 `검증 결과`, `계획 대비 변경 사항`, 또는 code-review의 일반 follow-up plan으로 처리한다._
|
||||||
|
|
||||||
|
- 상태: 없음
|
||||||
|
- 사유 유형: 없음
|
||||||
|
- 연결 대상: 없음
|
||||||
|
- 결정 필요: 없음
|
||||||
|
- 차단 근거: 없음
|
||||||
|
- 실행한 검증/명령: 없음
|
||||||
|
- 자동 후속 불가 이유: 없음
|
||||||
|
- 재개 조건: 없음
|
||||||
|
|
||||||
|
## 리뷰어를 위한 체크포인트
|
||||||
|
|
||||||
|
- Implementation waited for predecessor `01_scan_create_ledger` completion.
|
||||||
|
- `identity_backfilled` is durable and ordered after `develop_matched`.
|
||||||
|
- Backfill commit stages only the target Milestone identity block and records ledger only after push success.
|
||||||
|
|
||||||
|
## 검증 결과
|
||||||
|
|
||||||
|
_구현 에이전트가 각 중간 검증 및 최종 검증 명령 실행 후 출력을 여기에 붙여 넣는다._
|
||||||
|
|
||||||
|
### API-1 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/roadmapsync ./internal/storage
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-2 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/roadmapsyncpipeline ./internal/authoring
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-3 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/scheduler ./cmd/server ./internal/roadmapsyncpipeline
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 최종 검증
|
||||||
|
```sh
|
||||||
|
$ git diff --check
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go test -count=1 ./internal/roadmapsync ./internal/storage ./internal/authoring ./internal/roadmapsyncpipeline ./internal/scheduler ./cmd/server
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go vet ./internal/roadmapsync ./internal/storage ./internal/authoring ./internal/roadmapsyncpipeline ./internal/scheduler ./cmd/server
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — BEFORE SAVING] Have you filled in every implementation-owned section: completion table, implementation checklist, changes from plan, design decisions, and verification output?**
|
||||||
|
|
@ -0,0 +1,272 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/02+01_identity_backfill plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Plan - API
|
||||||
|
|
||||||
|
## 이 파일을 읽는 구현 에이전트에게
|
||||||
|
|
||||||
|
구현 후 active `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 반드시 실제 구현 내용과 검증 출력으로 채운다. 검증을 실행하고, active 파일은 그대로 둔 뒤 리뷰 준비를 보고한다. 최종 판정, log rename, `complete.log`, archive 이동은 code-review 스킬 전용이다.
|
||||||
|
|
||||||
|
선택된 Milestone의 `구현 잠금 > 결정 필요` 항목이 실구현을 막을 때만 review stub의 `사용자 리뷰 요청` 섹션을 채우고 멈춘다. 구현 중 사용자에게 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다.
|
||||||
|
|
||||||
|
## 배경
|
||||||
|
|
||||||
|
Missing-create는 Plane work item과 DB identity row를 만들지만, 그 identity를 source-of-truth roadmap markdown에 되돌려 쓰는 commit/push 경로가 아직 없다. 이 plan은 S04에 해당하는 identity-only backfill을 durable step으로 추가해, created Plane identity가 active Milestone 파일에 portable anchor로 남도록 한다.
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청 흐름
|
||||||
|
|
||||||
|
사용자 리뷰 요청은 선택된 Milestone lock decision만 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 직접 사용자 prompt는 금지이며, code-review가 정당성을 검증하고 실제 `USER_REVIEW.md` 작성을 소유한다.
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `identity-backfill`: Plane 생성 직후 Milestone markdown에 `Provider identity` block을 주입하고 Core-authored backfill commit을 `develop`에 push한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 분석 결과
|
||||||
|
|
||||||
|
### 읽은 파일
|
||||||
|
|
||||||
|
- `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- `agent-contract/outer/gito-branch-webhook-consumer-v1.md`
|
||||||
|
- `agent-test/local/rules.md`
|
||||||
|
- `agent-test/local/core-smoke.md`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service_test.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps_test.go`
|
||||||
|
- `services/core/internal/authoring/identity_write.go`
|
||||||
|
- `services/core/internal/authoring/identity_write_test.go`
|
||||||
|
- `services/core/internal/gitosync/scanner.go`
|
||||||
|
- `services/core/internal/gitosync/scanner_test.go`
|
||||||
|
- `services/core/internal/scheduler/roadmap_sync_jobs.go`
|
||||||
|
- `services/core/internal/scheduler/jobs.go`
|
||||||
|
- `services/core/queries/roadmap_sync_steps.sql`
|
||||||
|
- `services/core/migrations/00007_create_roadmap_sync_steps.sql`
|
||||||
|
|
||||||
|
### SDD 기준
|
||||||
|
|
||||||
|
- SDD: `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- 상태: `[승인됨]`, SDD 잠금 해제, 사용자 리뷰 없음.
|
||||||
|
- Targeted scenario: S04=`identity-backfill`.
|
||||||
|
- Evidence Map row: identity backfill writer test and git commit scope check; completion evidence must show `identity-backfill` Roadmap Completion and commit diff evidence.
|
||||||
|
- Checklist is derived from S04: inject provider identity block, commit only that block, push to `develop`, and record the durable step after the push succeeds.
|
||||||
|
|
||||||
|
### 테스트 환경 규칙
|
||||||
|
|
||||||
|
- test_env: `local`.
|
||||||
|
- `agent-test/local/rules.md` present/read.
|
||||||
|
- Matched profile read: `agent-test/local/core-smoke.md`.
|
||||||
|
- Current preflight: repo root `/config/workspace/nomadcode`, branch `main`, HEAD `d80abe83579dd0d6fbc86b1a74c83db6d18c756d`, `go version go1.26.2 linux/arm64`, `git version 2.43.0`.
|
||||||
|
- Verification commands use current checkout focused Go tests plus `git diff --check`. Remote runner evidence may be collected after source sync to `$HOME/agent-work/nomadcode`.
|
||||||
|
|
||||||
|
### 테스트 커버리지 공백
|
||||||
|
|
||||||
|
- Existing `authoring.LocalIdentityWriter` injects provider identity into changed milestone files, but it is tied to authoring task dirty workspace state and does not commit/push identity-only backfills.
|
||||||
|
- Existing `roadmapsyncpipeline.SyncCreation` missing-create branch returns after `StepDevelopMatched` and has no backfill step or git scope check.
|
||||||
|
- Existing storage step enum/check constraint lacks an identity-backfilled step.
|
||||||
|
|
||||||
|
### 심볼 참조
|
||||||
|
|
||||||
|
- New step symbol likely needed: `identity_backfilled`. Grep all `StepPlaneTodoMoved`, `OrderedSteps`, and `roadmap_sync_steps_step_check` references before editing.
|
||||||
|
|
||||||
|
### 분할 판단
|
||||||
|
|
||||||
|
- Split decision policy evaluated before file selection.
|
||||||
|
- This dependent subtask is `02+01_identity_backfill`; predecessor index `01` is required.
|
||||||
|
- Active predecessor lookup: no `agent-task/m-agent-origin-milestone-creation-sync/01_*/complete.log` or `01+*/complete.log` exists at plan creation.
|
||||||
|
- Archive predecessor lookup: not performed because this is a new active task group and no prior completion can satisfy the new first subtask.
|
||||||
|
- Implementer must wait for `01_scan_create_ledger` PASS/complete.log before starting this plan.
|
||||||
|
|
||||||
|
### 범위 결정 근거
|
||||||
|
|
||||||
|
- Include only identity backfill writer/commit/push and durable ledger step.
|
||||||
|
- Exclude self-loop redelivery interpretation, provider body/title update projection, broad conflict taxonomy, and live field smoke; those are later dependent plans.
|
||||||
|
|
||||||
|
### 빌드 등급
|
||||||
|
|
||||||
|
- `cloud-G08`: git write/push, DB step schema, pipeline side effects, and provider identity contracts are all in scope; verification must prove no unrelated roadmap diff is pushed.
|
||||||
|
|
||||||
|
## 의존 관계 및 구현 순서
|
||||||
|
|
||||||
|
`02+01_identity_backfill` depends on sibling predecessor `01_scan_create_ledger`. Start implementation only after `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/complete.log` exists or the matching archived `complete.log` is explicitly provided by runtime.
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `identity-backfill` step을 storage/domain ordered step set에 추가하고 DB check constraint migration/query tests를 갱신한다.
|
||||||
|
- [ ] missing-create Plane create + identity upsert 직후 Milestone markdown에 `Provider identity` block을 주입하는 pipeline seam을 추가한다.
|
||||||
|
- [ ] backfill writer가 identity block 외 unrelated roadmap 변경을 commit하지 않는 git scope check를 구현/테스트한다. 검증: backfill commit에는 identity block 외의 unrelated roadmap 변경이 포함되지 않는다.
|
||||||
|
- [ ] push 성공 뒤에만 `identity_backfilled` ledger step을 mark하고, 실패 시 retry가 create를 반복하지 않고 backfill부터 재개하게 한다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## [API-1] Durable Backfill Step
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
`services/core/internal/roadmapsync/retry.go:10` has only develop, comment, body, todo steps. `services/core/internal/storage/roadmap_sync_steps.go:15` mirrors the same closed set. S04 needs a durable identity backfill step between Plane create and later self-loop checks.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Add `identity_backfilled` to domain/storage ordered steps and migrate the DB check constraint. Keep ordering explicit so retries can resume after create/upsert without re-creating Plane work items.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// services/core/internal/roadmapsync/retry.go:10
|
||||||
|
const (
|
||||||
|
StepDevelopMatched Step = "develop_matched"
|
||||||
|
StepOriginalCommentPreserved Step = "original_comment_preserved"
|
||||||
|
StepPlaneBodyUpdated Step = "plane_body_updated"
|
||||||
|
StepPlaneTodoMoved Step = "plane_todo_moved"
|
||||||
|
)
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
const (
|
||||||
|
StepDevelopMatched Step = "develop_matched"
|
||||||
|
StepIdentityBackfilled Step = "identity_backfilled"
|
||||||
|
StepOriginalCommentPreserved Step = "original_comment_preserved"
|
||||||
|
StepPlaneBodyUpdated Step = "plane_body_updated"
|
||||||
|
StepPlaneTodoMoved Step = "plane_todo_moved"
|
||||||
|
)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/roadmapsync/retry.go`: add step and order.
|
||||||
|
- [ ] `services/core/internal/roadmapsync/retry_test.go`: first incomplete and all-complete cases include new step.
|
||||||
|
- [ ] `services/core/internal/storage/roadmap_sync_steps.go`: add storage step and validation.
|
||||||
|
- [ ] `services/core/internal/storage/roadmap_sync_steps_test.go`: validation and completed-set tests include new step.
|
||||||
|
- [ ] `services/core/migrations/00010_add_roadmap_identity_backfilled_step.sql`: update check constraint without dropping data.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required because this changes retry persistence semantics.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/roadmapsync ./internal/storage
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; ordered step tests prove `identity_backfilled` sits after `develop_matched`.
|
||||||
|
|
||||||
|
## [API-2] Identity Backfill Writer And Commit Scope
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
`services/core/internal/authoring/identity_write.go:37` injects identity into dirty authoring workspace files, but missing-create backfill needs a Core-authored identity-only commit in the develop checkout. `services/core/internal/roadmapsyncpipeline/service.go:179` creates the Plane item and line 223 marks only `develop_matched`, then returns.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Introduce a pipeline-owned backfill seam that writes the identity block to `Expected.RoadmapMilestonePath` in the configured develop checkout, stages only that path, verifies the diff contains only the provider identity block, commits with a Core-authored marker, and pushes to `develop`.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// services/core/internal/roadmapsyncpipeline/service.go:223
|
||||||
|
if _, err := s.store.MarkStepCompleted(ctx, identityRow.ID, toStorageStep(roadmapsync.StepDevelopMatched)); err != nil {
|
||||||
|
return SyncCreationResult{}, err
|
||||||
|
}
|
||||||
|
|
||||||
|
return SyncCreationResult{
|
||||||
|
Action: SyncActionProjected,
|
||||||
|
Reason: "plane work item created for missing active milestone",
|
||||||
|
NextStep: roadmapsync.StepDevelopMatched,
|
||||||
|
}, nil
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// after develop_matched ledger mark:
|
||||||
|
if err := s.backfiller.BackfillIdentity(ctx, BackfillInput{Identity: identity, MarkdownPath: identity.RoadmapMilestonePath}); err != nil {
|
||||||
|
return SyncCreationResult{}, err
|
||||||
|
}
|
||||||
|
if _, err := s.store.MarkStepCompleted(ctx, identityRow.ID, toStorageStep(roadmapsync.StepIdentityBackfilled)); err != nil {
|
||||||
|
return SyncCreationResult{}, err
|
||||||
|
}
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service.go`: add optional backfiller dependency and missing-create resume path.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: fake backfiller proves call order create -> identity upsert -> develop_matched mark -> backfill -> identity_backfilled mark.
|
||||||
|
- [ ] `services/core/internal/authoring/identity_write.go` or new nearby helper: reuse identity block rendering without dirty-worktree assumptions.
|
||||||
|
- [ ] `services/core/internal/authoring/identity_write_test.go`: identity block rendering remains parser-compatible.
|
||||||
|
- [ ] New git-scope test with temp repo: unrelated roadmap edit stays unstaged/uncommitted and commit diff contains only provider identity block.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S04, including temp git repo commit-scope test.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/roadmapsyncpipeline ./internal/authoring
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; fake backfiller and temp git tests prove retry and commit scope.
|
||||||
|
|
||||||
|
## [API-3] Scheduler Wiring And Review Evidence
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
`services/core/internal/scheduler/roadmap_sync_jobs.go:81` passes pipeline input but has no way to configure a backfill checkout/pusher. Without worker wiring, production jobs cannot perform S04.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Wire the backfiller at server/scheduler construction where Gito develop checkout path and remote/branch config are already available. If config is missing, missing-create backfill must fail explicitly rather than silently completing with only DB identity.
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/scheduler/roadmap_sync_jobs.go`: pass any new pipeline input fields only if needed; avoid putting secrets in job args.
|
||||||
|
- [ ] `services/core/cmd/server/main.go`: wire backfiller from `GITO_DEVELOP_REPO_PATH`, `GITO_REMOTE_NAME`, `GITO_BRANCH`.
|
||||||
|
- [ ] `services/core/internal/scheduler/jobs_test.go` or server wiring tests: configured roadmap sync worker has backfiller when Gito checkout is configured.
|
||||||
|
- [ ] `agent-task/m-agent-origin-milestone-creation-sync/02+01_identity_backfill/CODE_REVIEW-cloud-G08.md`: fill implementation-owned sections.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Add wiring tests if constructor seams allow it; otherwise record code inspection evidence plus focused pipeline tests.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/scheduler ./cmd/server ./internal/roadmapsyncpipeline
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS.
|
||||||
|
|
||||||
|
## 수정 파일 요약
|
||||||
|
|
||||||
|
| 파일 | 항목 |
|
||||||
|
|------|------|
|
||||||
|
| `services/core/internal/roadmapsync/retry.go` | API-1 |
|
||||||
|
| `services/core/internal/roadmapsync/retry_test.go` | API-1 |
|
||||||
|
| `services/core/internal/storage/roadmap_sync_steps.go` | API-1 |
|
||||||
|
| `services/core/internal/storage/roadmap_sync_steps_test.go` | API-1 |
|
||||||
|
| `services/core/migrations/00010_add_roadmap_identity_backfilled_step.sql` | API-1 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service.go` | API-2 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service_test.go` | API-2 |
|
||||||
|
| `services/core/internal/authoring/identity_write.go` | API-2 |
|
||||||
|
| `services/core/internal/authoring/identity_write_test.go` | API-2 |
|
||||||
|
| `services/core/internal/scheduler/roadmap_sync_jobs.go` | API-3 |
|
||||||
|
| `services/core/cmd/server/main.go` | API-3 |
|
||||||
|
| `services/core/internal/scheduler/jobs_test.go` | API-3 |
|
||||||
|
| `agent-task/m-agent-origin-milestone-creation-sync/02+01_identity_backfill/CODE_REVIEW-cloud-G08.md` | API-3 |
|
||||||
|
|
||||||
|
## 최종 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
cd services/core && go test -count=1 ./internal/roadmapsync ./internal/storage ./internal/authoring ./internal/roadmapsyncpipeline ./internal/scheduler ./cmd/server
|
||||||
|
cd services/core && go vet ./internal/roadmapsync ./internal/storage ./internal/authoring ./internal/roadmapsyncpipeline ./internal/scheduler ./cmd/server
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: all commands exit 0. Fresh `-count=1` is required for Go tests.
|
||||||
|
|
||||||
|
모든 코드 변경 완료 후 반드시 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채운다. 이 파일 작성이 구현의 마지막 단계다.
|
||||||
|
|
@ -0,0 +1,130 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Code Review Reference - API
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — READ FIRST] Filling in this file is the mandatory final step of implementation.**
|
||||||
|
> The task is NOT complete until every implementation-owned section below is filled in.
|
||||||
|
> Complete the `구현 체크리스트`; the final checklist item is mandatory before saving.
|
||||||
|
> Fill implementation-owned sections, then stop with active files in place and report ready for review.
|
||||||
|
> If implementation is blocked by a selected Milestone `구현 잠금 > 결정 필요` item, fill `사용자 리뷰 요청` with linked evidence and stop with active files in place; code-review decides whether to write `USER_REVIEW.md`.
|
||||||
|
> Do not ask the user directly, present choices in chat, or call `request_user_input` during implementation.
|
||||||
|
> Finalization (`코드리뷰 결과`, log rename, `complete.log`, archive moves, `코드리뷰 전용 체크리스트`) is review-agent-only.
|
||||||
|
|
||||||
|
## 개요
|
||||||
|
|
||||||
|
date=2026-07-02
|
||||||
|
task=m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict, plan=0, tag=API
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `self-loop`: Core-authored identity backfill webhook은 provider 생성/갱신을 반복하지 않고 ledger와 markdown identity 일치 여부만 확인한다.
|
||||||
|
- `identity-update`: provider identity가 이미 있는 Milestone의 agent-origin 본문/제목 변경은 Plane 본문/제목 갱신으로 수렴한다.
|
||||||
|
- `conflict-policy`: rename, filename slug reuse, provider identity mismatch, stale Plane work item, duplicate active slug를 안전하게 분류한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 이 파일을 읽는 리뷰 에이전트에게
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 아래 종결 절차는 코드리뷰 에이전트 전용이다. 구현 에이전트는 이 섹션을 실행하지 않는다.
|
||||||
|
|
||||||
|
각 항목의 구현을 실제 소스 파일과 대조하고, `검증 결과` 섹션의 출력이 코드와 일치하는지 확인하세요.
|
||||||
|
리뷰 완료는 판정 append, active 파일 log archive, PASS 시 `complete.log` 작성과 task directory archive까지 끝난 상태를 의미합니다.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 구현 항목별 완료 여부
|
||||||
|
|
||||||
|
| 항목 | 완료 여부 |
|
||||||
|
|------|---------|
|
||||||
|
| [API-1] Self-Loop Redelivery Guard | [ ] |
|
||||||
|
| [API-2] Existing Identity Update Projection | [ ] |
|
||||||
|
| [API-3] Conflict Classification Matrix | [ ] |
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `self-loop`에서 Core-authored identity-only backfill commit 재전달은 markdown provider identity와 DB ledger를 비교하고 provider create/update 없이 complete/no-op으로 수렴한다. 검증: backfill commit 재전달과 Core 재시작 후 재전달 모두 provider mutation을 호출하지 않는다.
|
||||||
|
- [ ] `identity-update`에서 provider identity가 이미 있는 active Milestone의 제목/본문 변경은 `after` revision guard 후 Plane title/body update로 투영하고 completed-step ledger로 partial failure 재시도가 가능하다.
|
||||||
|
- [ ] `conflict-policy`에서 rename, filename slug reuse, provider identity mismatch, stale Plane work item, duplicate active slug가 destructive overwrite 없이 conflict/not-ready/skip으로 분류된다.
|
||||||
|
- [ ] conflict/not-ready/skip result는 operator가 확인할 수 있는 reason/log를 남기고, provider create/update/status mutation이 제한되는지 테스트한다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## 코드리뷰 전용 체크리스트
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 이 체크리스트는 코드리뷰 에이전트만 사용한다.
|
||||||
|
|
||||||
|
- [ ] `코드리뷰 결과`에 `PASS`, `WARN`, `FAIL` 중 하나의 판정을 append한다.
|
||||||
|
- [ ] 판정과 `차원별 평가`, Required/Suggested/Nit 분류가 서로 일치한다.
|
||||||
|
- [ ] active `CODE_REVIEW-*-G??.md`를 `code_review_cloud_G08_N.log`로 아카이브한다.
|
||||||
|
- [ ] active `PLAN-*-G??.md`를 `plan_cloud_G08_M.log`로 아카이브한다.
|
||||||
|
- [ ] `.gitignore`의 Agent-Ops 관리 block이 `agent-task/**/*.md`와 `agent-task/**/*.log`를 unignore하고 `agent-roadmap/current.md`를 ignore하는지 확인한다.
|
||||||
|
- [ ] PASS이면 `complete.log`를 작성하고 active `.md` 파일을 남기지 않는다.
|
||||||
|
- [ ] PASS이면 active task 디렉터리를 `agent-task/archive/YYYY/MM/m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict/`로 이동한다.
|
||||||
|
- [ ] PASS이고 task group이 `m-<milestone-slug>`이면 런타임이 읽을 완료 이벤트 메타데이터를 보고하고, roadmap 수정이나 `update-roadmap` 직접 호출을 하지 않는다.
|
||||||
|
- [ ] PASS split 작업이면 이동 후 빈 active parent를 제거하거나, 남은 sibling/file이 있어 유지했다고 확인한다.
|
||||||
|
- [ ] WARN/FAIL이면 다음 active plan/review 파일 또는 `USER_REVIEW.md`를 작성하고 `complete.log`를 작성하지 않는다.
|
||||||
|
|
||||||
|
## 계획 대비 변경 사항
|
||||||
|
|
||||||
|
_구현 에이전트가 계획과 다르게 구현한 부분을 이유와 함께 기록한다._
|
||||||
|
|
||||||
|
## 주요 설계 결정
|
||||||
|
|
||||||
|
_구현 에이전트가 주요 설계 결정 사항을 기록한다._
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청
|
||||||
|
|
||||||
|
_기본값은 `없음`이다. 구현 중 새 결정이 필요해 보여도 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. 이 섹션은 선택된 Milestone `구현 잠금 > 결정 필요` 항목이 실구현을 차단할 때만 채운다. 외부 환경/secret/서비스 준비, 검증 증거 공백, 반복 실패, 일반 범위 조정은 사용자 리뷰 요청이 아니며 `검증 결과`, `계획 대비 변경 사항`, 또는 code-review의 일반 follow-up plan으로 처리한다._
|
||||||
|
|
||||||
|
- 상태: 없음
|
||||||
|
- 사유 유형: 없음
|
||||||
|
- 연결 대상: 없음
|
||||||
|
- 결정 필요: 없음
|
||||||
|
- 차단 근거: 없음
|
||||||
|
- 실행한 검증/명령: 없음
|
||||||
|
- 자동 후속 불가 이유: 없음
|
||||||
|
- 재개 조건: 없음
|
||||||
|
|
||||||
|
## 리뷰어를 위한 체크포인트
|
||||||
|
|
||||||
|
- Implementation waited for predecessor `01_scan_create_ledger` and `02+01_identity_backfill` completion.
|
||||||
|
- Self-loop redelivery compares markdown identity and ledger before returning complete/no-op.
|
||||||
|
- Existing identity title/body update is retryable through completed-step ledger.
|
||||||
|
- Conflict/not-ready/skip cases do not call provider mutation except the intended identity-update path.
|
||||||
|
|
||||||
|
## 검증 결과
|
||||||
|
|
||||||
|
_구현 에이전트가 각 중간 검증 및 최종 검증 명령 실행 후 출력을 여기에 붙여 넣는다._
|
||||||
|
|
||||||
|
### API-1 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-2 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/adapters/plane ./internal/workitem
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-3 중간 검증
|
||||||
|
```sh
|
||||||
|
$ cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/scheduler
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 최종 검증
|
||||||
|
```sh
|
||||||
|
$ git diff --check
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage ./internal/adapters/plane ./internal/workitem ./internal/scheduler ./internal/http
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go vet ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage ./internal/adapters/plane ./internal/workitem ./internal/scheduler ./internal/http
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — BEFORE SAVING] Have you filled in every implementation-owned section: completion table, implementation checklist, changes from plan, design decisions, and verification output?**
|
||||||
|
|
@ -0,0 +1,283 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Plan - API
|
||||||
|
|
||||||
|
## 이 파일을 읽는 구현 에이전트에게
|
||||||
|
|
||||||
|
구현 후 active `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 반드시 실제 구현 내용과 검증 출력으로 채운다. 검증을 실행하고, active 파일은 그대로 둔 뒤 리뷰 준비를 보고한다. 최종 판정, log rename, `complete.log`, archive 이동은 code-review 스킬 전용이다.
|
||||||
|
|
||||||
|
선택된 Milestone의 `구현 잠금 > 결정 필요` 항목이 실구현을 막을 때만 review stub의 `사용자 리뷰 요청` 섹션을 채우고 멈춘다. 구현 중 사용자에게 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다.
|
||||||
|
|
||||||
|
## 배경
|
||||||
|
|
||||||
|
Agent-origin 생성 경로가 identity backfill까지 완료되면, Core-authored backfill commit이 다시 Gito webhook으로 들어온다. 이 plan은 backfill 재전달을 provider 생성/갱신 반복 없이 complete/no-op으로 수렴시키고, provider identity가 이미 있는 active Milestone 변경은 Plane 본문/제목 갱신으로 재시도 가능하게 투영하며, destructive overwrite 위험은 conflict/not-ready/skip으로 멈춘다.
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청 흐름
|
||||||
|
|
||||||
|
사용자 리뷰 요청은 선택된 Milestone lock decision만 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 직접 사용자 prompt는 금지이며, code-review가 정당성을 검증하고 실제 `USER_REVIEW.md` 작성을 소유한다.
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `self-loop`: Core-authored identity backfill webhook은 provider 생성/갱신을 반복하지 않고 ledger와 markdown identity 일치 여부만 확인한다.
|
||||||
|
- `identity-update`: provider identity가 이미 있는 Milestone의 agent-origin 본문/제목 변경은 Plane 본문/제목 갱신으로 수렴한다.
|
||||||
|
- `conflict-policy`: rename, filename slug reuse, provider identity mismatch, stale Plane work item, duplicate active slug를 안전하게 분류한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 분석 결과
|
||||||
|
|
||||||
|
### 읽은 파일
|
||||||
|
|
||||||
|
- `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- `agent-contract/outer/gito-branch-webhook-consumer-v1.md`
|
||||||
|
- `agent-test/local/rules.md`
|
||||||
|
- `agent-test/local/core-smoke.md`
|
||||||
|
- `services/core/internal/gitosync/scanner.go`
|
||||||
|
- `services/core/internal/gitosync/scanner_test.go`
|
||||||
|
- `services/core/internal/gitosync/bridge.go`
|
||||||
|
- `services/core/internal/gitosync/bridge_test.go`
|
||||||
|
- `services/core/internal/gitosync/runner.go`
|
||||||
|
- `services/core/internal/gitosync/runner_test.go`
|
||||||
|
- `services/core/internal/roadmapsync/identity.go`
|
||||||
|
- `services/core/internal/roadmapsync/milestone_parser.go`
|
||||||
|
- `services/core/internal/roadmapsync/develop_match.go`
|
||||||
|
- `services/core/internal/roadmapsync/develop_match_test.go`
|
||||||
|
- `services/core/internal/roadmapsync/retry.go`
|
||||||
|
- `services/core/internal/roadmapsync/retry_test.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service_test.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_identities.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_identities_test.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps_test.go`
|
||||||
|
- `services/core/internal/adapters/plane/client.go`
|
||||||
|
- `services/core/internal/adapters/plane/client_test.go`
|
||||||
|
- `services/core/internal/workitem/provider.go`
|
||||||
|
- `services/core/internal/http/gito_webhook.go`
|
||||||
|
- `services/core/internal/http/gito_webhook_test.go`
|
||||||
|
- `services/core/internal/scheduler/roadmap_sync_jobs.go`
|
||||||
|
- `services/core/internal/scheduler/jobs.go`
|
||||||
|
|
||||||
|
### SDD 기준
|
||||||
|
|
||||||
|
- SDD: `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- 상태: `[승인됨]`, SDD 잠금 해제, 사용자 리뷰 없음.
|
||||||
|
- Targeted scenarios: S05=`self-loop`, S06=`identity-update`, S07=`conflict-policy`.
|
||||||
|
- Evidence Map rows: self-loop/redelivery test across process restart or durable ledger; provider identity update projection test; conflict classification tests.
|
||||||
|
- 구현 checklist는 actor/commit marker와 markdown identity/ledger 일치 확인, completed-step ledger 기반 retry, destructive overwrite 금지 순서로 역산한다.
|
||||||
|
|
||||||
|
### 테스트 환경 규칙
|
||||||
|
|
||||||
|
- test_env: `local`.
|
||||||
|
- `agent-test/local/rules.md` present/read.
|
||||||
|
- Matched profile read: `agent-test/local/core-smoke.md`.
|
||||||
|
- Current preflight: repo root `/config/workspace/nomadcode`, branch `main`, HEAD `d80abe83579dd0d6fbc86b1a74c83db6d18c756d`, `go version go1.26.2 linux/arm64`, `git version 2.43.0`.
|
||||||
|
- Verification commands use current checkout focused Go tests plus `git diff --check`.
|
||||||
|
|
||||||
|
### 테스트 커버리지 공백
|
||||||
|
|
||||||
|
- `self-loop`: Core-authored identity-only backfill commit을 재전달했을 때 provider create/update가 호출되지 않는 durable ledger or restart-equivalent test가 필요하다.
|
||||||
|
- `identity-update`: existing identity가 있는 Milestone의 title/body drift를 Plane update로 투영하고 partial failure 후 completed-step ledger에서 재개하는 테스트가 필요하다.
|
||||||
|
- `conflict-policy`: rename, slug reuse, provider identity mismatch, stale provider item, duplicate active slug를 destructive provider mutation 없이 구분하는 통합 classification coverage가 필요하다.
|
||||||
|
|
||||||
|
### 심볼 참조
|
||||||
|
|
||||||
|
- Optional event fields or commit markers may need new symbols. Before editing, grep `GitoBranchUpdatedEvent`, `ChangedFile`, `StepPlaneBodyUpdated`, `SyncActionConflict`, `SyncActionNotReady`, `UpsertRoadmapSyncIdentity`, and Plane provider update interfaces.
|
||||||
|
- If S05 needs actor identity, prefer an optional marker/actor field that preserves the existing webhook contract shape and keeps `changed_files` hint-only.
|
||||||
|
|
||||||
|
### 분할 판단
|
||||||
|
|
||||||
|
- Split decision policy evaluated before file selection.
|
||||||
|
- This dependent subtask is `03+01,02_self_loop_update_conflict`.
|
||||||
|
- Predecessors required:
|
||||||
|
- `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/complete.log`
|
||||||
|
- `agent-task/m-agent-origin-milestone-creation-sync/02+01_identity_backfill/complete.log`
|
||||||
|
- Active predecessor lookup: no predecessor `complete.log` files exist at plan creation.
|
||||||
|
- Archive predecessor lookup: not performed because no active predecessor completion exists and no runtime-provided archive evidence was specified.
|
||||||
|
- Implementer must wait for both predecessor PASS/complete.log files before starting this plan.
|
||||||
|
|
||||||
|
### 범위 결정 근거
|
||||||
|
|
||||||
|
- Include self-loop redelivery, existing-identity Plane title/body update, and conflict taxonomy.
|
||||||
|
- Exclude initial scan/missing-create/ledger foundation, identity backfill commit/push, live field smoke, Plane Todo lifecycle, and child ticket sync.
|
||||||
|
|
||||||
|
### 빌드 등급
|
||||||
|
|
||||||
|
- `cloud-G08`: self-loop and conflict behavior crosses webhook event interpretation, git revision scan, provider mutation, DB idempotency, and retry ordering. A wrong implementation can create duplicate Plane changes or hide destructive conflicts.
|
||||||
|
|
||||||
|
## 의존 관계 및 구현 순서
|
||||||
|
|
||||||
|
`03+01,02_self_loop_update_conflict` depends on sibling predecessors `01_scan_create_ledger` and `02+01_identity_backfill`. Start implementation only after both active `complete.log` files exist or matching archived `complete.log` evidence is explicitly provided by runtime.
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] `self-loop`에서 Core-authored identity-only backfill commit 재전달은 markdown provider identity와 DB ledger를 비교하고 provider create/update 없이 complete/no-op으로 수렴한다. 검증: backfill commit 재전달과 Core 재시작 후 재전달 모두 provider mutation을 호출하지 않는다.
|
||||||
|
- [ ] `identity-update`에서 provider identity가 이미 있는 active Milestone의 제목/본문 변경은 `after` revision guard 후 Plane title/body update로 투영하고 completed-step ledger로 partial failure 재시도가 가능하다.
|
||||||
|
- [ ] `conflict-policy`에서 rename, filename slug reuse, provider identity mismatch, stale Plane work item, duplicate active slug가 destructive overwrite 없이 conflict/not-ready/skip으로 분류된다.
|
||||||
|
- [ ] conflict/not-ready/skip result는 operator가 확인할 수 있는 reason/log를 남기고, provider create/update/status mutation이 제한되는지 테스트한다.
|
||||||
|
- [ ] `git diff --check`, focused `go test -count=1`, focused `go vet`를 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## [API-1] Self-Loop Redelivery Guard
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
S04의 identity backfill commit은 다시 `branch.updated` webhook을 만들 수 있다. S05는 이 재전달이 Plane 생성/갱신 반복으로 이어지지 않고 ledger와 markdown identity 일치 확인만 수행해야 한다고 요구한다.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Core-authored backfill commit을 actor/commit marker와 identity-only diff로 판별하되, 최종 source of truth는 `after` revision scan 결과와 `roadmap_sync_identities` row로 둔다. marker가 없거나 유실되어도 markdown identity와 ledger가 일치하면 provider mutation 없이 complete/no-op으로 수렴한다.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// pseudo-flow
|
||||||
|
scan after revision -> classify active milestone -> create/update provider
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// pseudo-flow
|
||||||
|
scan after revision -> if identity matches ledger and diff is identity-only/self-authored:
|
||||||
|
return complete/no-op without provider mutation
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/gitosync/scanner.go`: identity-only/self-authored hint를 scan result or classification input으로 보존한다.
|
||||||
|
- [ ] `services/core/internal/gitosync/scanner_test.go`: identity-only diff가 active scan을 우회하지 않고 hint로만 쓰이는지 테스트한다.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service.go`: ledger+markdown identity match면 provider mutation 없이 complete/no-op result를 반환한다.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: redelivery and restart-equivalent retry test를 추가한다.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S05. Provider fake must fail the test if create/update/status mutation is called on self-loop input.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; self-loop redelivery returns complete/no-op without provider mutation.
|
||||||
|
|
||||||
|
## [API-2] Existing Identity Update Projection
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
Provider identity가 이미 있는 active Milestone은 생성 후보가 아니라 Plane title/body update 후보여야 한다. S06은 `develop` revision guard와 completed-step ledger로 partial failure retry가 가능해야 한다고 요구한다.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Existing identity classification이 ledger row와 markdown identity를 확인한 뒤 Plane update provider를 호출하게 하고, `StepPlaneBodyUpdated` 등 기존 durable step을 재사용하거나 필요한 title/body step을 명확히 확장한다. 이미 완료된 step은 재시도에서 건너뛰고 다음 미완료 step부터 재개한다.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// provider identity present may be treated as already matched or skipped.
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// provider identity present:
|
||||||
|
verify revision -> compare body/title -> update provider -> mark durable step(s)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service.go`: existing identity update branch and retry step handling.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: title/body update, partial failure, retry-from-ledger tests.
|
||||||
|
- [ ] `services/core/internal/adapters/plane/client.go`: existing update API behavior is reused or minimally extended.
|
||||||
|
- [ ] `services/core/internal/adapters/plane/client_test.go`: request payload for title/body update stays provider-compatible.
|
||||||
|
- [ ] `services/core/internal/workitem/provider.go`: add or reuse provider update interface with narrow method shape.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S06. Include a fake provider that records call order and a completed-step seed proving retry resumes without repeating completed mutation.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/adapters/plane ./internal/workitem
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; existing identity changes project to provider title/body update with durable retry.
|
||||||
|
|
||||||
|
## [API-3] Conflict Classification Matrix
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
S07 requires rename, filename slug reuse, provider identity mismatch, stale Plane work item, and duplicate active slug to stop safely. Existing scanner/storage tests cover some pieces, but the pipeline needs an explicit classification matrix proving no destructive provider mutation happens before conflict/not-ready/skip is reported.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Centralize conflict reasons at the scan/classification boundary and propagate them to pipeline results. Treat duplicate active slug and provider identity mismatch as conflict, stale provider item as not-ready or conflict according to provider lookup result, and archive-only docs as skip. Never overwrite an existing provider identity block or ledger binding to "fix" a conflict automatically.
|
||||||
|
|
||||||
|
Before:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// conflicts may appear as generic errors or storage upsert failures.
|
||||||
|
```
|
||||||
|
|
||||||
|
After:
|
||||||
|
|
||||||
|
```go
|
||||||
|
// conflict matrix returns typed action/reason and provider fake sees no mutation.
|
||||||
|
```
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `services/core/internal/gitosync/scanner_test.go`: duplicate active slug and rename/slug reuse classification coverage.
|
||||||
|
- [ ] `services/core/internal/roadmapsyncpipeline/service_test.go`: provider identity mismatch and stale provider item coverage.
|
||||||
|
- [ ] `services/core/internal/storage/roadmap_sync_identities_test.go`: slug/provider conflict coverage remains aligned.
|
||||||
|
- [ ] `services/core/internal/scheduler/roadmap_sync_jobs.go` or job tests: conflict/not-ready/skip reason is logged/recorded without retry storm.
|
||||||
|
- [ ] `agent-task/m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict/CODE_REVIEW-cloud-G08.md`: fill implementation-owned sections.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Regression tests required for S07. Prefer table-driven tests with provider fake mutation counters.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/scheduler
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: PASS; every destructive case returns conflict/not-ready/skip with zero provider mutation unless the case is the intended identity-update projection.
|
||||||
|
|
||||||
|
## 수정 파일 요약
|
||||||
|
|
||||||
|
| 파일 | 항목 |
|
||||||
|
|------|------|
|
||||||
|
| `services/core/internal/gitosync/scanner.go` | API-1, API-3 |
|
||||||
|
| `services/core/internal/gitosync/scanner_test.go` | API-1, API-3 |
|
||||||
|
| `services/core/internal/gitosync/bridge.go` | API-1, API-3 |
|
||||||
|
| `services/core/internal/gitosync/bridge_test.go` | API-1, API-3 |
|
||||||
|
| `services/core/internal/roadmapsync/retry.go` | API-2 |
|
||||||
|
| `services/core/internal/roadmapsync/retry_test.go` | API-2 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service.go` | API-1, API-2, API-3 |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/service_test.go` | API-1, API-2, API-3 |
|
||||||
|
| `services/core/internal/storage/roadmap_sync_identities.go` | API-3 |
|
||||||
|
| `services/core/internal/storage/roadmap_sync_identities_test.go` | API-3 |
|
||||||
|
| `services/core/internal/adapters/plane/client.go` | API-2 |
|
||||||
|
| `services/core/internal/adapters/plane/client_test.go` | API-2 |
|
||||||
|
| `services/core/internal/workitem/provider.go` | API-2 |
|
||||||
|
| `services/core/internal/scheduler/roadmap_sync_jobs.go` | API-3 |
|
||||||
|
| `services/core/internal/scheduler/jobs.go` | API-3 |
|
||||||
|
| `agent-task/m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict/CODE_REVIEW-cloud-G08.md` | API-3 |
|
||||||
|
|
||||||
|
## 최종 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage ./internal/adapters/plane ./internal/workitem ./internal/scheduler ./internal/http
|
||||||
|
cd services/core && go vet ./internal/gitosync ./internal/roadmapsync ./internal/roadmapsyncpipeline ./internal/storage ./internal/adapters/plane ./internal/workitem ./internal/scheduler ./internal/http
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: all commands exit 0. Fresh `-count=1` is required for Go tests.
|
||||||
|
|
||||||
|
모든 코드 변경 완료 후 반드시 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채운다. 이 파일 작성이 구현의 마지막 단계다.
|
||||||
|
|
@ -0,0 +1,147 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Code Review Reference - API
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — READ FIRST] Filling in this file is the mandatory final step of implementation.**
|
||||||
|
> The task is NOT complete until every implementation-owned section below is filled in.
|
||||||
|
> Complete the `구현 체크리스트`; the final checklist item is mandatory before saving.
|
||||||
|
> Fill implementation-owned sections, then stop with active files in place and report ready for review.
|
||||||
|
> If implementation is blocked by a selected Milestone `구현 잠금 > 결정 필요` item, fill `사용자 리뷰 요청` with linked evidence and stop with active files in place; code-review decides whether to write `USER_REVIEW.md`.
|
||||||
|
> Do not ask the user directly, present choices in chat, or call `request_user_input` during implementation.
|
||||||
|
> Finalization (`코드리뷰 결과`, log rename, `complete.log`, archive moves, `코드리뷰 전용 체크리스트`) is review-agent-only.
|
||||||
|
|
||||||
|
## 개요
|
||||||
|
|
||||||
|
date=2026-07-02
|
||||||
|
task=m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke, plan=0, tag=API
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `field-smoke`: dev 환경에서 agent가 active Milestone을 직접 추가해 push한 뒤 Plane ticket 생성, identity backfill commit, 재전달 no-op까지 확인한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 이 파일을 읽는 리뷰 에이전트에게
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 아래 종결 절차는 코드리뷰 에이전트 전용이다. 구현 에이전트는 이 섹션을 실행하지 않는다.
|
||||||
|
|
||||||
|
각 항목의 구현을 실제 소스 파일과 대조하고, `검증 결과` 섹션의 출력이 코드와 일치하는지 확인하세요.
|
||||||
|
리뷰 완료는 판정 append, active 파일 log archive, PASS 시 `complete.log` 작성과 task directory archive까지 끝난 상태를 의미합니다.
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
## 구현 항목별 완료 여부
|
||||||
|
|
||||||
|
| 항목 | 완료 여부 |
|
||||||
|
|------|---------|
|
||||||
|
| [API-1] Remote Runner Preflight And Deploy | [ ] |
|
||||||
|
| [API-2] Agent-Origin Missing Create And Backfill Smoke | [ ] |
|
||||||
|
| [API-3] Redelivery No-Op Evidence And Cleanup | [ ] |
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] Remote runner checkout `toki@toki-labs.com:$HOME/agent-work/nomadcode`를 현재 검증 대상 상태로 동기화하고 Core server를 빌드/재배포한다.
|
||||||
|
- [ ] identity 없는 disposable active Milestone을 `develop`에 push하고 Gito `branch.updated` webhook delivery 또는 equivalent wakeup을 확인한다.
|
||||||
|
- [ ] Core가 `after` SHA를 fetch/verify하고 missing-create path로 Plane ticket을 생성한 증거를 DB/log/Plane에서 secret redaction 상태로 수집한다.
|
||||||
|
- [ ] identity backfill commit이 `develop`에 push됐고 diff가 provider identity block만 포함하는지 git evidence를 수집한다.
|
||||||
|
- [ ] backfill commit 재전달이 provider create/update 반복 없이 complete/no-op으로 수렴하는지 DB/log evidence를 수집한다.
|
||||||
|
- [ ] disposable smoke Milestone/Plane item cleanup 여부와 남은 dev 환경 상태를 기록한다.
|
||||||
|
- [ ] `git diff --check`, focused unit fallback tests, live smoke 명령을 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## 코드리뷰 전용 체크리스트
|
||||||
|
|
||||||
|
> **[REVIEW AGENT ONLY]** 이 체크리스트는 코드리뷰 에이전트만 사용한다.
|
||||||
|
|
||||||
|
- [ ] `코드리뷰 결과`에 `PASS`, `WARN`, `FAIL` 중 하나의 판정을 append한다.
|
||||||
|
- [ ] 판정과 `차원별 평가`, Required/Suggested/Nit 분류가 서로 일치한다.
|
||||||
|
- [ ] active `CODE_REVIEW-*-G??.md`를 `code_review_cloud_G07_N.log`로 아카이브한다.
|
||||||
|
- [ ] active `PLAN-*-G??.md`를 `plan_cloud_G07_M.log`로 아카이브한다.
|
||||||
|
- [ ] `.gitignore`의 Agent-Ops 관리 block이 `agent-task/**/*.md`와 `agent-task/**/*.log`를 unignore하고 `agent-roadmap/current.md`를 ignore하는지 확인한다.
|
||||||
|
- [ ] PASS이면 `complete.log`를 작성하고 active `.md` 파일을 남기지 않는다.
|
||||||
|
- [ ] PASS이면 active task 디렉터리를 `agent-task/archive/YYYY/MM/m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke/`로 이동한다.
|
||||||
|
- [ ] PASS이고 task group이 `m-<milestone-slug>`이면 런타임이 읽을 완료 이벤트 메타데이터를 보고하고, roadmap 수정이나 `update-roadmap` 직접 호출을 하지 않는다.
|
||||||
|
- [ ] PASS split 작업이면 이동 후 빈 active parent를 제거하거나, 남은 sibling/file이 있어 유지했다고 확인한다.
|
||||||
|
- [ ] WARN/FAIL이면 다음 active plan/review 파일 또는 `USER_REVIEW.md`를 작성하고 `complete.log`를 작성하지 않는다.
|
||||||
|
|
||||||
|
## 계획 대비 변경 사항
|
||||||
|
|
||||||
|
_구현 에이전트가 계획과 다르게 구현한 부분을 이유와 함께 기록한다._
|
||||||
|
|
||||||
|
## 주요 설계 결정
|
||||||
|
|
||||||
|
_구현 에이전트가 주요 설계 결정 사항을 기록한다._
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청
|
||||||
|
|
||||||
|
_기본값은 `없음`이다. 구현 중 새 결정이 필요해 보여도 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. 이 섹션은 선택된 Milestone `구현 잠금 > 결정 필요` 항목이 실구현을 차단할 때만 채운다. 외부 환경/secret/서비스 준비, 검증 증거 공백, 반복 실패, 일반 범위 조정은 사용자 리뷰 요청이 아니며 `검증 결과`, `계획 대비 변경 사항`, 또는 code-review의 일반 follow-up plan으로 처리한다._
|
||||||
|
|
||||||
|
- 상태: 없음
|
||||||
|
- 사유 유형: 없음
|
||||||
|
- 연결 대상: 없음
|
||||||
|
- 결정 필요: 없음
|
||||||
|
- 차단 근거: 없음
|
||||||
|
- 실행한 검증/명령: 없음
|
||||||
|
- 자동 후속 불가 이유: 없음
|
||||||
|
- 재개 조건: 없음
|
||||||
|
|
||||||
|
## 리뷰어를 위한 체크포인트
|
||||||
|
|
||||||
|
- Implementation waited for predecessor `01_scan_create_ledger`, `02+01_identity_backfill`, and `03+01,02_self_loop_update_conflict` completion.
|
||||||
|
- Evidence includes Plane ticket creation, identity backfill commit, and redelivery no-op.
|
||||||
|
- Tracked evidence is secret-free: no token, webhook secret, signature, password, or private credential value is copied.
|
||||||
|
- Any live smoke blocker is classified separately from Milestone lock decisions.
|
||||||
|
|
||||||
|
## 검증 결과
|
||||||
|
|
||||||
|
_구현 에이전트가 각 중간 검증 및 최종 검증 명령 실행 후 출력을 여기에 붙여 넣는다._
|
||||||
|
|
||||||
|
### API-1 중간 검증
|
||||||
|
```sh
|
||||||
|
$ ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode && git rev-parse HEAD && git status --short'
|
||||||
|
(output)
|
||||||
|
$ ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode/services/core && docker compose ps'
|
||||||
|
(output)
|
||||||
|
$ ssh toki@toki-labs.com 'curl -s http://127.0.0.1:18010/api/tasks | python3 -c "import sys,json; d=json.load(sys.stdin); print(\"task_count:\", len(d.get(\"tasks\",[])))"'
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-2 중간 검증
|
||||||
|
```sh
|
||||||
|
$ CORE_URL="http://127.0.0.1:18010"
|
||||||
|
$ curl -s "$CORE_URL/api/tasks" | python3 -c 'import sys,json; d=json.load(sys.stdin); print("task_count:", len(d.get("tasks",[])))'
|
||||||
|
(output)
|
||||||
|
$ git fetch origin develop
|
||||||
|
(output)
|
||||||
|
$ git rev-parse origin/develop
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### API-3 중간 검증
|
||||||
|
```sh
|
||||||
|
$ git diff --check
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go vet ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
### 최종 검증
|
||||||
|
```sh
|
||||||
|
$ git diff --check
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
(output)
|
||||||
|
$ cd services/core && go vet ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
(output)
|
||||||
|
$ ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode && git rev-parse HEAD && git status --short'
|
||||||
|
(output)
|
||||||
|
$ ssh toki@toki-labs.com 'curl -s http://127.0.0.1:18010/api/tasks | python3 -c "import sys,json; d=json.load(sys.stdin); print(\"task_count:\", len(d.get(\"tasks\",[])))"'
|
||||||
|
(output)
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
> **[IMPLEMENTING AGENT — BEFORE SAVING] Have you filled in every implementation-owned section: completion table, implementation checklist, changes from plan, design decisions, and verification output?**
|
||||||
|
|
@ -0,0 +1,231 @@
|
||||||
|
<!-- task=m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke plan=0 tag=API -->
|
||||||
|
|
||||||
|
# Plan - API
|
||||||
|
|
||||||
|
## 이 파일을 읽는 구현 에이전트에게
|
||||||
|
|
||||||
|
구현 후 active `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 반드시 실제 구현 내용과 검증 출력으로 채운다. 검증을 실행하고, active 파일은 그대로 둔 뒤 리뷰 준비를 보고한다. 최종 판정, log rename, `complete.log`, archive 이동은 code-review 스킬 전용이다.
|
||||||
|
|
||||||
|
선택된 Milestone의 `구현 잠금 > 결정 필요` 항목이 실구현을 막을 때만 review stub의 `사용자 리뷰 요청` 섹션을 채우고 멈춘다. 구현 중 사용자에게 직접 질문하거나 선택지를 제시하거나 `request_user_input`을 호출하지 않는다. secret, 외부 서비스 준비, 배포 상태, evidence 공백은 사용자 리뷰 요청이 아니라 검증 결과나 follow-up 대상이다.
|
||||||
|
|
||||||
|
## 배경
|
||||||
|
|
||||||
|
이 plan은 S08 field smoke 전용이다. 앞선 subtasks가 agent-origin 생성, identity ledger, identity backfill, self-loop, update, conflict policy를 구현한 뒤 dev Plane/Gito/NomadCode 환경에서 실제 active Milestone 추가 push를 통해 Plane ticket 생성, identity backfill commit, 재전달 no-op까지 확인한다.
|
||||||
|
|
||||||
|
## 사용자 리뷰 요청 흐름
|
||||||
|
|
||||||
|
사용자 리뷰 요청은 선택된 Milestone lock decision만 active review stub의 `사용자 리뷰 요청` 섹션에 기록한다. 직접 사용자 prompt는 금지이며, code-review가 정당성을 검증하고 실제 `USER_REVIEW.md` 작성을 소유한다.
|
||||||
|
|
||||||
|
## Roadmap Targets
|
||||||
|
|
||||||
|
- Milestone: `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- Task ids:
|
||||||
|
- `field-smoke`: dev 환경에서 agent가 active Milestone을 직접 추가해 push한 뒤 Plane ticket 생성, identity backfill commit, 재전달 no-op까지 확인한다.
|
||||||
|
- Completion mode: check-on-pass
|
||||||
|
|
||||||
|
## 분석 결과
|
||||||
|
|
||||||
|
### 읽은 파일
|
||||||
|
|
||||||
|
- `agent-roadmap/phase/agent-ops-mcp-control-plane/milestones/agent-origin-milestone-creation-sync.md`
|
||||||
|
- `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- `agent-contract/outer/gito-branch-webhook-consumer-v1.md`
|
||||||
|
- `agent-test/local/rules.md`
|
||||||
|
- `agent-test/local/core-smoke.md`
|
||||||
|
- `agent-test/live-cycle-smoke.md`
|
||||||
|
- `agent-test/plane-dev.md`
|
||||||
|
- `services/core/internal/gitosync/scanner.go`
|
||||||
|
- `services/core/internal/roadmapsyncpipeline/service.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_identities.go`
|
||||||
|
- `services/core/internal/storage/roadmap_sync_steps.go`
|
||||||
|
- `services/core/internal/http/gito_webhook.go`
|
||||||
|
- `services/core/internal/scheduler/roadmap_sync_jobs.go`
|
||||||
|
- `services/core/docker-compose.yml`
|
||||||
|
|
||||||
|
### SDD 기준
|
||||||
|
|
||||||
|
- SDD: `agent-roadmap/sdd/agent-ops-mcp-control-plane/agent-origin-milestone-creation-sync/SDD.md`
|
||||||
|
- 상태: `[승인됨]`, SDD 잠금 해제, 사용자 리뷰 없음.
|
||||||
|
- Targeted scenario: S08=`field-smoke`.
|
||||||
|
- Evidence Map row: dev field smoke with redacted logs/DB/Plane/git evidence; completion evidence must show Roadmap Completion and final dev cycle evidence without secrets.
|
||||||
|
- Field smoke must confirm Plane ticket creation, identity backfill commit, self-loop redelivery no-op, and secret redaction.
|
||||||
|
|
||||||
|
### 테스트 환경 규칙
|
||||||
|
|
||||||
|
- test_env: `local` with remote runner deployment for live smoke.
|
||||||
|
- `agent-test/local/rules.md`, `agent-test/live-cycle-smoke.md`, and `agent-test/plane-dev.md` present/read.
|
||||||
|
- Current preflight: repo root `/config/workspace/nomadcode`, branch `main`, HEAD `d80abe83579dd0d6fbc86b1a74c83db6d18c756d`, `go version go1.26.2 linux/arm64`, `git version 2.43.0`.
|
||||||
|
- Remote runner: `toki@toki-labs.com`, checkout `$HOME/agent-work/nomadcode`.
|
||||||
|
- Core URL for remote local profile: `http://127.0.0.1:18010`.
|
||||||
|
- Plane dev non-secret fixtures:
|
||||||
|
- Plane base URL: `https://plane.toki-labs.com`
|
||||||
|
- Workspace slug/id: `general` / `dadf050e-cd1e-4590-bc33-672511630841`
|
||||||
|
- Project id/identifier: `a6beb42f-7a8a-410c-b50f-ea3ca94828f3` / `NOMAD`
|
||||||
|
- Todo state id: `45ba7449-f684-4381-af6d-5854747c5e8d`
|
||||||
|
- Backlog state id: `62d4c50c-0cea-4a76-a0ed-ec97498b2d5f`
|
||||||
|
- AGENT assignee id: `5d116a77-d3df-4f54-80bf-eca61e0118c4`
|
||||||
|
- Secrets are loaded only from ignored/SOPS-backed local sources such as `.env.plane.local` or `secrets/nomadcode.dev.sops.yaml`; secret values must not be copied into tracked files or final output.
|
||||||
|
|
||||||
|
### 테스트 커버리지 공백
|
||||||
|
|
||||||
|
- Unit/focused tests can prove behavior, but S08 requires live dev evidence that the whole path works through Gito delivery, Core worker, Plane mutation, git backfill push, and redelivery.
|
||||||
|
- Existing live-cycle smoke describes Plane-origin lifecycle; this plan adapts the same runner/secret/evidence discipline to agent-origin missing-create/backfill.
|
||||||
|
|
||||||
|
### 심볼 참조
|
||||||
|
|
||||||
|
- No production symbol change is planned in this smoke subtask unless field validation exposes a bug. If a code fix is required, implementation must make the smallest fix and update this review file with the exact deviation.
|
||||||
|
|
||||||
|
### 분할 판단
|
||||||
|
|
||||||
|
- Split decision policy evaluated before file selection.
|
||||||
|
- This dependent subtask is `04+01,02,03_field_smoke`.
|
||||||
|
- Predecessors required:
|
||||||
|
- `agent-task/m-agent-origin-milestone-creation-sync/01_scan_create_ledger/complete.log`
|
||||||
|
- `agent-task/m-agent-origin-milestone-creation-sync/02+01_identity_backfill/complete.log`
|
||||||
|
- `agent-task/m-agent-origin-milestone-creation-sync/03+01,02_self_loop_update_conflict/complete.log`
|
||||||
|
- Active predecessor lookup: no predecessor `complete.log` files exist at plan creation.
|
||||||
|
- Archive predecessor lookup: not performed because no active predecessor completion exists and no runtime-provided archive evidence was specified.
|
||||||
|
- Implementer must wait for all predecessor PASS/complete.log files before starting this plan.
|
||||||
|
|
||||||
|
### 범위 결정 근거
|
||||||
|
|
||||||
|
- Include live dev smoke evidence and small bug fixes discovered only by the smoke.
|
||||||
|
- Exclude new feature design, broad refactors, non-agent-origin lifecycle, child ticket sync, and secrets/documentation of secret values.
|
||||||
|
|
||||||
|
### 빌드 등급
|
||||||
|
|
||||||
|
- `cloud-G07`: the task is primarily validation/evidence, but it touches live dev Plane/Gito/NomadCode and may require narrow fixes if integration drift appears.
|
||||||
|
|
||||||
|
## 의존 관계 및 구현 순서
|
||||||
|
|
||||||
|
`04+01,02,03_field_smoke` depends on sibling predecessors `01_scan_create_ledger`, `02+01_identity_backfill`, and `03+01,02_self_loop_update_conflict`. Start implementation only after all three active `complete.log` files exist or matching archived `complete.log` evidence is explicitly provided by runtime.
|
||||||
|
|
||||||
|
## 구현 체크리스트
|
||||||
|
|
||||||
|
- [ ] Remote runner checkout `toki@toki-labs.com:$HOME/agent-work/nomadcode`를 현재 검증 대상 상태로 동기화하고 Core server를 빌드/재배포한다.
|
||||||
|
- [ ] identity 없는 disposable active Milestone을 `develop`에 push하고 Gito `branch.updated` webhook delivery 또는 equivalent wakeup을 확인한다.
|
||||||
|
- [ ] Core가 `after` SHA를 fetch/verify하고 missing-create path로 Plane ticket을 생성한 증거를 DB/log/Plane에서 secret redaction 상태로 수집한다.
|
||||||
|
- [ ] identity backfill commit이 `develop`에 push됐고 diff가 provider identity block만 포함하는지 git evidence를 수집한다.
|
||||||
|
- [ ] backfill commit 재전달이 provider create/update 반복 없이 complete/no-op으로 수렴하는지 DB/log evidence를 수집한다.
|
||||||
|
- [ ] disposable smoke Milestone/Plane item cleanup 여부와 남은 dev 환경 상태를 기록한다.
|
||||||
|
- [ ] `git diff --check`, focused unit fallback tests, live smoke 명령을 실행한다.
|
||||||
|
- [ ] CODE_REVIEW-*-G??.md의 구현 에이전트 소유 섹션을 실제 구현 내용과 검증 출력으로 채운다. 이 항목이 완료되기 전에는 구현이 완료된 것이 아니다.
|
||||||
|
|
||||||
|
## [API-1] Remote Runner Preflight And Deploy
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
S08 evidence는 현재 reviewed code가 실행 중인 Core server에 배포되어 있을 때만 의미가 있다. remote checkout이 낡았거나 dirty여도 차단으로 간주하지 않고, 검증 대상 상태와 같게 동기화한 뒤 smoke를 수행해야 한다.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Remote runner checkout을 reset/clean/reclone or file sync로 현재 작업 상태와 맞추고 Docker Compose Core server를 rebuild/recreate한다. Secret은 ignored local file or SOPS에서 로드하되 값을 출력하지 않는다.
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] `agent-task/m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke/CODE_REVIEW-cloud-G07.md`: preflight command output 기록.
|
||||||
|
- [ ] If code/config fix is needed, update only the smallest related Core file and rerun predecessor-relevant focused tests.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
No new unit test is expected for deploy-only work unless smoke exposes a code bug.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode && git rev-parse HEAD && git status --short'
|
||||||
|
ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode/services/core && docker compose ps'
|
||||||
|
ssh toki@toki-labs.com 'curl -s http://127.0.0.1:18010/api/tasks | python3 -c "import sys,json; d=json.load(sys.stdin); print(\"task_count:\", len(d.get(\"tasks\",[])))"'
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: checkout matches reviewed change set, Core is reachable, and no secret values are printed.
|
||||||
|
|
||||||
|
## [API-2] Agent-Origin Missing Create And Backfill Smoke
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
The milestone acceptance requires a real agent-origin active Milestone push that starts without provider identity and ends with Plane ticket creation plus provider identity backfill commit.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Create a disposable active Milestone file on `develop` with a unique slug and no `Provider identity` block. Push it through Gito, wait for Core webhook/worker processing, then record Plane item id, `roadmap_sync_identities` row, completed steps, and backfill commit diff. Redact tokens, webhook signatures, and raw credentials.
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] Record disposable milestone slug and pushed `after` SHA.
|
||||||
|
- [ ] Record Gito webhook delivery id or equivalent accepted wakeup evidence if available.
|
||||||
|
- [ ] Record Plane work item id/key and state using non-secret evidence.
|
||||||
|
- [ ] Record DB identity row and completed steps with secret-free SQL/curl output.
|
||||||
|
- [ ] Record backfill commit SHA and `git show --stat`/diff excerpt proving identity-block-only scope.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
Live smoke evidence is required for S08. If live service is unavailable, run the runtime-equivalent unit fallback and record the blocker as follow-up rather than marking S08 complete.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
# On remote runner after secrets are loaded from ignored/SOPS-backed sources.
|
||||||
|
CORE_URL="http://127.0.0.1:18010"
|
||||||
|
curl -s "$CORE_URL/api/tasks" | python3 -c 'import sys,json; d=json.load(sys.stdin); print("task_count:", len(d.get("tasks",[])))'
|
||||||
|
git fetch origin develop
|
||||||
|
git rev-parse origin/develop
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: Core reachable; target develop revision visible to the checkout.
|
||||||
|
|
||||||
|
## [API-3] Redelivery No-Op Evidence And Cleanup
|
||||||
|
|
||||||
|
### 문제
|
||||||
|
|
||||||
|
Plane ticket creation and identity backfill are insufficient if the backfill webhook creates or updates provider state again. S08 requires the redelivery no-op evidence and secret-redacted final record.
|
||||||
|
|
||||||
|
### 해결 방법
|
||||||
|
|
||||||
|
Trigger or observe the backfill commit's Gito redelivery. Verify the same milestone slug/Plane item keeps one identity row, no second create/update happens, and the job completes or no-ops. Cleanup disposable data only if safe and record what was left behind for traceability.
|
||||||
|
|
||||||
|
### 수정 파일 및 체크리스트
|
||||||
|
|
||||||
|
- [ ] Record redelivery job/log/DB evidence showing no duplicate provider mutation.
|
||||||
|
- [ ] Record Plane item remains single and linked to the same milestone slug.
|
||||||
|
- [ ] Record cleanup decision and final dev environment state.
|
||||||
|
- [ ] `agent-task/m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke/CODE_REVIEW-cloud-G07.md`: fill implementation-owned sections.
|
||||||
|
|
||||||
|
### 테스트 작성
|
||||||
|
|
||||||
|
If redelivery cannot be triggered live, use the runtime-equivalent unit fallback and keep S08 incomplete or WARN according to code-review policy.
|
||||||
|
|
||||||
|
### 중간 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
cd services/core && go vet ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: local/focused fallback stays green after any smoke-driven fix.
|
||||||
|
|
||||||
|
## 수정 파일 요약
|
||||||
|
|
||||||
|
| 파일 | 항목 |
|
||||||
|
|------|------|
|
||||||
|
| `agent-task/m-agent-origin-milestone-creation-sync/04+01,02,03_field_smoke/CODE_REVIEW-cloud-G07.md` | API-1, API-2, API-3 |
|
||||||
|
| `services/core/internal/gitosync/*` | only if smoke exposes a minimal bug |
|
||||||
|
| `services/core/internal/roadmapsyncpipeline/*` | only if smoke exposes a minimal bug |
|
||||||
|
| `services/core/internal/storage/*` | only if smoke exposes a minimal bug |
|
||||||
|
| `services/core/internal/http/*` | only if smoke exposes a minimal bug |
|
||||||
|
| `services/core/internal/scheduler/*` | only if smoke exposes a minimal bug |
|
||||||
|
|
||||||
|
## 최종 검증
|
||||||
|
|
||||||
|
```sh
|
||||||
|
git diff --check
|
||||||
|
cd services/core && go test -count=1 ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
cd services/core && go vet ./internal/gitosync ./internal/roadmapsyncpipeline ./internal/storage ./internal/http ./internal/scheduler
|
||||||
|
ssh toki@toki-labs.com 'cd $HOME/agent-work/nomadcode && git rev-parse HEAD && git status --short'
|
||||||
|
ssh toki@toki-labs.com 'curl -s http://127.0.0.1:18010/api/tasks | python3 -c "import sys,json; d=json.load(sys.stdin); print(\"task_count:\", len(d.get(\"tasks\",[])))"'
|
||||||
|
```
|
||||||
|
|
||||||
|
Expected: all commands exit 0, live smoke evidence is secret-free, and S08 evidence includes Plane ticket, identity backfill commit, and redelivery no-op.
|
||||||
|
|
||||||
|
모든 코드 변경 완료 후 반드시 `CODE_REVIEW-*-G??.md`의 구현 에이전트 소유 섹션을 채운다. 이 파일 작성이 구현의 마지막 단계다.
|
||||||
Loading…
Reference in a new issue