금요일에 발생한 사고로 인해 작은 체크아웃 서비스가 중단되었습니다. 실패한 작업은 에이전트 풀 리퀘스트(agent pull request)에서 비롯되었습니다. 이 패치는 스모크 테스트를 위해 run_check이라는 헬퍼 함수를 추가했습니다.
디프(diff)는 40줄 분량이었고 대체로 깔끔해 보였습니다. 하지만 하나의 템플릿 문자열이 그 깔끔한 모습을 망가뜨렸습니다. 이 헬퍼 함수는 브랜치 이름으로부터 셸 명령어를 구축합니다.
요약 전에 코드를 읽어보세요
에이전트의 요약은 더 빠른 리뷰 루프를 약속했습니다. 하지만 핸들러(handler)는 더 엄격하고 작은 이야기를 들려주었습니다. 도구 JSON에서 온 브랜치 필드가 명령어 문자열 안으로 들어갔습니다.
// PR에서 가져온 신뢰할 수 없는 스케치입니다. 병합하지 마세요.
function runCheck(branch) {
const cmd = `git fetch origin ${branch} && npm test`;
...
도구 JSON은 이 핸들러 내에서 호출자 제어 입력(caller-controlled input)으로 간주됩니다. 셸 문자열은 경로에 두 번째 파서를 추가합니다. 오직 main만 통과하는 테스트는 그 파서가 존재하는지 알 수 없습니다.
목표는 유지하고 메커니즘은 제거하세요
기존 작업들이 이 도구를 호출한다면 도구 이름은 유지하세요. fetch와 테스트의 순서는 유지하세요. 타임아웃을 요청하는 주석은 모두 유지하세요.
다음 커밋에서 템플릿 문자열을 제거하세요. 이번 호출 경로에서는 셸 true 플래그를 제거하세요. 셸을 감싸는 역할만 하는 패키지는 제거하세요.
고정된 인자 목록을 요구하세요
별도의 인자 배열과 함께 execFile을 호출하세요. 엄격한 패턴에 실패하는 브랜치 텍스트를 거부하세요. 막히는 자식 프로세스를 종료하기 위해 타임아웃을 설정하세요.
import { execFile } from "node:child_process";
import { promisify } from "node:util";
...
이 블록을 제안된 패치로 취급하세요. 이는 실제 하드웨어에서 벤치마크되지 않았습니다. 이것은 리뷰가 요구해야 할 형태를 정의합니다.
규칙을 테스트 파일에 고정시키세요
다른 도구 테스트 옆에 이 하네스(harness)를 저장하세요. 테스트 중에 디스크에서 핸들러 소스를 읽으세요. 셸 모드가 돌아오면 작업을 실패시키세요.
import assert from "node:assert/strict";
import { readFileSync } from "node:fs";
import test from "node:test";
...
이 두 가지 거부 사례는 닫힌 방식으로(fail closed) 실패해야 합니다. git이나 npm이 시작되기 전에 예외를 발생시켜야 합니다. 깨끗한 체크아웃 트리에서 node --test로 실행하세요.
로컬 패스는 시작 신호일 뿐입니다. 동일한 파일은 일회용(disposable) 러너에서 실행되어야 합니다. 풀 리퀘스트에 종료 코드를 기록하세요.
8단계에 걸쳐 풀 리퀘스트 검토하기
- diff를 동결하고 첫 번째 패스 동안 에이전트 요약을 숨기세요.
- 도구 JSON, 환경 파일 또는 검토 텍스트에서 도착하는 값들을 나열하세요.
exec, spawn 또는 백틱 명령어에 도달하는 모든 값을 플래그 지정하세요.
- 셸 보간(shell interpolation)을 인자 배열과 명시적인 거부 경로로 대체하세요.
- 소스 단언(source assertions)과 하네스에서 가져온 두 가지 거부 사례를 추가하세요.
- 프로덕션 비밀 정보가 없는 무료 서버에서 해당 파일을 실행하세요.
- 동결된 diff와 테스트 로그만 무료 모델에 전송하세요.
- 인간 오너가 두 출력을 모두 읽은 후 병합을 승인하도록 하세요.
여섯 번째 단계는 공유 상태가 없는 스크래치 작업 공간이 필요합니다. 풀 리퀘스트 브랜치를 해당 작업 공간으로 클론하세요. 그 검토 머신에는 프로덕션 토큰을 두지 마세요.
명령어 출력을 검토 스레드에 복사하세요. 0이 아닌 종료 코드는 논쟁거리가 아니라 되돌리기(revert)로 간주하세요. 프로덕션 자격 증명을 첨부하여 작업을 재실행하지 마세요.
승인 대신 무료 모델에게 노트 초안 작성 맡기기
공개 정보: 이 기사는 MonkeyCode의 제품 홍보의 일환으로 준비되었습니다. 운영자는 MonkeyCode를 오픈 소스 프로젝트로 설명합니다. 무료 모델 접근을 통해 첫 번째 검토 노트를 초안 작성할 수 있습니다.
무료 서버 옵션은 노트북에서 하네스를 실행할 수 있게 합니다. 이 초안은 특정 모델을 명시하지 않습니다. 토큰 할당량, 디스크 크기 또는 keep-alive 시간을 언급하지도 않습니다.
이러한 세부 정보는 변경되므로, 장시간 실행 전에 현재 문서를 확인하세요. 이전 글들은 오늘날의 제한 사항에 대한 증거가 아닙니다. diff와 테스트 로그를 붙여넣으세요.
환경 파일, 고객 행(customer rows), 쿠키는 제외하세요. trust, revert, test라는 세 개의 열을 요청하세요. 자문 번호를 지어내는 줄은 모두 삭제하세요.
Review this frozen diff for shell interpolation.
Return trust, revert, and test rows.
Do not suggest new network calls.
노트에서 라이브 시크릿(live secret)을 요청하면 중지합니다. 노트가 핸들러를 재작성한 경우 하네스(harness)를 다시 실행하세요. 모델 텍스트는 주석으로 유지합니다.
이것 자체가 병합 승인(merge approval)은 아닙니다. 최종 병합 결정권자는 여전히 해당 인간 소유자입니다. 녹색의 모델 노트가 그 소유자를 대체하는 일은 결코 없습니다.
이미 접근 권한을 가진 독자들은 스크래치 브랜치(scratch branch)에서 이 하네스를 다시 실행할 수 있습니다. 그 종료 코드를 리뷰 노트 옆에 첨부하세요.
diff가 커질 때 매트릭스 사용하기
| diff의 신호 | 검토 조치 | 이유 |
|---|
| 툴 필드가 셸 문자열로 복사됨 | 되돌리기(Revert) | 신뢰할 수 없는 텍스트가 두 번째 파서에 도달함 |
| ... | | |
이 매트릭스는 오직 검토 보조 도구로만 작동합니다. 점수나 벤치마크가 아닙니다.
승인된 래퍼(sanctioned wrapper)의 경우 한 행이 틀릴 수 있습니다. 해당 래퍼를 리뷰 코멘트에 명시하세요. 여전히 새 툴에서 원본 명령어 문자열은 금지합니다.
같은 리뷰에 제한 사항 명시하기
브랜치 패턴(branch pattern)은 게이트일 뿐, 전체 리팩토링 문법(ref grammar)이 아닙니다. 유효한 Unicode 이름은 의도적으로 닫힌 실패(fail closed)를 보입니다. 프로덕션 CI는 git과 npm을 절대 경로로 호출해야 합니다.
무료 서버 이미지는 본 기사에서 통지 없이 변경될 수 있습니다. 가동 시간, 리전 또는 스토리지에 대한 어떠한 약속도 여기서는 하지 않습니다. 소스 스캔은 다른 파일에 있는 호출을 놓칠 수 있습니다.
풀 리퀘스트(pull request) 전체에 걸쳐 스캔을 실행하세요. execFile 호출은 여전히 로컬 바이너리를 시작합니다. 쓰기 가능한 PATH는 리뷰 목록에 남아있습니다.
셸 트루(shell true)를 언급하는 코멘트는 소스 스캔을 유발할 수 있습니다. 문서 파일을 되돌리기 전에 실제 호출과 일치하는지 확인하세요.
무료 모델은 붙여넣어진 컨텍스트만 봅니다. 다른 문서에 있는 정책 노트를 놓칠 수 있습니다. 인증(auth), 청구(billing), 마이그레이션에는 인간의 승인이 여전히 필요합니다.
이 경로를 세 가지 설정에서 사용하지 않기
러너가 프로덕션 자격 증명(credentials)을 보유하고 있을 때는 무료 서버를 건너뜁니다. 공유 용량은 그러한 시크릿(secrets)에 적합하지 않습니다. 그 경우에는 내부 잠금 러너(internal locked runner)를 사용하세요.
정책이 서명된 프라이빗 이미지(signed private image)를 요구할 때는 이 경로를 건너뜁니다. 공유 옵션으로는 그러한 통제를 충족시킬 수 없습니다. 예외 사항은 팀 핸드북에 기록해야 합니다.
유지보수자가 임의 스크립트를 실행해야 하는 경우에는 건너뛰세요. 그러한 요구사항은 별도의 허용 목록(allowlist) 설계가 필요합니다. 얇은 셸 문자열이 그 설계는 아닙니다.
스타일 검토만으로는 이 하네스(harness)를 안전하게 무시할 수 있습니다. 도구 코드가 프로세스를 시작할 수 있을 때 이 하네스를 사용하세요. 그 경계가 추가적인 작업을 작게 유지해 줍니다.
하나의 구체적인 댓글로 리뷰를 마무리하기
댓글에 되돌려진(reverted) 템플릿 문자열 이름을 명시하세요. 하네스 파일과 종료 코드를 연결하세요. 무료 서버 실행이 이 파일만 다루었음을 언급하세요.
저자에게 먼저 현재 무료 등급 제한을 확인해 달라고 요청하세요. 더 큰 기능군은 그 확인 후에 기다릴 수 있습니다. 댓글에 제품 홍보가 필요하지는 않습니다.
체크아웃 서비스에는 지루한 핸들러(handler)가 필요합니다. 브랜치 이름은 평범한 데이터로 유지되어야 합니다. 셸 스크립트가 되어서는 안 됩니다.