当库名称与包名称不同时如何导入 crate 依赖项?
How to import a crate dependency when the library name is different from the package name?
我有一个直接从 GitHub 进口的板条箱,根据 Cargo 的 documentation:
[dependencies]
libfoo = { git = "ssh://git@github.com/me/libfoo", branch = "dev" }
[lib]
path = "src/rust/lib.rs"
name = "myprj"
crate-type = ["cdylib"]
运行 cargo build
在这里工作正常,Cargo 获取 libfoo
并将其构建在 ~/.cargo
目录中。当我尝试在 lib.rs
:
中使用(导入)它时
extern crate libfoo; //also tried foo
货物扼流圈:
error[E0463]: can't find crate for `libfoo`
--> src/rust/lib.rs:1:1
|
1 | extern crate libfoo;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't find crate
有趣的是,当我在 lib.rs
中单击它时,IntelliJ 的 Rust 插件确实找到了箱子——它导航到 ~/.cargo
中下载的源...
在依赖项 libfoo
中,Cargo.toml
文件的 lib
部分指定为:
[package]
name = "libfoo"
[lib]
name = "foo"
crate-type = ["cdylib"]
我已经尝试了 libfoo 和 foo 的所有排列,看看 Cargo 是否混淆了 lib 名称和 package/directory 名称。
如果我指定依赖项的本地路径,它也会失败。 (Cargo 编译依赖项,但随后声称在 lib.rs
中为 declared/imported 时找不到它。)
[dependencies]
libfoo = { path = "/Users/me/dev/libfoo" }
如果我包含来自 git 的 crate 或具有与 [package]
名称相同的 [lib]
名称的文件系统,它工作正常。因此,问题似乎出在具有与包 ([package]
) 名称不同的库 ([lib]
) 名称的板条箱上。
如果我从依赖项的 Cargo.toml
文件中删除 [lib]
部分,它会起作用。
更新:如果从 libfoo
中删除 crate-type = ["cdylib"]
,这与导入的 foo
一起使用。如果存在,我会得到与 extern crate foo;
.
相同的错误
Cargo 对包名感兴趣,而编译器(rustc
)对库名[=61]感兴趣=] 当谈到加载他们的元数据并与他们链接时。
让我们再看一下这个Cargo.toml
摘录:
[package]
name = "libfoo"
[lib]
name = "foo"
这里,包名是libfoo
,库名是foo
.
当你想在项目中声明对libfoo
的依赖时,需要在[=]中写上包名(libfoo
) 20=] table。例如:
[dependencies]
libfoo = { git = "ssh://git@github.com/me/libfoo", branch = "dev" }
这是你已有的,而且是正确的。
但是,当你想在你的crate中导入库时,你需要在extern crate
项中写上库名,即
extern crate foo;
我是怎么想出来的?首先,如您所述,我在 Cargo.toml
和 extern crate
项中都写了 libfoo
。当我 运行 cargo build
时,我注意到 libfoo
构建成功,表明 Cargo 正确解决了依赖关系。但我也注意到编译器无法找到 libfoo
,如您所见。
然后我检查了 运行 cargo build --verbose
传递给 rustc
的命令行。这是我看到的(无关部分省略):
Running `rustc [...] --extern foo=/[path]/target/debug/deps/libfoo-5cf876c5c8ac1bfb.rlib`
--extern name=path
参数告诉 rustc
名为 name
的板条箱位于 path
。这里的名字是foo
,所以我们必须在代码中写extern crate foo;
来引用它。
我有一个直接从 GitHub 进口的板条箱,根据 Cargo 的 documentation:
[dependencies]
libfoo = { git = "ssh://git@github.com/me/libfoo", branch = "dev" }
[lib]
path = "src/rust/lib.rs"
name = "myprj"
crate-type = ["cdylib"]
运行 cargo build
在这里工作正常,Cargo 获取 libfoo
并将其构建在 ~/.cargo
目录中。当我尝试在 lib.rs
:
extern crate libfoo; //also tried foo
货物扼流圈:
error[E0463]: can't find crate for `libfoo`
--> src/rust/lib.rs:1:1
|
1 | extern crate libfoo;
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^ can't find crate
有趣的是,当我在 lib.rs
中单击它时,IntelliJ 的 Rust 插件确实找到了箱子——它导航到 ~/.cargo
中下载的源...
在依赖项 libfoo
中,Cargo.toml
文件的 lib
部分指定为:
[package]
name = "libfoo"
[lib]
name = "foo"
crate-type = ["cdylib"]
我已经尝试了 libfoo 和 foo 的所有排列,看看 Cargo 是否混淆了 lib 名称和 package/directory 名称。
如果我指定依赖项的本地路径,它也会失败。 (Cargo 编译依赖项,但随后声称在 lib.rs
中为 declared/imported 时找不到它。)
[dependencies]
libfoo = { path = "/Users/me/dev/libfoo" }
如果我包含来自 git 的 crate 或具有与 [package]
名称相同的 [lib]
名称的文件系统,它工作正常。因此,问题似乎出在具有与包 ([package]
) 名称不同的库 ([lib]
) 名称的板条箱上。
如果我从依赖项的 Cargo.toml
文件中删除 [lib]
部分,它会起作用。
更新:如果从 libfoo
中删除 crate-type = ["cdylib"]
,这与导入的 foo
一起使用。如果存在,我会得到与 extern crate foo;
.
Cargo 对包名感兴趣,而编译器(rustc
)对库名[=61]感兴趣=] 当谈到加载他们的元数据并与他们链接时。
让我们再看一下这个Cargo.toml
摘录:
[package]
name = "libfoo"
[lib]
name = "foo"
这里,包名是libfoo
,库名是foo
.
当你想在项目中声明对libfoo
的依赖时,需要在[=]中写上包名(libfoo
) 20=] table。例如:
[dependencies]
libfoo = { git = "ssh://git@github.com/me/libfoo", branch = "dev" }
这是你已有的,而且是正确的。
但是,当你想在你的crate中导入库时,你需要在extern crate
项中写上库名,即
extern crate foo;
我是怎么想出来的?首先,如您所述,我在 Cargo.toml
和 extern crate
项中都写了 libfoo
。当我 运行 cargo build
时,我注意到 libfoo
构建成功,表明 Cargo 正确解决了依赖关系。但我也注意到编译器无法找到 libfoo
,如您所见。
然后我检查了 运行 cargo build --verbose
传递给 rustc
的命令行。这是我看到的(无关部分省略):
Running `rustc [...] --extern foo=/[path]/target/debug/deps/libfoo-5cf876c5c8ac1bfb.rlib`
--extern name=path
参数告诉 rustc
名为 name
的板条箱位于 path
。这里的名字是foo
,所以我们必须在代码中写extern crate foo;
来引用它。