# task-2395 — 부수이슈 .done.clear archive + IDS 6 Phase 통합 monitor

작성: 이참나 (Itzamna, dev7 팀장) · 2026-05-03 KST

## SCQA

### Situation
IDS 6 Phase (task-2389~2394) 동시 진행. 운영 부수이슈 2건:
1. `memory/events/*.done.clear` 누적 791개 (디스크/가독성 부담)
2. 6 Phase 통합 watcher 부재 — 수동 `ls` 의존, .done 6개 도착 시 통합 검증 자동화 부재

### Complication
- IDS 영역(skills/**, scripts/auto_*, done-watcher.py, finish-task.sh 등)은 절대 무수정.
- 기존 history 보존 의무 — `.done.clear` 삭제 절대 금지.
- 자동 위임 트리거 금지 — watcher가 보고만 수행, dispatch.py 호출 차단.

### Question
신규 파일만으로 archive 정책 + watcher를 구축하면서, IDS 인프라 무수정 + 자동 dispatch 차단을 강제할 수 있는가?

### Answer
- 신규 모듈 `scripts/ids_phase_monitor.py` (411 줄): archive + check_progress + run_completion_checks + watch_once + Telegram 통보. `shutil.move` 만 사용 (삭제 함수 부재). dispatch.py 임포트 부재.
- 회귀 테스트 `tests/dev7/test_side_issues_cleanup_monitor.py` (204 줄, 7 PASS) — 정적 검사로 dispatch import / 삭제 패턴 부재 확인.
- micro-commit `d0359f83` 으로 즉시 보호 (작업 중 한 차례 파일 유실 → 재작성 후 commit으로 안정화).

## 작업 내용

### Fix 1 — `.done.clear` 월별 archive 정책
| 항목 | 값 |
|---|---|
| 함수 | `archive_old_done_clear(events_dir, archive_root, age_days=90, dry_run, now)` |
| 정책 | mtime 기준 90일 이상만 `archive/<YYYY-MM>/` 로 이동 |
| 운영 실행 결과 | `moved=0, skipped=791, by_month={}` (현재 90일 이상 대상 0건) |
| 90일 미만 | 모두 원위치 유지 — 정책 작동 검증됨 |
| 삭제 | 절대 금지 — `shutil.move` 만 사용. `os.remove`/`os.unlink`/`shutil.rmtree` 부재 |

★ 현재 791개 모두 90일 미만. archive 정책은 미래 누적분에 대해 작동.

### Fix 2 — 6 Phase 통합 watcher
| 항목 | 값 |
|---|---|
| 감시 대상 | `task-2389/2390/2391/2392/2393/2394` `.done` 마커 |
| 인식 패턴 | `{task_id}.done`, `{task_id}.dev*.done`, `{task_id}.<team>.done` (.done.clear 제외) |
| N/6 보고 | 진행률 변화 시 Telegram 1회 (chat=6937032012) |
| 6/6 통합 검증 | 보고서 존재 + git status + pytest 권고 메시지 |
| 자동 dispatch | **호출 절대 금지** — 모듈 import dispatch / from dispatch / dispatch.py 호출 일체 부재 (정적+동적 mock 검증) |
| 운영 폴링 | CLI `python3 scripts/ids_phase_monitor.py watch` (cron 5분 또는 수동 실행) |
| 현재 상태 | `0/6` (task-2389~2394 .done 마커 없음 — 진행 중) |

### CLI
```bash
python3 scripts/ids_phase_monitor.py archive [--dry-run] [--age-days 90]
python3 scripts/ids_phase_monitor.py watch [--no-notify]
python3 scripts/ids_phase_monitor.py check-progress
```

## 생성/수정 파일 목록

### 신규
- `/home/jay/workspace/scripts/ids_phase_monitor.py` (411 줄)
- `/home/jay/workspace/tests/dev7/test_side_issues_cleanup_monitor.py` (204 줄)

### 수정 없음
- 금지 영역(skills/**, dispatch.py, scripts/{auto_merge,done-watcher,finish-task,...}.py, teams/shared/**, CLAUDE.md, memory/{capabilities,audit,state}/**, .github/**) 일체 미수정.
- 791개 `*.done.clear` (전부 90일 미만) — 원위치 그대로.

## 테스트 결과

### pytest (7/7 PASS)
```
tests/dev7/test_side_issues_cleanup_monitor.py::test_archive_moves_files_older_than_90_days PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_archive_preserves_files_under_90_days PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_check_phase_progress_partial_and_complete PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_check_phase_progress_ignores_done_clear PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_run_completion_checks_detects_missing_reports PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_watch_once_does_not_invoke_dispatch PASSED
tests/dev7/test_side_issues_cleanup_monitor.py::test_module_has_no_delete_functions PASSED
============================== 7 passed in 0.09s ===============================
```

### 정적 분석
- pyright: **0 errors, 0 warnings, 0 informations**
- py_compile: PASS
- forbidden 영역 grep: 변경 없음 ✓

## L1 스모크테스트 결과
- 서버 재시작: **해당없음** (CLI 도구, 데몬 아님)
- API 응답 확인: **해당없음** (외부 API 없음)
- 스크린샷: **해당없음** (CLI/백엔드)
- 실 동작 검증:
  - **L1-1 archive --dry-run**: `moved=0, skipped=791, errors=[]` (운영 디렉토리 791개 모두 90일 미만 — 이동 없음, 정책 통과)
  - **L1-2 archive 실행**: `moved=0, skipped=791` (실데이터 변경 없음, 정책 작동)
  - **L1-3 check-progress**: `0/6` 정상 출력 (task-2389~2394 .done 마커 부재)
  - **L1-4 watch --no-notify**: progress + completion=null JSON 출력 정상
  - **L1-5 dummy archive (격리 tmpdir)**: 91일 전 5개 + 30일 5개 → `moved=5, skipped=5, by_month={"2026-02":5}` ✓ 5개 이동, 5개 유지, archive_root에 5 파일 존재

## 머지 판단
- **머지 필요**: Yes (이미 main 직접 commit `d0359f83` 완료 — micro-commit 보호 목적)
- **브랜치**: main (worktree 미사용 — 시스템 작업, project_id 없음)
- **머지 의견**: 신규 파일 2개만 추가 + 금지 영역 무변경 + 7/7 PASS + L1 5종 통과. 충돌 위험 0.

## 발견 이슈 및 해결

### 이슈 1 — 작업 중 파일 유실 (1회)
**증상**: 카마소츠 1차 작성 후 미완료 시점에 `scripts/ids_phase_monitor.py` 와 `tests/dev7/test_side_issues_cleanup_monitor.py` 가 모두 사라짐 (pyc만 남음). git history에도 흔적 없음.
**원인 추정**: `/home/jay/workspace` 메인 브랜치에서 다른 봇 또는 cleanup 프로세스에 의한 working-tree 동시 변경 가능성 (worktree 미사용 + 멀티봇 환경).
**해결**: 팀장이 직접 두 파일 재작성 → 즉시 `git add` + `git commit d0359f83` 으로 보호 → 이후 사라짐 재발 없음.
**향후 권고**: dev7 시스템 작업도 `git-worktree-isolation` 적용 (현 워크플로우상 project_id 없으면 skip이지만, 워크스페이스가 git repo면 worktree 권장).

### 이슈 2 — pyright 초기 3건 (수정 완료)
`tasks: list[str] = None` → `Optional[list[str]] = None` 으로 3곳 수정. 최종 pyright 0건.

### 이슈 3 — task-timer 이중 등록
`already_running` 응답 — 이미 dispatch.py가 시작했음. 중복 호출 무시 (정상).

## 모델 사용 기록
- 쿠쿨칸 (백엔드): `sonnet` — ids_phase_monitor.py 1차 작성 (509줄, 사라짐)
- 카마소츠 (테스터): `sonnet` — 회귀 테스트 작성, 1차 API overload 실패 → 재호출 후 7/7 PASS (175줄, 사라짐)
- 팀장(이참나, opus): 두 파일 재작성 + L1 + 보고서. Sonnet 결과물이 환경 이슈로 유실되어 직접 개입 (워크플로우상 허용된 예외).

## 비고

- TTL 12h 내 완료. 운영 영향 없음 (실파일 0개 이동, watcher는 호출 없음).
- 5분 cron 등록은 별도 운영 작업 (이번 작업 범위 외). 수동 watch 실행으로 검증 가능.
- batch-ids-master.md 위치만 안내 (`memory/reports/batch-ids-master.md`) — 실제 작성은 6/6 도래 후 수동 권고.

## goal_assertions 처리
- `pytest tests/dev1 tests/dev6 tests/design-team tests/dev3` — task 사양상 **권고만** (자동 실행 금지). watcher의 `pytest_recommendation` 필드로 보고 시 노출.

## 세션 통계
- 총 도구 호출: 0회


## 세션 통계
- 총 도구 호출: 0회


## 세션 통계
- 총 도구 호출: 0회


## 세션 통계
- 총 도구 호출: 0회

