Skip to content

add support for pre_start and post_start scripts #4

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -225,13 +225,20 @@ name = "homepage"
runs_on = ["docker1"]
# It requires that the traefik stack on docker1 be deployed first
depends_on = ["traefik"]
# It has a pre-start script that should be run before the stack is started
pre_start = ["./pre_start"]
# It has a post-script that should be run after the stack is started
post_start = ["./post_start"]
```

The stacks are topologically sorted based on their dependencies and then
started in that order.

It is not possible to depend on stacks that are running on other hosts.

`pre_start` and `post_start` scripts can be run to do any necessary setup such
as creating network resources.

## Stopping and removing a Stack

This is a two phase process:
Expand Down
8 changes: 8 additions & 0 deletions src/deploy_file.rs
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,14 @@ pub struct StackDeploy {
#[serde(default)]
pub secret_env: BTreeMap<String, String>,

/// List of scripts to run before starting the stack
#[serde(default)]
pub pre_start: Vec<String>,

/// List of scripts to run after starting the stack
#[serde(default)]
pub post_start: Vec<String>,

// TODO: secret_file
/// List of host names on which to run this service
pub runs_on: Vec<String>,
Expand Down
37 changes: 37 additions & 0 deletions src/main.rs
Original file line number Diff line number Diff line change
Expand Up @@ -155,10 +155,47 @@ fn do_compose_up(db: &KeePassDB, path: &Path, deploy: &StackDeploy) -> anyhow::R
"Cannot deploy {path:?} because of the errors above"
);

if !&deploy.pre_start.is_empty() {
let mut cmd = std::process::Command::new(&deploy.pre_start[0]);
cmd.current_dir(
path.parent()
.ok_or_else(|| anyhow::anyhow!("path {path:?} has no parent!?"))?,
);
for script in &deploy.pre_start[1..] {
cmd.arg(script);
}
for (k, v) in deploy.secret_env.iter() {
db.resolve_value(&v).map(|v| cmd.env(k, v));
}
let status = cmd
.status()
.with_context(|| format!("failed to run pre_start script in directory of {path:?}"))?;
anyhow::ensure!(status.success(), "pre_script exit status is {status:?}");
}

let status = cmd
.status()
.with_context(|| format!("failed to run docker compose up in directory of {path:?}"))?;
anyhow::ensure!(status.success(), "exit status is {status:?}");

if !&deploy.post_start.is_empty() {
let mut cmd = std::process::Command::new(&deploy.pre_start[0]);
cmd.current_dir(
path.parent()
.ok_or_else(|| anyhow::anyhow!("path {path:?} has no parent!?"))?,
);
for script in &deploy.post_start[1..] {
cmd.arg(script);
}
for (k, v) in deploy.secret_env.iter() {
db.resolve_value(&v).map(|v| cmd.env(k, v));
}
let status = cmd
.status()
.with_context(|| format!("failed to run post_start script in directory of {path:?}"))?;
anyhow::ensure!(status.success(), "post_start exit status is {status:?}");
}

Ok(())
}

Expand Down