요약
AI가 오래된 버그를 쉽게 찾아내면서 고칠 일이 늘어 Postgres 19 출시가 늦어지고 있습니다.
PostgreSQL 핵심 개발자이자 커미터(코드를 저장소에 반영할 권한이 있는 개발자)인 로버트 하스가 블로그에 쓴 글입니다. 보통 9월 중순에서 10월 중순 사이에 나오던 메이저 버전이 이번에는 11월로 밀릴 전망입니다. 하스는 그 원인으로 LLM을 꼽았습니다.
왜 중요한가
- LLM 덕분에 버그를 찾기는 쉬워졌지만, 고치고 검토하는 사람의 역량은 그대로라는 불균형을 보여 줍니다.
- 코드 품질이 나빠진 탓이 아닙니다. 커미터들은 평소만큼 신중했고, LLM이 그 실수를 더 많이 잡아냈습니다.
- 앞으로 모든 새 기능이 AI의 검증을 받게 되어, 예전엔 묻혔을 문제가 몇 시간 만에 드러날 수 있다고 봤습니다.
핵심 내용
- 출시를 앞둔 안정 브랜치의 커밋은 전년 같은 기간 724개에서 1,169개로 60% 넘게 늘었습니다.
- LLM이 쓴 수정안은 틀리거나 프로젝트 기준에 어긋날 때가 많아, 결국 사람이 검토하고 반영해야 합니다.
- 커미터들이 보안 문제와 이전 버전 버그에 매달리느라, 되돌릴 기능을 가리는 검토도 늦어졌습니다.
- 8월 말부터 9월 중순 사이에 SQL/PGQ(속성 그래프 질의) 등 큰 기능 여러 개가 되돌려졌습니다.
- 하스는 지연 기간이 짧고 품질을 지키려는 결과라서 크게 걱정할 일은 아니라고 했습니다.
HN 반응
- 일부 이용자는 자기 회사도 AI로 버그 수천 개를 고쳤다며, 해고 핑계가 아니라 기술 부채를 갚는 데 쓰는 게 옳다고 반겼습니다.
- 외부 라이브러리를 자체 코드로 바꾸자는 주장에는 덜 검증된 코드로 버그를 옮길 뿐이라는 반론과, Log4J처럼 안 쓰는 기능이 더 위험하다는 재반론이 맞섰습니다.
이건 좋은 일입니다. 기술 부채를 갚는 건 언제나 훌륭한 일이죠.
저희 회사의 150만 줄짜리 시스템에서도 지난 1년간 버그와 보안 구멍, 순환 의존성을 수천 개 찾아서 고쳤습니다. 코드 품질이 올라갔고 테스트 커버리지도 늘었습니다. 최근에는 컴파일러가 경고를 오류로 처리하도록, 그것도 최대한 엄격하게 설정했습니다. 빈틈이 메워지는 걸 보고 있으면 정말 놀랍습니다. 사람 개발자만으로는 불가능한 일이었을 테고, IDE로 했다면 몹시 불편했을 겁니다. 인프라 자동화와 모니터링에 있던 버그와 장애 유형도 모두 정리했습니다. 다음 프로젝트는 서드파티 의존성을 전부 없애는 것이고, 그다음에는 프레임워크를 전혀 쓰지 않고 프론트엔드를 완전히 새로 만들 겁니다. 그 뒤로는 npm에 다시는 손대지 않을 거고요.
그래서 postgres 소식을 읽고 정말 기뻤습니다. 이런 곁가지 임무를 찾아서 끝까지 밀어붙였다는 거잖아요. 코드베이스를 방탄으로 만들 수 있을 겁니다.
서드파티 라이브러리를 피하는 건 거짓된 안도감 같습니다. 스캐너 리포트에서 CVE가 안 보일 뿐이지, 버그는 그대로 있습니다. 공개 라이브러리보다 검증이 덜 된 자체 코드 안에 있을 뿐이죠.
무슨 말씀인지는 압니다. 그래도 우리가 필요한 기능만 하는 1천 줄짜리 자체 코드를 충분히 테스트하고 우리 통제 아래 두는 편이, 5만 줄짜리 코드에 의존하는 것보다 낫다고 봅니다. 5만 줄 중에 쓰는 기능은 10%쯤이고 나머지는 방해만 되는 데다, 인터넷의 아무나 수정할 수 있고, 서버 환경에는 정말 두고 싶지 않은 전이 의존성이나 텔레메트리 같은 불청객까지 끌고 들어오기도 하니까요. 지난 한 달 사이에 봤듯이 오픈소스 패키지는 악성코드나 해커가 시스템에 침투하는 데 점점 더 탐나는 표적이 될 겁니다. 말할 필요도 없고, 앞으로 더 심해질 겁니다. 기술 부채를 갚든가, 죽든가 둘 중 하나가 될 거예요.
우리가 허용하고 지원하고 싶은 "서드파티" 패키지는 이상적으로는 런타임의 LTS 버전에서 제공되는 것, 이 경우엔 dotnet 팀이 제공하고 마이크로소프트가 감사한 패키지뿐입니다. 그래서 항상 프레임워크가 제공하는 것을 중심으로 만들려고 합니다. 두 번째 선택지는 자체 코드, 세 번째는 오픈소스 패키지, 네 번째는 별도의 애플리케이션이나 어플라이언스입니다(티켓 관리용 ZenDesk 같은 것). 시간이 지나면 dotnet 팀 코드와 우리 코드만 남기도록 줄여 갈 겁니다.
대부분의 CVE는 공개적으로 라우팅되지 않고 실제 공격 경로도 없는 서버에서는 가려질 수 있다는 점을 기억하세요. 공개된 부분(예컨대 웹 서버가 올라간 리눅스 엣지 서버, 방화벽 몇 대, 열린 포트 몇 개)은 최대한 단단히 보안을 강화해서, 그 뒤에서 돌아가는 모든 서비스에 전면 접근하지 못하게 해야 합니다. 우리는 내부 서비스에 공인 IP조차 주지 않아서 트래픽을 보내는 것 자체를 거의 불가능하게 만들어 놨습니다.
우리 git 저장소도 공개 인프라에 있지 않습니다. 진지하게, 공개 서비스에 호스팅하는 게 정말 필요한지 신중하게 생각해 보세요. 저장소를 공개하는 건 말할 것도 없고요.
비밀 값과 인증서를 전담하는 관리 시스템도 따로 있어서 코드베이스나 파이프라인에는 자격 증명이 전혀 없습니다. 이 부분은 아주 엄격합니다.
"내부에 있으니 공격으로부터 (더) 안전하다"는 생각은 거짓된 안도감입니다. 머스크가 낫페트야 사태에서 뼈저리게 배웠듯이요.
https://www.wired.com/story/notpetya-cyberattack-ukraine-russia-code-crashed-the-world/
https://archive.is/Amlij
2000년에 나온 글입니다.
TV나 냉장고, 직원의 개인 기기(BYOD), 프린터가 LAN에 침투하기 전까지는 어느 정도 통하죠.
그러니까 사실상 안 통한다는 얘기예요.
다층 방어의 일부일 뿐이고, 유일한 보안 계층이 아닙니다. 그러니 어떻게든 뚫고 들어와도 또다시 아무것도 못 찾을 겁니다. 한 겹 깊이 들어갈수록 더 어려워지고요. 아, 멍청이들을 계속 붙잡아 두려고 곳곳에 깔아 둔 미끼와 허니팟은 세지도 않았습니다.
그리고 서드파티 라이브러리 중에는 모두가 라이브러리 하나로 모든 걸 해 주길 바라기 때문에 과하게 설계되고 지나치게 복잡해진 것도 있습니다.
이런 과도한 복잡성은 1천 줄짜리 솔루션에는 없는 보안 문제를 쉽게 끌어들일 수 있습니다.
보안 버그를 빼고 보더라도 의존성이 계속 바뀌는 큰 원인이기도 하죠.
반면 제 코드라면 우리 조직 밖의 누군가가 의존성에 깨지는 변경을 넣기로 했다는 이유만으로 생겨난 작업을 일정에 끼워 넣을 걱정을 안 해도 됩니다. 그 세금을 내는 일은 십 년 전에 지겨워졌고, 지금은 참을성이 거의 바닥났습니다.
여기서 Log4J가 떠오릅니다. 취약점은 제가 한 번도 쓰이는 걸 본 적 없는 마이너한 기능에 있었죠. 단순한 게 더 안전할 때가 있어요.
물론 단순하다는 게 "비밀번호를 해시 없이 저장했다"인 경우도 있으니, 적당한 중간 지점을 찾아야 합니다.
Log4J는 정말 좋은 예입니다. 끝없이 기능을 추가하지 않는 건 결국 메인테이너의 안목에 기댈 수밖에 없어요.
jackson-databind도요.
저희 생각도 100% 같습니다.
저라면 1천 줄의 기술 부채를 직접 떠안느니 5만 줄을 유지보수하는 대가를 다른 누군가에게 치르게 하겠습니다.
package.json이나 pyproject.toml(또는 <packagemanagerX>)에 있는 걸 전부 돈 내고 쓰시나요?
제품이 무엇이고, 서드파티 라이브러리를 어디에 쓰고, 대안이 무엇이냐에 따라 달라집니다. 안타깝게도 서드파티 라이브러리 쓰는 쪽으로 지나치게 치우쳐서 득실을 이해하지 못하는 사람들이 있습니다.
예를 들어 몇 년 전에 저는 꽤 큰 서드파티 수학 라이브러리를 걷어냈습니다. 수학 함수 하나만 쓰고 있었는데, 그건 직접 구현하기가 아주 쉬웠거든요.
서드파티 라이브러리는 다음을 해야 한다는 점을 기억하세요.
1: 라이선스 조건과 회사의 방침을 지키고 있는지 주기적으로 감사해야 합니다.
(1.5: 인수합병 때는 실사하러 오는 사람이 꼭 있어서 이게 중요해집니다.)
2: 주기적으로 업데이트해야 합니다(보안 버그에 대비해서).
2.5: 보안 문제가 공개되면 촉박한 일정에도 바로 업데이트해야 합니다.
그 수학 라이브러리의 경우 약 20줄의 코드와 100줄의 테스트로 대체한 쪽이, 위의 일들이 생길 때마다 계속 검토하는 것보다 훨씬 남는 장사입니다.
그렇다면 서드파티 라이브러리를 쓰는 게 "가치 있는" 시점은 언제일까요? 저희 경우엔 그 라이브러리를 훨씬 더 많이 써야 합니다. 적어도 20가지는 되는 수학 함수를 거기서 가져다 써야 할 겁니다.
제가 log4j를 직접 만들었다면 JNDI를 포맷 인자로 구현하는 일은 절대 없었을 거라고 기꺼이 내기할 수 있어요.
물론 암호화를 직접 만들면 안 되겠지만, 로거 정도는 쓸 수 있잖아요.
로깅은 보안 면에서 아주 복잡한 영역입니다. 로그에 민감한 데이터가 들어가는 일이 흔하고, 그게 네트워크를 타고 모니터링 서버로 전송되니까요.
게다가 프로그램의 어느 부분이든 로거에 데이터를 보낼 수 있습니다. 즉 로거는 어디서든 악성 페이로드를 받을 수 있다는 뜻이죠. 어쩌면 로거가 ASCII 제어 문자를 제대로 처리하지 못할 수도 있고요.
로깅이 복잡한 건 범용으로 만들 때의 관점에서 그렇습니다. 대부분의 사람은 그 기능을 전부 필요로 하지 않아요. 이게 바로 여기서 말하는 핵심입니다. Log4j는 프로젝트의 90%에는 필요 없는 기능이 너무 많았습니다. 물론 서버가 여러 대이고 로그 수집기로 보내는 대규모 프로젝트는 복잡하겠죠. 하지만 아마 두 회사 정도의 요구 때문에 영향을 받은 사람이 얼마나 되겠어요?
로그 메시지를 받아서 stderr에 바로 쓰는 건요? 그건 쉽습니다.
바로 이런 데서 LLM이 짠 라이브러리 대체품이 쓸 만합니다. 쉽게 바꿔 끼울 수 있는 중요하지 않은 코드라면 LLM이 로깅 패키지를 만들어 줘도 저는 괜찮아요. 보관용으로 로그 메시지를 별도 서버에 보내야 한다면요? 그때는 조금 더 따져 보겠습니다.
글쎄요, 저는 거의 항상 로거를 직접 만들어 썼습니다. 공유 라이브러리로 만든 것도 아니고, 그냥 다음 프로젝트에 복붙하거나, 그조차 귀찮아서 그 자리에서 뚝딱 만들 때도 많았어요. AI가 나오기 전에도요.
조금이라도 까다로운 부분은 "유니코드를 깨뜨리지 말 것" 정도뿐이고, 나머지는 단순합니다. 로깅 싱크나 설정 가능성, 플러시 시점, 모니터링 같은 걸 넣으면 복잡해질 수 있지만, 대부분의 경우엔 그런 게 전부 필요하진 않아요. 필요해질 때 만들면 됩니다.
모니터링 서버가 필요 없다고 상상해 보세요. 실제 log4j 배포 대다수가 아마 그럴걸요?
예를 들어 마인크래프트는 log4j로 콘솔과 로테이션되는 파일에 메시지를 씁니다.
기술적으로는 다른 곳으로 보내도록 설정할 수도 있겠죠. 아마도요. 실제로는 그냥 stdout을 리다이렉트하거나, 파일을 tail 하거나, 모드를 설치하는 게 낫지 않을까요?
솔직히 윈도에서 소프트웨어를 돌리겠다고 고집하는 게 아니라면, 얇은 래퍼를 거쳐서 로깅을 syslog에 맡기는 편이 훨씬 낫습니다. 아주 특이한 경우를 빼면 거의 다 처리해 주거든요. 하지만 이건 자바 진영의 이식성 공약과 자체 개발 선호(NIH) 성향에 어긋나서, 지금 같은 상황이 된 겁니다.
그리고 아마 더 중요한 건, AI가 꼭 필요한 기능만 있는 아주 단순한 로거를 5분이면, 아니 그보다 짧게 만들어 준다는 거죠.
만들 수 있는 것과 만들어야 하는 것은 다르지 않나요?
타이밍 공격이 가능한지 보려고 어셈블리까지 일일이 확인할 여유는 없어요.
하지만 암호화는 사실 작은 부분일 뿐입니다. 원자로를 설계할 생각은 없지만, 원자로에서 나오는 전기에 의존하는 일은 얼마든지 하잖아요. 마찬가지로 인증도 직접 만들 수 있습니다. 애플조차 속도 제한을 깜빡한 판국이니까요…
회사들이 AI를 써야 하는 방식이 바로 이겁니다. 개발자 절반을 자르는 핑계로 쓸 게 아니라요. 버그도 줄고, 장애도 줄고, 모두에게 더 나은 경험이 됩니다.
저희는 AI 때문에 단 한 명도 해고하지 않았습니다. 모두의 시간을 아끼고, 입력을 더 정확하게 만들고, 경리 담당자들이 더 일을 잘하게 하고, 기술자와 작업 카드를 더 잘 관리하는 식으로 활용하고 있습니다. 시스템도 방탄 수준으로 만들어서 지난 24개월 동안 주말 장애가 딱 한 번뿐이었고, 그것도 우리 잘못이 아니었습니다(서드파티 의존성이 금요일 밤에 대규모 배포를 했거든요). 이제 우리 시스템은 아주 "지루해졌고" 그게 정말 좋습니다.
저런, 저희는 예전의 절반 규모가 되어서 적은 인원으로 더 많은 일을 하게 됐어요. 더 많이 하고는 있지만 사람이 절반이라 여전히 빈틈이 너무 많아서, 저는 답답한 나머지 직접 그만두려고 합니다.
축하드려요, 멋지네요.
저도 그런 곳에서 일하고 싶네요! 채용 중인 자리 없나요? :)
이게 소프트웨어 개발의 미래이길 바랍니다. 아직 만들 게 정말 많으니까요.