refactor(nodejs): use base64 encoding and coder exp sync for pre/post install scripts
- Base64 encode pre/post install scripts to safely handle special characters - Use separate coder_script resources for pre_install, install, and post_install - Add coder exp sync want/start/complete for execution ordering - Base64 encode the main install script (run.sh) via templatefile + base64encode - Revert run.sh to original (no pre/post install handling) - Add sync name outputs for cross-module dependency coordination - Update README with cross-module coordination documentation - Add output assertions to tests
This commit is contained in:
parent
d0ef879e5f
commit
817238ea64
@ -55,6 +55,28 @@ module "nodejs" {
|
|||||||
}
|
}
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Cross-Module Dependency Ordering
|
||||||
|
|
||||||
|
This module uses `coder exp sync` to coordinate execution ordering with other modules. It exposes the following outputs for use with `coder exp sync want`:
|
||||||
|
|
||||||
|
- `install_script_name` — the sync name for the main Node.js installation script
|
||||||
|
- `pre_install_script_name` — the sync name for the pre-install script
|
||||||
|
- `post_install_script_name` — the sync name for the post-install script
|
||||||
|
|
||||||
|
For example, to ensure another module waits for Node.js to be fully installed:
|
||||||
|
|
||||||
|
```tf
|
||||||
|
module "nodejs" {
|
||||||
|
count = data.coder_workspace.me.start_count
|
||||||
|
source = "registry.coder.com/thezoker/nodejs/coder"
|
||||||
|
version = "1.1.0"
|
||||||
|
agent_id = coder_agent.example.id
|
||||||
|
}
|
||||||
|
|
||||||
|
# In another module's coder_script, wait for Node.js installation:
|
||||||
|
# coder exp sync want my-script ${module.nodejs[0].install_script_name}
|
||||||
|
```
|
||||||
|
|
||||||
## Full example
|
## Full example
|
||||||
|
|
||||||
A example with all available options:
|
A example with all available options:
|
||||||
|
|||||||
@ -50,17 +50,113 @@ variable "post_install_script" {
|
|||||||
default = null
|
default = null
|
||||||
}
|
}
|
||||||
|
|
||||||
|
locals {
|
||||||
|
encoded_pre_install_script = var.pre_install_script != null ? base64encode(var.pre_install_script) : ""
|
||||||
|
encoded_post_install_script = var.post_install_script != null ? base64encode(var.post_install_script) : ""
|
||||||
|
|
||||||
|
install_script = templatefile("${path.module}/run.sh", {
|
||||||
|
NVM_VERSION = var.nvm_version,
|
||||||
|
INSTALL_PREFIX = var.nvm_install_prefix,
|
||||||
|
NODE_VERSIONS = join(",", var.node_versions),
|
||||||
|
DEFAULT = var.default_node_version,
|
||||||
|
})
|
||||||
|
encoded_install_script = base64encode(local.install_script)
|
||||||
|
|
||||||
|
pre_install_script_name = "nodejs-pre_install_script"
|
||||||
|
install_script_name = "nodejs-install_script"
|
||||||
|
post_install_script_name = "nodejs-post_install_script"
|
||||||
|
|
||||||
|
module_dir_path = "$HOME/.nodejs-module"
|
||||||
|
|
||||||
|
pre_install_path = "${local.module_dir_path}/pre_install.sh"
|
||||||
|
pre_install_log_path = "${local.module_dir_path}/pre_install.log"
|
||||||
|
install_path = "${local.module_dir_path}/install.sh"
|
||||||
|
install_log_path = "${local.module_dir_path}/install.log"
|
||||||
|
post_install_path = "${local.module_dir_path}/post_install.sh"
|
||||||
|
post_install_log_path = "${local.module_dir_path}/post_install.log"
|
||||||
|
}
|
||||||
|
|
||||||
|
resource "coder_script" "pre_install_script" {
|
||||||
|
count = var.pre_install_script == null ? 0 : 1
|
||||||
|
agent_id = var.agent_id
|
||||||
|
display_name = "Node.js: Pre-Install"
|
||||||
|
run_on_start = true
|
||||||
|
script = <<-EOT
|
||||||
|
#!/bin/bash
|
||||||
|
set -o errexit
|
||||||
|
set -o pipefail
|
||||||
|
|
||||||
|
mkdir -p ${local.module_dir_path}
|
||||||
|
|
||||||
|
trap 'coder exp sync complete ${local.pre_install_script_name}' EXIT
|
||||||
|
coder exp sync start ${local.pre_install_script_name}
|
||||||
|
|
||||||
|
echo -n '${local.encoded_pre_install_script}' | base64 -d > ${local.pre_install_path}
|
||||||
|
chmod +x ${local.pre_install_path}
|
||||||
|
|
||||||
|
${local.pre_install_path} 2>&1 | tee ${local.pre_install_log_path}
|
||||||
|
EOT
|
||||||
|
}
|
||||||
|
|
||||||
resource "coder_script" "nodejs" {
|
resource "coder_script" "nodejs" {
|
||||||
agent_id = var.agent_id
|
agent_id = var.agent_id
|
||||||
display_name = "Node.js:"
|
display_name = "Node.js: Install"
|
||||||
script = templatefile("${path.module}/run.sh", {
|
script = <<-EOT
|
||||||
NVM_VERSION : var.nvm_version,
|
#!/bin/bash
|
||||||
INSTALL_PREFIX : var.nvm_install_prefix,
|
set -o errexit
|
||||||
NODE_VERSIONS : join(",", var.node_versions),
|
set -o pipefail
|
||||||
DEFAULT : var.default_node_version,
|
|
||||||
PRE_INSTALL_SCRIPT : var.pre_install_script != null ? var.pre_install_script : "",
|
mkdir -p ${local.module_dir_path}
|
||||||
POST_INSTALL_SCRIPT : var.post_install_script != null ? var.post_install_script : "",
|
|
||||||
})
|
trap 'coder exp sync complete ${local.install_script_name}' EXIT
|
||||||
|
%{if var.pre_install_script != null~}
|
||||||
|
coder exp sync want ${local.install_script_name} ${local.pre_install_script_name}
|
||||||
|
%{endif~}
|
||||||
|
coder exp sync start ${local.install_script_name}
|
||||||
|
|
||||||
|
echo -n '${local.encoded_install_script}' | base64 -d > ${local.install_path}
|
||||||
|
chmod +x ${local.install_path}
|
||||||
|
|
||||||
|
${local.install_path} 2>&1 | tee ${local.install_log_path}
|
||||||
|
EOT
|
||||||
run_on_start = true
|
run_on_start = true
|
||||||
start_blocks_login = true
|
start_blocks_login = true
|
||||||
}
|
}
|
||||||
|
|
||||||
|
resource "coder_script" "post_install_script" {
|
||||||
|
count = var.post_install_script != null ? 1 : 0
|
||||||
|
agent_id = var.agent_id
|
||||||
|
display_name = "Node.js: Post-Install"
|
||||||
|
run_on_start = true
|
||||||
|
script = <<-EOT
|
||||||
|
#!/bin/bash
|
||||||
|
set -o errexit
|
||||||
|
set -o pipefail
|
||||||
|
|
||||||
|
mkdir -p ${local.module_dir_path}
|
||||||
|
|
||||||
|
trap 'coder exp sync complete ${local.post_install_script_name}' EXIT
|
||||||
|
coder exp sync want ${local.post_install_script_name} ${local.install_script_name}
|
||||||
|
coder exp sync start ${local.post_install_script_name}
|
||||||
|
|
||||||
|
echo -n '${local.encoded_post_install_script}' | base64 -d > ${local.post_install_path}
|
||||||
|
chmod +x ${local.post_install_path}
|
||||||
|
|
||||||
|
${local.post_install_path} 2>&1 | tee ${local.post_install_log_path}
|
||||||
|
EOT
|
||||||
|
}
|
||||||
|
|
||||||
|
output "pre_install_script_name" {
|
||||||
|
description = "The name of the pre-install script for coder exp sync coordination."
|
||||||
|
value = local.pre_install_script_name
|
||||||
|
}
|
||||||
|
|
||||||
|
output "install_script_name" {
|
||||||
|
description = "The name of the install script for coder exp sync coordination."
|
||||||
|
value = local.install_script_name
|
||||||
|
}
|
||||||
|
|
||||||
|
output "post_install_script_name" {
|
||||||
|
description = "The name of the post-install script for coder exp sync coordination."
|
||||||
|
value = local.post_install_script_name
|
||||||
|
}
|
||||||
|
|||||||
@ -29,6 +29,11 @@ run "test_nodejs_basic" {
|
|||||||
condition = var.post_install_script == null
|
condition = var.post_install_script == null
|
||||||
error_message = "post_install_script should default to null"
|
error_message = "post_install_script should default to null"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
assert {
|
||||||
|
condition = output.install_script_name == "nodejs-install_script"
|
||||||
|
error_message = "install_script_name output should be set"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
run "test_with_scripts" {
|
run "test_with_scripts" {
|
||||||
@ -49,6 +54,16 @@ run "test_with_scripts" {
|
|||||||
condition = var.post_install_script == "echo 'Post-install script'"
|
condition = var.post_install_script == "echo 'Post-install script'"
|
||||||
error_message = "Post-install script should be set correctly"
|
error_message = "Post-install script should be set correctly"
|
||||||
}
|
}
|
||||||
|
|
||||||
|
assert {
|
||||||
|
condition = output.pre_install_script_name == "nodejs-pre_install_script"
|
||||||
|
error_message = "pre_install_script_name output should be set"
|
||||||
|
}
|
||||||
|
|
||||||
|
assert {
|
||||||
|
condition = output.post_install_script_name == "nodejs-post_install_script"
|
||||||
|
error_message = "post_install_script_name output should be set"
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
run "test_custom_options" {
|
run "test_custom_options" {
|
||||||
|
|||||||
@ -4,17 +4,10 @@ NVM_VERSION='${NVM_VERSION}'
|
|||||||
NODE_VERSIONS='${NODE_VERSIONS}'
|
NODE_VERSIONS='${NODE_VERSIONS}'
|
||||||
INSTALL_PREFIX='${INSTALL_PREFIX}'
|
INSTALL_PREFIX='${INSTALL_PREFIX}'
|
||||||
DEFAULT='${DEFAULT}'
|
DEFAULT='${DEFAULT}'
|
||||||
PRE_INSTALL_SCRIPT='${PRE_INSTALL_SCRIPT}'
|
|
||||||
POST_INSTALL_SCRIPT='${POST_INSTALL_SCRIPT}'
|
|
||||||
BOLD='\033[0;1m'
|
BOLD='\033[0;1m'
|
||||||
CODE='\033[36;40;1m'
|
CODE='\033[36;40;1m'
|
||||||
RESET='\033[0m'
|
RESET='\033[0m'
|
||||||
|
|
||||||
if [ -n "$${PRE_INSTALL_SCRIPT}" ]; then
|
|
||||||
printf "$${BOLD}Running pre-install script...$${RESET}\n"
|
|
||||||
eval "$${PRE_INSTALL_SCRIPT}"
|
|
||||||
fi
|
|
||||||
|
|
||||||
printf "$${BOLD}Installing nvm!$${RESET}\n"
|
printf "$${BOLD}Installing nvm!$${RESET}\n"
|
||||||
|
|
||||||
export NVM_DIR="$HOME/$${INSTALL_PREFIX}/nvm"
|
export NVM_DIR="$HOME/$${INSTALL_PREFIX}/nvm"
|
||||||
@ -58,8 +51,3 @@ if [ -n "$${DEFAULT}" ]; then
|
|||||||
printf "🛠️ Setting default node version $${CODE}$DEFAULT$${RESET}...\n"
|
printf "🛠️ Setting default node version $${CODE}$DEFAULT$${RESET}...\n"
|
||||||
output=$(nvm alias default $DEFAULT 2>&1)
|
output=$(nvm alias default $DEFAULT 2>&1)
|
||||||
fi
|
fi
|
||||||
|
|
||||||
if [ -n "$${POST_INSTALL_SCRIPT}" ]; then
|
|
||||||
printf "$${BOLD}Running post-install script...$${RESET}\n"
|
|
||||||
eval "$${POST_INSTALL_SCRIPT}"
|
|
||||||
fi
|
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user