Cloudflare Pi 작업이 parked에서 멈췄다면, 어떻게 재개할까?

결과를 기다리는 화면은 계속 돌아가는데 Pi 작업은 parked 상태로 이미 멈춰 있다. wait()가 끝나지 않는 이 작업은 어떻게 다시 움직이게 할까?

Cloudflare Pi 작업이 parked에서 멈췄다면, 어떻게 재개할까?
세 줄 요약
  • Agents SDK 0.30.0의 PiHarness는 Pi 1.4를 사용하며, 반복 충돌로 멈춘 작업을 parked로 표시한다.
  • parked 상태에서도 wait()는 계속 기다린다. 상태를 확인하고 재개 또는 중단을 선택해야 한다.
  • 업그레이드된 SQLite 세션 저장소는 Pi 1.3에서 열 수 없으므로 코드 롤백만으로 되돌릴 수 없다.

parked는 작업을 포기한 것도, 완료한 것도 아니다

Cloudflare의 PiHarness에서 결과를 기다리는데 작업 상태가 parked라면, 더 오래 기다리는 것으로 해결되지 않는다. 10월 22일 발표한 Agents SDK 0.30.0은 Pi 1.4의 반복 충돌 방지 기능을 지원한다. 같은 작업을 다시 시작해도 진전이 없으면 실행을 멈춰 둔다.

Pi의 충돌 복구 설명에서 기본 한도는 settings.restartLimit의 5회다. 작업이 새 상태를 저장하기 전에 충돌·축출·리셋으로 연속 중단된 횟수를 센다. 새 상태를 커밋하면 횟수는 다시 시작한다. 모델이 답변을 틀린 횟수나 모든 API 오류를 합산하는 설정이 아니다.

한 프로세스가 죽을 때 실행 중이던 작업들이 함께 집계된다. 따라서 parked 목록의 모든 작업이 각각 충돌 원인이라고 단정할 수는 없다. 메모리나 CPU 한도, 작업이 중단된 위치처럼 실제 재시작 원인을 먼저 좁혀야 한다.

pending에서 상태를 보고, 원인을 고친 뒤 retry한다

Cloudflare의 parked 설명에 따르면 이 상태는 pending()에 남으며 wait()는 계속 기다린다. 결과를 기다리는 화면에도 중단 상태와 운영자의 조치가 드러나야 한다.

호출역할
session.pending()미결 작업의 queued·running·parked 상태를 확인한다.
session.retry()재시작 한도로 멈춘 작업을 다시 실행한다. 대상이 없으면 false를 반환한다.
session.abort()인자 없이 호출하면 세션의 작업을 모두 중단한다.

재개 순서는 상태 확인, 중단 원인 수정, retry 호출이다. 같은 자원 부족이나 잘못된 실행 경로를 둔 채 재시도 버튼만 반복해서 누르면 작업을 멈춰 둔 이유가 해결되지 않는다. abort(operationId)는 대기열에 있는 해당 작업을 철회한다. 이미 실행에 합류한 작업이라면 그 작업이 속한 실행 전체를 중단한다.

대기 요청만 취소하는 것과 작업을 취소하는 것도 다르다. 세션 API에서 wait(operationId, signal)의 signal을 중단하면 기다림만 끝난다. 백그라운드 작업 자체를 멈추려는 의도라면 abort가 필요하다.

복구한다고 모든 도구 호출을 그대로 반복하지는 않는다

일반적인 충돌에서는 다음 알람이 객체를 깨우고 마지막 체크포인트부터 이어간다. 하지만 도구 재실행 정책은 별도다. 실행 중이던 도구가 replay: "safe"로 선언돼 있을 때는 다시 실행하고, 그렇지 않으면 모델에 중단된 결과를 전달해 다음 행동을 결정하게 한다.

여기서 safe는 두 번 실행해도 괜찮다는 뜻이다. 읽기 작업과 달리 카드 결제처럼 외부 상태를 바꾸는 호출은 무턱대고 safe로 표시할 수 없다. Pi의 도구 문서도 외부 부작용이 있는 재실행 가능 도구는 자체 멱등성이 필요하다고 설명한다. 중복 요청이 같은 작업으로 처리되도록 하는 장치는 도구 쪽에도 있어야 한다.

따라서 parked 해제와 외부 작업의 완료 확인은 함께 살펴야 한다. 작업 실행 기록이 이어진다는 사실만으로 결제가 한 번만 처리됐다거나 모든 도구가 성공했다는 결론이 나오지는 않는다.

Pi 1.4의 저장소 변경은 코드만 되돌려서는 취소되지 않는다

Pi 1.4는 SQLite 저장소를 열면서 schema version 2로 자동 전환한다. 전환된 데이터는 1.3.0 이하에서 열 수 없다. 새 코드가 마음에 들지 않는다고 이전 배포를 다시 올리는 것만으로 원래 상태로 돌아갈 수는 없다.

SDK 0.30.0 업그레이드 절차에는 Pi 패키지를 ~1.4.0으로 맞추고 @earendil-works/chord를 추가하는 작업이 포함된다. harness factory는 전달받은 onWake를 Harness.open()에 넘겨야 대기 중 객체가 메모리에 머무르지 않고 쉬었다가 깨어날 수 있다.

모듈 전역에 만들던 registry는 클래스 인스턴스로 옮기고, 저장소 오류 뒤 factory가 다시 실행돼도 안전하도록 구성한다. 작업 상태를 분기하는 코드에는 parked를 추가해야 한다. 운영 화면에는 parked 상태를 표시하고 복구 절차에는 재개·중단 방법을 반영해야 한다. 그래야 사용자가 완료되지 않을 결과를 계속 기다리지 않는다.