【发布时间】:2022-01-24 03:51:46
【问题描述】:
我有一个 proc-macro,它也公开了一些类型,所以我使用以下 crate 结构:
-
foo_core出口FooTrait -
foo_macro(取决于foo_core)导出foo_macro,生成一些实现FooTrait的结构体 -
foo(取决于foo_core和foo_macro)再出口FooTrait和foo_macro
我遇到的问题是重新导出 foo_core 会改变它的路径。
foo_macro 生成的代码大致如下:
struct Bar;
impl ::foo_core::FooTrait for Bar {
// ...
}
我在foo_macro 中有一堆trybuild 测试通过了,因为foo_core 是一个可用的板条箱。
问题是当我尝试在 foo(或仅依赖于 foo 的 crate 中)编写测试时,我收到错误消息,告诉我找不到 crate foo_core。
这对我来说有点道理; foo 的消费者没有明确依赖 foo_core,但如果我的 crate 的用户不必添加 foo 和 foo_core(并确保版本匹配),我会喜欢它,而不是我希望他们能够只添加foo,这样就可以了。
目前,我可以通过foo::foo_core::FooTrait 访问foo_core,但这显然与我的宏生成代码的方式不同(::foo_core::FooTrait)。有没有办法让foo重新导出整个foo_core crate?
如果这不可能,那么处理这种模式的最佳方法是什么?我可以以某种方式让foo_macro 根据它定义的箱子改变它的行为吗?还是应该将所有测试移至foo 而不是foo_macro?
Is there a way to have a public trait in a proc-macro crate? an answer to this question提到了这个问题,但只是说“你必须使用完全限定的名称”,但我的理解是这就是路径上领先的::的意思。
这似乎是一种相对常见的模式,所以我希望那里有一个不错的解决方案。
【问题讨论】:
-
这似乎与 Rocket 中的三个 crate(rocket_codegen、rocket_http 和 rocket)github.com/SergioBenitez/Rocket/tree/master/core 中的情况类似。因此,在您的情况下,lib
foo似乎将重新导出foo_core,就像火箭在rocketgithub.com/SergioBenitez/Rocket/blob/v0.5-rc/core/lib/src/… 中重新导出rocket_http。因此,在您的情况下,您在生成和测试的代码中的完全限定名称将是foo::foo_core::FooTrait?
标签: rust rust-cargo