provisioning-core/nulib/domain/workspace/sync.nu

241 lines
8.1 KiB
Text

use platform/user/config.nu [get-active-workspace get-workspace-path]
export def "workspace update" [
workspace_name?: string
--check (-c)
--force (-f)
--yes (-y)
--verbose (-v)
] {
let force_final = ($force or $yes)
let ws_name = if ($workspace_name | is-not-empty) {
$workspace_name
} else {
let active = (get-active-workspace)
if ($active == null or ($active | is-empty)) {
print $"(ansi red)✗(ansi reset) No active workspace"
print $"(ansi yellow)Specify workspace name or activate a workspace first(ansi reset)"
exit 1
}
$active
}
let workspace_path = (get-workspace-path $ws_name)
if ($workspace_path == null or not ($workspace_path | path exists)) {
print $"(ansi red)✗(ansi reset) Workspace not found: ($ws_name)"
exit 1
}
let parent1 = ($workspace_path | path dirname)
let parent2 = ($parent1 | path dirname)
let prov_root = if (($parent1 | path join "provisioning" | path exists)) {
$parent1
} else if (($parent2 | path join "provisioning" | path exists)) {
$parent2
} else {
""
}
if ($prov_root | is-empty) {
print $"(ansi red)✗(ansi reset) Cannot find provisioning root"
print " Expected: <root>/provisioning"
print $" Workspace: ($workspace_path)"
exit 1
}
print $"(ansi cyan)🔄 Updating workspace...(ansi reset)"
print $" Workspace: (ansi green)($ws_name)(ansi reset)"
print $" Path: ($workspace_path)"
print ""
let updates = [
{name: ".providers", source: ($prov_root | path join "provisioning/catalog/providers"), target: ($workspace_path | path join ".providers")}
{name: ".clusters", source: ($prov_root | path join "provisioning/catalog/clusters"), target: ($workspace_path | path join ".clusters")}
{name: ".taskservs", source: ($prov_root | path join "provisioning/catalog/taskservs"), target: ($workspace_path | path join ".taskservs")}
{name: ".nickel", source: ($prov_root | path join "provisioning/nickel"), target: ($workspace_path | path join ".nickel")}
]
print $"(ansi green_bold)Directories to update:(ansi reset)"
print ""
for update in $updates {
let src_exists = ($update.source | path exists)
let status = if $src_exists { $"(ansi green)✓(ansi reset)" } else { $"(ansi yellow)⊘(ansi reset)" }
print $" ($status) ($update.name)"
if $verbose {
print $" Source: ($update.source)"
print $" Target: ($update.target)"
}
}
print ""
if $check {
print $"(ansi cyan)[CHECK MODE](ansi reset) No changes will be made"
return
}
if not $force_final {
print $"(ansi yellow)⚠ This will overwrite existing directories(ansi reset)"
print ""
print "To proceed, use: provisioning ws update --yes"
return
}
print ""
print $"(ansi cyan)Updating...(ansi reset)"
print ""
for update in $updates {
let src_exists = ($update.source | path exists)
if not $src_exists {
print $" (ansi yellow)⊘(ansi reset) Skipped: ($update.name) \(source-not-found\)"
continue
}
if ($update.target | path exists) { rm -rf $update.target }
cp -r $update.source $update.target
print $" (ansi green)✓(ansi reset) Updated: ($update.name)"
if ($update.name == ".providers") {
_fix-provider-nickel-paths $update.target $verbose
}
}
print ""
print $"(ansi green)✓(ansi reset) Workspace update complete"
}
def _fix-provider-nickel-paths [providers_path: string, verbose: bool] {
let nickel_mods = (glob $"($providers_path)/**/nickel.mod")
if ($nickel_mods | is-empty) { return }
for mod_file in $nickel_mods {
if not ($mod_file | path exists) { continue }
let content = (open $mod_file)
let updated = (
$content
| str replace --all '{ path = "../../../../nickel' '{ path = "../../../.nickel/packages/provisioning'
| str replace --all '{ path = "../../../../.nickel' '{ path = "../../../.nickel/packages/provisioning'
)
if ($content != $updated) {
$updated | save -f $mod_file
if $verbose { print $" Fixed Nickel path in: ($mod_file)" }
}
}
}
export def "workspace check-updates" [
workspace_name?: string
--verbose (-v)
] {
let ws_name = if ($workspace_name | is-not-empty) {
$workspace_name
} else {
let active = (get-active-workspace)
if ($active == null or ($active | is-empty)) {
print $"(ansi red)✗(ansi reset) No active workspace"
exit 1
}
$active
}
let workspace_path = (get-workspace-path $ws_name)
if ($workspace_path == null or not ($workspace_path | path exists)) {
print $"(ansi red)✗(ansi reset) Workspace not found: ($ws_name)"
exit 1
}
print $"(ansi cyan)📋 Checking workspace updates...(ansi reset)"
print $" Workspace: (ansi green)($ws_name)(ansi reset)"
print $" Path: ($workspace_path)"
print ""
let checks = [
{name: ".providers", path: ($workspace_path | path join ".providers")}
{name: ".clusters", path: ($workspace_path | path join ".clusters")}
{name: ".taskservs", path: ($workspace_path | path join ".taskservs")}
{name: ".nickel", path: ($workspace_path | path join ".nickel")}
{name: "config", path: ($workspace_path | path join "config")}
]
let status_list = ($checks | each {|check|
let exists = ($check.path | path exists)
if $exists {
print $" (ansi green)✓(ansi reset) ($check.name) - present"
} else {
print $" (ansi yellow)⊘(ansi reset) ($check.name) - missing"
}
if $verbose { print $" Path: ($check.path)" }
{name: $check.name, exists: $exists}
})
let missing_count = ($status_list | where {|s| $s.exists == false} | length)
print ""
if $missing_count == 0 {
print $"(ansi green)✓(ansi reset) All directories are present and up-to-date"
} else {
let label = if $missing_count == 1 { "directory needs" } else { "directories need" }
print $"(ansi yellow)⚠(ansi reset) ($missing_count) ($label) updating"
print ""
print $"(ansi cyan)Update with:(ansi reset) provisioning workspace update"
}
}
export def "workspace sync-modules" [
workspace_name?: string
--check (-c)
--force (-f)
--verbose (-v)
] {
let ws_name = if ($workspace_name | is-not-empty) {
$workspace_name
} else {
let active = (get-active-workspace)
if ($active == null or ($active | is-empty)) {
print $"(ansi red)✗(ansi reset) No active workspace"
exit 1
}
$active
}
let workspace_path = (get-workspace-path $ws_name)
if ($workspace_path == null or not ($workspace_path | path exists)) {
print $"(ansi red)✗(ansi reset) Workspace not found: ($ws_name)"
exit 1
}
let config_path = ($workspace_path | path join "config")
if not ($config_path | path exists) {
print $"(ansi red)✗(ansi reset) Workspace config not found"
exit 1
}
print $"(ansi cyan)🔄 Syncing workspace modules...(ansi reset)"
print $" Workspace: (ansi green)($ws_name)(ansi reset)"
print $" Path: ($workspace_path)"
print ""
if (($config_path | path join "providers") | path exists) {
print "Configured Providers:"
ls ($config_path | path join "providers")
| where {|f| ($f.type == "file") and ($f.name | str ends-with ".toml")}
| each {|f| print $" - ($f.name)"} | ignore
}
if (($config_path | path join "clusters") | path exists) {
print ""
print "Configured Clusters:"
ls ($config_path | path join "clusters")
| where {|f| ($f.type == "file") and ($f.name | str ends-with ".toml")}
| each {|f| print $" - ($f.name)"} | ignore
}
print ""
print $"(ansi green)✓(ansi reset) Module sync complete"
}