288 lines
8.9 KiB
Plaintext
Executable File
288 lines
8.9 KiB
Plaintext
Executable File
#!/usr/bin/env nu
|
|
|
|
# Provider Management CLI
|
|
# Manages cloud providers for infrastructures with KCL integration
|
|
# Author: JesusPerezLorenzo
|
|
# Date: 2025-09-29
|
|
|
|
use ../nulib/lib_provisioning/kcl_module_loader.nu *
|
|
|
|
# Main providers command
|
|
def main [] {
|
|
print_help
|
|
}
|
|
|
|
# List all available providers
|
|
export def "main list" [
|
|
--kcl # Show KCL module information (always enabled)
|
|
--format: string = "table" # Output format: table, json, yaml
|
|
] {
|
|
# Always use KCL module loader
|
|
let providers = (discover-kcl-modules "providers")
|
|
|
|
match $format {
|
|
"json" => ($providers | to json)
|
|
"yaml" => ($providers | to yaml)
|
|
_ => ($providers | table)
|
|
}
|
|
}
|
|
|
|
# Show detailed information about a provider
|
|
export def "main info" [
|
|
provider: string # Provider name
|
|
--kcl # Show KCL schema information
|
|
] {
|
|
print $"📋 Provider Information: ($provider)"
|
|
print ""
|
|
|
|
let providers = (discover-kcl-modules "providers")
|
|
let provider_info = ($providers | where name == $provider)
|
|
|
|
if ($provider_info | is-empty) {
|
|
print $"❌ Provider not found: ($provider)"
|
|
return
|
|
}
|
|
|
|
let info = ($provider_info | first)
|
|
|
|
print $" Name: ($info.name)"
|
|
print $" Type: ($info.type)"
|
|
print $" Path: ($info.path)"
|
|
print $" Has KCL: ($info.has_kcl)"
|
|
|
|
if $kcl and $info.has_kcl {
|
|
print ""
|
|
print " KCL Module:"
|
|
print $" Module Name: ($info.kcl_module_name)"
|
|
print $" KCL Path: ($info.kcl_path)"
|
|
print $" Version: ($info.version)"
|
|
print $" Edition: ($info.edition)"
|
|
|
|
# Check for kcl.mod file
|
|
let kcl_mod = ($info.kcl_path | path join "kcl.mod")
|
|
if ($kcl_mod | path exists) {
|
|
print ""
|
|
print $" kcl.mod content:"
|
|
open $kcl_mod | lines | each {|line| print $" ($line)"}
|
|
}
|
|
}
|
|
}
|
|
|
|
# Install a provider for an infrastructure
|
|
export def "main install" [
|
|
provider: string, # Provider name (e.g., upcloud, aws, local)
|
|
infra: string, # Infrastructure name or path
|
|
--version: string = "0.0.1", # Provider version
|
|
--manifest: string = "providers.manifest.yaml" # Manifest file name
|
|
] {
|
|
# Resolve infrastructure path
|
|
let infra_path = resolve-infra-path $infra
|
|
|
|
if ($infra_path | is-empty) {
|
|
print $"❌ Infrastructure not found: ($infra)"
|
|
return
|
|
}
|
|
|
|
# Use library function to install provider
|
|
install-provider $provider $infra_path --version $version
|
|
|
|
print ""
|
|
print $"💡 Next steps:"
|
|
print $" 1. Check the manifest: ($infra_path)/($manifest)"
|
|
print $" 2. Update server definitions to use ($provider)"
|
|
print $" 3. Run: kcl run defs/servers.k"
|
|
}
|
|
|
|
# Remove a provider from an infrastructure
|
|
export def "main remove" [
|
|
provider: string, # Provider name
|
|
infra: string, # Infrastructure name or path
|
|
--force # Force removal without confirmation
|
|
] {
|
|
# Resolve infrastructure path
|
|
let infra_path = resolve-infra-path $infra
|
|
|
|
if ($infra_path | is-empty) {
|
|
print $"❌ Infrastructure not found: ($infra)"
|
|
return
|
|
}
|
|
|
|
# Confirmation unless forced
|
|
if not $force {
|
|
print $"⚠️ This will remove provider ($provider) from ($infra)"
|
|
print " KCL dependencies will be updated."
|
|
let response = (input "Continue? (y/N): ")
|
|
|
|
if ($response | str downcase) != "y" {
|
|
print "❌ Cancelled"
|
|
return
|
|
}
|
|
}
|
|
|
|
# Use library function to remove provider
|
|
remove-provider $provider $infra_path
|
|
}
|
|
|
|
# List installed providers for an infrastructure
|
|
export def "main installed" [
|
|
infra: string, # Infrastructure name or path
|
|
--format: string = "table" # Output format
|
|
] {
|
|
# Resolve infrastructure path
|
|
let infra_path = resolve-infra-path $infra
|
|
|
|
if ($infra_path | is-empty) {
|
|
print $"❌ Infrastructure not found: ($infra)"
|
|
return
|
|
}
|
|
|
|
let manifest_path = ($infra_path | path join "providers.manifest.yaml")
|
|
|
|
if not ($manifest_path | path exists) {
|
|
print $"❌ No providers.manifest.yaml found in ($infra)"
|
|
return
|
|
}
|
|
|
|
let manifest = (open $manifest_path)
|
|
let providers = if ($manifest | get providers? | is-not-empty) {
|
|
$manifest | get providers
|
|
} else if ($manifest | get loaded_providers? | is-not-empty) {
|
|
$manifest | get loaded_providers
|
|
} else {
|
|
[]
|
|
}
|
|
|
|
print $"📦 Installed providers for ($infra):"
|
|
print ""
|
|
|
|
match $format {
|
|
"json" => ($providers | to json)
|
|
"yaml" => ($providers | to yaml)
|
|
_ => ($providers | table)
|
|
}
|
|
}
|
|
|
|
# Validate provider installation for an infrastructure
|
|
export def "main validate" [
|
|
infra: string # Infrastructure name or path
|
|
] {
|
|
print $"🔍 Validating providers for ($infra)..."
|
|
print ""
|
|
|
|
# Resolve infrastructure path
|
|
let infra_path = resolve-infra-path $infra
|
|
|
|
if ($infra_path | is-empty) {
|
|
print $"❌ Infrastructure not found: ($infra)"
|
|
return
|
|
}
|
|
|
|
mut validation_errors = []
|
|
|
|
# Check manifest exists
|
|
let manifest_path = ($infra_path | path join "providers.manifest.yaml")
|
|
if not ($manifest_path | path exists) {
|
|
$validation_errors = ($validation_errors | append "providers.manifest.yaml not found")
|
|
} else {
|
|
# Check each provider in manifest
|
|
let manifest = (open $manifest_path)
|
|
let providers = ($manifest | get providers)
|
|
|
|
for provider in $providers {
|
|
print $" Checking ($provider.name)..."
|
|
|
|
# Check if provider exists
|
|
let available = (discover-kcl-modules "providers" | where name == $provider.name)
|
|
|
|
if ($available | is-empty) {
|
|
$validation_errors = ($validation_errors | append $"Provider not found: ($provider.name)")
|
|
print $" ❌ Not found in extensions"
|
|
} else {
|
|
let provider_info = ($available | first)
|
|
|
|
# Check if symlink exists
|
|
let modules_dir = ($infra_path | path join ".kcl-modules")
|
|
let link_path = ($modules_dir | path join $provider_info.kcl_module_name)
|
|
|
|
if not ($link_path | path exists) {
|
|
$validation_errors = ($validation_errors | append $"Symlink missing: ($link_path)")
|
|
print $" ❌ Symlink not found"
|
|
} else {
|
|
print $" ✓ OK"
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
# Check kcl.mod
|
|
let kcl_mod_path = ($infra_path | path join "kcl.mod")
|
|
if not ($kcl_mod_path | path exists) {
|
|
$validation_errors = ($validation_errors | append "kcl.mod not found")
|
|
}
|
|
|
|
print ""
|
|
|
|
# Report results
|
|
if ($validation_errors | is-empty) {
|
|
print "✅ Validation passed - all providers correctly installed"
|
|
return true
|
|
} else {
|
|
print "❌ Validation failed:"
|
|
for error in $validation_errors {
|
|
print $" • ($error)"
|
|
}
|
|
return false
|
|
}
|
|
}
|
|
|
|
# Helper: Resolve infrastructure path
|
|
def resolve-infra-path [infra: string]: nothing -> string {
|
|
if ($infra | path exists) {
|
|
return $infra
|
|
}
|
|
|
|
# Try workspace/infra path
|
|
let workspace_path = $"workspace/infra/($infra)"
|
|
if ($workspace_path | path exists) {
|
|
return $workspace_path
|
|
}
|
|
|
|
# Try absolute workspace path
|
|
let abs_workspace_path = $"/Users/Akasha/project-provisioning/workspace/infra/($infra)"
|
|
if ($abs_workspace_path | path exists) {
|
|
return $abs_workspace_path
|
|
}
|
|
|
|
return ""
|
|
}
|
|
|
|
# Helper: Print help
|
|
def print_help [] {
|
|
print "Provider Management CLI"
|
|
print ""
|
|
print "Usage: providers <command> [options]"
|
|
print ""
|
|
print "COMMANDS:"
|
|
print " list [--kcl] [--format <fmt>] - List all available providers"
|
|
print " info <provider> [--kcl] - Show detailed provider information"
|
|
print " install <provider> <infra> [--version <v>] - Install provider for infrastructure"
|
|
print " remove <provider> <infra> [--force] - Remove provider from infrastructure"
|
|
print " installed <infra> [--format <fmt>] - List installed providers"
|
|
print " validate <infra> - Validate provider installation"
|
|
print ""
|
|
print "OPTIONS:"
|
|
print " --kcl Show KCL module information"
|
|
print " --format <fmt> Output format: table, json, yaml"
|
|
print " --force Skip confirmation prompts"
|
|
print " --version <v> Specify provider version (default: 0.0.1)"
|
|
print ""
|
|
print "EXAMPLES:"
|
|
print " providers list --kcl"
|
|
print " providers info upcloud --kcl"
|
|
print " providers install upcloud wuji"
|
|
print " providers installed wuji"
|
|
print " providers validate wuji"
|
|
print " providers remove aws wuji --force"
|
|
print ""
|
|
print "See also: module-loader sync-kcl"
|
|
} |