336 lines
12 KiB
Plaintext
336 lines
12 KiB
Plaintext
|
|
#!/usr/bin/env nu
|
||
|
|
# Info: Script to run Provisioning Module Management
|
||
|
|
# Author: JesusPerezLorenzo
|
||
|
|
# Release: 1.0.0
|
||
|
|
# Date: 29-09-2025
|
||
|
|
|
||
|
|
use std log
|
||
|
|
|
||
|
|
use lib_provisioning *
|
||
|
|
use env.nu *
|
||
|
|
|
||
|
|
# - > Help on Module
|
||
|
|
export def "main help" [
|
||
|
|
--src: string = ""
|
||
|
|
--notitles # not titles
|
||
|
|
--out: string # Print Output format: json, yaml, text (default)
|
||
|
|
]: nothing -> nothing {
|
||
|
|
if $notitles == null or not $notitles { show_titles }
|
||
|
|
^$"($env.PROVISIONING_NAME)" -mod module --help
|
||
|
|
if ($out | is-not-empty) { $env.PROVISIONING_NO_TERMINAL = false }
|
||
|
|
print (provisioning_options $src)
|
||
|
|
if not $env.PROVISIONING_DEBUG { end_run "" }
|
||
|
|
}
|
||
|
|
|
||
|
|
# > Module Management - Discovery and loading with template support
|
||
|
|
def main [
|
||
|
|
...args: string # Other options, use help to get info
|
||
|
|
-v # Show version
|
||
|
|
-i # Show Info
|
||
|
|
--version (-V) # Show version with title
|
||
|
|
--info (-I) # Show Info with title
|
||
|
|
--about (-a) # Show About
|
||
|
|
--notitles # Do not show banner titles
|
||
|
|
--format: string = "table" # Output format: table, json, yaml, names
|
||
|
|
--layer: string = "workspace" # Layer: workspace, infra, all
|
||
|
|
--type: string = "taskservs" # Module type: taskservs, providers, clusters
|
||
|
|
--category: string = "" # Filter by category
|
||
|
|
--group: string = "" # Filter by group
|
||
|
|
--manifest: string = "providers.manifest.yaml" # Manifest file name
|
||
|
|
--kcl # Show KCL module info
|
||
|
|
--validate # Validate after loading
|
||
|
|
--template-type: string = "all" # Template type: taskservs, providers, servers, clusters
|
||
|
|
--from: string = "" # Template to base on
|
||
|
|
--dry-run # Show what would be done
|
||
|
|
--override-file: string = "" # Override file path
|
||
|
|
--modules: list<string> = [] # Modules list
|
||
|
|
--template: string = "" # Template name
|
||
|
|
--provider: string = "upcloud" # Default provider
|
||
|
|
--overwrite # Overwrite existing
|
||
|
|
--force (-f) # Force overwrite existing files
|
||
|
|
--check (-c) # Only check mode, no actual changes
|
||
|
|
--yes (-y) # Confirm task
|
||
|
|
--debug (-x) # Use Debug mode
|
||
|
|
--xm # Debug with PROVISIONING_METADATA
|
||
|
|
--xld # Log level with DEBUG PROVISIONING_LOG_LEVEL=debug
|
||
|
|
--metadata # Error with metadata (-xm)
|
||
|
|
--helpinfo (-h) # For more details use options "help" (no dashes)
|
||
|
|
--out: string # Print Output format: json, yaml, text (default)
|
||
|
|
]: nothing -> nothing {
|
||
|
|
if ($out | is-not-empty) {
|
||
|
|
$env.PROVISIONING_OUT = $out
|
||
|
|
$env.PROVISIONING_NO_TERMINAL = true
|
||
|
|
}
|
||
|
|
# Set NO_TITLES to prevent double display when called from main provisioning
|
||
|
|
$env.PROVISIONING_NO_TITLES = true
|
||
|
|
provisioning_init $helpinfo "module" $args
|
||
|
|
if $version or $v { ^$env.PROVISIONING_NAME -v ; exit }
|
||
|
|
if $info or $i { ^$env.PROVISIONING_NAME -i ; exit }
|
||
|
|
if $about {
|
||
|
|
_print (get_about_info)
|
||
|
|
exit
|
||
|
|
}
|
||
|
|
if $debug { $env.PROVISIONING_DEBUG = true }
|
||
|
|
if $metadata { $env.PROVISIONING_METADATA = true }
|
||
|
|
|
||
|
|
let task = if ($args | length) > 0 { ($args | get 0) } else { "" }
|
||
|
|
let ops = $"($env.PROVISIONING_ARGS? | default "") " | str replace $" ($task) " "" | str trim
|
||
|
|
|
||
|
|
$env.PROVISIONING_MODULE = "module"
|
||
|
|
|
||
|
|
match $task {
|
||
|
|
"h" | "help" => {
|
||
|
|
# Redirect to main categorized help system
|
||
|
|
exec $"($env.PROVISIONING_NAME)" help development --notitles
|
||
|
|
},
|
||
|
|
"discover" => {
|
||
|
|
let module_type = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
$type
|
||
|
|
}
|
||
|
|
let query = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
let parts = ($ops | split row " ")
|
||
|
|
if ($parts | length) > 1 { $parts | get 1 } else { "" }
|
||
|
|
} else {
|
||
|
|
""
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"🔍 Discovering ($module_type) modules..."
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "discover" $module_type]
|
||
|
|
if ($query | is-not-empty) { $cmd = ($cmd | append $query) }
|
||
|
|
if ($format | is-not-empty) { $cmd = ($cmd | append ["--format" $format]) }
|
||
|
|
if ($category | is-not-empty) { $cmd = ($cmd | append ["--category" $category]) }
|
||
|
|
if ($group | is-not-empty) { $cmd = ($cmd | append ["--group" $group]) }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"load" => {
|
||
|
|
let parts = ($ops | split row " ")
|
||
|
|
let module_type = if ($parts | length) > 0 and not (($parts | get 0) | str starts-with "-") {
|
||
|
|
$parts | get 0
|
||
|
|
} else {
|
||
|
|
$type
|
||
|
|
}
|
||
|
|
let workspace = if ($parts | length) > 1 and not (($parts | get 1) | str starts-with "-") {
|
||
|
|
$parts | get 1
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
let module_names = if ($parts | length) > 2 {
|
||
|
|
$parts | skip 2 | where { not ($in | str starts-with "-") }
|
||
|
|
} else {
|
||
|
|
$modules
|
||
|
|
}
|
||
|
|
|
||
|
|
if ($module_names | is-empty) {
|
||
|
|
print "❌ No modules specified for loading"
|
||
|
|
print "Use 'provisioning module help' for usage"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"📦 Loading ($module_names | length) ($module_type) into ($workspace) at layer ($layer)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "load" $module_type $workspace ...$module_names]
|
||
|
|
if ($layer | is-not-empty) { $cmd = ($cmd | append ["--layer" $layer]) }
|
||
|
|
if $validate { $cmd = ($cmd | append "--validate") }
|
||
|
|
if $force { $cmd = ($cmd | append "--force") }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"list" => {
|
||
|
|
let parts = ($ops | split row " ")
|
||
|
|
let module_type = if ($parts | length) > 0 and not (($parts | get 0) | str starts-with "-") {
|
||
|
|
$parts | get 0
|
||
|
|
} else {
|
||
|
|
$type
|
||
|
|
}
|
||
|
|
let workspace = if ($parts | length) > 1 and not (($parts | get 1) | str starts-with "-") {
|
||
|
|
$parts | get 1
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"📋 Listing ($module_type) in ($workspace) for layer ($layer)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "list" $module_type $workspace]
|
||
|
|
if ($layer | is-not-empty) { $cmd = ($cmd | append ["--layer" $layer]) }
|
||
|
|
if ($format | is-not-empty) { $cmd = ($cmd | append ["--format" $format]) }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"unload" => {
|
||
|
|
let parts = ($ops | split row " ")
|
||
|
|
let module_type = if ($parts | length) > 0 and not (($parts | get 0) | str starts-with "-") {
|
||
|
|
$parts | get 0
|
||
|
|
} else {
|
||
|
|
$type
|
||
|
|
}
|
||
|
|
let workspace = if ($parts | length) > 1 and not (($parts | get 1) | str starts-with "-") {
|
||
|
|
$parts | get 1
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
let module_name = if ($parts | length) > 2 and not (($parts | get 2) | str starts-with "-") {
|
||
|
|
$parts | get 2
|
||
|
|
} else {
|
||
|
|
""
|
||
|
|
}
|
||
|
|
|
||
|
|
if ($module_name | is-empty) {
|
||
|
|
print "❌ No module specified for unloading"
|
||
|
|
print "Use 'provisioning module help' for usage"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"🗑️ Unloading ($module_name) from ($workspace) at layer ($layer)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "unload" $module_type $workspace $module_name]
|
||
|
|
if ($layer | is-not-empty) { $cmd = ($cmd | append ["--layer" $layer]) }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"sync-kcl" => {
|
||
|
|
let infra = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
""
|
||
|
|
}
|
||
|
|
|
||
|
|
if ($infra | is-empty) {
|
||
|
|
print "❌ No infrastructure specified"
|
||
|
|
print "Use 'provisioning module sync-kcl <infra>' to sync KCL dependencies"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"🔄 Syncing KCL dependencies for ($infra)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "sync-kcl" $infra]
|
||
|
|
if ($manifest | is-not-empty) { $cmd = ($cmd | append ["--manifest" $manifest]) }
|
||
|
|
if $kcl { $cmd = ($cmd | append "--kcl") }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"init" => {
|
||
|
|
let workspace = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"🚀 Initializing workspace: ($workspace)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "init" $workspace]
|
||
|
|
if not ($modules | is-empty) { $cmd = ($cmd | append ["--modules" ($modules | to json)]) }
|
||
|
|
if ($template | is-not-empty) { $cmd = ($cmd | append ["--template" $template]) }
|
||
|
|
if ($provider | is-not-empty) { $cmd = ($cmd | append ["--provider" $provider]) }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"validate" => {
|
||
|
|
let workspace = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"🔍 Validating workspace: ($workspace)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
^nu $module_loader "validate" $workspace
|
||
|
|
},
|
||
|
|
"info" => {
|
||
|
|
let workspace = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
"."
|
||
|
|
}
|
||
|
|
|
||
|
|
print $"📊 Workspace information: ($workspace)"
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
^nu $module_loader "info" $workspace
|
||
|
|
},
|
||
|
|
"template" => {
|
||
|
|
let subcommand = if ($ops | is-not-empty) and not ($ops | str starts-with "-") {
|
||
|
|
($ops | split row " " | get 0)
|
||
|
|
} else {
|
||
|
|
""
|
||
|
|
}
|
||
|
|
|
||
|
|
let module_loader = ($env.PROVISIONING? | default "/usr/local/provisioning" | path join "core" "cli" "module-loader")
|
||
|
|
|
||
|
|
match $subcommand {
|
||
|
|
"list" => {
|
||
|
|
print $"📋 Listing templates (type: ($template_type))"
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "template" "list"]
|
||
|
|
if ($template_type | is-not-empty) { $cmd = ($cmd | append ["--template-type" $template_type]) }
|
||
|
|
if ($format | is-not-empty) { $cmd = ($cmd | append ["--format" $format]) }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
"apply" => {
|
||
|
|
let parts = ($ops | split row " " | skip 1)
|
||
|
|
let template_name = if ($parts | length) > 0 { $parts | get 0 } else { "" }
|
||
|
|
let target = if ($parts | length) > 1 { $parts | get 1 } else { "" }
|
||
|
|
|
||
|
|
if ($template_name | is-empty) or ($target | is-empty) {
|
||
|
|
print "❌ Missing template name or target"
|
||
|
|
print "Use 'provisioning module template apply <template> <target>'"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
|
||
|
|
if $dry_run {
|
||
|
|
print $"🔍 [DRY RUN] Would apply template ($template_name) to ($target)"
|
||
|
|
} else {
|
||
|
|
print $"📥 Applying template ($template_name) to ($target)"
|
||
|
|
}
|
||
|
|
|
||
|
|
mut cmd = [$module_loader "template" "apply" $template_name $target]
|
||
|
|
if ($override_file | is-not-empty) { $cmd = ($cmd | append ["--override-file" $override_file]) }
|
||
|
|
if $dry_run { $cmd = ($cmd | append "--dry-run") }
|
||
|
|
|
||
|
|
^nu ...$cmd
|
||
|
|
},
|
||
|
|
_ => {
|
||
|
|
print $"❌ Unknown template subcommand: ($subcommand)"
|
||
|
|
print "Available: list, apply"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
}
|
||
|
|
},
|
||
|
|
_ => {
|
||
|
|
print $"❌ Unknown task: ($task)"
|
||
|
|
print "Use 'provisioning module help' for available commands"
|
||
|
|
print ""
|
||
|
|
print "Available commands:"
|
||
|
|
print " discover <type> [query] - Discover available modules"
|
||
|
|
print " load <type> <workspace> <modules...> - Load modules into workspace"
|
||
|
|
print " list <type> <workspace> - List loaded modules"
|
||
|
|
print " unload <type> <workspace> <module> - Unload module from workspace"
|
||
|
|
print " sync-kcl <infra> - Sync KCL dependencies"
|
||
|
|
print " init <workspace> - Initialize workspace with modules"
|
||
|
|
print " validate <workspace> - Validate workspace integrity"
|
||
|
|
print " info <workspace> - Show workspace information"
|
||
|
|
print " template list - List available templates"
|
||
|
|
print " template apply <name> <target> - Apply template to target"
|
||
|
|
exit 1
|
||
|
|
}
|
||
|
|
}
|
||
|
|
}
|