</>
Skip to content
Rust lessons (35/43)

Rust — Packages

The hierarchy, top-down

Package  (Cargo.toml at the root)      ← what you ship/build
├── Crate: library (lib.rs)            ← reusable code unit
├── Crate: binary  (main.rs)           ← executable entry
└── Modules inside each crate          ← organization within
  • Crate = smallest compilable unit (a lib or a bin)
  • Package = bundle of one-or-more crates + manifest

cargo new myapp creates a package with ONE binary crate.

Anatomy of a package

myapp/
├── Cargo.toml          ← name, version, dependencies
├── src/
│   ├── main.rs         ← binary crate root
│   └── …modules…
└── tests/              ← integration tests (optional)

Minimal Cargo.toml

[package]
name = "myapp"
version = "0.1.0"
edition = "2021"

[dependencies]

Adding a library crate to the same package

Create src/lib.rs:

// src/lib.rs — the LIBRARY crate root
pub mod math {
    pub fn add(a: i32, b: i32) -> i32 { a + b }
}

Now main.rs can import it as an external-looking crate:

// src/main.rs — the BINARY crate
use myapp::math::add;        // crate name from Cargo.toml!

fn main() {
    println!("{}", add(2, 2));
}

This split is standard practice: logic in lib.rs, thin CLI wrapper in main.rs. It also unlocks unit testing of internals.

Dependencies — pulling from crates.io

[dependencies]
rand = "0.8"
serde = { version = "1.0", features = ["derive"] }
$ cargo build
    Updating crates.io index
     Downloading rand v0.8.5 …

First build downloads + compiles everything into Cargo.lock (exact versions, committed to git for apps). Subsequent builds are instant until deps change.

Useful commands

cargo add rand            # edit Cargo.toml for you
cargo update              # bump deps within semver ranges
cargo tree                # dependency graph
cargo doc --open          # docs for your code AND dependencies

Workspaces (preview)

Multiple related packages under one repo:

# root Cargo.toml
[workspace]
members = ["core", "cli", "server"]

Shared target dir, versioned together — how large Rust projects stay manageable.

Package naming & conventions

  • lowercase with hyphens on crates.io (my-cool-tool)
  • code identifiers stay snake_case regardless
  • binary targets may live in src/bin/*.rs — each file becomes its own executable

Mini Practice

  1. cargo new; add rand; print three random numbers.
  2. Create lib.rs with a pub function; call it from main.
  3. Run cargo tree; count transitive dependencies.
  4. Add serde with derive feature; confirm compile.
  5. Sketch which files you'd create for a CLI + core-library app.

Next: crates →

Related Topics

Frequently Asked Questions about Packages

What is Packages in Rust?

Packages is a fundamental concept in Rust. This lesson explains it step by step with clear examples, making it easy for beginners to understand.

How do I learn Packages?

Start by reading the explanation above, then try the code examples. Practice by modifying the examples and experimenting with different values. Hands-on practice is the best way to learn Packages.

Why is Packages important in Rust?

Packages is essential for Rust development. Understanding this concept will help you write better code and solve real-world problems more effectively.