diff options
author | notgne2 | 2021-02-08 15:24:13 -0700 |
---|---|---|
committer | GitHub | 2021-02-08 15:24:13 -0700 |
commit | 4f4c1e3cf7c9bc13a1dfd7d0035696cf6e7eaeb6 (patch) | |
tree | 5203fdc4082bbdfe6599de79144cc5027b1b85e5 /src/bin/deploy.rs | |
parent | c00e29a39df47c8cdba8c4bb43868a27f32df3b8 (diff) | |
parent | 99f2127ccee5e612b1c26a7300f7380f5d1575b0 (diff) |
Merge pull request #63 from serokell/balsoft/lazy-eval
Evaluate deploy output lazily
Diffstat (limited to 'src/bin/deploy.rs')
-rw-r--r-- | src/bin/deploy.rs | 84 |
1 files changed, 62 insertions, 22 deletions
diff --git a/src/bin/deploy.rs b/src/bin/deploy.rs index caf3d4e..30ebd25 100644 --- a/src/bin/deploy.rs +++ b/src/bin/deploy.rs @@ -156,43 +156,84 @@ enum GetDeploymentDataError { DecodeUtf8(#[from] std::string::FromUtf8Error), #[error("Error decoding the JSON from evaluation: {0}")] DecodeJson(#[from] serde_json::error::Error), + #[error("Impossible happened: profile is set but node is not")] + ProfileNoNode, } /// Evaluates the Nix in the given `repo` and return the processed Data from it async fn get_deployment_data( supports_flakes: bool, - repo: &str, + flake: &deploy::DeployFlake<'_>, extra_build_args: &[String], ) -> Result<deploy::data::Data, GetDeploymentDataError> { - info!("Evaluating flake in {}", repo); + info!("Evaluating flake in {}", flake.repo); - let mut c = match supports_flakes { - true => Command::new("nix"), - false => Command::new("nix-instantiate"), + let mut c = if supports_flakes { + Command::new("nix") + } else { + Command::new("nix-instantiate") }; - let mut build_command = match supports_flakes { - true => { - c.arg("eval") + if supports_flakes { + c.arg("eval") .arg("--json") - .arg(format!("{}#deploy", repo)) - } - false => { - c - .arg("--strict") - .arg("--read-write-mode") - .arg("--json") - .arg("--eval") - .arg("-E") - .arg(format!("let r = import {}/.; in if builtins.isFunction r then (r {{}}).deploy else r.deploy", repo)) + .arg(format!("{}#deploy", flake.repo)) + // We use --apply instead of --expr so that we don't have to deal with builtins.getFlake + .arg("--apply"); + match (&flake.node, &flake.profile) { + (Some(node), Some(profile)) => { + // Ignore all nodes and all profiles but the one we're evaluating + c.arg(format!( + r#" + deploy: + (deploy // {{ + nodes = {{ + "{0}" = deploy.nodes."{0}" // {{ + profiles = {{ + inherit (deploy.nodes."{0}".profiles) "{1}"; + }}; + }}; + }}; + }}) + "#, + node, profile + )) + } + (Some(node), None) => { + // Ignore all nodes but the one we're evaluating + c.arg(format!( + r#" + deploy: + (deploy // {{ + nodes = {{ + inherit (deploy.nodes) "{}"; + }}; + }}) + "#, + node + )) + } + (None, None) => { + // We need to evaluate all profiles of all nodes anyway, so just do it strictly + c.arg(format!("deploy: deploy")) + } + (None, Some(_)) => return Err(GetDeploymentDataError::ProfileNoNode), } + } else { + c + .arg("--strict") + .arg("--read-write-mode") + .arg("--json") + .arg("--eval") + .arg("-E") + .arg(format!("let r = import {}/.; in if builtins.isFunction r then (r {{}}).deploy else r.deploy", flake.repo)) }; for extra_arg in extra_build_args { - build_command = build_command.arg(extra_arg); + c.arg(extra_arg); } - let build_child = build_command + let build_child = c .stdout(Stdio::piped()) .spawn() .map_err(GetDeploymentDataError::NixEval)?; @@ -524,8 +565,7 @@ async fn run() -> Result<(), RunError> { check_deployment(supports_flakes, deploy_flake.repo, &opts.extra_build_args).await?; } - let data = - get_deployment_data(supports_flakes, deploy_flake.repo, &opts.extra_build_args).await?; + let data = get_deployment_data(supports_flakes, &deploy_flake, &opts.extra_build_args).await?; let result_path = opts.result_path.as_deref(); |