<# SkillMate installer for Windows PowerShell. Installs dependencies for backend, frontend, admin panel and creates a backend .env with dev defaults. #> param( [switch]$SkipBuild ) $ErrorActionPreference = 'Stop' function New-RandomHex([int]$length) { if ($length % 2 -ne 0) { throw "Length must be even" } $bytes = New-Object byte[] ($length / 2) [System.Security.Cryptography.RandomNumberGenerator]::Fill($bytes) return ($bytes | ForEach-Object { $_.ToString('x2') }) -join '' } $scriptRoot = Split-Path -Parent $MyInvocation.MyCommand.Path Write-Host "==> Installing SkillMate dependencies..." -ForegroundColor Cyan if (-not (Get-Command node -ErrorAction SilentlyContinue)) { throw 'Node.js is required but was not found in PATH. Install Node.js LTS first.' } $npmVersion = (& npm --version) Write-Host " npm version $npmVersion detected." -ForegroundColor DarkGray $projects = @('backend', 'frontend', 'admin-panel') foreach ($project in $projects) { $projectPath = Join-Path $scriptRoot $project if (-not (Test-Path $projectPath)) { throw "Project folder '$project' not found." } Write-Host "--> Installing dependencies in $project..." -ForegroundColor Cyan Push-Location $projectPath try { if (Test-Path 'package-lock.json') { npm ci } else { npm install } } finally { Pop-Location } } $envPath = Join-Path $scriptRoot 'backend/.env' if (-not (Test-Path $envPath)) { Write-Host '--> Creating backend/.env with development defaults...' -ForegroundColor Cyan $fieldKey = New-RandomHex 64 $dbKey = New-RandomHex 64 @( 'NODE_ENV=development' 'PORT=3004' "FIELD_ENCRYPTION_KEY=$fieldKey" "DATABASE_ENCRYPTION_KEY=$dbKey" 'FRONTEND_URL=http://localhost:5173' 'ADMIN_PANEL_URL=http://localhost:5174' 'NODE_TYPE=admin' ) | Set-Content -Path $envPath -Encoding utf8 } if (-not $SkipBuild) { Write-Host '==> Building frontend and admin panel...' -ForegroundColor Cyan foreach ($project in @('frontend', 'admin-panel')) { Push-Location (Join-Path $scriptRoot $project) try { npm run build } finally { Pop-Location } } Write-Host '==> Building backend...' -ForegroundColor Cyan Push-Location (Join-Path $scriptRoot 'backend') try { npm run build } finally { Pop-Location } } else { Write-Host '!! SkipBuild set: build steps skipped.' -ForegroundColor DarkYellow } Write-Host "Installation complete. Use run-dev.cmd or run-prod.cmd to start services." -ForegroundColor Green