nushell-plugins/scripts/register-provisioning-plugins.nu
Jesús Pérez 4b92aa764a
Some checks failed
Build and Test / Validate Setup (push) Has been cancelled
Build and Test / Build (darwin-amd64) (push) Has been cancelled
Build and Test / Build (darwin-arm64) (push) Has been cancelled
Build and Test / Build (linux-amd64) (push) Has been cancelled
Build and Test / Build (windows-amd64) (push) Has been cancelled
Build and Test / Build (linux-arm64) (push) Has been cancelled
Build and Test / Security Audit (push) Has been cancelled
Build and Test / Package Results (push) Has been cancelled
Build and Test / Quality Gate (push) Has been cancelled
implements a production-ready bootstrap installer with comprehensive error handling, version-agnostic archive extraction, and clear user messaging. All improvements follow DRY principles using symlink-based architecture for single-source-of-truth maintenance
2025-12-11 22:04:54 +00:00

292 lines
8.9 KiB
Plaintext

#!/usr/bin/env nu
# Register provisioning critical plugins with Nushell
#
# This script registers the three critical provisioning plugins:
# - nu_plugin_auth: JWT authentication with system keyring
# - nu_plugin_kms: Multi-backend KMS encryption
# - nu_plugin_orchestrator: Local orchestrator operations
#
# Usage:
# nu scripts/register-provisioning-plugins.nu
# nu scripts/register-provisioning-plugins.nu --verify
# nu scripts/register-provisioning-plugins.nu --force
use std log
# Plugin metadata
const PROVISIONING_PLUGINS = [
{
name: "nu_plugin_auth"
description: "JWT authentication with system keyring"
commands: ["auth login", "auth logout", "auth verify", "auth sessions", "auth mfa enroll", "auth mfa verify"]
priority: 1
}
{
name: "nu_plugin_kms"
description: "Multi-backend KMS encryption (RustyVault, Age, AWS, Vault, Cosmian)"
commands: ["kms encrypt", "kms decrypt", "kms generate-key", "kms status", "kms list-backends"]
priority: 2
}
{
name: "nu_plugin_orchestrator"
description: "Local orchestrator operations (10-30x faster than HTTP)"
commands: ["orch status", "orch tasks", "orch validate", "orch submit", "orch monitor"]
priority: 3
}
]
# Get plugin binary path for the current platform
def get-plugin-path [plugin_name: string, base_dir: path]: nothing -> path {
let release_path = ($base_dir | path join $plugin_name "target" "release" $plugin_name)
let debug_path = ($base_dir | path join $plugin_name "target" "debug" $plugin_name)
# Prefer release build
if ($release_path | path exists) {
return $release_path
}
# Fall back to debug build
if ($debug_path | path exists) {
return $debug_path
}
# Not found
return ""
}
# Check if plugin is already registered
def is-plugin-registered [plugin_name: string]: nothing -> bool {
let registered = (plugin list | where name == $plugin_name)
($registered | length) > 0
}
# Register a single plugin
def register-plugin [
plugin_name: string
plugin_path: path
--force: bool = false
]: nothing -> record {
let start_time = (date now)
# Check if already registered
if (not $force) and (is-plugin-registered $plugin_name) {
return {
name: $plugin_name
status: "already_registered"
message: "Plugin already registered (use --force to re-register)"
duration_ms: 0
}
}
# Check if plugin binary exists
if ($plugin_path | is-empty) or (not ($plugin_path | path exists)) {
return {
name: $plugin_name
status: "not_found"
message: $"Plugin binary not found at expected location"
duration_ms: 0
}
}
# Register the plugin
try {
plugin add $plugin_path
let duration = ((date now) - $start_time) | into int | $in / 1_000_000
return {
name: $plugin_name
status: "registered"
message: "Plugin registered successfully"
path: $plugin_path
duration_ms: $duration
}
} catch { |err|
let duration = ((date now) - $start_time) | into int | $in / 1_000_000
return {
name: $plugin_name
status: "error"
message: $"Failed to register: ($err.msg)"
duration_ms: $duration
}
}
}
# Verify plugin registration by checking commands
def verify-plugin-registration [plugin_name: string]: nothing -> record {
let plugin_info = (PROVISIONING_PLUGINS | where name == $plugin_name | first)
if ($plugin_info == null) {
return {
name: $plugin_name
verified: false
message: "Unknown plugin"
}
}
# Check if plugin is in plugin list
let registered = (plugin list | where name == $plugin_name)
if ($registered | length) == 0 {
return {
name: $plugin_name
verified: false
message: "Plugin not found in registry"
}
}
return {
name: $plugin_name
verified: true
description: $plugin_info.description
commands: $plugin_info.commands
message: "Plugin verified successfully"
}
}
# Main entry point
def main [
--force (-f) # Force re-registration even if already registered
--verify (-v) # Verify registration after completion
--quiet (-q) # Suppress output
]: nothing -> nothing {
let base_dir = ($env.PWD | path dirname | path dirname | path dirname | path join "plugins" "nushell-plugins")
# Fallback: try current directory if we're already in nushell-plugins
let base_dir = if ($base_dir | path join "nu_plugin_auth" | path exists) {
$base_dir
} else if (($env.PWD | path join "nu_plugin_auth") | path exists) {
$env.PWD
} else {
# Try to find from script location
let script_dir = ($env.CURRENT_FILE? | default $env.PWD | path dirname)
let parent = ($script_dir | path dirname)
if ($parent | path join "nu_plugin_auth" | path exists) {
$parent
} else {
$env.PWD
}
}
if not $quiet {
print ""
print "======================================================"
print " Provisioning Plugins Registration"
print "======================================================"
print ""
print $"Base directory: ($base_dir)"
print ""
}
mut results = []
mut registered_count = 0
mut failed_count = 0
# Register each plugin
for plugin_info in $PROVISIONING_PLUGINS {
let plugin_name = $plugin_info.name
let plugin_path = (get-plugin-path $plugin_name $base_dir)
if not $quiet {
print $"Registering ($plugin_name)..."
}
let result = (register-plugin $plugin_name $plugin_path --force=$force)
$results = ($results | append $result)
match $result.status {
"registered" | "already_registered" => {
$registered_count = ($registered_count + 1)
if not $quiet {
if $result.status == "registered" {
print $" [OK] ($result.message) \(($result.duration_ms)ms\)"
} else {
print $" [SKIP] ($result.message)"
}
}
}
"not_found" => {
$failed_count = ($failed_count + 1)
if not $quiet {
print $" [WARN] ($result.message)"
print $" Expected at: ($base_dir)/($plugin_name)/target/release/($plugin_name)"
}
}
"error" => {
$failed_count = ($failed_count + 1)
if not $quiet {
print $" [ERROR] ($result.message)"
}
}
_ => {
$failed_count = ($failed_count + 1)
}
}
}
if not $quiet {
print ""
print "------------------------------------------------------"
print $"Summary: ($registered_count) registered, ($failed_count) failed"
print "------------------------------------------------------"
}
# Verify if requested
if $verify {
if not $quiet {
print ""
print "Verifying plugin registration..."
print ""
}
for plugin_info in $PROVISIONING_PLUGINS {
let verification = (verify-plugin-registration $plugin_info.name)
if not $quiet {
if $verification.verified {
print $"[OK] ($verification.name): ($verification.description)"
print $" Commands: ($verification.commands | str join ', ')"
} else {
print $"[FAIL] ($verification.name): ($verification.message)"
}
}
}
}
if not $quiet {
print ""
print "Plugin commands available:"
print " - auth login/logout/verify/sessions/mfa"
print " - kms encrypt/decrypt/generate-key/status/list-backends"
print " - orch status/tasks/validate/submit/monitor"
print ""
print "Verify with: plugin list"
print ""
}
}
# Export for use as module
export def "provisioning-plugins register" [--force (-f), --verify (-v), --quiet (-q)] {
main --force=$force --verify=$verify --quiet=$quiet
}
export def "provisioning-plugins list" [] {
PROVISIONING_PLUGINS
}
export def "provisioning-plugins status" [] {
mut status_list = []
for plugin_info in $PROVISIONING_PLUGINS {
let registered = (is-plugin-registered $plugin_info.name)
$status_list = ($status_list | append {
name: $plugin_info.name
registered: $registered
description: $plugin_info.description
commands: ($plugin_info.commands | length)
})
}
$status_list
}