1use crate::tasks::workflows::{
  2    runners::{Arch, Platform},
  3    steps::NamedJob,
  4};
  5
  6use super::{runners, steps, steps::named, vars};
  7use gh_workflow::*;
  8use indoc::indoc;
  9
 10pub(crate) fn build_nix(
 11    platform: Platform,
 12    arch: Arch,
 13    flake_output: &str,
 14    cachix_filter: Option<&str>,
 15    deps: &[&NamedJob],
 16) -> NamedJob {
 17    // on our macs we manually install nix. for some reason the cachix action is running
 18    // under a non-login /bin/bash shell which doesn't source the proper script to add the
 19    // nix profile to PATH, so we manually add them here
 20    pub fn set_path() -> Step<Run> {
 21        named::bash(indoc! {r#"
 22                echo "/nix/var/nix/profiles/default/bin" >> "$GITHUB_PATH"
 23                echo "/Users/administrator/.nix-profile/bin" >> "$GITHUB_PATH"
 24            "#})
 25    }
 26
 27    pub fn install_nix() -> Step<Use> {
 28        named::uses(
 29            "cachix",
 30            "install-nix-action",
 31            "02a151ada4993995686f9ed4f1be7cfbb229e56f", // v31
 32        )
 33        .add_with(("github_access_token", vars::GITHUB_TOKEN))
 34    }
 35
 36    pub fn cachix_action(cachix_filter: Option<&str>) -> Step<Use> {
 37        let mut step = named::uses(
 38            "cachix",
 39            "cachix-action",
 40            "0fc020193b5a1fa3ac4575aa3a7d3aa6a35435ad", // v16
 41        )
 42        .add_with(("name", "zed"))
 43        .add_with(("authToken", vars::CACHIX_AUTH_TOKEN))
 44        .add_with(("cachixArgs", "-v"));
 45        if let Some(cachix_filter) = cachix_filter {
 46            step = step.add_with(("pushFilter", cachix_filter));
 47        }
 48        step
 49    }
 50
 51    pub fn build(flake_output: &str) -> Step<Run> {
 52        named::bash(&format!(
 53            "nix build .#{} -L --accept-flake-config",
 54            flake_output
 55        ))
 56    }
 57
 58    pub fn limit_store() -> Step<Run> {
 59        named::bash(indoc! {r#"
 60                if [ "$(du -sm /nix/store | cut -f1)" -gt 50000 ]; then
 61                    nix-collect-garbage -d || true
 62                fi"#
 63        })
 64    }
 65
 66    let runner = match platform {
 67        Platform::Windows => unimplemented!(),
 68        Platform::Linux => runners::LINUX_X86_BUNDLER,
 69        Platform::Mac => runners::MAC_DEFAULT,
 70    };
 71    let mut job = Job::default()
 72        .timeout_minutes(60u32)
 73        .continue_on_error(true)
 74        .cond(Expression::new(
 75            "github.repository_owner == 'zed-industries'",
 76        ))
 77        .runs_on(runner)
 78        .add_env(("ZED_CLIENT_CHECKSUM_SEED", vars::ZED_CLIENT_CHECKSUM_SEED))
 79        .add_env(("ZED_MINIDUMP_ENDPOINT", vars::ZED_SENTRY_MINIDUMP_ENDPOINT))
 80        .add_env((
 81            "ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON",
 82            vars::ZED_CLOUD_PROVIDER_ADDITIONAL_MODELS_JSON,
 83        ))
 84        .add_env(("GIT_LFS_SKIP_SMUDGE", "1")) // breaks the livekit rust sdk examples which we don't actually depend on
 85        .add_step(steps::checkout_repo());
 86
 87    if deps.len() > 0 {
 88        job = job.needs(deps.iter().map(|d| d.name.clone()).collect::<Vec<String>>());
 89    }
 90
 91    job = if platform == Platform::Linux {
 92        job.add_step(install_nix())
 93            .add_step(cachix_action(cachix_filter))
 94            .add_step(build(&flake_output))
 95    } else {
 96        job.add_step(set_path())
 97            .add_step(cachix_action(cachix_filter))
 98            .add_step(build(&flake_output))
 99            .add_step(limit_store())
100    };
101
102    NamedJob {
103        name: format!("build_nix_{platform}_{arch}"),
104        job,
105    }
106}