Rust工作空间编译时如何将非依赖库输出到指定子目录?
Rust工作空间成员单独指定编译输出目录方案
问题背景
基于Rust 1.72.1开发软件,需在运行时从特定文件夹动态加载库,CI测试阶段遇到编译目录配置难题:希望仅修改lib_a、lib_b的编译输出目录,不改变主程序main_program的target目录,同时避免依赖的master_lib被重复编译。
工作空间初始布局:
workspace_root ├── Cargo.toml ├── lib_a │ ├── Cargo.toml │ └── src │ └── lib.rs ├── lib_b │ ├── Cargo.toml │ └── src │ └── lib.rs ├── main_program │ ├── Cargo.toml │ └── src │ └── main.rs └── master_lib ├── Cargo.toml └── src └── lib.rs
期望编译后生成的目录结构:
target ├── libraries │ ├── lib_a.dll │ └── lib_b.dll └── main_program.exe
此前尝试通过build.rs调用cargo命令单独编译每个库,导致master_lib重复编译产生冗余;考虑过cargo-make插件,但推测会存在同样的重复编译问题。核心疑问:能否为Rust工作空间的每个成员单独指定编译输出文件夹?
可行解决方案
1. 利用Cargo成员独立target-dir配置(推荐)
Cargo支持为单个工作空间成员单独设置target-dir,且能共享依赖编译产物,完全避免重复编译:
- 分别在
lib_a/Cargo.toml和lib_b/Cargo.toml中添加以下配置(保留原有package配置):
[package] target-dir = "../../target/libraries"
- 主程序
main_program/Cargo.toml不修改target-dir,默认使用工作空间根目录的target文件夹。 - 在工作空间根目录执行
cargo build(或cargo build --release),Cargo会自动复用master_lib的编译产物,同时将lib_a、lib_b的输出文件放到target/libraries下,主程序输出到target根目录。
2. 编译后产物移动(备选CI快速适配方案)
如果上述配置不符合需求,可通过编译后脚本移动产物,同样不会重复编译依赖:
- 正常在工作空间根目录执行
cargo build,所有产物默认输出到target/debug(release编译则为target/release)。 - 编写简单脚本(如Bash、PowerShell),将
lib_a.dll、lib_b.dll移动到target/libraries目录,主程序保留在原位置。示例PowerShell脚本:
New-Item -ItemType Directory -Force -Path "./target/libraries" Copy-Item "./target/debug/lib_a.dll" "./target/libraries/" Copy-Item "./target/debug/lib_b.dll" "./target/libraries/"
- 该方案无需修改Cargo配置,适合CI环境快速部署。
注意事项
- 配置
target-dir时,Cargo会自动创建目标目录,无需手动提前创建。 - 若区分debug和release编译,可在库的
Cargo.toml中分别配置不同的target目录,比如:
[package] target-dir = "../../target/libraries/debug" [profile.release] target-dir = "../../target/libraries/release"
这样debug和release产物会分开存放,避免互相覆盖。
内容的提问来源于stack exchange,提问作者LordNocturnus
相关产品推荐
相关产品推荐

