에이전트를 활용해 Git을 Rust 라이브러리로 처음부터 다시 구현한 Grit 프로젝트의 과정, 교훈, 비용, 그리고 앞으로의 가능성을 다룹니다.
몇 달 전 Anthropic이 에이전트 떼를 풀어 동작하는 C 컴파일러를 작성한 실험에 대해 읽었고, 우리가 GitHub를 시작한 직후부터 지난 15년 동안 꿈꿔 왔던 일, 즉 Git을 처음부터 라이브러리 기반으로 다시 쓰는 일을 같은 접근법으로 해낼 수 있을지 궁금해졌습니다.
물론 Git은 매우 복잡한 소프트웨어입니다. 수많은 "플럼빙" 명령이 있고, 많은 상위 수준 명령도 있습니다. 지난 20년 동안 수천 명의 사람들이 크고 작은 프로젝트를 위해 점진적으로 쌓아 올렸습니다. 애초에 링크 가능한 재진입 라이브러리를 기반으로 설계된 것이 아니라, 더 단순한 명령을 연결하는 "Unix" 철학 위에 만들어졌기 때문에, 장시간 실행되는 프로세스에서 이것을 사용하려면 모든 작업마다 fork/exec 오버헤드를 감수해야 해서 어렵습니다.
하지만 흥미롭게도 Git 프로젝트에는 1,400개가 넘는 스크립트에 42,000개 이상의 테스트로 이루어진 매우 포괄적인 테스트 스위트가 있어서, 무엇이 어떻게 동작해야 하고 동작하면 안 되는지를 꽤 단단하게 정의해 줍니다.
그렇다면 Anthropic이 처음부터 만드는 C 컴파일러에서 사용한 기본 아이디어를 그대로 써보면 어떨까요? 완전히 새로운 구현을 시작하고, Rust 라이브러리로 설계한 다음, 에이전트 떼를 문제에 투입하고, 모든 테스트가 통과할 때까지 계속 밀어붙이는 겁니다.
저는 지난 몇 달 동안 틈틈이 그렇게 해봤고, 그 결과가 Grit입니다. 이것은 Git을 처음부터 다시 구현한, 라이브러리 기반의, 메모리 안전한, Rust다운 Rust 재구현이며, 전체 Git 테스트 스위트의 99% 이상을 통과합니다.
주의! Grit은 테스트를 통과하지만, 검증된 것은 아닙니다. 아직 아무도 이것을 실제 용도로 써보지 않았습니다. 한번 가지고 놀아보려면, 지금은 잘못된 동작을 할 가능성이 높고 심지어 무언가를 망가뜨릴 수도 있다는 점을 경고합니다. 책임은 사용자에게 있습니다. 하지만 뭔가를 발견하면 알려 주세요. 저희가 고치겠습니다.
Anthropic의 실험과 달리, 이것은 단지 될 수 있는지 보기 위한 것은 아니었습니다. 시작할 때 저는 이게 성공한다면, C Git이 문제를 일으키는 몇몇 영역에서 실제로 꽤 유용한 무언가를 얻을 수 있겠다고 생각했습니다. 하지만 그 이야기는 조금 뒤에 하겠습니다.
제가 여기서 얻고자 했던 것은 무엇이었을까요?
제가 원하지 않았던 것은 C Git을 Rust로 그대로 옮긴 포트였습니다. 사실 이 일을 더 깊이 파고들수록, Git에서 지금까지 내려온 모든 결정을 전부 복제해야 했는지조차 확신이 서지 않았습니다. 하지만 원래 목표는 달성했으니, 이제는 그 부분을 다듬어 갈 수 있습니다.
제가 원했던 것은 Git 저장소와 정석적으로, 충실하게 상호작용할 수 있는 순수 Rust 코어 라이브러리였습니다. 재진입 가능하고, 링크 가능하고, 모듈식이며, 포괄적인 라이브러리 말입니다. 그리고 그 포괄성을 보장하는 방법으로, 그 라이브러리를 사용해서 가능한 한 많은 Git 테스트 스위트를 통과하는 CLI 표면을 구현하는 독립적인 크레이트를 두고 싶었습니다.
이것이 우리가 해낸 일입니다.
음, 완전히 그렇진 않지만, 흥미롭고 논쟁의 여지 없이 이미 유용합니다.
먼저, 몇 가지 단서가 있습니다.
실제로 모든 테스트 하나하나를 통과하는 것은 아닙니다. 다만 그것은 의도적인 부분도 있습니다. 이와 같은 라이브러리에서 재현할 가치가 없다고 생각한 테스트 스위트의 일부는 "건너뜀"으로 표시했습니다. 이메일 관련 기능, i18n, perforce/svn 임포터, 일부 midx/bitmap 관련 내용 같은 것들입니다. 하지만 이 글을 읽는 거의 모든 사람에게 관련 있다고 확신하는 부분에 대해서는, 이제 Grit 라이브러리/CLI가 Git 테스트 스위트를 완전히 통과할 수 있습니다.
그렇다고 완벽하다는 뜻일까요? 아닙니다. 여전히 꽤 느립니다. 어떤 경우에는 지수적으로 느리기도 합니다. 아직 테스트되지 않은 기능도 있고, API도 아주 깔끔하진 않으며, Windows 빌드도 없습니다. 이것은 첫 번째 시도의 첫 번째 이정표입니다.
그래도 몇 달과 수십억 토큰에 해당하는 작업의 결과로서는 꽤 흥미로운 출발점입니다.
이걸로 무엇을 할 수 있을까요? 흥미로운 프로젝트였지만, 단지 가능성을 보기 위해서만 한 것은 아닙니다. 저는 Grit이 충분히 유용한 무언가로 쉽게 발전할 수 있다고 생각합니다.
제가 가장 사용하고 싶은 주요 용도 중 하나는 GitButler와 네트워크 기능이 필요한 다른 독립형 Git 도구들(예: Jujutsu)에 복잡한 push/fetch 기능을 내장하는 것입니다.
현재 Gitoxide와 libgit2의 네트워킹 기능은 둘 다 부분적이거나, 느리거나, 아예 없습니다. GitButler와 Jujutsu 모두 데이터를 push하거나 pull하기 위해 Git 프로세스를 따로 실행하는 방식에 의존합니다. 큰 이유 중 하나는 자격 증명 로직이 엄청나게 복잡하기 때문인데, 이 모든 부분이 현재 Grit에서는 (이론적으로는) 커버되어 있습니다.
또 다른 가능한 사용 사례는 아주 폭넓고 흥미로운 일을 할 수 있는 WASM 빌드입니다. 예를 들어 edge Vercel 함수에서 거의 모든 Git 명령을 실행할 수 있습니다. 또는 isomorphic-git 같은 부분 구현에 의존하지 않고, 완전히 규격을 준수하는 Grit의 WASM 빌드를 바탕으로 Cloudflare Artifacts 같은 것을 만들 수도 있을 것입니다.
Git의 일부를 개별적이고 임베드 가능한 라이브러리 조각으로 갖게 되면, Rust로 커스텀 Git 서버나 클라이언트 기능을 만드는 일도 가능해집니다.
에이전트용 데스크톱 빌드나 Zed 같은 에디터 안에, 알려진 버전의 Git 전체(또는 어쩌면 필요한 부분만)를 네이티브하게 임베드할 수도 있습니다.
현재 Rust로 구현된 전체 Git 기능 빌드는 약 27M 정도이지만, 그중 큰 부분이 라이브러리이기 때문에 기능 영역별로 쉽게 쪼갤 수 있음은 분명합니다. 특정 작업을 수행하는 서브크레이트들로 말입니다. 어쩌면 필요한 부분집합만 사용할 수도 있을 것입니다.
오늘의 Grit으로 이 모든 것이 가능한 것은 아니지만, 저는 이번 이정표가 약간의 추가 작업만으로도 그것이 분명 손에 닿는 범위라는 것을 보여준다고 믿습니다.
WASM 이야기에서 이미 마음을 빼앗겼군요...
세부 사항으로 들어가기 전에, 거의 모든 코드가 메모리 안전하다는 점은 흥미롭습니다.
사실상 C와 FFI 글루를 통해 통신해야 하는 모듈은 하나뿐입니다. date/time 모듈과 TTY 체크 하나입니다. (localtime_r / strftime / mktime를 TZ 환경을 존중하는 형태로 대체할 순수 Rust 등가물이 없는 듯해서, 그 부분의 FFI는 피할 수 없어 보입니다.)
Grit의 나머지 모든 것은 안전한 Rust입니다.
이건 실제로 꽤 에이전트스러운 작은 여정이었습니다. 처음에는 어떤 종류의 에이전트 파일을 정의하고, 여러 에이전트를 루프에서 돌리면 며칠 안에 다 끝낼 수 있을 거라고 생각했습니다.
결론적으로 그렇게는 되지 않더군요. 적어도 이 정도 복잡도의 프로젝트에서는요. 아니면 제가 이걸 잘 못하는 걸 수도 있지만, 어쨌든 배우기에는 꽤 비싸고, 또 몹시 비결정적이라 답답한 교훈이었습니다.
이 모든 과정을 단계별로 나열하는 대신, 이 작업을 하며 배운 것들을 TLDR 형태로 정리하는 편이 더 흥미로울 것 같습니다.
에이전트에게 "이 Git 테스트들을 통과하게 만들어"라고 하면, 에이전트는 그걸 하기 위해 Git에 그냥 그대로 넘기는 단순한 함수를 작성하고 싶어 하는 유혹을 강하게 받습니다. 테스트가 너무 빨리, 너무 많이 통과하는 걸 몇 번 보고 나서야 에이전트가 속임수를 쓰고 있다는 걸 깨닫고, AGENTS 파일을 다듬어 그런 짓을 정말 못 하게 만들었습니다.
소원을 들어주는 지니에게 소원을 비는 것과 비슷합니다. 바닥 규칙을 아주 명확하게 적어야 합니다. 추가 소원 금지, 젠장.
좋은 예 하나를 들자면 sha256 지원입니다. 이걸 테스트하는 곳이 몇 군데 있는데, 테스트만 통과하도록 딱 필요한 만큼만 구현하면, LLM들은 실제로 sha256 지원을 구현하지 않고도 통과할 수 있다는 걸 알아냈습니다.
제가 Grit이 사실 sha256으로 초기화된 저장소에서는 전혀 동작하지 않는다는 걸 깨닫고 Claude에게 물었을 때, Claude는 이렇게 보고했습니다.
소수의 테스트가 실제로
git init --object-format=sha256을 실행합니다(t0001-init, t1900-repo-info, t0610-reftable-basics). 이것들은 실제로 실행되고 통과합니다. 하지만 무엇을 검증하는지 보세요(t0001:519-587). 모두rev-parse --show-object-format이sha256을 보고하는지만 확인합니다. 즉 init이 config에extensions.objectformat=sha256을 썼는지만 보는 것입니다. grit의 init.rs는 그 메타데이터를 올바르게 처리합니다(is_known_object_format이 "sha256"을 허용, 869-870행). 이 테스트들 중 어느 것도 그 저장소에서 add, commit, log를 하지 않습니다.
그러니까 테스트가 무엇을 보는지 파악하고, 실제로는 그냥 일반 sha1 처리를 하면서 그 부분만 동작하게 만든 겁니다. "실제 sha256 지원도 구현해야 하지 않을까"라고 생각하지는 않습니다.
이 프로젝트가 몇 주 이상 걸린 이유는, 병렬 에이전트 그룹 중 하나가 테스트 하네스의 근본적인 부분을 망가뜨렸고, 그 결과가 엄청난 회귀처럼 보여서 중간에 거의 포기할 뻔했기 때문입니다.
저는 병렬 작업이 득보다 실이 많고, 어쩌면 이 프로젝트는 달성하기에 비용이 지나치게 큰 불가능한 일일지도 모른다고 생각해서, 한동안 거의 완전히 손을 놓았습니다.
아래는 제가 시작한 4월 1일부터 오늘까지, 시간에 따라 테스트 스위트가 통과한 비율의 대략적인 타임라인입니다.
보라색 막대는 일일 커밋 수입니다. 그래서 4월 초의 일주일 남짓과 6월 초의 일주일 남짓, 두 번의 노력 구간이 보일 것입니다.

일일 커밋 수와 테스트 스위트 통과 비율
점선은 보고된 통과 비율입니다. 4월 중순에 큰 하락이 보이는데, 이것이 프로젝트에 대한 제 흥미를 떨어뜨렸습니다.
6월 초에 이 작업을 더 단순한 무언가로라도 살려 보려고 다시 집어 들었고, 작업 과정에서 에이전트 하나가 실수를 찾아 테스트 하네스를 고치면서 통과 비율이 다시 80% 정도까지 뛰어올랐습니다. 그게 저를 자극해서 끝까지 마무리해 보기로 했습니다.
저는 전에도 OpenClaw와 Ralph로 작업해 봤고, 병렬 에이전트도 여러 번 돌려 봤습니다. 그런데 제가 예상했던 것보다 더 어려웠던 것은 장시간 실행과 병렬성의 결합이었습니다.
아마 시도 비용이 꽤 크기 때문에 흔한 문제는 아닐 수도 있지만, 여러 개 혹은 수십 개의 장시간 실행 에이전트가 공유 작업 목록 하나를 두고 계속 파고드는 구조는 매우 어렵다는 걸 알게 됐습니다.
특히 제가 어느 정도 직접 몰아가고 싶을 때는 더 그렇습니다. 이 경우에는 중간에 멈추고, 모든 것을 병합하고, 방향을 바꾸고, 다시 팀을 생성해야 합니다.
저는 주로 체크박스가 달린 계획 파일을 공유해서 써보려고 했는데, 꽤 지저분했습니다. 조율을 위해서는 Linear나 GitHub 이슈 같은 것이 더 나았을지도 모릅니다. 하지만 그것은 더 느리고, 네트워크 접근과 인증, 그리고 모든 클라이언트에 도구 구성이 필요합니다.
프로젝트 말미에는 제 로컬 티켓 시스템 프로젝트인 Ticgit을 쓰기 시작했습니다. 이렇게 하면 작업 목록을 로컬에서 쉽게 수정하고 Git으로 함께 옮길 수 있습니다. 하지만 그건 또 다른 블로그 글의 주제입니다.
아마 어디선가 성능 좋은 서버에서 이걸 돌렸어야 했겠지만, 대신 저는 아주 여러 곳에서 작업했습니다. 제 노트북, Mac studio, Hostinger 슬라이스, Cursor 클라우드 에이전트 등입니다. 앞의 세 환경은 병렬성이 높아질 때마다 각기 자원 문제를 겪었습니다. 여러 개를 동시에 돌릴 때 Rust 컴파일이 제가 예상했던 것보다 훨씬 더 배고프다는 걸 알게 됐습니다.
에이전트 자체는 문제를 디버깅하고 해결하는 데 꽤 능숙한 편입니다. (swap thrashing, cpu thrashing 등) 하지만 상황이 가끔 바뀌고, 관리 난이도는 제가 예상한 것보다 높았습니다. Anthropic은 컴파일러 실험을 컨테이너에서 했으니, 제 식의 돌격형 접근보다는 사전에 시스템 계획을 세우는 편이 더 나았을지도 모릅니다.
진행 중인 작업을 인계하는 일도 계속 문제였습니다. 여러 시스템에서 작업했고, 그중 일부는 실제로 실행하고 테스트하기 위해 제 노트북에서 했기 때문에, 제가 하던 상태를 한데 묶어서 다른 곳으로 쉽게 가져갈 수 있었다면 좋았을 겁니다.
몇몇 에이전트 하네스가 각자 어느 정도 이런 것에 해당하는 기능을 제공하긴 하지만, 저는 여러 제공자를 사용하고 있었기 때문에(구독을 잘 활용해야 하니까요), 여전히 마찰이 많았습니다. 이것은 저희가 GitButler에서 하네스 종속 계층이 아니라 VCS 계층에서 제공하려고 작업 중인 부분이니, 기대해 주세요.
정말 조심해야 합니다.
Cursor와 Anthropic(제가 주로 쓴 제공자들) 사이에서 정확히 얼마를 썼는지는 잘 모르겠지만, 아마 $10-15k 정도였을 겁니다.
병렬로 돌아가게 만들기, 장시간 실행시키기, 비용 대비 테스트 통과 비율의 변화를 보면서, 제 접근 방식은 여러 번 바뀌었습니다.
저는 OpenClaw와 Claude Code를 API 사용 방식으로 많이 돌렸는데, 그건 꽤 비쌌습니다. 그다음에는 짧게 살아 있는 Cursor 클라우드 에이전트를 많이 띄워서 composer-2로 개별 테스트 파일을 처리하는 방식으로 엄청난 양의 작업을 했습니다. 프로젝트 마무리는 모든 시스템에서 구독 토큰을 써가며 했습니다. (Codex, Claude, Cursor를 병렬로 돌리면서 한도를 신경 썼습니다.)
토큰 관점에서, 이 프로젝트에 들어간 양을 대략 추정하면 다음과 같습니다.

4월의 Cursor 모델 사용량 간단 개요
데이터가 여기저기 흩어져 있고 다른 프로젝트와 섞여 있어서 정확히 말하기는 조금 어렵지만, 총합은 대략 45B tokens 정도라고 해두죠. 흥미롭게도 프로젝트의 거의 절반은 Cursor의 composer-2 모델과 다수의 짧고 집중적인 클라우드 에이전트로 완료되었습니다.
앞서 말했듯, 저는 시간에 따라 이 문제를 해결하기 위해 아주 다양한 접근을 시도했습니다. 아래는 그중 더 흥미로웠던 몇 가지 시도와 각각에 대한 제 경험입니다.
처음에는 프로젝트를 시작했을 때 제가 하루에 몇 시간씩 Bay Area를 Uber로 이동하고 있었기 때문에, 원격으로 돌리기에 꽤 괜찮은 방식이어서 OpenClaw에서 Claude Code 서브에이전트를 많이 사용했습니다.
하지만 더 비싼 토큰당 API를 써야 했기 때문에, 결국 프로젝트 전체 비용의 대부분을 고작 며칠 만에 써버렸습니다.

일주일에 8k, 나쁘지 않네요...
비용 외에도 계속 돌리기가 꽤 어려웠습니다. 머신에서 메모리와 CPU 문제를 겪었고, Hostinger 머신은 어느 시점에 그냥 죽어버렸으며, 다시 온라인으로 올리는 데 꽤 애를 먹었습니다. 매우 깨지기 쉬운 환경이었습니다.
프로젝트를 끝내려면 수만 달러를 더 써야 할 것 같다는 걸 깨달았을 때, 저는 전략을 바꿔 구독 토큰과 더 저렴한 모델을 활용하기 시작했습니다.
결국 프로젝트 작업의 대부분을 해낸 전략은 아마도 작업하고 싶은 파일마다 Cursor 클라우드 에이전트를 하나씩 띄우고, 각각 완료될 때마다 병합하는 방식이었습니다.
여기서 부딪힌 문제는 이 과정이 매우 수작업이었다는 점입니다. Git의 대체 구현을 만들고 있을 때는, 일부 테스트가 환경을 망가뜨린 다음 Git 대신 당신의 바이너리를 쓰려고 하거나, 컨테이너의 Git 접근이 의존하는 자격 증명 저장소를 망가뜨립니다. 즉 Cursor 에이전트가 컨테이너 밖으로 생성된 코드를 push하기 위해 Git을 쓸 수 없게 됩니다. 이것은 이 프로젝트에 아주 특수한 문제였고, 무슨 일이 일어나는지 파악하는 데 도움을 준 vmg와 Cursor 팀에게 큰 감사를 전합니다.
제 테스트가 어떤 방식으로 env를 덮어써서 push를 망가뜨리는지는 끝내 완전히 알아내지 못했지만, 그 때문에 정말 많은 경우에 컨테이너 터미널에 들어가서 remote를 수동으로 추가하고 커밋을 push해야 했습니다. 때로는 Rust 코드 3줄을 바꾸기 위해 수동 클릭과 복사/붙여넣기에 많은 시간을 썼습니다.
이상적이진 않았지만, 그렇게 많이 띄우고 있었기 때문에 병렬로 많은 일을 해내긴 했습니다.
여러 가지를 다 해본 뒤에도, 사실 이것이 제가 가장 선호하는 방식입니다.
저는 이것을 몰랐는데, A16Z의 멋진 파트너 Matt가 거기서 제 팟캐스트 녹음 중에 이 기능을 알려줬습니다.
Cursor 클라우드 에이전트를 시작하고 모델 선택기에서 "Long-running"을 선택해 "Grind mode"로 넣을 수 있습니다. 그러면 계획을 작성한 뒤, 그 프롬프트가 끝났다고 스스로 판단할 때까지 계속, 계속 파고듭니다.

Grind mode
이 프로젝트에서 정말 많은 작업이 제가 그냥 "t1 테스트 패밀리를 전부 통과하게 만들어"라고 말하고, 하루 동안 기다리며 PR에 커밋 100개가 쌓이는 걸 보는 방식으로 이루어졌습니다. 정말 대단했습니다.
Codex와 Claude Code의 /goal 모드도 이런 종류의 일을 합니다. 다만 제 경험상 그것들은 훨씬 느렸고, Claude 쪽은 다소 혼란스럽고 자주 멈춘 것처럼 보였습니다.
/goal 모드로 실행한 Codex는 계속 작동하면서 일을 해내는 편이었습니다. 반면 Claude는 제가 개입하기 전까지 그냥 거기 멈춰서 별로 일을 안 하는 경우가 잦았습니다. 왜 그런지는 끝내 정확히 모르겠지만, 그래서 점점 피하게 되었습니다.
이번 마지막 주에는 프로젝트를 마무리하기 위해, 새로 나온 Claude의 "Ultracode" 노력 모드에서 dynamic workflows도 시험해 봤습니다.

3개 스레드에서 70개 에이전트가 22시간 동안 돌아간 Claude dynamic workflow
"t1 계열 테스트를 모두 통과시켜라" 같은 큰 작업을 쪼개는 데는 이 형식이 꽤 마음에 듭니다. 다만 여기서도 자원 관리를 조심해야 합니다. rustc 병렬 빌드 때문에 CPU와 메모리를 신나게 갈아버리고, 왜 이렇게 느린지 파악해 보라고 시킬 때까지 거의 멈춘 듯 느려질 수 있습니다.
마지막 며칠 동안 Codex와 Cursor 양쪽에서 구독 토큰을 다 써버렸기 때문에, 주말에는 Claude의 일련의 dynamic workflow로 마지막 몇 퍼센트 테스트를 마무리했습니다. 제대로 설정해 두면, 크고 복잡한 목록도 꽤 똑똑하게 여러 시간 동안 묵묵히 밀어붙일 수 있습니다.
마무리로 작은 조언 하나를 더 하겠습니다.
가볍게 조율하는 에이전트 떼에게 테스트 파일 하나씩 집어서 알아서 되게 만들라고 하고 싶은 마음도 있었지만, 제가 느끼기에 가장 좋고 가장 빠른 성과는 제가 직접 접근했을 법한 방식으로 일하도록 에이전트를 지시했을 때 나왔습니다.
그냥 "다음 테스트 잡고 계속 가"라고 하는 대신, 제가 이 프로젝트를 개인적으로 다시 쓴다면 문제를 어떻게 접근할지 적는 편이 더 좋았습니다. 기본 플럼빙 명령부터 시작하고, 그다음 그것들에 의존하는 더 중요한 명령으로 가며, 아래에서 위로 쌓아 올리는 식입니다. 예를 들어 diff 포맷팅 출력 같은 것은 맨 마지막까지 미뤄도 됩니다. 실제로 다른 곳에서 거의 쓰이지 않기 때문입니다. 기본기가 동작하면, 그 위에서의 리팩터링은 상대적으로 더 쉬워집니다.
문제를 어떻게 접근할지 자세히 정리한 다음, 그것을 단계별로 넘기세요. 제가 그 원칙에서 벗어나 대규모 병렬화로 생각을 덜 하고 싶어질 때마다, 문제를 겪었고 수렁에 빠졌습니다.
이건 흥미로운 지점이고, 아마 이것만으로도 별도의 블로그 글 하나가 나올 만합니다.
Git 소스 코드는 GPL 라이선스입니다. libgit2 코드는 GPL에 링크 예외가 붙어 있는데, 링크가 애초에 핵심 목적이었고 사람들이 실제로 쓰이길 원했기 때문입니다.
아마 20년 전, 아직 아무도 크게 신경 쓰지 않았고 어느 정도 논의의 여지가 있었을 때 libgit2를 더 허용적인 라이선스로 밀어붙였어야 했을지도 모릅니다. 그리고 그 이후 그 프로젝트에 기여한 대부분의 사람들도 그 편을 선호했을 것이라고 생각합니다. (라이선스 문제는 지금까지도 계속 이슈입니다.) 하지만 아쉽게도 그 당시 저는 거기에 에너지를 쏟고 싶지 않았습니다.
LLM들이 이 프로젝트를 위해 만들어낸 코드를 살펴본 결과, 특히 구현을 라이브러리화하고 메모리 안전하게 만들기 위해 필요했던 꽤 크고 광범위한 아키텍처 변화들을 고려했을 때, 우리는 이 코드베이스가 GPL 라이선스를 그대로 이어받아야 하는 파생 저작물은 아니라고 판단했고, 대신 MIT로 코드를 공개하기로 결정했습니다.
이건 조금 논란이 될 수도 있지만, 결국 방어 가능한 판단이라고 생각하며, 더 중요하게는 더 넓은 Git 커뮤니티를 위해 최선이라고 생각합니다.
저는 4월에 몇 주를 여기에 쏟고, 프로젝트를 잠시 멈췄다가, 6월 첫 주에 마무리했습니다. 합쳐서 보면 총 2주에서 3주 정도 동안 하루 몇 시간씩 쓴 셈일 겁니다. 대부분의 시간에는 작업이 백그라운드에서 그냥 돌아가고 있었고, 저는 다른 일을 할 수 있었기 때문에, 주로 방향을 잡고, 통합하고, 무엇이 잘못됐는지를 파악하는 역할을 했습니다.
전체 실험이 끝났을 때, 우리가 얻게 된 것은 다음과 같습니다.
360,000+ LOC
500+ pull requests
7000+ commits
41,715 / 42,001 tests passing (99.3%)
꽤 재미있는 실험이었고, 이것을 전체 커뮤니티에 정말 유용한 무언가로 발전시킬 수 있다고 생각합니다.
Grit을 한번 써보고 싶다면 프로젝트 홈페이지의 자세한 내용을 확인해 보세요: https://grit-scm.com. 그리고 앞으로의 진행 상황이 궁금하다면, 여기에서 이어질 후속 소식을 지켜봐 주세요!
작성자Scott Chacon
Scott Chacon은 GitHub와 GitButler의 공동 창업자로, 현대적인 버전 관리에 맞는 혁신적인 도구를 만들고 있습니다. 그는 Pro Git의 저자이며, Git과 소프트웨어 협업에 대해 전 세계에서 강연해 왔습니다.