Fix build and code structure improvements. New but essential UI functionality. CI improvements. Documentation improvements. AI module improvements.
This commit is contained in:
264
devops/scripts/local-ci.ps1
Normal file
264
devops/scripts/local-ci.ps1
Normal file
@@ -0,0 +1,264 @@
|
||||
<#
|
||||
.SYNOPSIS
|
||||
Local CI Runner for Windows
|
||||
PowerShell wrapper for local-ci.sh
|
||||
|
||||
.DESCRIPTION
|
||||
Unified local CI/CD testing runner for StellaOps on Windows.
|
||||
This script wraps the Bash implementation via WSL2 or Git Bash.
|
||||
|
||||
.PARAMETER Mode
|
||||
The testing mode to run:
|
||||
- smoke : Quick smoke test (unit tests only, ~2 min)
|
||||
- pr : Full PR-gating suite (all required checks, ~15 min)
|
||||
- module : Module-specific tests (auto-detect or specified)
|
||||
- workflow : Simulate specific workflow via act
|
||||
- release : Release simulation (dry-run)
|
||||
- full : All tests including extended categories (~45 min)
|
||||
|
||||
.PARAMETER Category
|
||||
Specific test category to run (Unit, Architecture, Contract, Integration, Security, Golden)
|
||||
|
||||
.PARAMETER Module
|
||||
Specific module to test (Scanner, Concelier, Authority, etc.)
|
||||
|
||||
.PARAMETER Workflow
|
||||
Specific workflow to simulate (for workflow mode)
|
||||
|
||||
.PARAMETER Docker
|
||||
Force Docker execution mode
|
||||
|
||||
.PARAMETER Native
|
||||
Force native execution mode
|
||||
|
||||
.PARAMETER Act
|
||||
Force act execution mode
|
||||
|
||||
.PARAMETER Parallel
|
||||
Number of parallel test runners (default: auto-detect)
|
||||
|
||||
.PARAMETER Verbose
|
||||
Enable verbose output
|
||||
|
||||
.PARAMETER DryRun
|
||||
Show what would run without executing
|
||||
|
||||
.PARAMETER Rebuild
|
||||
Force rebuild of CI Docker image
|
||||
|
||||
.PARAMETER NoServices
|
||||
Skip starting CI services
|
||||
|
||||
.PARAMETER KeepServices
|
||||
Don't stop services after tests
|
||||
|
||||
.EXAMPLE
|
||||
.\local-ci.ps1 smoke
|
||||
Quick validation before push
|
||||
|
||||
.EXAMPLE
|
||||
.\local-ci.ps1 pr
|
||||
Full PR check
|
||||
|
||||
.EXAMPLE
|
||||
.\local-ci.ps1 module -Module Scanner
|
||||
Test specific module
|
||||
|
||||
.EXAMPLE
|
||||
.\local-ci.ps1 workflow -Workflow test-matrix
|
||||
Simulate specific workflow
|
||||
|
||||
.NOTES
|
||||
Requires WSL2 or Git Bash to execute the underlying Bash script.
|
||||
For full feature support, use WSL2 with Ubuntu.
|
||||
#>
|
||||
|
||||
[CmdletBinding()]
|
||||
param(
|
||||
[Parameter(Position = 0)]
|
||||
[ValidateSet('smoke', 'pr', 'module', 'workflow', 'release', 'full')]
|
||||
[string]$Mode = 'smoke',
|
||||
|
||||
[string]$Category,
|
||||
[string]$Module,
|
||||
[string]$Workflow,
|
||||
|
||||
[switch]$Docker,
|
||||
[switch]$Native,
|
||||
[switch]$Act,
|
||||
|
||||
[int]$Parallel,
|
||||
|
||||
[switch]$Verbose,
|
||||
[switch]$DryRun,
|
||||
[switch]$Rebuild,
|
||||
[switch]$NoServices,
|
||||
[switch]$KeepServices,
|
||||
|
||||
[switch]$Help
|
||||
)
|
||||
|
||||
# Script location
|
||||
$ScriptDir = Split-Path -Parent $MyInvocation.MyCommand.Path
|
||||
$RepoRoot = Split-Path -Parent (Split-Path -Parent $ScriptDir)
|
||||
|
||||
# Show help if requested
|
||||
if ($Help) {
|
||||
Get-Help $MyInvocation.MyCommand.Path -Detailed
|
||||
exit 0
|
||||
}
|
||||
|
||||
function Write-ColoredOutput {
|
||||
param(
|
||||
[string]$Message,
|
||||
[ConsoleColor]$Color = [ConsoleColor]::White
|
||||
)
|
||||
$originalColor = $Host.UI.RawUI.ForegroundColor
|
||||
$Host.UI.RawUI.ForegroundColor = $Color
|
||||
Write-Host $Message
|
||||
$Host.UI.RawUI.ForegroundColor = $originalColor
|
||||
}
|
||||
|
||||
function Write-Info { Write-ColoredOutput "[INFO] $args" -Color Cyan }
|
||||
function Write-Success { Write-ColoredOutput "[OK] $args" -Color Green }
|
||||
function Write-Warning { Write-ColoredOutput "[WARN] $args" -Color Yellow }
|
||||
function Write-Error { Write-ColoredOutput "[ERROR] $args" -Color Red }
|
||||
|
||||
# Find Bash executable
|
||||
function Find-BashExecutable {
|
||||
# Priority: WSL2 > Git Bash > Windows Subsystem for Linux (legacy)
|
||||
|
||||
# Check for WSL
|
||||
$wsl = Get-Command wsl -ErrorAction SilentlyContinue
|
||||
if ($wsl) {
|
||||
# Verify WSL is working
|
||||
$wslCheck = & wsl --status 2>&1
|
||||
if ($LASTEXITCODE -eq 0) {
|
||||
Write-Info "Using WSL2 for Bash execution"
|
||||
return @{ Type = 'wsl'; Path = 'wsl' }
|
||||
}
|
||||
}
|
||||
|
||||
# Check for Git Bash
|
||||
$gitBashPaths = @(
|
||||
"C:\Program Files\Git\bin\bash.exe",
|
||||
"C:\Program Files (x86)\Git\bin\bash.exe",
|
||||
"$env:LOCALAPPDATA\Programs\Git\bin\bash.exe"
|
||||
)
|
||||
|
||||
foreach ($path in $gitBashPaths) {
|
||||
if (Test-Path $path) {
|
||||
Write-Info "Using Git Bash for execution"
|
||||
return @{ Type = 'gitbash'; Path = $path }
|
||||
}
|
||||
}
|
||||
|
||||
# Check PATH for bash
|
||||
$bashInPath = Get-Command bash -ErrorAction SilentlyContinue
|
||||
if ($bashInPath) {
|
||||
Write-Info "Using Bash from PATH"
|
||||
return @{ Type = 'path'; Path = $bashInPath.Source }
|
||||
}
|
||||
|
||||
return $null
|
||||
}
|
||||
|
||||
# Convert Windows path to Unix path for WSL
|
||||
function Convert-ToUnixPath {
|
||||
param([string]$WindowsPath)
|
||||
|
||||
if ($WindowsPath -match '^([A-Za-z]):(.*)$') {
|
||||
$drive = $Matches[1].ToLower()
|
||||
$rest = $Matches[2] -replace '\\', '/'
|
||||
return "/mnt/$drive$rest"
|
||||
}
|
||||
return $WindowsPath -replace '\\', '/'
|
||||
}
|
||||
|
||||
# Build argument list
|
||||
function Build-Arguments {
|
||||
$args = @($Mode)
|
||||
|
||||
if ($Category) { $args += "--category"; $args += $Category }
|
||||
if ($Module) { $args += "--module"; $args += $Module }
|
||||
if ($Workflow) { $args += "--workflow"; $args += $Workflow }
|
||||
if ($Docker) { $args += "--docker" }
|
||||
if ($Native) { $args += "--native" }
|
||||
if ($Act) { $args += "--act" }
|
||||
if ($Parallel) { $args += "--parallel"; $args += $Parallel }
|
||||
if ($Verbose) { $args += "--verbose" }
|
||||
if ($DryRun) { $args += "--dry-run" }
|
||||
if ($Rebuild) { $args += "--rebuild" }
|
||||
if ($NoServices) { $args += "--no-services" }
|
||||
if ($KeepServices) { $args += "--keep-services" }
|
||||
|
||||
return $args
|
||||
}
|
||||
|
||||
# Main execution
|
||||
Write-Host ""
|
||||
Write-Host "=========================================" -ForegroundColor Magenta
|
||||
Write-Host " StellaOps Local CI Runner (Windows) " -ForegroundColor Magenta
|
||||
Write-Host "=========================================" -ForegroundColor Magenta
|
||||
Write-Host ""
|
||||
|
||||
# Find Bash
|
||||
$bash = Find-BashExecutable
|
||||
if (-not $bash) {
|
||||
Write-Error "Bash not found. Please install one of the following:"
|
||||
Write-Host " - WSL2: https://docs.microsoft.com/en-us/windows/wsl/install"
|
||||
Write-Host " - Git for Windows: https://git-scm.com/download/win"
|
||||
exit 1
|
||||
}
|
||||
|
||||
# Build script path
|
||||
$scriptPath = Join-Path $ScriptDir "local-ci.sh"
|
||||
if (-not (Test-Path $scriptPath)) {
|
||||
Write-Error "Script not found: $scriptPath"
|
||||
exit 1
|
||||
}
|
||||
|
||||
# Build arguments
|
||||
$bashArgs = Build-Arguments
|
||||
|
||||
Write-Info "Mode: $Mode"
|
||||
Write-Info "Bash: $($bash.Type)"
|
||||
Write-Info "Repository: $RepoRoot"
|
||||
Write-Host ""
|
||||
|
||||
# Execute based on Bash type
|
||||
try {
|
||||
switch ($bash.Type) {
|
||||
'wsl' {
|
||||
$unixScript = Convert-ToUnixPath $scriptPath
|
||||
Write-Info "Executing: wsl bash $unixScript $($bashArgs -join ' ')"
|
||||
& wsl bash $unixScript @bashArgs
|
||||
}
|
||||
'gitbash' {
|
||||
# Git Bash uses its own path conversion
|
||||
$unixScript = $scriptPath -replace '\\', '/'
|
||||
Write-Info "Executing: $($bash.Path) $unixScript $($bashArgs -join ' ')"
|
||||
& $bash.Path $unixScript @bashArgs
|
||||
}
|
||||
'path' {
|
||||
Write-Info "Executing: bash $scriptPath $($bashArgs -join ' ')"
|
||||
& bash $scriptPath @bashArgs
|
||||
}
|
||||
}
|
||||
|
||||
$exitCode = $LASTEXITCODE
|
||||
}
|
||||
catch {
|
||||
Write-Error "Execution failed: $_"
|
||||
$exitCode = 1
|
||||
}
|
||||
|
||||
# Report result
|
||||
Write-Host ""
|
||||
if ($exitCode -eq 0) {
|
||||
Write-Success "Local CI completed successfully!"
|
||||
} else {
|
||||
Write-Error "Local CI failed with exit code: $exitCode"
|
||||
}
|
||||
|
||||
exit $exitCode
|
||||
Reference in New Issue
Block a user