218 lines
5.5 KiB
Text
218 lines
5.5 KiB
Text
# GitOps module for event-driven deployments
|
|
#
|
|
# Manages declarative GitOps rules and event-driven automation.
|
|
# Follows NUSHELL_GUIDELINES.md: single purpose, explicit types, early return
|
|
|
|
# Load GitOps rules from configuration file
|
|
#
|
|
# Parameters:
|
|
# config_path: string - Path to rules configuration file
|
|
#
|
|
# Returns: table - Parsed GitOps rules
|
|
# Errors: propagates if file not found or invalid format
|
|
export def gitops-rules [config_path: string] {
|
|
# Validate input early
|
|
if (not ($config_path | path exists)) {
|
|
error make {msg: $"Config file not found: [$config_path]"}
|
|
}
|
|
|
|
let result = (do { open $config_path } | complete)
|
|
if $result.exit_code != 0 {
|
|
error make {msg: $"Failed to read config file: [$config_path]"}
|
|
}
|
|
let content = $result.stdout
|
|
|
|
# Return rules from config (assuming YAML/JSON structure)
|
|
if ($content | type) == "table" {
|
|
$content
|
|
} else if ($content | type) == "record" {
|
|
if ($content | has rules) {
|
|
$content.rules
|
|
} else {
|
|
error make {msg: "Config must contain 'rules' field"}
|
|
}
|
|
} else {
|
|
error make {msg: "Invalid config format"}
|
|
}
|
|
}
|
|
|
|
# Watch for Git events and trigger deployments
|
|
#
|
|
# Parameters:
|
|
# --provider: string - Git provider (github, gitlab, gitea)
|
|
# --webhook-port: int - Webhook listener port
|
|
# --check: bool - Dry-run mode
|
|
#
|
|
# Returns: record - Watcher configuration
|
|
# Errors: propagates if port unavailable or provider invalid
|
|
export def gitops-watch [
|
|
--provider: string = "github"
|
|
--webhook-port: int = 8080
|
|
--check = false
|
|
] {
|
|
# Validate inputs early
|
|
let valid_providers = ["github", "gitlab", "gitea"]
|
|
if (not ($provider | inside $valid_providers)) {
|
|
error make {msg: $"Invalid provider: [$provider]. Must be one of: [$valid_providers]"}
|
|
}
|
|
|
|
if ($webhook_port <= 1024 or $webhook_port > 65535) {
|
|
error make {msg: $"Invalid port: [$webhook_port]. Must be between 1024 and 65535"}
|
|
}
|
|
|
|
if $check {
|
|
return {
|
|
provider: $provider
|
|
webhook_port: $webhook_port
|
|
status: "would-start"
|
|
}
|
|
}
|
|
|
|
{
|
|
provider: $provider
|
|
webhook_port: $webhook_port
|
|
status: "listening"
|
|
started_at: (date now | into string)
|
|
}
|
|
}
|
|
|
|
# Manually trigger a GitOps deployment
|
|
#
|
|
# Parameters:
|
|
# rule_name: string - Name of the rule to trigger
|
|
# --environment: string - Target environment (dev, staging, prod)
|
|
# --check: bool - Dry-run mode
|
|
#
|
|
# Returns: record - Deployment info
|
|
# Errors: propagates if rule not found
|
|
export def gitops-trigger [
|
|
rule_name: string
|
|
--environment: string = "dev"
|
|
--check = false
|
|
] {
|
|
# Validate inputs early
|
|
if ($rule_name | str trim) == "" {
|
|
error make {msg: "Rule name cannot be empty"}
|
|
}
|
|
|
|
let valid_envs = ["dev", "staging", "prod"]
|
|
if (not ($environment | inside $valid_envs)) {
|
|
error make {msg: $"Invalid environment: [$environment]. Must be one of: [$valid_envs]"}
|
|
}
|
|
|
|
if $check {
|
|
return {
|
|
rule: $rule_name
|
|
environment: $environment
|
|
status: "would-deploy"
|
|
}
|
|
}
|
|
|
|
{
|
|
rule: $rule_name
|
|
environment: $environment
|
|
status: "triggered"
|
|
deployment_id: (
|
|
$"deploy-($rule_name)-($environment)-" + (date now | format date "%Y%m%d%H%M%S")
|
|
)
|
|
timestamp: (date now | into string)
|
|
}
|
|
}
|
|
|
|
# Get event types for GitOps triggers
|
|
#
|
|
# Returns: list - Supported event types
|
|
# Errors: none
|
|
export def gitops-event-types [] {
|
|
[
|
|
"push"
|
|
"pull-request"
|
|
"webhook"
|
|
"scheduled"
|
|
"health-check"
|
|
"manual"
|
|
]
|
|
}
|
|
|
|
# Configure GitOps rule
|
|
#
|
|
# Parameters:
|
|
# name: string - Rule name
|
|
# repo: string - Repository URL
|
|
# branch: string - Target branch
|
|
# --provider: string - Git provider
|
|
# --command: string - Deployment command
|
|
#
|
|
# Returns: record - Rule configuration
|
|
# Errors: propagates if repo URL invalid
|
|
export def gitops-rule-config [
|
|
name: string
|
|
repo: string
|
|
branch: string
|
|
--provider: string = "github"
|
|
--command: string = "provisioning deploy"
|
|
] {
|
|
# Validate inputs early
|
|
if ($name | str trim) == "" {
|
|
error make {msg: "Rule name cannot be empty"}
|
|
}
|
|
|
|
if ($repo | str trim) == "" {
|
|
error make {msg: "Repository URL cannot be empty"}
|
|
}
|
|
|
|
if ($branch | str trim) == "" {
|
|
error make {msg: "Branch cannot be empty"}
|
|
}
|
|
|
|
{
|
|
name: $name
|
|
provider: $provider
|
|
repository: $repo
|
|
branch: $branch
|
|
command: $command
|
|
enabled: true
|
|
created_at: (date now | into string)
|
|
}
|
|
}
|
|
|
|
# List active GitOps deployments
|
|
#
|
|
# Parameters:
|
|
# --status: string - Filter by status (triggered, running, completed, failed)
|
|
#
|
|
# Returns: table - Active deployments
|
|
# Errors: none
|
|
export def gitops-deployments [--status: string = ""] {
|
|
let all_deployments = [
|
|
{
|
|
id: "deploy-app-prod-20250115120000"
|
|
rule: "deploy-app"
|
|
environment: "prod"
|
|
status: "completed"
|
|
created_at: "2025-01-15T12:00:00"
|
|
duration_secs: 180
|
|
}
|
|
]
|
|
|
|
if ($status | str trim) == "" {
|
|
$all_deployments
|
|
} else {
|
|
$all_deployments | where status == $status
|
|
}
|
|
}
|
|
|
|
# Get GitOps status and statistics
|
|
#
|
|
# Returns: record - Overall status information
|
|
# Errors: none
|
|
export def gitops-status [] {
|
|
{
|
|
active_rules: 5
|
|
total_deployments: 42
|
|
successful: 40
|
|
failed: 2
|
|
last_deployment: "2025-01-15T12:00:00"
|
|
health: "healthy"
|
|
}
|
|
}
|