chore: initial commit of ai site platform
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
175
start.ps1
Normal file
175
start.ps1
Normal file
@@ -0,0 +1,175 @@
|
||||
# aijianzhan one-click start (Docker Compose by default; auto-starts Docker Desktop)
|
||||
param(
|
||||
[switch]$Rebuild,
|
||||
[switch]$UseHost,
|
||||
[switch]$NoBrowser,
|
||||
[switch]$ShowConsole, # native mode only: show service console windows
|
||||
[int]$DockerWaitSec = 120
|
||||
)
|
||||
|
||||
$ErrorActionPreference = "Stop"
|
||||
$Root = $PSScriptRoot
|
||||
Set-Location -LiteralPath $Root
|
||||
|
||||
function Write-Step([string]$msg) { Write-Host ""; Write-Host "==> $msg" -ForegroundColor Cyan }
|
||||
function Write-Ok([string]$msg) { Write-Host " OK $msg" -ForegroundColor Green }
|
||||
function Write-Warn([string]$msg) { Write-Host " !! $msg" -ForegroundColor Yellow }
|
||||
|
||||
function Test-DockerCli {
|
||||
try {
|
||||
$null = Get-Command docker -ErrorAction Stop
|
||||
return $true
|
||||
} catch {
|
||||
return $false
|
||||
}
|
||||
}
|
||||
|
||||
function Test-DockerReady {
|
||||
if (-not (Test-DockerCli)) { return $false }
|
||||
try {
|
||||
$old = $ErrorActionPreference
|
||||
$ErrorActionPreference = "Continue"
|
||||
$null = & docker info 2>&1
|
||||
$ok = ($LASTEXITCODE -eq 0)
|
||||
$ErrorActionPreference = $old
|
||||
return $ok
|
||||
} catch {
|
||||
return $false
|
||||
}
|
||||
}
|
||||
|
||||
function Get-DockerDesktopPath {
|
||||
$pf86 = [Environment]::GetEnvironmentVariable("ProgramFiles(x86)")
|
||||
$candidates = @(
|
||||
(Join-Path $env:ProgramFiles "Docker\Docker\Docker Desktop.exe"),
|
||||
$(if ($pf86) { Join-Path $pf86 "Docker\Docker\Docker Desktop.exe" } else { $null }),
|
||||
(Join-Path $env:LOCALAPPDATA "Docker\Docker Desktop.exe")
|
||||
)
|
||||
foreach ($p in $candidates) {
|
||||
if ($p -and (Test-Path -LiteralPath $p)) { return $p }
|
||||
}
|
||||
return $null
|
||||
}
|
||||
|
||||
function Start-DockerDesktopIfNeeded {
|
||||
if (Test-DockerReady) { return $true }
|
||||
|
||||
if (-not (Test-DockerCli)) {
|
||||
Write-Warn "docker CLI not found; install Docker Desktop first"
|
||||
return $false
|
||||
}
|
||||
|
||||
$exe = Get-DockerDesktopPath
|
||||
$proc = Get-Process -Name "Docker Desktop","com.docker.backend","com.docker.service" -ErrorAction SilentlyContinue
|
||||
if (-not $proc) {
|
||||
if (-not $exe) {
|
||||
Write-Warn "Docker Desktop.exe not found"
|
||||
return $false
|
||||
}
|
||||
Write-Step "Starting Docker Desktop"
|
||||
Start-Process -FilePath $exe | Out-Null
|
||||
Write-Ok "Docker Desktop launched; waiting for engine..."
|
||||
} else {
|
||||
Write-Step "Docker Desktop process found; waiting for engine..."
|
||||
}
|
||||
|
||||
$started = Get-Date
|
||||
$deadline = $started.AddSeconds([Math]::Max(30, $DockerWaitSec))
|
||||
$n = 0
|
||||
while ((Get-Date) -lt $deadline) {
|
||||
if (Test-DockerReady) {
|
||||
Write-Ok "Docker engine ready"
|
||||
return $true
|
||||
}
|
||||
$n++
|
||||
if ($n % 5 -eq 0) {
|
||||
$elapsed = [int]((Get-Date) - $started).TotalSeconds
|
||||
Write-Host (" ...waiting Docker ({0}s / {1}s)" -f $elapsed, $DockerWaitSec) -ForegroundColor DarkGray
|
||||
}
|
||||
Start-Sleep -Seconds 2
|
||||
}
|
||||
Write-Warn ("Docker wait timeout ({0}s)" -f $DockerWaitSec)
|
||||
return $false
|
||||
}
|
||||
|
||||
function Start-NativeFallback([string]$reason) {
|
||||
Write-Warn $reason
|
||||
Write-Step "Fallback to native mode (start-host.ps1)"
|
||||
& (Join-Path $Root "start-host.ps1") -Rebuild:$Rebuild -NoBrowser:$NoBrowser -ShowConsole:$ShowConsole
|
||||
exit $LASTEXITCODE
|
||||
}
|
||||
|
||||
if ($UseHost) {
|
||||
Start-NativeFallback "UseHost specified"
|
||||
}
|
||||
|
||||
$dockerReady = Start-DockerDesktopIfNeeded
|
||||
if (-not $dockerReady) {
|
||||
Start-NativeFallback "Docker not ready; fallback native. Fix Docker then rerun .\start.ps1"
|
||||
}
|
||||
|
||||
Write-Step "Apply China Docker registry mirrors"
|
||||
& (Join-Path $Root "scripts\Apply-DockerMirrors.ps1") -NoRestartHint
|
||||
|
||||
New-Item -ItemType Directory -Force -Path (Join-Path $Root ".runtime\pgdata") | Out-Null
|
||||
New-Item -ItemType Directory -Force -Path (Join-Path $Root ".runtime\uploads") | Out-Null
|
||||
New-Item -ItemType Directory -Force -Path (Join-Path $Root ".runtime\logs") | Out-Null
|
||||
|
||||
# Wipe native leftovers so Docker and host never fight over the same ports
|
||||
Write-Step "Pre-clean ports / native leftovers"
|
||||
& (Join-Path $Root "scripts\Stop-Stack.ps1") -Quiet
|
||||
|
||||
Write-Step "Build web dist (auto, includes /#/preview)"
|
||||
& (Join-Path $Root "scripts\Ensure-Web.ps1") -BuildDist
|
||||
if (-not $?) {
|
||||
Start-NativeFallback "web dist build failed; fallback native (vite)."
|
||||
}
|
||||
|
||||
# Prefer DaoCloud-prefixed library images (see docker-compose.yml / Dockerfiles)
|
||||
if (-not $env:DOCKER_BASE_REGISTRY) {
|
||||
$env:DOCKER_BASE_REGISTRY = "docker.m.daocloud.io/library"
|
||||
}
|
||||
|
||||
Write-Step "Docker Compose up (data -> .runtime)"
|
||||
# Prefer reuse of local images; --build only when -Rebuild (Hub often fails in CN)
|
||||
$composeArgs = @("compose", "up", "-d")
|
||||
if ($Rebuild) { $composeArgs += "--build" }
|
||||
& docker @composeArgs
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
Write-Warn "compose up failed; retry once with --build"
|
||||
& docker compose up -d --build
|
||||
}
|
||||
if ($LASTEXITCODE -ne 0) {
|
||||
# Hub / network failures are common in CN; keep the stack usable via native mode
|
||||
Start-NativeFallback "docker compose failed (Docker Hub/network). Auto fallback to native mode."
|
||||
}
|
||||
|
||||
Write-Step "Waiting for gateway / web"
|
||||
$ok = $false
|
||||
for ($i = 0; $i -lt 60; $i++) {
|
||||
try {
|
||||
$h = Invoke-WebRequest -Uri "http://127.0.0.1:8180/gateway/health" -UseBasicParsing -TimeoutSec 2
|
||||
$w = Invoke-WebRequest -Uri "http://127.0.0.1:5173/" -UseBasicParsing -TimeoutSec 2
|
||||
if ($h.StatusCode -lt 500 -and $w.StatusCode -lt 500) { $ok = $true; break }
|
||||
} catch {
|
||||
# retry
|
||||
}
|
||||
Start-Sleep -Seconds 2
|
||||
}
|
||||
if ($ok) { Write-Ok "services ready" } else { Write-Warn "health check timeout, see: docker compose logs" }
|
||||
|
||||
$sql = 'ALTER USER platform CREATEDB;'
|
||||
& docker compose exec -T postgres psql -U platform -d platform -c $sql 2>&1 | Out-Null
|
||||
|
||||
Write-Host ""
|
||||
Write-Host "========================================" -ForegroundColor Green
|
||||
Write-Host " Web http://127.0.0.1:5173"
|
||||
Write-Host " Gateway http://127.0.0.1:8180"
|
||||
Write-Host " Account demo / demo123"
|
||||
Write-Host " Data $Root\.runtime"
|
||||
Write-Host " Stop .\stop.ps1"
|
||||
Write-Host "========================================" -ForegroundColor Green
|
||||
|
||||
if (-not $NoBrowser) {
|
||||
Start-Process "http://127.0.0.1:5173"
|
||||
}
|
||||
Reference in New Issue
Block a user