Rust 系统编程语言完全教程 / 第20章:Cargo 深入
第20章:Cargo 深入
20.1 Features 系统
定义 Features
# Cargo.toml
[features]
default = ["json"] # 默认启用的 features
json = ["dep:serde", "dep:serde_json"]
xml = ["dep:quick-xml"]
full = ["json", "xml", "logging"]
logging = []
[dependencies]
serde = { version = "1.0", features = ["derive"], optional = true }
serde_json = { version = "1.0", optional = true }
quick-xml = { version = "0.31", optional = true }
条件编译
#[cfg(feature = "json")]
pub mod json_support {
pub fn parse(s: &str) -> serde_json::Value {
serde_json::from_str(s).unwrap()
}
}
#[cfg(feature = "xml")]
pub mod xml_support {
pub fn parse(s: &str) -> String {
format!("XML: {}", s)
}
}
pub fn auto_parse(s: &str) -> String {
#[cfg(feature = "json")]
{ return format!("JSON: {:?}", json_support::parse(s)); }
#[cfg(not(feature = "json"))]
{ return format!("原始: {}", s); }
}
使用 Features
# 使用默认 features
cargo build
# 启用特定 features
cargo build --features "json,xml"
# 禁用默认 features
cargo build --no-default-features
# 禁用默认 + 启用特定
cargo build --no-default-features --features "xml"
20.2 依赖管理
版本指定
[dependencies]
# 精确版本
serde = "1.0.200"
# 语义化版本范围
tokio = "1" # ^1.0.0 (>=1.0.0, <2.0.0)
axum = "0.7" # ^0.7.0 (>=0.7.0, <0.8.0)
# 更多版本格式
foo = ">=1.0, <2.0" # 范围
bar = "=1.0.5" # 精确匹配
baz = "~1.2.3" # >=1.2.3, <1.3.0
qux = "*" # 任意版本(不推荐)
# Git 依赖
mylib = { git = "https://github.com/user/mylib.git", branch = "main" }
mylib2 = { git = "https://github.com/user/mylib.git", tag = "v1.0" }
mylib3 = { git = "https://github.com/user/mylib.git", rev = "abc123" }
# 本地路径
utils = { path = "../utils" }
依赖重命名
[dependencies]
# 重命名以避免冲突
my_serde = { package = "serde", version = "1.0" }
平台特定依赖
# 只在特定平台编译
[target.'cfg(windows)'.dependencies]
winapi = "0.3"
[target.'cfg(target_os = "linux")'.dependencies]
nix = "0.29"
[target.'cfg(target_arch = "wasm32")'.dependencies]
wasm-bindgen = "0.2"
查看依赖树
cargo tree
cargo tree -d # 只显示重复的依赖
cargo tree --depth 1 # 限制深度
cargo tree -i serde # 反向查找谁依赖 serde
20.3 Profile 配置
# Cargo.toml
# 开发配置(cargo build)
[profile.dev]
opt-level = 0 # 0-3, s, z
debug = true
debug-assertions = true
overflow-checks = true
lto = false
incremental = true
codegen-units = 256
# 发布配置(cargo build --release)
[profile.release]
opt-level = 3
debug = false
debug-assertions = false
overflow-checks = false
lto = true # 链接时优化
codegen-units = 1 # 更好优化,更慢编译
strip = true # 去除调试信息
panic = "abort" # panic 时直接终止
# 测试配置
[profile.test]
opt-level = 1
# 基准测试配置
[profile.bench]
opt-level = 3
lto = true
优化级别说明
| 级别 | 说明 |
|---|
| 0 | 无优化(默认开发模式) |
| 1 | 基本优化 |
| 2 | 更多优化 |
| 3 | 最高优化(默认发布模式) |
| s | 优化大小 |
| z | 最小大小 |
20.4 构建脚本(build.rs)
基本用法
// build.rs
fn main() {
// 设置环境变量
println!("cargo:rerun-if-changed=build.rs");
println!("cargo:rerun-if-env-changed=MY_VAR");
// 条件编译
if cfg!(target_os = "linux") {
println!("cargo:rustc-cfg=linux");
}
// 链接原生库
// println!("cargo:rustc-link-lib=static=mylib");
// println!("cargo:rustc-link-search=native=/usr/local/lib");
}
使用 cc crate 编译 C 代码
# Cargo.toml
[build-dependencies]
cc = "1.0"
// build.rs
fn main() {
cc::Build::new()
.file("src/helper.c")
.compile("helper");
}
20.5 Cargo 子命令
常用子命令安装
cargo install cargo-watch # 文件变化自动重新编译
cargo install cargo-edit # cargo add/rm/upgrade
cargo install cargo-expand # 展开宏
cargo install cargo-audit # 安全审计
cargo install cargo-outdated # 检查过期依赖
cargo install cargo-deny # 依赖策略检查
cargo install cargo-bloat # 分析二进制大小
cargo install cargo-flamegraph # 性能火焰图
常用子命令
# 文件变化自动编译运行
cargo watch -x run
cargo watch -x test
cargo watch -x 'test -- --show-output'
# 安全审计
cargo audit
# 检查过期依赖
cargo outdated
# 展开宏
cargo expand
# 分析二进制大小
cargo bloat --release
# 性能分析
cargo flamegraph
20.6 发布到 crates.io
准备工作
# Cargo.toml
[package]
name = "my-awesome-crate"
version = "0.1.0"
edition = "2024"
authors = ["Your Name <email@example.com>"]
description = "A short description of what this crate does"
license = "MIT OR Apache-2.0"
repository = "https://github.com/user/my-awesome-crate"
homepage = "https://my-crate.com"
documentation = "https://docs.rs/my-awesome-crate"
readme = "README.md"
keywords = ["tool", "utility"]
categories = ["command-line-utilities"]
rust-version = "1.70"
发布流程
# 1. 登录
cargo login <your-api-token>
# 2. 检查包内容
cargo package --list
# 3. 试运行发布(不实际发布)
cargo publish --dry-run
# 4. 正式发布
cargo publish
# 5. 发布新版本
# 修改 Cargo.toml 中的 version
cargo publish
版本管理
# 使用 cargo-release 自动化
cargo install cargo-release
# 补丁版本 (0.1.0 → 0.1.1)
cargo release patch
# 次版本 (0.1.0 → 0.2.0)
cargo release minor
# 主版本 (0.1.0 → 1.0.0)
cargo release major
20.7 业务场景示例
生产级 Cargo.toml
[package]
name = "my-service"
version = "0.3.1"
edition = "2024"
rust-version = "1.70"
[dependencies]
tokio = { version = "1", features = ["full"] }
axum = "0.7"
serde = { version = "1", features = ["derive"] }
serde_json = "1"
tracing = "0.1"
tracing-subscriber = { version = "0.3", features = ["env-filter"] }
anyhow = "1"
[dev-dependencies]
tokio-test = "0.4"
reqwest = { version = "0.12", features = ["json"] }
[profile.release]
opt-level = 3
lto = true
codegen-units = 1
strip = true
panic = "abort"
[profile.dev]
opt-level = 1
20.8 本章小结
| 要点 | 说明 |
|---|
| Features | 条件编译功能模块 |
| 版本管理 | 语义化版本,^ 为默认前缀 |
| Profile | dev/release/test/bench 配置 |
| build.rs | 构建脚本,编译原生代码 |
| 发布 | cargo publish 发布到 crates.io |
扩展阅读
- Cargo 手册 — 官方文档
- Cargo.toml 参考 — 完整配置参考