Split View: Rust 2025: 45.5% 조직 채택, TIOBE 13위, Linux 커널 진입 — 당신의 팀도 Rust를 배워야 하는가?
Rust 2025: 45.5% 조직 채택, TIOBE 13위, Linux 커널 진입 — 당신의 팀도 Rust를 배워야 하는가?
- 1. Rust 2025: 숫자로 보는 현재 위치
- 2. Rust가 쓰이는 곳: 실전 사용처 완전 정리
- 3. 왜 Rust인가: Go, C++, Java와 비교
- 4. Rust 학습 로드맵: 솔직한 가이드
- 5. Rust의 도전과 41.6%의 우려
- 6. Go에서 Rust로, C++에서 Rust로: 마이그레이션 전략
- 7. 2025 Rust 생태계 하이라이트
- 실전 퀴즈
- 참고 자료
1. Rust 2025: 숫자로 보는 현재 위치
2025년은 Rust에게 역사적인 해였습니다. 단순한 "관심받는 신생 언어"에서 "기업 핵심 인프라 언어"로의 전환이 숫자로 확인됐기 때문입니다.
핵심 지표 요약
조직 채택률: 45.5% (+17.6% YoY)
메인 언어 사용: 38.2%
상업적 사용: 68.75% (2021년 대비 성장)
TIOBE 순위: 13위 (역대 최고)
Stack Overflow: 9년 연속 "가장 사랑하는 언어"
crates.io 패키지: 150,000+ (2024년 말 기준)
조직 채택률의 의미
45.5%라는 숫자가 왜 중요한가요? 2023년에 27.9%였던 수치가 불과 2년 만에 17.6%p 상승했습니다. 이는 단순한 개인 프로젝트 수준이 아닌, 기업 의사결정자들이 프로덕션 환경에 Rust를 도입하기 시작했다는 증거입니다.
연도별 조직 채택률 변화:
2020: ~15%
2021: ~20%
2022: ~25%
2023: 27.9%
2024: 34.8%
2025: 45.5%
상업적 사용의 폭발적 성장
2021년에 Rust를 "회사 업무의 대부분"에 사용하는 비율은 불과 약 8%였습니다. 2025년에는 이 수치가 13.5%에 도달하며 68.75%라는 놀라운 성장률을 기록했습니다. 특히 주목할 점은 "Rust를 업무에 전혀 사용하지 않는다"고 답한 비율이 급격히 줄었다는 것입니다.
TIOBE 13위의 상징성
TIOBE 인덱스에서 Rust가 13위에 오른 것은 단순 순위 이상의 의미가 있습니다. C, C++, Java, Python, JavaScript 같은 레거시 강자들 틈에서 비교적 신생 시스템 프로그래밍 언어가 이 위치에 도달한 것은 이례적입니다. 2020년에는 30위권 밖이었습니다.
Stack Overflow 9년 연속 1위
Stack Overflow 개발자 설문조사에서 Rust는 2016년부터 2024년까지 9년 연속으로 "가장 사랑하는 언어(Most Admired Language)"에 선정됐습니다. 2024년 조사에서는 개발자의 약 83%가 Rust를 계속 사용하고 싶다고 답했습니다. 이는 사용 경험이 있는 개발자들의 만족도가 압도적으로 높다는 것을 의미합니다.
2. Rust가 쓰이는 곳: 실전 사용처 완전 정리
"Rust를 누가 쓰나요?"라는 질문에 대한 답은 이제 명확합니다. 세계 최대 기업들이 핵심 인프라에 Rust를 적극 도입하고 있습니다.
Linux 커널 (Rust for Linux)
2022년 Linux 6.1에서 Rust가 공식 지원 언어로 추가된 이후, Rust for Linux 프로젝트는 꾸준히 확장되고 있습니다.
// 기존 Linux 커널 드라이버 (C 언어)
// NULL 포인터, 버퍼 오버플로우 등 메모리 버그 위험
static int my_driver_probe(struct platform_device *pdev) {
struct my_data *data;
data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
if (!data)
return -ENOMEM;
// ... 수동 메모리 관리
}
// Rust로 작성한 커널 드라이버
// 컴파일 타임에 메모리 안전성 보장
use kernel::prelude::*;
module! {
type: MyDriver,
name: "my_driver",
license: "GPL",
}
struct MyDriver {
// 소유권 시스템이 메모리 안전성 보장
}
impl kernel::Module for MyDriver {
fn init(_module: &'static ThisModule) -> Result<Self> {
pr_info!("Rust driver loaded\n");
Ok(MyDriver {})
}
}
핵심 포인트: Linux 커널에서 발견되는 보안 취약점의 약 70%가 메모리 안전성 문제입니다. Rust는 이 문제를 근본적으로 해결합니다.
Android
Google은 Android에서 Rust를 적극 도입하고 있습니다.
- Bluetooth 스택: Android 13부터 Gabeldorsche Bluetooth 스택을 Rust로 재작성
- WiFi 스택: 핵심 네트워킹 컴포넌트에 Rust 도입
- Keystore2: Android의 키 관리 시스템을 Rust로 재구현
- UWB(Ultra-Wideband): 근거리 통신 스택
Google의 보고에 따르면, Android에서 새로운 코드에 Rust를 도입한 후 메모리 안전성 취약점이 눈에 띄게 감소했습니다.
AWS (Amazon Web Services)
AWS는 Rust의 가장 적극적인 기업 후원자 중 하나입니다.
Firecracker: 서버리스 워크로드용 마이크로 VM (Lambda, Fargate 기반)
Bottlerocket: 컨테이너 전용 Linux 기반 OS
S2N-TLS: TLS 프로토콜 구현체
Mountpoint: S3용 파일 시스템 클라이언트
Cedar: 인증/인가 정책 언어 및 엔진
Firecracker는 특히 주목할 만합니다. AWS Lambda와 Fargate를 구동하는 핵심 기술로, 마이크로초 단위의 부팅 시간과 최소한의 메모리 오버헤드를 제공합니다.
Cloudflare
Cloudflare는 인터넷 트래픽의 상당 부분을 처리하는 인프라를 Rust로 구축하고 있습니다.
- Pingora: Nginx를 대체하는 HTTP 프록시 프레임워크. 하루에 수조 건의 요청 처리
- 엣지 컴퓨팅: Workers 런타임의 핵심 컴포넌트
- DNS 인프라: 고성능 DNS 처리
Pingora는 2024년에 오픈소스로 공개됐으며, 기존 C 기반 솔루션 대비 메모리 사용량과 CPU 사용량 모두에서 개선을 보였습니다.
Discord
Discord의 Go에서 Rust로의 마이그레이션 사례는 Rust 커뮤니티에서 가장 많이 인용되는 성공 사례 중 하나입니다.
서비스: Read States (읽음 상태 추적)
문제: Go의 GC(가비지 컬렉터)로 인한 레이턴시 스파이크
결과: Go -> Rust 마이그레이션 후:
- P99 레이턴시 10배 개선
- 메모리 사용량 대폭 감소
- GC 관련 레이턴시 스파이크 완전 해결
Meta (Facebook)
Meta는 Rust를 대규모로 도입한 초기 기업 중 하나입니다.
- Mononoke: Git 호환 소스 컨트롤 서버 (수만 명의 엔지니어가 사용)
- Buck2: 차세대 빌드 시스템 (전체를 Rust로 재작성)
- Sapling: 새로운 소스 컨트롤 클라이언트
- Relay: GraphQL 컴파일러
Microsoft
Microsoft는 Rust를 Windows 커널에 도입하기 시작했습니다.
- Windows 커널: DWriteCore 등 일부 컴포넌트를 Rust로 전환
- Azure: IoT Edge 런타임의 일부
- VS Code: 검색 기능 (ripgrep 기반)
Microsoft의 보안팀은 자사 제품 보안 취약점의 약 70%가 메모리 안전성 문제라고 밝힌 바 있으며, 이것이 Rust 도입의 주요 동기입니다.
Dropbox
Dropbox는 Rust의 초기 도입 기업 중 하나로, 파일 동기화 엔진의 핵심 부분을 Rust로 작성했습니다.
- 동기화 엔진: Magic Pocket 스토리지 인프라
- 크로스 플랫폼: Windows, macOS, Linux에서 동일한 Rust 코드 공유
그 외 주요 기업들
1Password: 비밀번호 관리 핵심 로직
Figma: 멀티플레이어 서버
Vercel: Turbopack (차세대 번들러)
Shopify: YJIT (Ruby JIT 컴파일러, Rust로 작성)
npm: 레지스트리 인프라 일부
3. 왜 Rust인가: Go, C++, Java와 비교
Rust를 선택해야 하는 이유를 이해하려면, 경쟁 언어들과의 비교가 필수입니다.
핵심 비교표
| 기준 | Rust | Go | C++ | Java |
|---|---|---|---|---|
| 메모리 안전성 | 컴파일 타임 보장 | GC 기반 | 수동 관리 | GC 기반 |
| 성능 | C/C++ 급 | 약간 느림 | 최고 수준 | JVM 오버헤드 |
| 동시성 모델 | 컴파일 타임 검증 | goroutine | 수동 관리 | Thread 기반 |
| 학습 곡선 | 가파름 | 완만 | 매우 가파름 | 보통 |
| 빌드 속도 | 느림 | 매우 빠름 | 느림 | 보통 |
| 바이너리 크기 | 작음 | 보통 | 작음 | 큼 (JVM) |
| 에코시스템 성숙도 | 성장 중 | 성숙 | 매우 성숙 | 매우 성숙 |
| 주요 도메인 | 시스템, 인프라 | 클라우드, 마이크로서비스 | 시스템, 게임 | 엔터프라이즈 |
Rust vs Go: 언제 무엇을 선택할까
Go와 Rust는 종종 비교되지만, 실제로는 사용처가 꽤 다릅니다.
Go를 선택해야 하는 경우:
- 빠른 개발 속도가 최우선
- 마이크로서비스 / API 서버
- DevOps 도구 (Kubernetes 생태계)
- 팀 온보딩 속도가 중요
- 프로토타이핑 후 빠른 출시
Rust를 선택해야 하는 경우:
- 극한의 성능이 필요 (P99 레이턴시 중요)
- 메모리 안전성이 보안에 직결
- 시스템 프로그래밍 (커널, 드라이버)
- GC 없는 예측 가능한 성능
- 임베디드 / 리소스 제한 환경
Rust vs C++: 후계자인가, 경쟁자인가
// Rust: 컴파일러가 메모리 안전성 보장
fn process_data(data: &[u8]) -> Vec<u8> {
let mut result = Vec::new();
for &byte in data {
if byte > 0 {
result.push(byte * 2);
}
}
result
// result의 메모리는 스코프를 벗어나면 자동 해제
}
// C++: 개발자가 직접 메모리 관리
std::vector<uint8_t> process_data(const uint8_t* data, size_t len) {
std::vector<uint8_t> result;
for (size_t i = 0; i < len; ++i) {
if (data[i] > 0) {
result.push_back(data[i] * 2);
}
}
return result;
// data가 댕글링 포인터일 가능성? 컴파일러가 검증 안 함
}
C++보다 Rust가 나은 점:
- 컴파일 타임 메모리 안전성
- 데이터 레이스 방지
- 현대적인 패키지 매니저(Cargo)
- 더 나은 에러 메시지
C++가 여전히 강한 영역:
- 기존 코드베이스 규모 (수십 년간 축적)
- 게임 엔진 생태계 (Unreal Engine 등)
- 특정 하드웨어/플랫폼 지원
- 성숙한 라이브러리 생태계
Rust vs Java: 다른 차원의 비교
Java와 Rust는 대상 도메인이 매우 다르지만, 일부 영역에서는 경쟁합니다.
Java의 강점:
- 엔터프라이즈 생태계 (Spring, Jakarta EE)
- 방대한 라이브러리
- JVM 최적화 (HotSpot)
- 풍부한 인력 풀
Rust의 강점 (Java 대비):
- GC 없는 예측 가능한 레이턴시
- 훨씬 작은 바이너리 / 메모리 풋프린트
- 네이티브 컴파일
- 시스템 레벨 접근
4. Rust 학습 로드맵: 솔직한 가이드
Rust 학습은 다른 프로그래밍 언어와 근본적으로 다릅니다. 솔직하게 이야기하면, 처음 2주가 가장 고통스럽습니다.
Week 1-2: 소유권, 빌림, 수명 (가장 어려운 관문)
이 세 개념은 Rust의 핵심이자, 대부분의 개발자가 포기하는 구간입니다.
소유권(Ownership) 기본
fn main() {
let s1 = String::from("hello");
let s2 = s1; // s1의 소유권이 s2로 이동(move)
// println!("{}", s1); // 컴파일 에러! s1은 더 이상 유효하지 않음
println!("{}", s2); // OK
}
핵심 규칙:
- 모든 값에는 정확히 하나의 소유자가 있다
- 소유자가 스코프를 벗어나면 값이 해제된다
- 값을 다른 변수에 할당하면 소유권이 이동한다
빌림(Borrowing)과 참조
fn main() {
let s1 = String::from("hello");
// 불변 빌림: 여러 개 가능
let len = calculate_length(&s1);
println!("'{}' 길이: {}", s1, len); // s1 여전히 사용 가능
// 가변 빌림: 동시에 하나만 가능
let mut s2 = String::from("hello");
change(&mut s2);
println!("{}", s2); // "hello, world"
}
fn calculate_length(s: &String) -> usize {
s.len()
}
fn change(s: &mut String) {
s.push_str(", world");
}
빌림 규칙:
- 불변 참조는 여러 개 동시에 가능
- 가변 참조는 동시에 하나만 가능
- 불변 참조와 가변 참조를 동시에 가질 수 없음
수명(Lifetime) 기초
// 수명 주석이 필요한 경우
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
if x.len() > y.len() {
x
} else {
y
}
}
fn main() {
let string1 = String::from("long string");
let result;
{
let string2 = String::from("xyz");
result = longest(string1.as_str(), string2.as_str());
println!("가장 긴 문자열: {}", result);
}
// 여기서 result를 사용하면 에러 (string2가 이미 해제됨)
}
학습 팁: 수명을 처음부터 완벽히 이해하려 하지 마세요. 컴파일러 에러 메시지를 따라가며 점진적으로 익히는 것이 효과적입니다.
Week 3-4: 구조체, 열거형, 패턴 매칭
// 열거형과 패턴 매칭
enum Shape {
Circle(f64),
Rectangle(f64, f64),
Triangle(f64, f64, f64),
}
fn area(shape: &Shape) -> f64 {
match shape {
Shape::Circle(r) => std::f64::consts::PI * r * r,
Shape::Rectangle(w, h) => w * h,
Shape::Triangle(a, b, c) => {
let s = (a + b + c) / 2.0;
(s * (s - a) * (s - b) * (s - c)).sqrt()
}
}
}
// 에러 처리: Result와 Option
fn divide(a: f64, b: f64) -> Result<f64, String> {
if b == 0.0 {
Err("0으로 나눌 수 없습니다".to_string())
} else {
Ok(a / b)
}
}
fn main() {
match divide(10.0, 3.0) {
Ok(result) => println!("결과: {}", result),
Err(e) => println!("에러: {}", e),
}
// ? 연산자로 간결하게
let result = divide(10.0, 0.0).unwrap_or(0.0);
println!("기본값 사용: {}", result);
}
Month 2: Traits, 제네릭, 클로저, 이터레이터
// Trait 정의와 구현
trait Summarizable {
fn summary(&self) -> String;
// 기본 구현 제공 가능
fn preview(&self) -> String {
format!("{}...", &self.summary()[..20])
}
}
struct Article {
title: String,
content: String,
}
impl Summarizable for Article {
fn summary(&self) -> String {
format!("{}: {}", self.title, &self.content[..50])
}
}
// 제네릭과 Trait 바운드
fn print_summary<T: Summarizable>(item: &T) {
println!("{}", item.summary());
}
// 이터레이터와 클로저
fn process_numbers(numbers: Vec<i32>) -> Vec<i32> {
numbers
.iter()
.filter(|&&n| n > 0)
.map(|&n| n * 2)
.collect()
}
Month 3: 비동기 프로그래밍 (tokio), 웹 프레임워크
// Axum 웹 서버 예제
use axum::{routing::get, Router, Json};
use serde::Serialize;
#[derive(Serialize)]
struct User {
id: u64,
name: String,
}
async fn get_user() -> Json<User> {
Json(User {
id: 1,
name: "Alice".to_string(),
})
}
#[tokio::main]
async fn main() {
let app = Router::new()
.route("/user", get(get_user));
let listener = tokio::net::TcpListener::bind("0.0.0.0:3000")
.await
.unwrap();
axum::serve(listener, app).await.unwrap();
}
# Cargo.toml 의존성
[dependencies]
axum = "0.7"
tokio = { version = "1", features = ["full"] }
serde = { version = "1", features = ["derive"] }
serde_json = "1"
Month 4+: unsafe, FFI, 매크로, 최적화
// unsafe 블록: 필요한 경우에만 사용
unsafe fn dangerous() {
// 원시 포인터 역참조 등
}
// FFI: C 라이브러리 호출
extern "C" {
fn abs(input: i32) -> i32;
}
fn main() {
let result = unsafe { abs(-5) };
println!("절대값: {}", result);
}
// 선언적 매크로
macro_rules! vec_of_strings {
($($x:expr),*) => {
vec![$($x.to_string()),*]
};
}
fn demo() {
let names = vec_of_strings!["Alice", "Bob", "Charlie"];
println!("{:?}", names);
}
추천 학습 자료
무료 자료:
1. The Rust Programming Language (공식 북)
- https://doc.rust-lang.org/book/
- 가장 체계적인 입문서
2. Rustlings (인터랙티브 연습)
- https://github.com/rust-lang/rustlings
- 작은 문제를 풀며 배우기
3. Rust by Example
- https://doc.rust-lang.org/rust-by-example/
- 예제 중심 학습
4. 100 Exercises To Learn Rust
- https://rust-exercises.com/
- 2024년 공개된 무료 코스
5. Comprehensive Rust (Google)
- https://google.github.io/comprehensive-rust/
- Google 내부 교육 자료 공개판
유료/심화 자료:
6. Programming Rust, 2nd Edition (O'Reilly)
7. Rust in Action (Manning)
8. Zero To Production In Rust (웹 백엔드 특화)
현실적인 학습 시간 예상
배경별 예상 학습 기간:
- C/C++ 개발자: 2-3개월 (메모리 모델 이해가 빠름)
- Go 개발자: 3-4개월 (소유권 개념 적응 필요)
- Java/C# 개발자: 4-5개월 (GC 없는 환경 적응)
- Python/JS 개발자: 5-6개월 (시스템 프로그래밍 + 소유권)
- 첫 프로그래밍 언어: 추천하지 않음 (다른 언어 먼저 배우기)
5. Rust의 도전과 41.6%의 우려
Rust가 장점만 있는 것은 아닙니다. 2025년 Rust 설문조사에서 드러난 주요 우려사항을 살펴보겠습니다.
복잡성 증가에 대한 우려 (41.6%)
Rust 사용자의 41.6%가 "언어의 복잡성 증가"를 우려하고 있습니다. Rust는 매 에디션마다 새로운 기능이 추가되며, 이를 모두 따라가기가 점점 어려워지고 있습니다.
주요 우려 사항 (2025년 설문):
1. 복잡성 증가: 41.6%
2. 부족한 산업 채택: 42.1%
3. 학습 곡선: (상위 불만 사항)
4. 컴파일 시간: (지속적 이슈)
5. 불완전한 도구 지원: (IDE, 디버거)
학습 곡선의 현실
솔직하게 말하면, Rust의 학습 곡선은 가파릅니다.
소유권 시스템 (2-4주): 다른 언어에서 전혀 경험하지 못한 개념입니다. "왜 이 코드가 컴파일 안 되지?"라는 좌절을 수없이 경험하게 됩니다.
수명 주석 (수개월): 복잡한 수명 관계를 이해하는 데는 실제 프로젝트 경험이 필요합니다. 이론만으로는 한계가 있습니다.
비동기 프로그래밍: Rust의 async/await는 다른 언어와 다르게 동작합니다. Pin, Future 등의 개념이 추가 학습을 요구합니다.
// Rust의 async가 복잡한 이유를 보여주는 예
// 다른 언어와 달리 async 함수의 반환 타입이 복잡할 수 있음
use std::future::Future;
fn make_request(url: &str) -> impl Future<Output = Result<String, reqwest::Error>> + '_ {
async move {
let response = reqwest::get(url).await?;
response.text().await
}
}
컴파일 시간 문제
대규모 Rust 프로젝트에서 컴파일 시간은 여전히 고통 포인트입니다.
프로젝트 규모별 대략적 컴파일 시간 (clean build):
- 소규모 (1만 줄): 10-30초
- 중규모 (10만 줄): 2-5분
- 대규모 (50만 줄+): 10-30분
개선 방법:
- cargo check 활용 (타입 검사만, 코드 생성 생략)
- sccache로 캐싱
- 워크스페이스 분리
- incremental compilation 활용
- cranelift 백엔드 (디버그 빌드)
에코시스템 성숙도
Rust 생태계는 빠르게 성장하고 있지만, Java나 Python에 비하면 아직 부족한 영역이 있습니다.
성숙한 영역:
- 웹 프레임워크 (Axum, Actix)
- 직렬화 (serde)
- HTTP 클라이언트 (reqwest)
- CLI 도구 (clap)
- 비동기 런타임 (tokio)
성장 중인 영역:
- GUI (iced, egui - 아직 초기)
- ORM (diesel, sea-orm - 발전 중)
- 엔터프라이즈 패턴 (Spring 같은 통합 프레임워크 부재)
- 머신러닝 (burn, candle - 초기 단계)
인력 부족
Rust 개발자를 채용하기는 여전히 어렵습니다. 수요 대비 공급이 부족하며, 이는 채용 시장에서 양날의 검입니다.
Rust 개발자 시장:
- 수요: 급증 (특히 인프라, 보안 분야)
- 공급: 부족 (전체 개발자 중 소수)
- 평균 연봉: 상위권 (US 기준 약 120-180K)
- 시사점: 배우면 경쟁력 높음, 하지만 팀 빌딩이 어려움
6. Go에서 Rust로, C++에서 Rust로: 마이그레이션 전략
전체 시스템을 한 번에 Rust로 재작성하는 것은 거의 항상 잘못된 접근입니다. 성공한 팀들은 점진적 마이그레이션 전략을 사용합니다.
점진적 마이그레이션 원칙
1. FFI 경계에서 시작하기
- 기존 코드와 Rust를 FFI로 연결
- 가장 위험한 부분(메모리 안전성 이슈)부터 Rust로 전환
- 성능이 중요한 핫 경로부터 시작
2. 새 서비스는 Rust로 작성
- 기존 코드는 그대로 유지
- 새로운 마이크로서비스는 Rust로 시작
- 점진적으로 Rust 영역 확대
3. Strangler Fig 패턴
- 기존 시스템을 감싸는 새 Rust 계층 구축
- 트래픽을 점진적으로 새 계층으로 이전
- 구 시스템을 단계적으로 제거
Go에서 Rust로 마이그레이션
Discord의 사례를 기반으로 한 실전 가이드:
언제 마이그레이션할까:
- GC 관련 레이턴시 스파이크가 비즈니스에 영향
- P99 레이턴시 요구사항이 매우 엄격
- 메모리 사용량 최적화가 필수
- 동시성 버그로 인한 장애 반복
마이그레이션 하지 말아야 할 때:
- Go의 성능이 충분한 경우
- 팀에 Rust 경험이 전무한 경우
- 빠른 개발 속도가 최우선인 경우
- CRUD 중심의 비즈니스 로직
// Go에서 Rust로: HTTP 핸들러 비교
// Go 버전 (참고용 의사코드)
// func getUser(w http.ResponseWriter, r *http.Request) {
// id := r.URL.Query().Get("id")
// user, err := db.FindUser(id)
// if err != nil {
// http.Error(w, err.Error(), 500)
// return
// }
// json.NewEncoder(w).Encode(user)
// }
// Rust (Axum) 버전
use axum::{extract::Query, Json};
use serde::Deserialize;
#[derive(Deserialize)]
struct UserQuery {
id: String,
}
async fn get_user(Query(params): Query<UserQuery>) -> Result<Json<User>, AppError> {
let user = db::find_user(¶ms.id).await?;
Ok(Json(user))
}
C++에서 Rust로 마이그레이션
단계별 접근:
1단계: Rust로 새 모듈 작성, C++ FFI로 연결
2단계: 테스트 커버리지 확보 (기존 C++ 코드)
3단계: 가장 위험한 모듈부터 Rust로 포팅
4단계: 통합 테스트로 동작 검증
5단계: 점진적 확대
FFI 도구:
- cxx: C++와 Rust 간 안전한 FFI
- bindgen: C/C++ 헤더에서 Rust 바인딩 자동 생성
- cbindgen: Rust에서 C/C++ 헤더 생성
// cxx를 사용한 C++ 연동 예제
#[cxx::bridge]
mod ffi {
// C++ 측에서 제공하는 함수
unsafe extern "C++" {
include!("legacy/include/processor.h");
fn process_legacy_data(input: &[u8]) -> Vec<u8>;
}
// Rust 측에서 제공하는 함수
extern "Rust" {
fn validate_data(data: &[u8]) -> bool;
}
}
fn validate_data(data: &[u8]) -> bool {
// Rust의 안전한 검증 로직
!data.is_empty() && data.len() < 1_000_000
}
마이그레이션 체크리스트
사전 준비:
[ ] 팀 내 Rust 챔피언 1-2명 확보
[ ] 파일럿 프로젝트로 경험 축적 (2-3개월)
[ ] 현재 시스템의 성능 베이스라인 측정
[ ] 마이그레이션 대상 모듈 우선순위 선정
[ ] CI/CD 파이프라인에 Rust 빌드 추가
실행:
[ ] FFI 인터페이스 설계
[ ] 단위 테스트 작성 (Rust 측)
[ ] 통합 테스트 유지 (기존 테스트 슈트)
[ ] 점진적 트래픽 전환
[ ] 성능 모니터링 및 비교
사후:
[ ] 성능 개선 측정 및 문서화
[ ] 팀 교육 자료 작성
[ ] 다음 마이그레이션 대상 선정
7. 2025 Rust 생태계 하이라이트
2025년 Rust 생태계에서 주목할 프로젝트와 트렌드를 정리합니다.
웹 프레임워크
Axum (tokio 팀 개발):
- tokio 생태계와 완벽한 통합
- Tower 미들웨어 호환
- 타입 안전한 라우팅
- 2024-2025년 가장 빠르게 성장하는 Rust 웹 프레임워크
Actix Web:
- 최고 수준의 벤치마크 성능
- 성숙한 에코시스템
- 엔터프라이즈 사용 사례 다수
Loco.rs:
- Ruby on Rails 스타일의 올인원 프레임워크
- 2024년 등장, 빠르게 성장 중
- 개발 생산성에 초점
게임 및 그래픽
Bevy:
- 데이터 지향 게임 엔진
- ECS(Entity Component System) 아키텍처
- 빠르게 성장하는 커뮤니티
- 아직 1.0 전이지만 주목도 높음
wgpu:
- WebGPU 구현체
- 크로스 플랫폼 GPU 프로그래밍
- Firefox에서 사용
데스크톱 애플리케이션
Tauri:
- Electron 대안
- 웹 기술(HTML/CSS/JS) + Rust 백엔드
- 훨씬 작은 바이너리 크기 (Electron 대비 10-100배)
- 메모리 사용량 대폭 절감
- v2.0 출시로 모바일 지원 추가
Dioxus:
- React 스타일의 Rust UI 프레임워크
- 웹, 데스크톱, 모바일 지원
WebAssembly (WASM)
Rust는 WebAssembly의 최고의 파트너입니다.
// Rust -> WASM 예제 (wasm-bindgen 사용)
use wasm_bindgen::prelude::*;
#[wasm_bindgen]
pub fn fibonacci(n: u32) -> u64 {
match n {
0 => 0,
1 => 1,
_ => {
let mut a: u64 = 0;
let mut b: u64 = 1;
for _ in 2..=n {
let temp = b;
b = a + b;
a = temp;
}
b
}
}
}
// JavaScript에서 호출:
// import { fibonacci } from './pkg/my_wasm';
// console.log(fibonacci(50));
Rust + WASM 사용 사례:
- Figma: 실시간 협업 편집기의 핵심 로직
- Cloudflare Workers: 엣지 컴퓨팅
- 1Password: 브라우저 확장 프로그램
- Amazon Prime Video: 비디오 처리
- AutoCAD: 웹 버전의 렌더링 엔진
AI/ML 생태계
burn:
- PyTorch 스타일의 딥러닝 프레임워크
- 다양한 백엔드 지원 (GPU, CPU, WASM)
- 순수 Rust 구현
candle (Hugging Face):
- 경량 ML 추론 프레임워크
- LLM 추론에 특화
- Python 의존성 없이 ML 모델 실행
ort:
- ONNX Runtime의 Rust 바인딩
- 학습된 모델의 프로덕션 배포에 적합
- 다양한 하드웨어 가속 지원
linfa:
- scikit-learn 스타일의 전통 ML 라이브러리
- 클러스터링, 분류, 회귀 등
CLI 도구 생태계
Rust로 작성된 CLI 도구들이 기존 Unix 도구를 대체하고 있습니다.
기존 도구 -> Rust 대체:
grep -> ripgrep (rg)
find -> fd
cat -> bat
ls -> exa/eza
du -> dust
top -> bottom (btm)
sed -> sd
curl -> xh
diff -> delta
CLI 라이브러리:
- clap: 명령줄 인자 파싱 (사실상 표준)
- ratatui: TUI(터미널 UI) 프레임워크
- indicatif: 프로그레스 바
- dialoguer: 대화형 프롬프트
Embedded / IoT
embassy:
- 비동기 임베디드 프레임워크
- no_std 환경에서 async/await 지원
- STM32, nRF, RP2040 등 다양한 MCU 지원
esp-rs:
- ESP32 계열 MCU용 Rust 지원
- WiFi, Bluetooth 포함
probe-rs:
- 디버깅/플래싱 도구
- ARM, RISC-V 지원
실전 퀴즈
배운 내용을 점검해 봅시다.
Q1. Rust의 소유권 규칙에서, 하나의 값에 동시에 존재할 수 있는 소유자는 최대 몇 명인가요?
정답: 1명
Rust의 소유권 시스템에서 모든 값은 정확히 하나의 소유자만 가질 수 있습니다. 값을 다른 변수에 할당하면 소유권이 이동(move)합니다. 이 규칙이 GC 없이 메모리를 안전하게 관리하는 핵심 메커니즘입니다.
Q2. Discord가 Go에서 Rust로 마이그레이션한 주된 이유는 무엇인가요?
정답: GC(가비지 컬렉터)로 인한 레이턴시 스파이크
Discord의 Read States 서비스에서 Go의 GC가 주기적으로 레이턴시 스파이크를 일으켰습니다. Rust로 마이그레이션한 후 P99 레이턴시가 10배 개선되었고, GC 관련 스파이크가 완전히 사라졌습니다.
Q3. 다음 Rust 코드에서 컴파일 에러가 발생하는 이유는 무엇인가요?
let mut s = String::from("hello");
let r1 = &s;
let r2 = &mut s;
println!("{} {}", r1, r2);
정답: 불변 참조(r1)와 가변 참조(r2)를 동시에 가질 수 없음
Rust의 빌림 규칙에 의해, 불변 참조가 존재하는 동안 가변 참조를 생성할 수 없습니다. 이 규칙이 데이터 레이스를 컴파일 타임에 방지합니다.
Q4. AWS에서 Lambda와 Fargate를 구동하는 Rust 기반 기술의 이름은?
정답: Firecracker
Firecracker는 AWS가 Rust로 개발한 마이크로 VM 모니터입니다. 마이크로초 단위의 부팅 시간과 최소한의 메모리 오버헤드를 제공하며, AWS Lambda와 Fargate의 기반 기술로 사용됩니다.
Q5. Rust에서 소유권을 이전하지 않고 값을 함수에 전달하는 메커니즘을 무엇이라 하나요?
정답: 빌림(Borrowing)
빌림은 참조(&)를 통해 소유권을 이전하지 않고 값에 접근하는 메커니즘입니다. 불변 빌림(&T)은 여러 개 동시에 가능하고, 가변 빌림(&mut T)은 동시에 하나만 가능합니다.
참고 자료
-
Rust Survey 2024 Results - The Rust Foundation
-
TIOBE Index - TIOBE Software
-
Stack Overflow Developer Survey 2024
-
Rust for Linux Project
-
Memory Safety in Android
-
AWS and Rust
-
Cloudflare Pingora
-
Discord Blog - Why Discord is switching from Go to Rust
-
The Rust Programming Language (공식 북)
-
Rustlings
-
Comprehensive Rust by Google
-
Axum Web Framework
-
Tauri Framework
-
Bevy Game Engine
-
burn - Deep Learning Framework
-
candle - Hugging Face ML Framework
-
crates.io - Rust Package Registry
-
Are We Web Yet?
-
Rust Edition Guide
Rust in 2025: 45.5% Adoption, TIOBE #13, Linux Kernel — Should Your Team Learn Rust?
- 1. Rust in 2025: The Numbers Tell the Story
- 2. Where Rust Is Used: A Complete Guide to Real-World Applications
- 3. Why Rust: Comparing Go, C++, and Java
- 4. Rust Learning Roadmap: An Honest Guide
- Week 1-2: Ownership, Borrowing, Lifetimes (The Hardest Gate)
- Week 3-4: Structs, Enums, Pattern Matching
- Month 2: Traits, Generics, Closures, Iterators
- Month 3: Async Programming (tokio), Web Frameworks
- Month 4+: unsafe, FFI, Macros, Optimization
- Recommended Learning Resources
- Realistic Learning Time Estimates
- 5. Rust's Challenges and the 41.6% Concern
- 6. Migrating from Go to Rust, C++ to Rust: Strategy Guide
- 7. 2025 Rust Ecosystem Highlights
- Practice Quiz
- References
1. Rust in 2025: The Numbers Tell the Story
2025 was a historic year for Rust. The transition from "interesting newcomer" to "enterprise-critical infrastructure language" was confirmed by the numbers.
Key Metrics Summary
Organizational Adoption: 45.5% (+17.6% YoY)
Primary Language Use: 38.2%
Commercial Use: 68.75% growth (vs. 2021)
TIOBE Ranking: #13 (all-time high)
Stack Overflow: 9 consecutive years "Most Admired Language"
crates.io Packages: 150,000+ (as of late 2024)
What 45.5% Organizational Adoption Means
Why does 45.5% matter? In 2023, this figure was 27.9%. A 17.6 percentage point increase in just two years signals that enterprise decision-makers are actively deploying Rust in production environments, not just experimenting with personal projects.
Year-over-Year Organizational Adoption:
2020: ~15%
2021: ~20%
2022: ~25%
2023: 27.9%
2024: 34.8%
2025: 45.5%
Explosive Growth in Commercial Use
In 2021, the percentage of respondents using Rust for "most of their work" was approximately 8%. By 2025, this figure reached 13.5%, recording a remarkable 68.75% growth rate. Notably, the percentage answering "I don't use Rust at work at all" has dropped dramatically.
The Significance of TIOBE #13
Rust reaching #13 on the TIOBE Index carries meaning beyond the raw ranking. For a relatively young systems programming language to achieve this position among legacy powerhouses like C, C++, Java, Python, and JavaScript is exceptional. In 2020, Rust was outside the top 30.
9 Consecutive Years at Stack Overflow
Rust has been selected as the "Most Admired Language" in the Stack Overflow Developer Survey for nine consecutive years from 2016 to 2024. In the 2024 survey, approximately 83% of developers who used Rust expressed desire to continue using it. This indicates overwhelmingly high satisfaction among experienced Rust developers.
2. Where Rust Is Used: A Complete Guide to Real-World Applications
The answer to "Who uses Rust?" is now crystal clear. The world's largest companies are actively adopting Rust for critical infrastructure.
Linux Kernel (Rust for Linux)
Since Rust was officially added as a supported language in Linux 6.1 in 2022, the Rust for Linux project has been steadily expanding.
// Traditional Linux kernel driver (C language)
// Risk of NULL pointer, buffer overflow and other memory bugs
static int my_driver_probe(struct platform_device *pdev) {
struct my_data *data;
data = devm_kzalloc(&pdev->dev, sizeof(*data), GFP_KERNEL);
if (!data)
return -ENOMEM;
// ... manual memory management
}
// Kernel driver written in Rust
// Memory safety guaranteed at compile time
use kernel::prelude::*;
module! {
type: MyDriver,
name: "my_driver",
license: "GPL",
}
struct MyDriver {
// Ownership system ensures memory safety
}
impl kernel::Module for MyDriver {
fn init(_module: &'static ThisModule) -> Result<Self> {
pr_info!("Rust driver loaded\n");
Ok(MyDriver {})
}
}
Key Point: Approximately 70% of security vulnerabilities found in the Linux kernel are memory safety issues. Rust fundamentally solves this problem.
Android
Google is actively adopting Rust in Android.
- Bluetooth Stack: Rewriting the Gabeldorsche Bluetooth stack in Rust since Android 13
- WiFi Stack: Introducing Rust to core networking components
- Keystore2: Reimplementing Android's key management system in Rust
- UWB (Ultra-Wideband): Near-field communication stack
According to Google's reports, memory safety vulnerabilities noticeably decreased after introducing Rust for new code in Android.
AWS (Amazon Web Services)
AWS is one of the most active corporate sponsors of Rust.
Firecracker: Micro VM for serverless workloads (powers Lambda, Fargate)
Bottlerocket: Container-focused Linux-based OS
S2N-TLS: TLS protocol implementation
Mountpoint: File system client for S3
Cedar: Authorization policy language and engine
Firecracker is particularly noteworthy. As the core technology powering AWS Lambda and Fargate, it provides microsecond-level boot times with minimal memory overhead.
Cloudflare
Cloudflare is building infrastructure that handles a significant portion of internet traffic in Rust.
- Pingora: HTTP proxy framework replacing Nginx. Handles trillions of requests per day
- Edge Computing: Core components of the Workers runtime
- DNS Infrastructure: High-performance DNS processing
Pingora was open-sourced in 2024 and showed improvements in both memory usage and CPU usage compared to existing C-based solutions.
Discord
Discord's migration from Go to Rust is one of the most frequently cited success stories in the Rust community.
Service: Read States (read status tracking)
Problem: Latency spikes caused by Go's GC (Garbage Collector)
Result: After Go -> Rust migration:
- P99 latency improved by 10x
- Significant reduction in memory usage
- GC-related latency spikes completely eliminated
Meta (Facebook)
Meta is one of the early companies to adopt Rust at scale.
- Mononoke: Git-compatible source control server (used by tens of thousands of engineers)
- Buck2: Next-generation build system (entirely rewritten in Rust)
- Sapling: New source control client
- Relay: GraphQL compiler
Microsoft
Microsoft has begun introducing Rust into the Windows kernel.
- Windows Kernel: Transitioning some components like DWriteCore to Rust
- Azure: Parts of the IoT Edge runtime
- VS Code: Search functionality (based on ripgrep)
Microsoft's security team has revealed that approximately 70% of their product security vulnerabilities are memory safety issues, which is the primary motivation for Rust adoption.
Dropbox
Dropbox was one of the early adopters of Rust, writing core parts of their file sync engine in Rust.
- Sync Engine: Magic Pocket storage infrastructure
- Cross-Platform: Sharing the same Rust code across Windows, macOS, and Linux
Other Major Companies
1Password: Core password management logic
Figma: Multiplayer server
Vercel: Turbopack (next-generation bundler)
Shopify: YJIT (Ruby JIT compiler, written in Rust)
npm: Parts of registry infrastructure
3. Why Rust: Comparing Go, C++, and Java
To understand why you should choose Rust, comparing it with competing languages is essential.
Core Comparison Table
| Criteria | Rust | Go | C++ | Java |
|---|---|---|---|---|
| Memory Safety | Compile-time guarantee | GC-based | Manual management | GC-based |
| Performance | C/C++ level | Slightly slower | Top tier | JVM overhead |
| Concurrency Model | Compile-time verification | goroutines | Manual management | Thread-based |
| Learning Curve | Steep | Gentle | Very steep | Moderate |
| Build Speed | Slow | Very fast | Slow | Moderate |
| Binary Size | Small | Medium | Small | Large (JVM) |
| Ecosystem Maturity | Growing | Mature | Very mature | Very mature |
| Primary Domain | Systems, Infrastructure | Cloud, Microservices | Systems, Games | Enterprise |
Rust vs Go: When to Choose Which
Go and Rust are often compared, but their actual use cases differ considerably.
Choose Go when:
- Rapid development speed is the top priority
- Building microservices / API servers
- DevOps tooling (Kubernetes ecosystem)
- Team onboarding speed matters
- Prototyping with quick releases
Choose Rust when:
- Extreme performance is needed (P99 latency matters)
- Memory safety directly impacts security
- Systems programming (kernel, drivers)
- Predictable performance without GC
- Embedded / resource-constrained environments
Rust vs C++: Successor or Competitor?
// Rust: Compiler guarantees memory safety
fn process_data(data: &[u8]) -> Vec<u8> {
let mut result = Vec::new();
for &byte in data {
if byte > 0 {
result.push(byte * 2);
}
}
result
// Memory for result is automatically freed when going out of scope
}
// C++: Developer manually manages memory
std::vector<uint8_t> process_data(const uint8_t* data, size_t len) {
std::vector<uint8_t> result;
for (size_t i = 0; i < len; ++i) {
if (data[i] > 0) {
result.push_back(data[i] * 2);
}
}
return result;
// Could data be a dangling pointer? Compiler doesn't verify
}
Where Rust wins over C++:
- Compile-time memory safety
- Data race prevention
- Modern package manager (Cargo)
- Better error messages
Where C++ remains strong:
- Existing codebase size (decades of accumulation)
- Game engine ecosystem (Unreal Engine, etc.)
- Specific hardware/platform support
- Mature library ecosystem
Rust vs Java: A Different Dimension
Java and Rust target very different domains, but they compete in some areas.
Java's Strengths:
- Enterprise ecosystem (Spring, Jakarta EE)
- Vast libraries
- JVM optimizations (HotSpot)
- Abundant talent pool
Rust's Advantages (vs Java):
- Predictable latency without GC
- Much smaller binary / memory footprint
- Native compilation
- System-level access
4. Rust Learning Roadmap: An Honest Guide
Learning Rust is fundamentally different from learning other programming languages. Honestly speaking, the first two weeks are the most painful.
Week 1-2: Ownership, Borrowing, Lifetimes (The Hardest Gate)
These three concepts are the core of Rust and the point where most developers give up.
Ownership Basics
fn main() {
let s1 = String::from("hello");
let s2 = s1; // Ownership of s1 moves to s2
// println!("{}", s1); // Compile error! s1 is no longer valid
println!("{}", s2); // OK
}
Core Rules:
- Every value has exactly one owner
- When the owner goes out of scope, the value is freed
- Assigning a value to another variable moves ownership
Borrowing and References
fn main() {
let s1 = String::from("hello");
// Immutable borrow: multiple allowed
let len = calculate_length(&s1);
println!("'{}' length: {}", s1, len); // s1 still usable
// Mutable borrow: only one at a time
let mut s2 = String::from("hello");
change(&mut s2);
println!("{}", s2); // "hello, world"
}
fn calculate_length(s: &String) -> usize {
s.len()
}
fn change(s: &mut String) {
s.push_str(", world");
}
Borrowing Rules:
- Multiple immutable references are allowed simultaneously
- Only one mutable reference at a time
- Cannot have immutable and mutable references simultaneously
Lifetime Basics
// When lifetime annotations are needed
fn longest<'a>(x: &'a str, y: &'a str) -> &'a str {
if x.len() > y.len() {
x
} else {
y
}
}
fn main() {
let string1 = String::from("long string");
let result;
{
let string2 = String::from("xyz");
result = longest(string1.as_str(), string2.as_str());
println!("Longest string: {}", result);
}
// Using result here would cause an error (string2 already freed)
}
Learning Tip: Don't try to perfectly understand lifetimes from the start. Following compiler error messages and learning incrementally is the most effective approach.
Week 3-4: Structs, Enums, Pattern Matching
// Enums and pattern matching
enum Shape {
Circle(f64),
Rectangle(f64, f64),
Triangle(f64, f64, f64),
}
fn area(shape: &Shape) -> f64 {
match shape {
Shape::Circle(r) => std::f64::consts::PI * r * r,
Shape::Rectangle(w, h) => w * h,
Shape::Triangle(a, b, c) => {
let s = (a + b + c) / 2.0;
(s * (s - a) * (s - b) * (s - c)).sqrt()
}
}
}
// Error handling: Result and Option
fn divide(a: f64, b: f64) -> Result<f64, String> {
if b == 0.0 {
Err("Cannot divide by zero".to_string())
} else {
Ok(a / b)
}
}
fn main() {
match divide(10.0, 3.0) {
Ok(result) => println!("Result: {}", result),
Err(e) => println!("Error: {}", e),
}
// Concise with the ? operator
let result = divide(10.0, 0.0).unwrap_or(0.0);
println!("With default: {}", result);
}
Month 2: Traits, Generics, Closures, Iterators
// Trait definition and implementation
trait Summarizable {
fn summary(&self) -> String;
// Default implementation possible
fn preview(&self) -> String {
format!("{}...", &self.summary()[..20])
}
}
struct Article {
title: String,
content: String,
}
impl Summarizable for Article {
fn summary(&self) -> String {
format!("{}: {}", self.title, &self.content[..50])
}
}
// Generics and trait bounds
fn print_summary<T: Summarizable>(item: &T) {
println!("{}", item.summary());
}
// Iterators and closures
fn process_numbers(numbers: Vec<i32>) -> Vec<i32> {
numbers
.iter()
.filter(|&&n| n > 0)
.map(|&n| n * 2)
.collect()
}
Month 3: Async Programming (tokio), Web Frameworks
// Axum web server example
use axum::{routing::get, Router, Json};
use serde::Serialize;
#[derive(Serialize)]
struct User {
id: u64,
name: String,
}
async fn get_user() -> Json<User> {
Json(User {
id: 1,
name: "Alice".to_string(),
})
}
#[tokio::main]
async fn main() {
let app = Router::new()
.route("/user", get(get_user));
let listener = tokio::net::TcpListener::bind("0.0.0.0:3000")
.await
.unwrap();
axum::serve(listener, app).await.unwrap();
}
# Cargo.toml dependencies
[dependencies]
axum = "0.7"
tokio = { version = "1", features = ["full"] }
serde = { version = "1", features = ["derive"] }
serde_json = "1"
Month 4+: unsafe, FFI, Macros, Optimization
// unsafe block: use only when necessary
unsafe fn dangerous() {
// Raw pointer dereferencing, etc.
}
// FFI: Calling C libraries
extern "C" {
fn abs(input: i32) -> i32;
}
fn main() {
let result = unsafe { abs(-5) };
println!("Absolute value: {}", result);
}
// Declarative macros
macro_rules! vec_of_strings {
($($x:expr),*) => {
vec![$($x.to_string()),*]
};
}
fn demo() {
let names = vec_of_strings!["Alice", "Bob", "Charlie"];
println!("{:?}", names);
}
Recommended Learning Resources
Free Resources:
1. The Rust Programming Language (Official Book)
- https://doc.rust-lang.org/book/
- The most systematic introduction
2. Rustlings (Interactive Exercises)
- https://github.com/rust-lang/rustlings
- Learn by solving small problems
3. Rust by Example
- https://doc.rust-lang.org/rust-by-example/
- Example-driven learning
4. 100 Exercises To Learn Rust
- https://rust-exercises.com/
- Free course released in 2024
5. Comprehensive Rust (Google)
- https://google.github.io/comprehensive-rust/
- Google's internal training material, open-sourced
Paid/Advanced Resources:
6. Programming Rust, 2nd Edition (O'Reilly)
7. Rust in Action (Manning)
8. Zero To Production In Rust (web backend focused)
Realistic Learning Time Estimates
Estimated learning period by background:
- C/C++ developer: 2-3 months (quick to grasp memory model)
- Go developer: 3-4 months (needs to adapt to ownership)
- Java/C# developer: 4-5 months (adapting to GC-free environment)
- Python/JS developer: 5-6 months (systems programming + ownership)
- First programming language: Not recommended (learn another first)
5. Rust's Challenges and the 41.6% Concern
Rust is not without its challenges. Let's examine the key concerns revealed in the 2025 Rust survey.
Growing Complexity Concern (41.6%)
41.6% of Rust users are concerned about the "growing complexity of the language." Rust adds new features with every edition, making it increasingly difficult to keep up.
Key Concerns (2025 Survey):
1. Growing complexity: 41.6%
2. Insufficient adoption: 42.1%
3. Learning curve: (top complaint)
4. Compile times: (persistent issue)
5. Incomplete tooling: (IDE, debugger)
The Reality of the Learning Curve
Speaking frankly, Rust's learning curve is steep.
Ownership System (2-4 weeks): A concept you have never encountered in other languages. You will repeatedly experience the frustration of "Why won't this code compile?"
Lifetime Annotations (months): Understanding complex lifetime relationships requires real project experience. Theory alone has its limits.
Async Programming: Rust's async/await works differently from other languages. Concepts like Pin and Future require additional study.
// Showing why Rust's async is complex
// Unlike other languages, async function return types can be complicated
use std::future::Future;
fn make_request(url: &str) -> impl Future<Output = Result<String, reqwest::Error>> + '_ {
async move {
let response = reqwest::get(url).await?;
response.text().await
}
}
Compile Time Issues
Compile times remain a pain point for large Rust projects.
Approximate compile times by project size (clean build):
- Small (10K lines): 10-30 seconds
- Medium (100K lines): 2-5 minutes
- Large (500K+ lines): 10-30 minutes
Mitigation strategies:
- Use cargo check (type checking only, skips code generation)
- Cache with sccache
- Split workspaces
- Leverage incremental compilation
- Use cranelift backend (debug builds)
Ecosystem Maturity
The Rust ecosystem is growing rapidly, but some areas remain underdeveloped compared to Java or Python.
Mature Areas:
- Web frameworks (Axum, Actix)
- Serialization (serde)
- HTTP client (reqwest)
- CLI tools (clap)
- Async runtime (tokio)
Growing Areas:
- GUI (iced, egui - still early)
- ORM (diesel, sea-orm - evolving)
- Enterprise patterns (no unified framework like Spring)
- Machine learning (burn, candle - early stage)
Talent Shortage
Hiring Rust developers remains challenging. Supply lags behind demand, which is a double-edged sword in the job market.
Rust Developer Market:
- Demand: Surging (especially in infrastructure, security)
- Supply: Limited (small fraction of total developers)
- Average Salary: Upper tier (approximately 120-180K USD)
- Implication: Learning it boosts competitiveness, but team building is difficult
6. Migrating from Go to Rust, C++ to Rust: Strategy Guide
Rewriting an entire system in Rust all at once is almost always the wrong approach. Successful teams use incremental migration strategies.
Incremental Migration Principles
1. Start at the FFI Boundary
- Connect existing code with Rust via FFI
- Convert the riskiest parts (memory safety issues) to Rust first
- Start with performance-critical hot paths
2. Write New Services in Rust
- Keep existing code as-is
- Start new microservices in Rust
- Gradually expand the Rust footprint
3. Strangler Fig Pattern
- Build a new Rust layer wrapping the existing system
- Gradually shift traffic to the new layer
- Incrementally retire the old system
Migrating from Go to Rust
A practical guide based on Discord's case:
When to Migrate:
- GC-related latency spikes impact business
- P99 latency requirements are very strict
- Memory usage optimization is essential
- Repeated outages due to concurrency bugs
When NOT to Migrate:
- Go's performance is sufficient
- Team has zero Rust experience
- Rapid development speed is the top priority
- CRUD-centric business logic
// Go to Rust: HTTP Handler Comparison
// Go version (pseudocode for reference)
// func getUser(w http.ResponseWriter, r *http.Request) {
// id := r.URL.Query().Get("id")
// user, err := db.FindUser(id)
// if err != nil {
// http.Error(w, err.Error(), 500)
// return
// }
// json.NewEncoder(w).Encode(user)
// }
// Rust (Axum) version
use axum::{extract::Query, Json};
use serde::Deserialize;
#[derive(Deserialize)]
struct UserQuery {
id: String,
}
async fn get_user(Query(params): Query<UserQuery>) -> Result<Json<User>, AppError> {
let user = db::find_user(¶ms.id).await?;
Ok(Json(user))
}
Migrating from C++ to Rust
Step-by-Step Approach:
Step 1: Write new modules in Rust, connect via C++ FFI
Step 2: Establish test coverage (existing C++ code)
Step 3: Port the riskiest modules to Rust first
Step 4: Verify behavior with integration tests
Step 5: Gradually expand
FFI Tools:
- cxx: Safe FFI between C++ and Rust
- bindgen: Auto-generate Rust bindings from C/C++ headers
- cbindgen: Generate C/C++ headers from Rust
// Example of C++ interop using cxx
#[cxx::bridge]
mod ffi {
// Functions provided by the C++ side
unsafe extern "C++" {
include!("legacy/include/processor.h");
fn process_legacy_data(input: &[u8]) -> Vec<u8>;
}
// Functions provided by the Rust side
extern "Rust" {
fn validate_data(data: &[u8]) -> bool;
}
}
fn validate_data(data: &[u8]) -> bool {
// Safe validation logic in Rust
!data.is_empty() && data.len() < 1_000_000
}
Migration Checklist
Preparation:
[ ] Secure 1-2 Rust champions within the team
[ ] Build experience with a pilot project (2-3 months)
[ ] Measure performance baselines of the current system
[ ] Prioritize modules for migration
[ ] Add Rust build to CI/CD pipeline
Execution:
[ ] Design FFI interfaces
[ ] Write unit tests (Rust side)
[ ] Maintain integration tests (existing test suite)
[ ] Gradually shift traffic
[ ] Monitor and compare performance
Post-Migration:
[ ] Measure and document performance improvements
[ ] Create team training materials
[ ] Select next migration target
7. 2025 Rust Ecosystem Highlights
Here are the notable projects and trends in the 2025 Rust ecosystem.
Web Frameworks
Axum (developed by the tokio team):
- Perfect integration with the tokio ecosystem
- Tower middleware compatibility
- Type-safe routing
- Fastest growing Rust web framework in 2024-2025
Actix Web:
- Top-tier benchmark performance
- Mature ecosystem
- Multiple enterprise use cases
Loco.rs:
- Rails-style all-in-one framework
- Emerged in 2024, growing rapidly
- Focused on developer productivity
Games and Graphics
Bevy:
- Data-oriented game engine
- ECS (Entity Component System) architecture
- Rapidly growing community
- Not yet 1.0 but highly promising
wgpu:
- WebGPU implementation
- Cross-platform GPU programming
- Used in Firefox
Desktop Applications
Tauri:
- Electron alternative
- Web technologies (HTML/CSS/JS) + Rust backend
- Much smaller binary size (10-100x smaller than Electron)
- Significant memory usage reduction
- v2.0 released with mobile support
Dioxus:
- React-style Rust UI framework
- Web, desktop, and mobile support
WebAssembly (WASM)
Rust is the best partner for WebAssembly.
// Rust -> WASM example (using wasm-bindgen)
use wasm_bindgen::prelude::*;
#[wasm_bindgen]
pub fn fibonacci(n: u32) -> u64 {
match n {
0 => 0,
1 => 1,
_ => {
let mut a: u64 = 0;
let mut b: u64 = 1;
for _ in 2..=n {
let temp = b;
b = a + b;
a = temp;
}
b
}
}
}
// Called from JavaScript:
// import { fibonacci } from './pkg/my_wasm';
// console.log(fibonacci(50));
Rust + WASM Use Cases:
- Figma: Core logic of the real-time collaborative editor
- Cloudflare Workers: Edge computing
- 1Password: Browser extension
- Amazon Prime Video: Video processing
- AutoCAD: Rendering engine for the web version
AI/ML Ecosystem
burn:
- PyTorch-style deep learning framework
- Multiple backend support (GPU, CPU, WASM)
- Pure Rust implementation
candle (Hugging Face):
- Lightweight ML inference framework
- Specialized for LLM inference
- Run ML models without Python dependencies
ort:
- Rust bindings for ONNX Runtime
- Suitable for production deployment of trained models
- Various hardware acceleration support
linfa:
- scikit-learn style traditional ML library
- Clustering, classification, regression, etc.
CLI Tool Ecosystem
CLI tools written in Rust are replacing traditional Unix tools.
Legacy Tool -> Rust Replacement:
grep -> ripgrep (rg)
find -> fd
cat -> bat
ls -> exa/eza
du -> dust
top -> bottom (btm)
sed -> sd
curl -> xh
diff -> delta
CLI Libraries:
- clap: Command-line argument parsing (de facto standard)
- ratatui: TUI (Terminal UI) framework
- indicatif: Progress bars
- dialoguer: Interactive prompts
Embedded / IoT
embassy:
- Async embedded framework
- async/await support in no_std environments
- Support for STM32, nRF, RP2040, and various MCUs
esp-rs:
- Rust support for ESP32 family MCUs
- Includes WiFi and Bluetooth
probe-rs:
- Debugging/flashing tool
- ARM and RISC-V support
Practice Quiz
Let's test what you've learned.
Q1. Under Rust's ownership rules, how many owners can simultaneously exist for a single value?
Answer: 1
In Rust's ownership system, every value can have exactly one owner. When you assign a value to another variable, ownership moves. This rule is the core mechanism that manages memory safely without a GC.
Q2. What was the primary reason Discord migrated from Go to Rust?
Answer: Latency spikes caused by the GC (Garbage Collector)
Go's GC was periodically causing latency spikes in Discord's Read States service. After migrating to Rust, P99 latency improved by 10x, and GC-related spikes were completely eliminated.
Q3. Why does the following Rust code produce a compile error?
let mut s = String::from("hello");
let r1 = &s;
let r2 = &mut s;
println!("{} {}", r1, r2);
Answer: Cannot have an immutable reference (r1) and mutable reference (r2) simultaneously
Under Rust's borrowing rules, you cannot create a mutable reference while an immutable reference exists. This rule prevents data races at compile time.
Q4. What is the name of the Rust-based technology that powers AWS Lambda and Fargate?
Answer: Firecracker
Firecracker is a micro VM monitor developed by AWS in Rust. It provides microsecond-level boot times and minimal memory overhead, and serves as the underlying technology for AWS Lambda and Fargate.
Q5. What is the mechanism in Rust for passing values to functions without transferring ownership?
Answer: Borrowing
Borrowing is the mechanism for accessing values through references (&) without transferring ownership. Immutable borrows (&T) allow multiple simultaneous references, while mutable borrows (&mut T) allow only one at a time.
References
-
Rust Survey 2024 Results - The Rust Foundation
-
TIOBE Index - TIOBE Software
-
Stack Overflow Developer Survey 2024
-
Rust for Linux Project
-
Memory Safety in Android
-
AWS and Rust
-
Cloudflare Pingora
-
Discord Blog - Why Discord is switching from Go to Rust
-
The Rust Programming Language (Official Book)
-
Rustlings
-
Comprehensive Rust by Google
-
Axum Web Framework
-
Tauri Framework
-
Bevy Game Engine
-
burn - Deep Learning Framework
-
candle - Hugging Face ML Framework
-
crates.io - Rust Package Registry
-
Are We Web Yet?
-
Rust Edition Guide