Rust가 빛나는 분야와 생태계의 한계, 그리고 프로젝트에 Rust를 선택하기 전에 고려해야 할 사항을 살펴봅니다.
“Rust는 이 프로젝트에 잘 맞을까요?”
저는 이 질문을 꽤 자주 받습니다. 고통스럽고 비용이 많이 드는 실수를 몇 가지라도 피하는 데 도움이 될 수 있다면, 제 생각을 적어 둘 때가 되었다고 생각합니다.
짧게 답하면: 아마 아닙니다(팀이 이미 Rust 전문가들로 가득한 경우가 아니라면)
“하지만, 하지만, 하지만 Amazon, Cloudflare, Google, Meta, Discord 등이 모든 것을 Rust로 옮기고 있다면 우리도 아마 따라야 하는 것 아닌가요?”
아니요.
Rust에 관한 책(Black Hat Rust)을 쓴 사람의 말이라 놀라울 수 있습니다. 그러니 저처럼 설명 없는 짧은 답변에 결코 만족하지 못한다면, 계속 읽어 주세요.
Rust의 컴파일러가 강제하는 정확성은 일부 프로젝트에서 많은 시간을 아껴 줄 수 있지만, 분열된 생태계는 다른 프로젝트에서 많은 시간을 잃게 할 수 있으며, 그 가장 큰 단점은 Rust를 선택한 것을 후회하게 만들 것입니다.
Rust는 10년 연속 Stack Overflow에서 가장 원하고 / 존경하는 언어이지만, 가장 많이 사용되는 프로그래밍 언어 순위에서는 14위입니다.
사람들이 원하는 것과 실제 세계에서 하는 일 사이에는 분명한 불일치가 있습니다. 때때로 Rust는 _메타버스_와 같다고 느낍니다. 많은 사람이 이야기하지만, 그 안에서 하루를 보내는 사람은 많지 않습니다.
Rust 코드를 감사할 때 제가 가장 먼저 하는 일은 실행기를 차단하는 동기 함수를 찾는 것입니다. 이는 흔히 디버깅하기 어려운 성능 불일치나 잠재적인 서비스 거부(DoS) 공격으로 이어집니다. 수천 줄이 넘는 코드의 프로젝트 중 이벤트 루프를 차단하는 사례가 적어도 하나는 없었던 프로젝트는 기억나지 않습니다.
또한 async는 Rust의 가장 (악명 높은) 기능인 소유권을 이해하고 설계하는 일을 더 어렵게 만듭니다. 제네릭, 수명, 비동기가 공존하는 방식 때문에 요구 사항 변경으로 기존 소유권 가정이 더 이상 유효하지 않아, 지나치게 많은 코드 줄을 바꾸는 일도 드물지 않습니다.
하지만 제 경험상 async의 가장 큰 단점은 생태계의 분열입니다. 이제 동기 함수와 라이브러리, async 함수와 라이브러리가 있으며, 서로 호환되지 않는 여러 런타임 때문에 I/O용 전용 라이브러리가 필요합니다(sans-IO 패턴을 사용하지 않는 한). Python에 관심이 많은 친구와 이야기했을 때, 그들도 정확히 같은 문제를 겪고 있으며 async 코드가 동기 코드를 호출할 수 있도록 래퍼를 작성하는 잡일이 많이 생긴다고 했습니다.
2020년 1월부터 2026년 5월까지 Rust는 54번의 릴리스를 내놓았고, 이는 7,500줄의 변경 로그에 해당합니다. 초보자에게 더 큰 혼란을 주는 Rust “에디션”은 아직 언급하지도 않았습니다.
그러니 사용자 문제를 해결하는 것만으로도 일이 충분하지 않다고 생각한다면, 이제 6주마다 도구 체인, Dockerfile, 의존성 등을 업데이트해야 합니다. 프로그래밍 언어는 제품이 아니라 플랫폼입니다. 개발자의 시간 대부분이 도구와 싸우는 데 쓰이지 않도록, 안정적이고 천천히 변화해야 합니다.
기능은 시간이 갈수록 누적되며 관리할 수 없는 복잡성으로 이어집니다.

너무 빠르게 변화하는 언어는 생태계에 많은 변동을 가져옵니다. 일부 개발자는 자신의 라이브러리에 _이달의 새 기능_을 서둘러 넣고 싶어 하며, 이는 실제로 전달되는 가치가 거의 없는 잡일로 이어집니다.
전문적인 세계™에서는 프로젝트가 3년 이상 손대지 않은 채 방치되었다가 갑자기 업데이트가 필요해지는 일이 드물지 않습니다. 이제 54개 버전이나 뒤처진 서비스의 의존성을 업데이트하는 임무를 맡았다고 상상해 보세요.
같은 기간에 Go는 12번, Node.js는 12번(그중 LTS는 6번), Python은 5번 릴리스되었습니다.
Rust는 고급 이론으로 뒷받침되는 강력한 언어에 모든 것을 걸고 있습니다. 그러나 개발자에게는 기업의 문제에 대한 해결책을 만들기 위해 언어 이상의 것이 필요하다는 점을 잊었습니다. 매번 바퀴를 다시 발명하지 않도록 많은 시간을 아껴 주는 강력한 라이브러리 생태계도 필요합니다.
불행히도 Rust의 라이브러리 생태계는 미성숙한 정도가 아니라 그보다 나쁩니다. hyper, regex, tokio처럼 다른 어떤 생태계에서도 비교할 수 없을 만큼 높은 품질의 라이브러리도 있습니다. 하지만 이 라이브러리들은 “공식”이 아니기 때문에(Rust 프로젝트 / Rust의 확장 표준 라이브러리의 일부가 아니기 때문에), 날짜·시간 및 암호화 라이브러리처럼 모두에게 필요한 라이브러리는 끊임없이 변동합니다. 시간이 갈수록 매달 새 라이브러리가 등장하고 다른 라이브러리가 그만큼 자주 버려지면서 생태계가 더 분열되는 듯하기에, 더 나쁘다고 말하는 것입니다.
예를 들어 제가 작업 중인 작은 프로젝트의 의존성을 방금 살펴보았는데, 서로 다른 암호화 라이브러리가 5개 이상(!) 있습니다. ring의 서로 다른 버전 2개, aws-lc-rs, boring, 그리고 RustCrypto의 다양한 라이브러리입니다. 다양한 의존성이 암호화 기본 요소로 각각 다른 것을 선택했기 때문입니다. 이는 터무니없습니다. 우선 공급망 공격의 진입점을 많이 만들며, 우리가 이 모두를 감사할 방법도 없고, FIPS 검증 모드를 제공하는 것은 aws-lc-rs와 boring뿐이기 때문입니다.
Go에서는 표준 라이브러리에 필요한 모든 암호화 기본 요소가 들어 있으며, 모두 전문가가 작성하고 감사했습니다. 이것이 하나의 생태계를 향해 노력을 축적하는 힘입니다.
Rust의 악명 높은 가파른 학습 곡선은 아예 언급하지도 않았습니다. Rust 프로젝트를 방치되어 망가지지 않게 하려면 투입해야 할 노력에 비하면 이것은 아무것도 아닙니다.
요약: C / C++를 대체하는 용도입니다.
모든 조직이 크로스 플랫폼 애플리케이션을 구축해야 하는 것은 아니지만, 요즘 Rust의 가장 빠르게 성장하고 가장 성공적인 활용 사례는 모바일 플랫폼, 컴퓨터, WebAssembly를 통한 웹, 심지어 서버에서도 사용할 수 있는 공통 코어 또는 공유 라이브러리를 만드는 일일 수 있습니다.
Rust는 메모리 안전성과 패키지 관리자를 제공하면서 이 모든 플랫폼을 대상으로 할 수 있는 유일한 프로그래밍 언어입니다.

크로스 플랫폼 앱 구축은 어쨌든 매우 어렵고 비용이 많이 듭니다. 그러므로 Rust는 이를 더 어렵게 만들지 않고, 더 쉽고 저렴하게 만듭니다.
자세한 내용, 아키텍처 분석 및 코드 예시는 크로스 플랫폼 Rust: WhatsApp, Signal 등이 수십억 기기에 Rust를 제공하는 방식 분석 및 사례 연구: Proton이 수백만 명을 위한 안전한 크로스 플랫폼 애플리케이션을 구축하는 데 Rust를 사용하는 방법을 참조하세요.
매우 낮은 리소스 소비 덕분에 Rust는 시스템 데몬과 백그라운드에서 실행되며 운영 체제와 연동해야 하는 기타 프로그램에 완벽하게 맞습니다.
Go도 바짝 뒤따르지만 심각한 바이너리 비대화 문제를 겪습니다.
Firecracker 심층 분석: Rust와 microVM이 클라우드 인프라를 혁신하는 방식 및 공격 보안을 위해 Rust를 사용하는 이유를 참조하세요.
흔히 하는 말처럼 IoT(Internet of Things, 연결된 기기)의 S는 Security를 뜻합니다.
임베디드 개발은 늘 열악한 개발 관행과 도구 모음, 실시간 OS로 인한 복잡성, 심각하게 오래된 의존성, 그리고 너무 많은 취약점에 시달려 왔습니다.
그래서 임베디드 세계가 Rust로 전환하고 있습니다.
칩 제조업체가 프로덕션 준비가 된 Rust HAL(Hardware Abstraction Layer)과 SDK를 항상 제공하는 것은 아니므로 전환은 아직 다소 느립니다. 그러나 점점 더 많은 업체가 이를 제공하고 있으며, 투자에 대한 막대한 수익을 보고 있습니다.
요즘 Rust와 함께 사용할 주요 마이크로컨트롤러는 RISC-V 기반 ESP32-C3 / ESP32-C6 / ESP32-C5 시리즈일 것입니다. Espressif가 제공하는 훌륭한 HAL과 커뮤니티가 구축한 건강한 패키지 생태계를 모두 갖추고 있습니다.
ESP32-C6에서 Rust를 컴파일하고 실행하는 데는 문자 그대로 두 명령만 필요합니다:
$ rustup target add riscv32imac-unknown-none-elf
$ cargo run
nRF5xxx, RP2040 및 RP2350, STM32 마이크로컨트롤러에도 상당히 성숙한 HAL과 SDK가 있습니다.
임베디드 Rust를 시작하려면 Rust를 이용한 임베디드 개발 입문: 생태계 개요 및 Rust와 ESP32-C6 마이크로컨트롤러로 펜테스트 기기 만들기를 참조하세요.
데이터베이스에는 성능, 네트워킹, 고수준 추상화가 필요하므로 Rust가 완벽하게 맞습니다. 이 주제에 대해 더 알아보려면 모든 데이터베이스는 결국 Rust로 (재)작성될 것이다를 참조하세요.
마지막으로 AWS나 Cloudflare이거나, 서버의 메모리 한 바이트와 CPU 시간 1마이크로초까지 쥐어짜야 할 만큼 매초 엄청나게 많은 트랜잭션을 처리하는 차세대 데이터베이스를 만들고 있다면, Rust는 필요한 모든 제어 기능을 제공하면서도 고수준 추상화를 허용하므로 잘 맞습니다.
생태계는 Go보다 속도를 늦출 것이지만, Rust의 정확성과 성능을 보장하는 타입 시스템이 규모가 커지면 이를 보완할 것입니다.
비용 없는 추상화 외에도 Rust는 메모리 할당자 변경처럼 프로그램을 특정 작업 부하에 맞게 조정하는 데 필요한 모든 조절 장치를 제공합니다. jemalloc으로 Rust의 메모리 단편화 방지하기 및 Cloudflare가 초당 5천만 건 이상의 요청에서 수백만 웹사이트를 제공하고 (망가뜨리는) 데 Rust를 사용하는 방법을 참조하세요.
인간 또는 AI 에이전트로 이루어진 팀이 이미 Rust에 대한 폭넓은 경험이 있고 그 단점을 헤쳐 나가는 방법을 안다면, Rust는 거의 모든 프로젝트에 잘 맞을 수 있으며 고급 컴파일러와 타입 시스템 덕분에 많은 시간, 노력 및 $$를 아껴 줄 가능성이 큽니다. Axum, SQLx, PostgreSQL을 사용해 Rust에서 중간 규모 웹 서비스 아키텍처 설계 및 구축하기를 참조하세요.
“안다” 대신 “좋아한다”라고 말한 이유는 Rust 코드베이스를 유지보수하는 데는 백엔드 서비스의 황금 표준인 Go와 비교해 필연적으로 더 많은 리소스가 들기 때문입니다. 따라서 의존성과 즉각적으로 사업 가치를 제공하지 않는 기타 작업을 관리하는 데 어느 정도 열정이 필요하며, 그것은 전혀 괜찮습니다.
이제 너무 늦기 전에 Rust를 배우고 현대 소프트웨어 개발 열차에 합류하려면 어떻게 해야 할지, 그리고 누군가가 꿈의 직업을 가져가기 전에 무엇을 해야 할지 궁금할 수 있습니다. 좋은 소식이 있습니다!
SIMD 프로그래밍을 배우고 싶다면 순수 Rust로 하는 SIMD 프로그래밍을 살펴보세요.
Rust 백엔드 개발을 배우고 싶다면 제 글 Axum, SQLx, PostgreSQL을 사용해 Rust에서 중간 규모 웹 서비스 아키텍처 설계 및 구축하기를 살펴보세요.
응용 암호학을 배우고 싶다면 암호학적 올바른 해답: 양자 이후 및 Rust 판부터 시작하세요.
마지막으로 제 책 Black hat Rust에서는 Rust가 무엇인지(제네릭, 트레이트, 이터레이터 등이 무엇인지)뿐 아니라 Rust를 _어떻게 하는지_도 배울 수 있습니다. 즉, Rust 프로젝트를 어떻게 설계하는지, Rust에서 어떤 패턴을 사용해야 하고 어떤 패턴을 피해야 하는지를 다룹니다. Black hat Rust에서는 이론에서 실습으로 나아가 웹 서버, 종단 간 암호화된 원격 접근 도구(RAT) 구축, 어셈블리 대신 #![no_std]를 사용한 Rust 셸코드 제작 등 다양한 응용 프로젝트를 직접 만들며 배웁니다. 이 밖에도 며칠 또는 몇 주 동안 읽고 코딩하는 것만으로 프로덕션 수준의 Rust 실력을 갖게 해 줄 실습 프로젝트가 많이 있습니다.
이 블로그의 Rust 태그 아래에서도 어려운 방식으로 얻은 많은 교훈을 찾을 수 있습니다.
즐겁게 읽으시길 바랍니다 :)