sj-loop

star 1

루프 엔지니어링 전문가. "에이전트에 직접 프롬프트"를 "에이전트를 프롬프트하는 루프 설계"로 바꾼다. 목적·1회 반복 작업·기계 검증 가능한 정지 조건·메모리(상태 파일)· 가드레일을 갖춘 루프 프롬프트를 생성해 docs/sj-company/loops/에 저장하고, 드라이런·세션 내 반복(/loop)·클라우드 스케줄(/schedule) 중 선택해 실행한다. "루프 만들어줘", "반복 자동화", "계속 돌려줘", "야간에 알아서 돌게 해줘" 요청 시 사용.

s0613 By s0613 schedule Updated 6/11/2026

name: sj-loop version: 1.1.0 description: | 루프 엔지니어링 전문가. "에이전트에 직접 프롬프트"를 "에이전트를 프롬프트하는 루프 설계"로 바꾼다. 목적·1회 반복 작업·기계 검증 가능한 정지 조건·메모리(상태 파일)· 가드레일을 갖춘 루프 프롬프트를 생성해 docs/sj-company/loops/에 저장하고, 드라이런·세션 내 반복(/loop)·클라우드 스케줄(/schedule) 중 선택해 실행한다. "루프 만들어줘", "반복 자동화", "계속 돌려줘", "야간에 알아서 돌게 해줘" 요청 시 사용. allowed-tools: - Bash - Read - Write - Edit - Skill - AskUserQuestion triggers: - /sj-loop

SJ Loop — 루프 엔지니어링

build the loop, stay the engineer. 루프는 일을 대신하지만 검증·이해·승인은 사람 몫이다.

컨벤션: 프릭션 로그 — 드라이런·반복 실행 중 마찰(정지 조건 오판, 상태 파일 누락, 가드레일 충돌)을 만나면 한 줄 기록한다. 무인 실행일수록 마찰 신호가 다음 개선의 입력이 된다.

컨벤션: 셀프-하네스 게이트 — 같은 실패가 반복되면(가드레일의 "2회 반복 → 멈춤"이 약점 마이닝이다) 루프 프롬프트 자체를 고치고 싶어진다. 그 변경은 회귀가 녹색일 때만 채택하고, 채택은 사람 게이트. 루프가 자기 프롬프트를 자동 수정하지 않는다.

불변 원칙

  1. 사람 게이트 — 어떤 루프도 PR 머지·프로덕션 배포를 자동 실행하지 않는다. 이 문구가 없는 루프 프롬프트는 저장 금지. (단일 정의)
  2. 기계 검증 가능한 정지 조건 — "잘 되면" 같은 모호한 조건이면 저장 전 재작성한다. 정지 판단은 작업 결과 서술이 아니라 실행 결과(종료 코드·관찰 가능한 상태)로만 한다.
  3. 메모리는 디스크에 — 모델은 실행 사이에 잊는다. 상태는 loops/{slug}-state.md에 기록해 다음 반복이 이어받는다. 최적화형 루프(점수·커버리지·지표를 점진 개선)는 단순 시도/통과/미해결만으로 부족하다 — 모델은 반복 전반의 최적화 상태 추적에 약하므로(autoresearch/Centaur: 명시적 상태를 외부 공유하니 작은 모델로도 frontier 추월), best-so-far(현재 최선 지표 + 그 설정)와 다음 방향을 상태 파일에 명시해 매 반복이 재유도 없이 이어받게 한다.
  4. 첫 실행은 드라이런 — 무인으로 돌리기 전에 1회 실행으로 루프 프롬프트를 검증한다.

모드 판정

입력 모드
인자 없음 기존 루프 목록 출력 → 새로 만들기/실행 선택
루프 목적 서술 (예: "테스트 깨진 거 잡는 루프") 생성 모드
run {slug} 또는 기존 루프명 실행 모드
mkdir -p docs/sj-company/loops
ls docs/sj-company/loops/*.md 2>/dev/null | grep -v -- "-state.md"

생성 모드

Step G1: 목적 구체화

docs/sj-company/PROJECT.md가 있으면 읽어 goal·stack 맥락을 확보한다. 아래 세 가지가 입력에서 파악되지 않으면 AskUserQuestion 1회로 묶어서 묻는다 (답이 모호해도 최선의 가정으로 진행):

  1. 무엇을 — 1회 반복에서 할 일
  2. 언제까지/얼마나 자주 — 정지 조건 또는 반복 주기
  3. 끝났다는 증거 — 기계 검증 가능한 조건 (명령어 + 기대 결과)

Step G2: 루프 프롬프트 작성

slug는 영소문자-하이픈 (예: fix-failing-tests). 아래 템플릿으로 작성한다:

# Loop: {이름}
> 생성: {YYYY-MM-DD} | 프로젝트: {프로젝트명} | slug: {slug}

## 목적
{한 문장}

## 이번 반복에서 할 일
1. `docs/sj-company/loops/{slug}-state.md`를 읽어 지난 반복 상태를 파악한다 (없으면 첫 반복)
2. {1회 반복 작업 — 파일·명령 수준으로 구체적으로}
3. 결과를 상태 파일에 기록한다: `## 시도` / `## 통과` / `## 미해결` 섹션에 append
4. 스스로 판단할 수 없는 항목은 `docs/sj-company/triage-inbox.md`에
   `- [ ] {날짜} [{slug}] {항목}` 형식으로 append한다
5. 아래 정지 조건을 **실제로 실행**해 전부 참이면 상태 파일 상단의 `status:` 줄을
   `status: DONE`으로 바꾸고 종료 보고한다 (정지 신호는 출력 문장이 아니라 상태 파일의 이 줄이다)

## 정지 조건 (기계 검증 가능)
- {예: `npm test` 종료 코드 0}
- {예: `npm run lint` 에러 0건}

## 가드레일
- git push·PR 머지·프로덕션 배포 금지 (사람 게이트 — 머지 준비가 되면 triage-inbox에 기록하고 멈춘다)
- 한 반복에서 수정 파일 {N}개 초과 금지
- 같은 실패가 2회 반복되면 시도를 멈추고 triage-inbox에 기록한다
- PROJECT.md·*-context.md를 통째로 재작성하지 않는다 (archive-only 불변식)

Step G3: 저장 + 상태 파일 초기화

  • 루프 프롬프트 → docs/sj-company/loops/{slug}.md
  • 상태 파일 → docs/sj-company/loops/{slug}-state.md:
# State: {slug}
> 마지막 반복: 없음
status: RUNNING

## 시도
## 통과
## 미해결

최적화형 루프라면 위 템플릿에 다음 세 줄을 추가해, 모델이 매 반복 상태를 재유도하지 않게 한다:

best-so-far: {지표값 + 그 값을 낸 설정/커밋}   # 예: val_bpb 1.42 @ lr=3e-4
다음 방향: {이번 반복에서 시도할 한 가지}
시도한 방향: {지금까지 시도한 방향들 — 개선 실패해도 여기 누적}

매 반복은 (1) 이번 방향을 시도한 방향에 append하고, (2) best-so-far는 개선했을 때만 덮어쓴다(실패 시 유지), (3) 다음 다음 방향시도한 방향없는 것으로 고른다. 고를 새 방향이 없으면 ## 미해결에 적고 정지 조건/사람 게이트로 넘긴다 — 같은 방향을 오가는 진동(oscillation)을 막는다.

저장 전 확인 (기계 검증): grep -q "사람 게이트" docs/sj-company/loops/{slug}.md — 실패하면 저장하지 말고 가드레일 섹션을 다시 작성한다.

동일 slug의 루프가 이미 존재하면: 기존 {slug}.md·{slug}-state.mdloops/archive/{slug}-{YYYYMMDD}-*.md로 이동(백업)한 뒤 새로 생성한다 (archive-only 불변식).

Step G4: 검수 + 실행 연결

저장한 루프 프롬프트 전문을 사용자에게 보여주고 AskUserQuestion:

  • A) 드라이런 지금 1회 실행 (권장)
  • B) 바로 반복 실행 설정 → 실행 모드 Step R2로
  • C) 저장만 (나중에 /sj-loop run {slug})

실행 모드

Step R1: 루프 선택

slug 인자가 없으면 loops/ 목록을 보여주고 AskUserQuestion으로 선택받는다. 선택된 loops/{slug}.md 전문을 읽는다.

Step R2: 실행 방식 선택

AskUserQuestion:

방식 동작 조건
A) 드라이런 지금 이 세션에서 1회 반복만 수행 항상 가능. 첫 실행이면 이것 권장
B) 세션 내 반복 Claude Code 내장 loop 스킬 호출 — 간격마다 또는 자기 페이스로 재실행 노트북·세션이 켜져 있어야 함
C) 클라우드 스케줄 Claude Code 내장 schedule 스킬 호출 — cron 주기 클라우드 routine 노트북 꺼져도 동작. GitHub repo 필요

실행 전 상태 확인: loops/{slug}-state.mdstatus: DONE 줄이 있으면 이 루프는 이미 완료된 것이다. 사용자에게 알리고, 다시 돌리려면 상태 파일을 archive 후 초기화(status: RUNNING)할지 AskUserQuestion으로 확인한다.

Step R3: 실행

A) 드라이런: 루프 프롬프트의 "이번 반복에서 할 일"을 지금 1회 수행한다. 상태 파일·triage-inbox 갱신까지 포함해 루프 1사이클을 그대로 밟고, 끝나면 "이대로 무인 반복해도 되겠는지" 관찰 결과를 보고한다. 단, 정지 조건은 평가하되 status: DONE을 기록하지 않고 충족 여부만 보고한다 (드라이런 목적은 종료가 아니라 검증).

드라이런 보고에는 다음 두 가지를 반드시 포함한다:

  • 정지 조건이 이미 전부 충족된 경우: "무인 등록 시 첫 반복에서 즉시 DONE 처리된다"고 명시적으로 알리고, 그래도 등록할 가치가 있는지(예: 회귀를 상시 감시하는 목적) 사용자 판단을 받는다. 일회성 검사였다면 등록 대신 루프를 archive하도록 안내한다.
  • 경로 커버리지: "이번 반복에서 할 일" 각 단계 중 실제 실행된 단계와 실행되지 않은 단계를 구분해 표시한다 (예: 수정 대상 0건 → 수정·triage 경로 미검증). 미검증 경로가 있으면 무인 반복 권장 여부 판단에 그 사실을 반영한다.

B) 세션 내 반복: Skill 도구로 loop 스킬을 호출한다. 인자: {간격} docs/sj-company/loops/{slug}.md 파일을 읽고 그 지시대로 1회 반복을 수행하라. docs/sj-company/loops/{slug}-state.md에 status: DONE 줄이 있으면 루프를 종료하라. (간격 미지정 시 자기 페이스)

C) 클라우드 스케줄: Skill 도구로 schedule 스킬을 호출해 routine을 생성한다. 프롬프트는 B와 동일하게 루프 파일 참조 방식. cron 주기는 사용자 입력 기반(기본: 평일 매일 07:00).

loop/schedule은 Claude Code 내장 스킬이라 이 레포에 파일로 존재하지 않는다. 구버전 CLI 등으로 내장 스킬이 없거나, C 선택 시 GitHub repo가 없으면: launchd(macOS)·cron(Linux) + claude -p headless 등록으로 대체한다. 예:

0 7 * * 1-5 cd {프로젝트 경로} && claude -p "docs/sj-company/loops/{slug}.md 파일을 읽고 그 지시대로 1회 반복을 수행하라."

등록 자체는 sj-automation 스킬로 위임할 수 있다.


루프 수명주기

  • 정지 신호는 상태 파일의 status: DONE 줄 하나다. 출력 문장(예: "LOOP_DONE")은 신호가 아니다.
  • status: DONE이 된 루프는 실행 대상에서 제외한다. 보관이 필요 없으면 {slug}.md·{slug}-state.mdloops/archive/로 이동한다.
  • 같은 slug를 다시 만들거나 다시 돌릴 때는 기존 파일을 archive로 백업한 뒤 상태 파일을 초기화한다 (통째 삭제 금지 — archive-only 불변식).
  • 상태 파일의 ## 시도가 과도하게 길어지면(약 200줄 초과) 오래된 항목을 archive로 옮기고 요약 한 줄만 남긴다.

절대 하지 말 것

  • 사람 게이트 문구 없는 루프 프롬프트 저장
  • 모호한 정지 조건("안정화되면", "충분히 좋아지면")을 그대로 저장
  • 드라이런 없이 클라우드 스케줄 등록 (사용자가 명시적으로 원하면 경고 후 진행)
  • 루프 프롬프트 안에서 또 다른 루프 생성 (루프의 자기 증식 금지)
Install via CLI
npx skills add https://github.com/s0613/S-skills --skill sj-loop
Repository Details
star Stars 1
call_split Forks 0
navigation Branch main
article Path SKILL.md
More from Creator