Skip to content

Commit

Permalink
Refactor homologate data structures
Browse files Browse the repository at this point in the history
  • Loading branch information
blaggacao committed Aug 11, 2021
1 parent 519661d commit c6c2f00
Show file tree
Hide file tree
Showing 5 changed files with 144 additions and 200 deletions.
188 changes: 55 additions & 133 deletions src/cli.rs
Original file line number Diff line number Diff line change
Expand Up @@ -28,66 +28,16 @@ pub struct Opts {
/// A list of flakes to deploy alternatively
#[clap(long, group = "deploy")]
targets: Option<Vec<String>>,
/// Check signatures when using `nix copy`
#[clap(short, long)]
checksigs: bool,
/// Use the interactive prompt before deployment
#[clap(short, long)]
interactive: bool,
/// Extra arguments to be passed to nix build
extra_build_args: Vec<String>,

/// Print debug logs to output
#[clap(short, long)]
debug_logs: bool,
/// Directory to print logs to (including the background activation process)
#[clap(long)]
log_dir: Option<String>,

/// Keep the build outputs of each built profile
#[clap(short, long)]
keep_result: bool,
/// Location to keep outputs from built profiles in
#[clap(short, long)]
result_path: Option<String>,

/// Skip the automatic pre-build checks
#[clap(short, long)]
skip_checks: bool,

/// Override the SSH user with the given value
#[clap(long)]
ssh_user: Option<String>,
/// Override the profile user with the given value
#[clap(long)]
profile_user: Option<String>,
/// Override the SSH options used
#[clap(long)]
ssh_opts: Option<String>,
/// Override if the connecting to the target node should be considered fast
#[clap(long)]
fast_connection: Option<bool>,
/// Override if a rollback should be attempted if activation fails
#[clap(long)]
auto_rollback: Option<bool>,
/// Override hostname used for the node
#[clap(long)]
hostname: Option<String>,
/// Make activation wait for confirmation, or roll back after a period of time
#[clap(long)]
magic_rollback: Option<bool>,
/// How long activation should wait for confirmation (if using magic-rollback)
#[clap(long)]
confirm_timeout: Option<u16>,
/// Where to store temporary files (only used by magic-rollback)
#[clap(long)]
temp_path: Option<String>,
/// Show what will be activated on the machines
#[clap(long)]
dry_activate: bool,
/// Revoke all previously succeeded deploys when deploying multiple profiles
#[clap(long)]
rollback_succeeded: Option<bool>,

#[clap(flatten)]
flags: data::Flags,

#[clap(flatten)]
generic_settings: settings::GenericSettings,
}

/// Returns if the available Nix installation supports flakes
Expand Down Expand Up @@ -240,27 +190,20 @@ type ToDeploy<'a> = Vec<(
)>;

async fn run_deploy(
deploy_targets: Vec<data::Target>,
data: Vec<settings::Root>,
targets: Vec<data::Target>,
settings: Vec<settings::Root>,
supports_flakes: bool,
check_sigs: bool,
interactive: bool,
cmd_overrides: &data::CmdOverrides,
keep_result: bool,
result_path: Option<&str>,
extra_build_args: &[String],
debug_logs: bool,
dry_activate: bool,
log_dir: &Option<String>,
rollback_succeeded: bool,
hostname: Option<String>,
cmd_settings: settings::GenericSettings,
cmd_flags: data::Flags,
) -> Result<(), RunDeployError> {
let to_deploy: ToDeploy = deploy_targets
let to_deploy: ToDeploy = targets
.iter()
.zip(&data)
.map(|(deploy_target, data)| {
let to_deploys: ToDeploy = match (&deploy_target.node, &deploy_target.profile) {
.zip(&settings)
.map(|(target, root)| {
let to_deploys: ToDeploy = match (&target.node, &target.profile) {
(Some(node_name), Some(profile_name)) => {
let node = match data.nodes.get(node_name) {
let node = match root.nodes.get(node_name) {
Some(x) => x,
None => Err(RunDeployError::NodeNotFound(node_name.to_owned()))?,
};
Expand All @@ -270,14 +213,14 @@ async fn run_deploy(
};

vec![(
&deploy_target,
&data,
&target,
&root,
(node_name.as_str(), node),
(profile_name.as_str(), profile),
)]
}
(Some(node_name), None) => {
let node = match data.nodes.get(node_name) {
let node = match root.nodes.get(node_name) {
Some(x) => x,
None => return Err(RunDeployError::NodeNotFound(node_name.to_owned())),
};
Expand Down Expand Up @@ -306,13 +249,13 @@ async fn run_deploy(

profiles_list
.into_iter()
.map(|x| (deploy_target, data, (node_name.as_str(), node), x))
.map(|x| (target, root, (node_name.as_str(), node), x))
.collect()
}
(None, None) => {
let mut l = Vec::new();

for (node_name, node) in &data.nodes {
for (node_name, node) in &root.nodes {
let mut profiles_list: Vec<(&str, &settings::Profile)> = Vec::new();

for profile_name in [
Expand All @@ -337,7 +280,7 @@ async fn run_deploy(

let ll: ToDeploy = profiles_list
.into_iter()
.map(|x| (deploy_target, data, (node_name.as_str(), node), x))
.map(|x| (target, root, (node_name.as_str(), node), x))
.collect();

l.extend(ll);
Expand All @@ -360,39 +303,39 @@ async fn run_deploy(
data::DeployDefs,
)> = Vec::new();

for (deploy_target, data, (node_name, node), (profile_name, profile)) in to_deploy {
for (target, root, (node_name, node), (profile_name, profile)) in to_deploy {
let deploy_data = data::make_deploy_data(
&data.generic_settings,
&root.generic_settings,
&cmd_settings,
&cmd_flags,
node,
node_name,
profile,
profile_name,
&cmd_overrides,
debug_logs,
log_dir.as_deref(),
hostname.as_deref(),
);

let deploy_defs = deploy_data.defs()?;

parts.push((deploy_target, deploy_data, deploy_defs));
parts.push((target, deploy_data, deploy_defs));
}

if interactive {
if cmd_flags.interactive {
prompt_deployment(&parts[..])?;
} else {
print_deployment(&parts[..])?;
}

for (deploy_target, deploy_data, deploy_defs) in &parts {
for (target, deploy_data, deploy_defs) in &parts {
deploy::push::push_profile(deploy::push::PushProfileData {
supports_flakes,
check_sigs,
repo: &deploy_target.repo,
supports_flakes: &supports_flakes,
check_sigs: &cmd_flags.checksigs,
repo: &target.repo,
deploy_data: &deploy_data,
deploy_defs: &deploy_defs,
keep_result,
result_path,
extra_build_args,
keep_result: &cmd_flags.keep_result,
result_path: cmd_flags.result_path.as_deref(),
extra_build_args: &cmd_flags.extra_build_args,
})
.await?;
}
Expand All @@ -404,14 +347,14 @@ async fn run_deploy(
// Rollbacks adhere to the global seeting to auto_rollback and secondary
// the profile's configuration
for (_, deploy_data, deploy_defs) in &parts {
if let Err(e) = deploy::deploy::deploy_profile(deploy_data, deploy_defs, dry_activate).await
if let Err(e) = deploy::deploy::deploy_profile(deploy_data, deploy_defs, cmd_flags.dry_activate).await
{
error!("{}", e);
if dry_activate {
if cmd_flags.dry_activate {
info!("dry run, not rolling back");
}
info!("Revoking previous deploys");
if rollback_succeeded && cmd_overrides.auto_rollback.unwrap_or(true) {
if cmd_flags.rollback_succeeded && cmd_settings.auto_rollback.unwrap_or(true) {
// revoking all previous deploys
// (adheres to profile configuration if not set explicitely by
// the command line)
Expand Down Expand Up @@ -456,8 +399,8 @@ pub async fn run(args: Option<&ArgMatches>) -> Result<(), RunError> {
};

deploy::init_logger(
opts.debug_logs,
opts.log_dir.as_deref(),
opts.flags.debug_logs,
opts.flags.log_dir.as_deref(),
deploy::LoggerType::Deploy,
)?;

Expand All @@ -466,51 +409,30 @@ pub async fn run(args: Option<&ArgMatches>) -> Result<(), RunError> {
.targets
.unwrap_or_else(|| vec![opts.clone().target.unwrap_or(".".to_string())]);

let deploy_targets: Vec<data::Target> = deploys
.into_iter()
.map(|f| f.parse::<data::Target>())
.collect::<Result<Vec<data::Target>, data::ParseTargetError>>()?;

let cmd_overrides = data::CmdOverrides {
ssh_user: opts.ssh_user,
profile_user: opts.profile_user,
ssh_opts: opts.ssh_opts,
fast_connection: opts.fast_connection,
auto_rollback: opts.auto_rollback,
hostname: opts.hostname,
magic_rollback: opts.magic_rollback,
temp_path: opts.temp_path,
confirm_timeout: opts.confirm_timeout,
dry_activate: opts.dry_activate,
};

let supports_flakes = test_flake_support().await.map_err(RunError::FlakeTest)?;

if !supports_flakes {
warn!("A Nix version without flakes support was detected, support for this is work in progress");
}

if !opts.skip_checks {
for deploy_target in deploy_targets.iter() {
flake::check_deployment(supports_flakes, &deploy_target.repo, &opts.extra_build_args).await?;
let targets: Vec<data::Target> = deploys
.into_iter()
.map(|f| f.parse::<data::Target>())
.collect::<Result<Vec<data::Target>, data::ParseTargetError>>()?;

if !opts.flags.skip_checks {
for target in targets.iter() {
flake::check_deployment(supports_flakes, &target.repo, &opts.flags.extra_build_args).await?;
}
}
let result_path = opts.result_path.as_deref();
let data = flake::get_deployment_data(supports_flakes, &deploy_targets, &opts.extra_build_args).await?;
let settings = flake::get_deployment_data(supports_flakes, &targets, &opts.flags.extra_build_args).await?;
run_deploy(
deploy_targets,
data,
targets,
settings,
supports_flakes,
opts.checksigs,
opts.interactive,
&cmd_overrides,
opts.keep_result,
result_path,
&opts.extra_build_args,
opts.debug_logs,
opts.dry_activate,
&opts.log_dir,
opts.rollback_succeeded.unwrap_or(true),
opts.hostname,
opts.generic_settings,
opts.flags,
)
.await?;

Expand Down
Loading

0 comments on commit c6c2f00

Please sign in to comment.