2026.10.26 월
farol: 머지 전에 PR 위험 확인하기
오늘의 픽: farol
farol 은 풀 리퀘스트에서 변경된 코드를 사용하는 페이지와 엔드포인트를 정적 분석으로 찾고, 머지 위험 점수와 먼저 읽을 파일을 보여 주는 프로덕트다.
오늘의 픽으로 선정한 이유는 AI 리뷰를 거친 뒤에도 머지 승인자가 여러 페이지에 영향을 주는 변경을 알아챌 수 있게 하기 때문이다.

- 출처
- Show HN
- 만든 방식
- TypeScript, Python, Go
무엇이 문제인가
AI 에이전트가 작성하고 AI 리뷰어가 검토한 풀 리퀘스트도 머지 승인은 개발자가 직접 한다. farol 의 제작자 Erich Oliveira 는 README 에서, 승인자가 모든 풀 리퀘스트를 같은 시간 동안 읽으면 결국 대충 보게 된다고 했다. 그러면 여러 페이지가 함께 사용하는 코드에서 한 줄이 바뀌어 페이지 40개가 망가져도 승인자가 알아채지 못한다고 했다. 제작자는 README 에서 특정 프로덕트를 꼽지 않고 AI 리뷰 에이전트 전반과 farol 을 비교했다. 이 기록에서는 AI 리뷰의 예로 GitHub 의 Copilot 코드 리뷰와 비교한다.
GitHub 의 Copilot 코드 리뷰 문서에 따르면 Copilot 은 풀 리퀘스트에서 문제를 찾아 수정을 제안한다. Copilot 이 풀 리퀘스트에 남기는 요약 댓글에는, 리뷰 뒤에 이 풀 리퀘스트를 승인해도 된다고 판단했는지가 들어간다. GitHub 은 같은 문서에서 Copilot 이 모든 문제를 찾는다는 보장은 없다며, 개발자가 직접 리뷰해 보완하라고 권한다.
어떻게 해결했나
farol 은 2026년 10월 25일 Hacker News 에 Show HN개발자 커뮤니티 Hacker News 에서 자신이 만든 프로덕트를 소개하는 글. 제목이 "Show HN:"으로 시작한다. 글로 올라왔다. farol 은 AI 리뷰가 끝난 뒤, 머지 승인자에게 이 풀 리퀘스트가 얼마나 위험한지와 어느 파일부터 읽을지를 보여 준다. 기준 브랜치와 풀 리퀘스트 브랜치의 코드를 모두 읽고, 변경된 함수를 호출하는 페이지와 엔드포인트를 찾는다.
이 결과로 풀 리퀘스트를 분류한다. 새 코드만 추가했으면 isolated, 기존 코드를 바꿨으면 touches-existing, 프로젝트 전체에 영향을 주면 global, farol 이 코드 일부를 읽지 못했으면 unknown 이다. 여기에 더해 0부터 100까지의 머지 위험 점수를 계산하고, 리뷰 수준을 fast track, quick review, careful review 가운데 하나로 판정한다. 결과는 풀 리퀘스트 댓글과 HTML 보고서로 보여 준다. farol 은 머지를 막거나 승인하지 않는다.
무엇이 다른가
첫째, 판단의 근거가 다르다. GitHub 문서에 따르면 Copilot 코드 리뷰는 여러 모델과 프롬프트를 조합해 작동한다. farol 은 LLM대규모 언어 모델. 많은 글로 학습해 글을 이해하고 생성하는 AI 모델이다. 대신 정적 분석프로그램을 실행하지 않고 소스 코드만 읽어 구조와 오류를 찾는 방법.으로 판단한다. TypeScript 와 Go 코드는 타입 검사기로, Python 코드는 표준 라이브러리의 AST소스 코드를 문법 구조에 따라 트리로 나타낸 자료 구조. 컴파일러와 분석 도구가 코드를 읽을 때 만든다. 파서로 읽는다. 그래서 결과가 결정적같은 입력을 넣으면 항상 같은 결과가 나오는 성질. 실행할 때마다 결과가 달라질 수 있는 LLM 의 출력과 대비된다.이다. 판정마다 변경된 파일에서 엔드포인트까지 이어지는 호출 경로도 함께 보여 준다. 트레이드오프는 함수로 계산하는 라우트 경로처럼, 코드를 실행해야 알 수 있는 값은 읽지 못한다는 점이다.
둘째, 알려 주는 것이 다르다. farol 은 Copilot 과 달리 코드의 버그를 찾지 않는다. 코드 변경이 어디까지 영향을 주는지, 머지 승인자가 어느 파일을 먼저 읽고 어느 엔드포인트를 직접 시험할지를 보여 준다. 엔드포인트가 받는 파라미터의 타입이 바뀌면 호환성을 깨는 변경이전 버전의 API 에 맞춰 만든 클라이언트가 더는 작동하지 않을 수 있는 API 변경.으로 표시한다. 제작자는 README 에서 AI 리뷰와 farol 을 함께 사용하되, AI 리뷰 다음에 farol 을 실행하라고 했다.
셋째, 비용이 다르다. GitHub 문서에 따르면 Copilot 리뷰는 한 번에 약 $0.05~$5 의 AI 크레딧을 사용한다. farol 은 MIT 라이선스의 무료 CLI 이고, 로컬이나 CI지속적 통합(continuous integration). 코드를 올릴 때마다 빌드와 테스트를 자동으로 실행하는 체계다. 에서 실행된다. 대신 Copilot 처럼 클릭 몇 번으로 수정을 적용하는 기능은 없다.
어떻게 만들었나
- 공개 저장소의 커밋 이력은 2026년 10월 21일 첫 커밋 "farol 0.1.0" 에서 시작한다. 이 커밋에 파일 504개가 들어 있어, 공개 전의 개발 과정은 저장소에서 확인할 수 없다. 10월 24일까지 커밋은 9개다.
- 커밋 9개에는 모두 Claude 와 함께 작성했다는 Co-authored-by 트레일러가 있다.
- src 디렉토리의 TypeScript 코드는 13,300줄이다. test 디렉토리에는 파일 333개가 있다.
- 제작자는 HN 댓글에서 자신이 Winnin 이라는 회사에서 farol 을 만들었다고 밝혔다. Winnin 이 farol 을 MIT 라이선스로 공개했다고도 했다. UI 디자인을 AI 로 만든 것 같다는 댓글에는, AI 로 만들었고 자신은 디자인 실력이 부족하다고 답했다.
실행해 보니
Python 파일 5개로 FastAPI 서비스를 작성했다. 아래 단계마다 브랜치를 만들어 기준 브랜치와 비교해 분석했다.
- 설치와 설정. npm 으로 farol 0.1.3 을 설치했다. 의존 패키지는 없었다.
farol.config.json에 언어와 분석 대상을 지정했다. - 기존 코드 변경.
fetch_items에 필터를 추가하고,GET /items/{item_id}의item_id타입을 int 에서 str 로 바꿨다. 판정은 careful review, 점수는 75/100 이었다.fetch_items가 있는db.py는 엔드포인트 3개 가운데 2개가 사용해, 파일 위험도 세 단계(high, medium, low) 가운데 high 로 분류됐다.item_id의 타입 변경은 호환성을 깨는 변경으로 표시됐다. - 계산한 경로. README 에 따르면 farol 이 엔드포인트를 읽지 못하면 풀 리퀘스트는 unknown 이 된다. FastAPI 는 경로가 겹치면 먼저 등록된 라우트가 응답하므로, 경로를 함수
path("summary")로 계산하는 라우트를 기존GET /reports/summary앞에 추가했다. farol 은 이 라우트를GET /reports{path('summary')}라는 새 엔드포인트로 보고 isolated, fast track, 2/100 으로 판정했다. 진단 항목의 읽지 못한 라우트 목록도 비어 있었다. FastAPI 의 테스트 클라이언트로GET /reports/summary를 요청하자 기존 핸들러 대신 새 라우트가 응답했다. - prefix 계산 방식 변경. 라우터의 prefix 를 문자열로 지정하는 대신, 기존 prefix 와 같은 값을 반환하는 함수로 계산하게 바꿨다. farol 은 기존 엔드포인트가 삭제되고 새 엔드포인트가 추가됐다고 인식하고 touches-existing, careful review, 42/100 으로 판정했다. 경로는 바뀌지 않았으므로 과한 판정이었지만, 3단계와 달리 위험을 낮게 평가하지는 않았다.
- 속도. 네트워크를 차단하고 분석을 다섯 번 실행했다. 실제 경과 시간의 중앙값은 0.55초였다.
README 에 따르면 farol 은 같은 풀 리퀘스트에는 늘 같은 결과를 출력하고, 분석 대상 코드를 실행하지 않는다. 이 두 설명도 실행 결과와 일치했다. 같은 분석을 두 번 실행한 결과는 분석 시각과 단계별 소요 시간만 달랐다. db.py 첫 줄에 import 되면 파일을 만드는 코드를 넣었지만, 분석 뒤에도 그 파일은 생기지 않았다.
"detail": "new entry point GET /reports{path('summary')} (registered in app/reports.py)"
- **Merge risk score:** 2/100 (low; higher is riskier)
{'count': 0}


확인하지 못한 것
- 큰 저장소의 속도. README 에 따르면 파일 300개인 Python 서비스의 분석 시간은 약 3초다. 실제 서비스 저장소에서 측정하자.
- TypeScript 와 Go 프로젝트. Next.js 앱에서 공유 컴포넌트를 고친 브랜치를 분석해 영향을 받는 페이지 목록을 확인하자.
- 풀 리퀘스트 댓글.
farol comment는 GITHUB_TOKEN 이 필요하다. 테스트 저장소의 풀 리퀘스트에 새 커밋을 푸시했을 때 farol 이 앞서 남긴 댓글이 수정되는지 확인하자.
판정
작동한다. 코드를 실행하지 않고 위험도가 높은 파일과 파라미터 타입 변경을 찾았다. 다만 함수로 계산한 라우트 경로는 읽지 못했고, 그 라우트가 기존 응답을 바꿨는데도 fast track 으로 판정했다. AI 리뷰를 거친 풀 리퀘스트를 개발자가 직접 승인하고, 라우트 경로를 문자열로 지정하는 경우에 써 볼 만하다. 라우트 경로를 함수로 계산하는 코드가 많은 저장소라면, 오늘처럼 기존 응답이 바뀌어도 가장 가벼운 리뷰 수준인 fast track 으로 판정될 수 있어 이 프로덕트는 적합하지 않다.
시작하기
npm install @winninjs/farol@0.1.3node_modules/.bin/farol analyze --base main --head feature --out farol.json && node_modules/.bin/farol html --in farol.json --out farol.html
- 필요한 것
- Node.js 22 이상, git · Python 프로젝트는 python3 3.11 이상, Go 프로젝트는 go · 저장소 루트의 farol.config.json. Python 서비스라면 { "language": "python", "surface": "backend" }
- 비용
- MIT, 무료. README 에 따르면 계정, 호스팅 서비스, 유료 요금제가 없다.
커버리지 보고서를 지정하지 않으면 farol 은 변경된 라인이 모두 테스트되지 않았다고 간주하고 머지 위험 점수를 계산한다.
실행해서 확인한 절차다.
진행
- 3일예정
- 7일예정
- 15일예정
- 30일예정
- 90일예정
- 180일예정
- 365일예정