Rust 시작하기: Rust vs. Node.js 앱 프로젝트 비교

넥스트플랫폼 동준상 대표 (naebon@naver.com)

2026.07.05 / 동준상.넥스트플랫폼
(AWS SAA, AWS AIF, GCP GenAI Leader)

Rust Vibe Day 1 프로젝트 실행 결과를 바탕으로, JS/TS와 다른 Rust의 특징을 파일 구조 → Cargo → TOML 순서로 정리했어요.

GitHub | Rust Vibe Coding — Day 1
https://github.com/junsang-dong/nextai-260705-rust-vibe-d1


1. 프로젝트 구조: JS/TS와 무엇이 다른가?

JS/TS (Node.js) 프로젝트

my-app/
├── package.json      ← 프로젝트 메타 + 의존성
├── package-lock.json
├── node_modules/     ← 설치된 패키지 (수천 개 파일)
├── src/
│   └── index.ts
└── tsconfig.json

이번 Rust 프로젝트

nextai-260705-rust-vibe-d1/
├── Cargo.toml          ← workspace 루트 (모노레포 설정)
├── Cargo.lock          ← 의존성 잠금 파일
├── hello-rust/
│   ├── Cargo.toml      ← 각 crate(패키지) 설정
│   └── src/
│       └── main.rs     ← 실행 진입점
├── greeting-app/
├── mini-calculator/
└── rust-profile/

비교표

비교JS/TSRust (이번 프로젝트)
패키지 매니저npm / yarn / pnpmCargo (공식, 유일)
설정 파일package.json (JSON)Cargo.toml (TOML)
진입점index.js, main.ts 등 자유src/main.rsfn main() (관례)
실행node index.js / npm run devcargo run (빌드 + 실행 한 번에)
타입TS는 선택, JS는 런타임컴파일 시점에 타입 검사 (필수)
런타임Node.js / 브라우저 필요네이티브 바이너리로 컴파일 (런타임 불필요)

2. Cargo의 역할

Cargo = Rust의 npm + webpack + jest + 프로젝트 생성기를 합친 공식 도구입니다.

이번 프로젝트에서 Cargo가 하는 일:

명령어JS/TS 대응설명
cargo new hello-rust --binnpm init + 폴더 생성프로젝트 스캐폴딩
cargo buildtsc / webpack build소스 → 기계어 바이너리 컴파일
cargo run -p hello-rustnpm start / node dist/index.js빌드 후 실행
cargo testnpm test / jest테스트 실행
cargo build --workspacemonorepo 전체 빌드workspace 내 4 crate 한꺼번에 빌드

JS/TS와 가장 큰 차이

  • Node.js 없이 실행cargo run 결과는 OS에서 바로 돌아가는 실행 파일입니다.
  • 빌드가 필수 — JS는 .js 파일을 바로 실행하지만, Rust는 .rs → 컴파일 → 바이너리 과정이 있습니다.
  • 도구가 하나 — npm, webpack, babel, jest 등을 따로 쓰지 않고 Cargo 하나로 관리합니다.

target/ 폴더

JS의 node_modules/ + dist/를 합친 느낌입니다. 컴파일 결과물이 들어가며 .gitignore로 Git에서 제외합니다.


3. Cargo.toml 파일의 역할

TOML(Tom’s Obvious Minimal Language)은 사람이 읽기 쉬운 설정 형식입니다. JSON보다 주석(#)을 쓸 수 있고, 중첩이 덜 복잡합니다.

(1) 루트 Cargo.toml — Workspace 설정

[workspace]
members = [
    "hello-rust",
    "greeting-app",
    "mini-calculator",
    "rust-profile",
]
resolver = "2"

JS/TS의 monorepo(pnpm workspace, Lerna, Turborepo)와 같은 개념입니다.

  • 하나의 Git repo 안에 4개의 독립 실행 프로그램(crate)을 묶어 관리
  • 루트에서 cargo build --workspace로 전체 빌드
  • cargo run -p greeting-app처럼 -p로 특정 crate만 실행

(2) 각 crate의 Cargo.toml — 패키지 설정

[package]
name = "hello-rust"
version = "0.1.0"
edition = "2024"

[dependencies]

package.json과 1:1로 대응되는 부분:

Cargo.tomlpackage.json
[package] name"name"
version"version"
[dependencies]"dependencies"
edition = "2024"(없음 — Rust 언어 버전/문법 세대)

edition은 Rust만의 개념입니다. 2015, 2018, 2021, 2024처럼 언어 문법·표준 라이브러리 세대를 지정합니다.

[dependencies]가 비어 있는 이유: Day 1 프로젝트는 표준 라이브러리(std)만 사용합니다. 외부 crate(npm 패키지에 해당)가 없어서 비어 있습니다.

예를 들어 나중에 HTTP 클라이언트를 쓰면:

[dependencies]
reqwest = "0.12"   # npm의 "reqwest": "^0.12"와 비슷

(3) Cargo.lock — 잠금 파일

package-lock.json / pnpm-lock.yaml과 같은 역할입니다. 정확히 같은 버전으로 다시 빌드되게 고정합니다.


4. main.rs — JS/TS 코드와 다른 Rust 특징

진입점: fn main()은 필수

fn main() {
    println!("Hello NextPlatform!");
}
  • JS: index.js 최상단부터 실행
  • Rust: fn main() 이 프로그램 시작점 (C/Java와 유사)

println! — 매크로 (함수가 아님)

!가 붙은 것은 매크로입니다. 컴파일 시점에 코드로 펼쳐집니다.

  • JS: console.log(`Hello ${name}`)
  • Rust: println!("Hello {}!", name){}가 자리 표시자

변수: let + 불변(immutable) 기본

let mut name = String::new();
// ...
let name = name.trim();
RustJS/TS
let x = 1기본 불변 — 재할당 불가
let mut x = 1가변 — 재할당 가능
let name = name.trim()shadowing — 같은 이름으로 새 변수

JS/TS는 기본이 let으로 재할당 가능한데, Rust는 기본이 불변이라는 점이 큰 차이입니다.

타입을 컴파일러가 추론하지만, 명시도 가능

let left: i32 = parts[0]
    .parse()
    .expect("Please enter a valid number on the left");
  • i32: 32비트 정수 (JS의 number와 달리 크기·부호가 고정)
  • .parse(): 문자열 → 숫자 변환 (실패 가능 → Result 타입)
  • .expect(...): 실패 시 panic (Day 1 수준의 단순 처리)

TS도 타입이 있지만 런타임에는 사라집니다. Rust는 컴파일할 때 타입·메모리·소유권을 검사합니다.

use std::io — 모듈 import

use std::io;
  • JS: import { readline } from 'node:readline'
  • Rust: use std::io표준 라이브러리는 별도 설치 없이 내장

5. 빌드 흐름

src/main.rs  ──┐
               ├──▶  cargo build  ──▶  target/debug/hello-rust  ──▶  실행 파일 (바이너리)
Cargo.toml   ──┘
  • JS/TS: 소스 → (번들러) → JS 파일 → Node/브라우저에서 해석 실행
  • Rust: 소스 → Cargo/컴파일러 → 기계어 바이너리 → OS에서 직접 실행

6. Day 1 핵심 요약

개념JS/TSRust (이번 프로젝트)
프로젝트 설정package.jsonCargo.toml
패키지 매니저npmCargo
진입점자유src/main.rsfn main()
실행node / npm runcargo run -p crate이름
의존성 잠금package-lock.jsonCargo.lock
빌드 산출물dist/, node_modules/target/
타입TS: 선택, 런타임 없음컴파일 필수, 런타임 검사
변수기본 가변기본 불변 (let mut로 가변)

7. 워크북 연결 — 코드 분석 키워드

키워드설명
fn함수 정의 (JS의 function)
main프로그램 시작 함수 (필수)
println!출력 매크로 (! = 매크로)
;문(statement) 끝 (Rust는 표현식/문 구분이 엄격)

답글 남기기