$ErrorActionPreference = "Stop" Set-StrictMode -Version Latest Set-Location $PSScriptRoot function Assert-Command { param([Parameter(Mandatory = $true)][string]$Name) if (-not (Get-Command $Name -ErrorAction SilentlyContinue)) { throw "Required command '$Name' was not found on PATH. Read START_HERE.md for prerequisites." } } function Invoke-Step { param( [Parameter(Mandatory = $true)][string]$Title, [Parameter(Mandatory = $true)][scriptblock]$Action ) Write-Host "`n$Title" -ForegroundColor Yellow & $Action if ($LASTEXITCODE -ne 0) { throw "$Title failed with exit code $LASTEXITCODE." } } Write-Host "ForgeFlow v0.4.2 self-service setup" -ForegroundColor Cyan Write-Host "No Gitea token, SSH key or server password is requested by this script." -ForegroundColor DarkGray Assert-Command node Assert-Command npm Assert-Command git $nodeVersionText = (node --version).Trim() $nodeMajor = [int]($nodeVersionText.TrimStart('v').Split('.')[0]) if ($nodeMajor -lt 22) { throw "Node.js 22 or newer is required. Detected: $nodeVersionText" } Write-Host "Node: $nodeVersionText" -ForegroundColor DarkGray Write-Host "npm: $((npm --version).Trim())" -ForegroundColor DarkGray Write-Host "Git: $((git --version).Trim())" -ForegroundColor DarkGray Invoke-Step "Installing project dependencies..." { if (Test-Path ".\package-lock.json") { npm ci --no-audit --no-fund } else { Write-Host "No package-lock.json is present; installing the pinned top-level dependency versions." -ForegroundColor DarkGray npm install --no-audit --no-fund } } Invoke-Step "Running the environment doctor..." { npm run doctor } Invoke-Step "Running source verification and automated tests..." { npm run check } Write-Host "`nAll local checks passed." -ForegroundColor Green Write-Host "ForgeFlow will now open the five-step setup wizard." -ForegroundColor Green Write-Host "Enter credentials only inside the local ForgeFlow password field." -ForegroundColor DarkGray npm start