-1

我有一个程序宏板条箱Proc和二进制板条箱BinBin依赖于Proc. Proc需要一个填充的环境变量才能正常运行。

build.rs这是我的 in里面的一些代码BinProc使用以下代码时可以成功找到env值:

fn main() {
    println!("cargo:rustc-env=SOME_ENV_VALUE=somevalue");
}

但是,在我的 in 中Proc使用此代码时找不到环境变量(注意:在调用后立即检查存在时,我可以验证密钥是否实际存在):build.rsBindotenv

fn main() {
    dotenv::dotenv().unwrap();
}

这是我的Proc箱子:

use proc_macro::TokenStream;

#[proc_macro_derive(MyProcMacro)]
pub fn my_proc_macro(input: TokenStream) -> TokenStream {
    if std::env::var("SOME_ENV_VALUE").is_err() {
        panic!("Failed to retrieve env value")
    }

    TokenStream::new()
}

为什么它不会因println!命令而失败?它可以使用dotenv吗?否则我需要编写一些代码将密钥从我的env文件复制到println!命令中......

所有代码都在我的最小复制项目中。

4

1 回答 1

4

我鼓励您重新阅读Cargo 文档的构建脚本章节。构建脚本是Cargo 在开始构建源代码之前构建和执行的单独可执行文件。

  1. 货物开始
  2. Cargo 执行rustc构建构建脚本
  3. Cargo 执行构建脚本
  4. Cargo 执行rustc以构建您的代码
  5. 货物出口

[ dotenv ] 从 .env 文件(如果可用)加载环境变量,并将它们与操作系统提供的实际环境变量混合。

它加载的变量被放入当前进程环境变量中。在您的示例中,这是构建脚本可执行文件。

[ cargo:rustc-env] 告诉 Cargo 在编译包时设置给定的环境变量

构建脚本的标准输出与 Cargo 交互,然后修改代码的编译方式,包括要设置的环境变量。


您需要加载dotenv文件设置环境变量以进行后续编译。像这个编译但未经测试的例子:

fn main() {
    if let Ok(env) = dotenv::dotenv_iter() {
        for (k,v) in env.flatten() {
            println!("cargo:rustc-env={}={}", k, v);
        }
    }
}

不要担心此方法被标记为已弃用。维护者改变了主意

于 2020-07-22T20:16:42.650 回答