provisioning/tools/build/compile-platform.nu

220 lines
7.0 KiB
Plaintext
Raw Normal View History

2025-10-07 11:12:02 +01:00
#!/usr/bin/env nu
# Platform compilation tool - compiles all Rust components for distribution
#
# Compiles:
# - orchestrator (provisioning-orchestrator binary)
# - control-center (control center API)
# - control-center-ui (web UI)
# - mcp-server-rust (MCP integration)
use std log
def main [
--target: string = "x86_64-unknown-linux-gnu" # Target platform
--release: bool = false # Build in release mode
--features: string = "" # Comma-separated features to enable
--output-dir: string = "dist/platform" # Output directory for binaries
--verbose: bool = false # Enable verbose logging
--clean: bool = false # Clean before building
] -> record {
let repo_root = ($env.PWD | path dirname | path dirname | path dirname)
let build_config = {
target: $target
release: $release
features: ($features | if $in == "" { [] } else { $in | split column "," | get column1 })
output_dir: ($output_dir | path expand)
verbose: $verbose
clean: $clean
}
log info $"Starting platform compilation with config: ($build_config)"
# Ensure output directory exists
mkdir ($build_config.output_dir)
let rust_projects = [
{
name: "orchestrator"
path: ($repo_root | path join "orchestrator")
binary: "provisioning-orchestrator"
features: ["surrealdb"]
},
{
name: "control-center"
path: ($repo_root | path join "control-center")
binary: "control-center"
features: []
},
{
name: "control-center-ui"
path: ($repo_root | path join "control-center-ui")
binary: "control-center-ui"
features: []
},
{
name: "mcp-server"
path: ($repo_root | path join "provisioning" "mcp-server-rust")
binary: "mcp-server-rust"
features: []
}
]
let results = $rust_projects | each {|project|
compile_rust_project $project $build_config $repo_root
}
let summary = {
total: ($results | length)
successful: ($results | where status == "success" | length)
failed: ($results | where status == "failed" | length)
build_config: $build_config
results: $results
}
if $summary.failed > 0 {
log error $"Platform compilation completed with ($summary.failed) failures"
exit 1
} else {
log info $"Platform compilation completed successfully - all ($summary.total) components built"
}
return $summary
}
# Compile a single Rust project
def compile_rust_project [
project: record
build_config: record
repo_root: string
] -> record {
log info $"Compiling ($project.name)..."
if not ($project.path | path exists) {
log warning $"Project path does not exist: ($project.path)"
return {
project: $project.name
status: "skipped"
reason: "path not found"
binary_path: null
duration: 0
}
}
cd ($project.path)
let start_time = (date now)
try {
# Clean if requested
if $build_config.clean {
log info $"Cleaning ($project.name)..."
cargo clean
}
# Build cargo command
let mut cargo_cmd = ["cargo", "build"]
if $build_config.release {
$cargo_cmd = ($cargo_cmd | append "--release")
}
if $build_config.target != "native" {
$cargo_cmd = ($cargo_cmd | append ["--target", $build_config.target])
}
# Add project-specific features
let all_features = ($build_config.features | append $project.features | uniq)
if ($all_features | length) > 0 {
$cargo_cmd = ($cargo_cmd | append ["--features", ($all_features | str join ",")])
}
if $build_config.verbose {
$cargo_cmd = ($cargo_cmd | append "--verbose")
}
# Execute build
let build_result = (run-external --redirect-combine $cargo_cmd.0 ...$cargo_cmd.1..)
# Determine binary path
let profile = if $build_config.release { "release" } else { "debug" }
let target_dir = if $build_config.target == "native" {
$"target/($profile)"
} else {
$"target/($build_config.target)/($profile)"
}
let binary_path = ($project.path | path join $target_dir $project.binary)
if ($binary_path | path exists) {
# Copy binary to output directory
let output_binary = ($build_config.output_dir | path join $"($project.name)-($build_config.target)")
cp $binary_path $output_binary
log info $"Successfully compiled ($project.name) -> ($output_binary)"
{
project: $project.name
status: "success"
binary_path: $output_binary
source_path: $binary_path
duration: ((date now) - $start_time)
size: (ls $output_binary | get 0.size)
}
} else {
log error $"Binary not found after build: ($binary_path)"
{
project: $project.name
status: "failed"
reason: "binary not found"
binary_path: null
duration: ((date now) - $start_time)
}
}
} catch {|err|
log error $"Failed to compile ($project.name): ($err.msg)"
{
project: $project.name
status: "failed"
reason: $err.msg
binary_path: null
duration: ((date now) - $start_time)
}
}
}
# Show build environment info
def "main info" [] {
{
rust_version: (rustc --version)
cargo_version: (cargo --version)
available_targets: (rustup target list --installed)
default_target: (rustc -vV | grep "host:" | str replace "host: " "")
}
}
# List available Rust projects
def "main list" [] {
let repo_root = ($env.PWD | path dirname | path dirname | path dirname)
[
{ name: "orchestrator", path: ($repo_root | path join "orchestrator"), status: (check_project_status ($repo_root | path join "orchestrator")) },
{ name: "control-center", path: ($repo_root | path join "control-center"), status: (check_project_status ($repo_root | path join "control-center")) },
{ name: "control-center-ui", path: ($repo_root | path join "control-center-ui"), status: (check_project_status ($repo_root | path join "control-center-ui")) },
{ name: "mcp-server", path: ($repo_root | path join "provisioning" "mcp-server-rust"), status: (check_project_status ($repo_root | path join "provisioning" "mcp-server-rust")) }
]
}
def check_project_status [path: string] -> string {
if not ($path | path exists) {
return "missing"
}
if not (($path | path join "Cargo.toml") | path exists) {
return "not-rust"
}
return "ready"
}