Rust + Rocket: Full-Stack REST API for Order Management

💡 For engineering managers evaluating whether Rust is ready for production backends — and why companies like Discord, Cloudflare and Amazon are hiring Rust developers.


🎯 Why Discord Replaced Go with Rust (And What It Means for Your API)

Discord replaced their Go backend with Rust and reduced memory usage by 5x while improving performance. Amazon's Lambda engine (Firecracker) and Cloudflare's edge network are built in Rust. The question isn't "Can Rust do web APIs?" — it's "Can you afford NOT to learn it?"

Technical subtitle: Full-stack REST API with Rocket framework, SQLx compile-time validated queries, and Next.js frontend for production-grade order management


📋 Table of Contents

  1. The Backend Language Dilemma
  2. The Project: Northwind Orders Management
  3. Full Stack Architecture
  4. The Hardest Part: Rust's Ownership
  5. Impact: What Rust Brings to Your API
  6. Why This Matters Beyond Your Project
  7. Key Metrics
  8. Continuous Learning
  9. Contribute
  10. Related Articles

� The Backend Language Dilemma: Speed vs Developer Experience

Most developers start with Node.js or Python — languages that prioritize developer speed over runtime performance. But when your API needs to handle:

Use Case Node.js/Python Rust
High-concurrency API GC pauses affect latency Native performance, no GC
Financial transactions Runtime errors in production Compile-time type safety
Blockchain node backend Memory-unsafe, no guarantees Memory-safe, zero-cost abstractions
Cost at scale More servers needed Fewer servers, same output

The short answer from our Northwind project: Rust is completely viable for production APIs, with some learning friction that pays off exponentially.


💡 The Project: Northwind Orders Management

The Northwind dataset is the "Hello World" of relational databases — orders, customers, products, employees. A CRUD API on top of it is the perfect test case for evaluating a web framework.

Why Rocket

Rocket is the most ergonomic Rust web framework to get started with. Its routing system is declarative and integrates well with the Rust toolchain:

#[get("/orders")] async fn get_orders(db: &State<Pool<MySql>>) -> Json<Vec<Order>> { let orders = sqlx::query_as!(Order, "SELECT * FROM orders") .fetch_all(db.inner()) .await .unwrap(); Json(orders) }

Compare this to equivalent Express.js code:

Feature Express.js (Node.js) Rocket (Rust)
Route typing Runtime only Compile-time validated
Database errors Found at runtime Found at compile time
Memory safety Garbage collected Zero-cost, no GC
Concurrency Event loop (single thread) Async + multi-threaded

SQLx: Compile-Time Validated Queries

The killer feature of SQLx is that SQL queries are validated against the actual database schema at compile time. If your query has a syntax error or references a column that doesn't exist, the build fails before you ever reach production.

// This query fails at compile-time if 'order_date' doesn't exist in the table let order = sqlx::query_as!( Order, "SELECT order_id, customer_id, order_date FROM orders WHERE order_id = ?", id ) .fetch_one(&pool) .await?;

This means: Errors that in Node.js would be 3 AM production bugs are caught before the code even compiles in Rust.


🏗️ Full Stack Architecture

Backend (Rust)

Crate Role Why It Matters
rocket 0.5 Async web framework Ergonomic routing, middleware support
sqlx 0.7 ORM with compile-time safe queries SQL errors caught at compile time
serde JSON serialization/deserialization Works with any format (JSON, CBOR)
rust_decimal Monetary values without precision loss Financial-grade accuracy
rocket_cors CORS middleware Cross-origin security made easy

Frontend (Next.js)

Technology Purpose
Next.js 16 + React 19 Server-side rendering, modern React
TypeScript Type-safe frontend
TailwindCSS v4 Utility-first styling
flowchart TD
    subgraph Frontend[&#34;Frontend (Next.js + TypeScript)&#34;]
        UI[React Components]
        API[API Client]
    end
    
    subgraph Backend[&#34;Backend (Rust + Rocket)&#34;]
        Routes[Route Handlers]
        DB[SQLx Queries]
    end
    
    subgraph Database[&#34;Database (MariaDB)&#34;]
        Tables[Northwind Tables]
    end
    
    UI --&gt; API
    API --&gt;|&#34;HTTP/JSON&#34;| Routes
    Routes --&gt; DB
    DB --&gt;|&#34;Compile-time validated&#34;| Tables

🔥 The Hardest Part: Rust's Ownership

The biggest obstacle wasn't Rocket or SQLx, but Rust's own ownership and borrowing system.

For example, passing a database connection between handlers requires understanding Arc<Mutex<T>> properly, or using Rocket's State<T> system which abstracts this away. At first it generates many compiler errors, but those are errors that in other languages are production bugs.

sequenceDiagram
    participant Handler1
    participant State&lt;T&gt;
    participant Handler2
    participant DB
    
    Handler1-&gt;&gt;State&lt;T&gt;: request DB pool
    State&lt;T&gt;--&gt;&gt;Handler1: ✅ Cloneable reference
    Handler2-&gt;&gt;State&lt;T&gt;: request DB pool
    State&lt;T&gt;--&gt;&gt;Handler2: ✅ Cloneable reference
    Handler1-&gt;&gt;DB: query (safe, concurrent)
    Handler2-&gt;&gt;DB: query (safe, concurrent)
    Note over Handler1,Handler2: No data races, guaranteed by compiler

The compiler is your safety net: Every error the compiler catches is a bug that cannot exist in production.


📈 Impact: What Rust Brings to Your API

Metric Node.js/Python Rust + Rocket
Startup Time ~100ms ~10ms
Memory per 1K connections ~50MB ~5MB
API Latency (p99) Variable (GC pauses) Consistent
Production bugs (SQL) Common Impossible (compile-time)
Server cost at scale Higher Lower

📊 Key Metrics

Benchmark Rust + Rocket Node.js/Express Go (Gin)
TechEmpoint Round 21 ~150K req/s ~10K req/s ~130K req/s
Cold Start Time ~10ms ~100ms ~20ms
Memory (1K idle conns) ~5MB ~50MB ~15MB
Build Time 30-120s ~2s 10-30s

Source: TechEmpoint Benchmark Round 21


🤔 Why This Matters Beyond Your Project

Rust isn't just a "faster JavaScript." It represents a paradigm shift in how we think about software reliability:

  1. Compile-time guarantees replace runtime testing — if it compiles, it works
  2. Memory safety without garbage collection — the best of both worlds
  3. Zero-cost abstractions — write high-level code, get low-level performance
  4. Growing ecosystem — from web backends to blockchain to operating systems

For high-performance backends or critical services (including blockchain nodes), the investment in learning Rust is worth it.


✅ Key Takeaways

  1. Rust is production-ready for web APIs — companies like Discord, Cloudflare and Amazon prove it
  2. SQLx prevents entire categories of bugs — compile-time SQL validation is a game-changer
  3. Ownership is hard but worth it — compiler errors prevent production bugs
  4. Native performance matters at scale — lower memory, consistent latency, fewer servers
  5. The learning curve pays off — initial friction becomes long-term reliability

🔗 Explore the Code

Want to see the full implementation? Check out the complete project at github.com/87maxi/rocket:

  • src/main.rs — Rocket application entry point with database setup
  • src/routes/ — All REST API route handlers
  • src/models/ — SQLx models with compile-time validation
  • frontend/ — Next.js + TypeScript frontend

🔗 Continuous Learning


🤝 Contribute

Want to see more Rust backend examples or contribute to this project? Check out the github.com/87maxi/rocket repository and open a Pull Request!


💬

Comments

Powered by Giscus · GitHub Discussions

🦀 Rust & Systems