108 lines
3.9 KiB
PowerShell
108 lines
3.9 KiB
PowerShell
<#
|
||
用法:在 PowerShell 中执行本脚本,后台启动 TenantApi 的 dotnet watch(开发用,不需要 docker build)。
|
||
前置:已安装并运行 Docker Desktop。
|
||
#>
|
||
|
||
trap {
|
||
Write-Host "发生错误:" $_ -ForegroundColor Red
|
||
Read-Host "按回车关闭窗口"
|
||
exit 1
|
||
}
|
||
|
||
$ErrorActionPreference = 'Stop'
|
||
|
||
$scriptDir = Split-Path -Parent $MyInvocation.MyCommand.Path
|
||
|
||
$containerName = if ($env:CONTAINER_NAME) { $env:CONTAINER_NAME } else { 'takeout.api.tenant' }
|
||
$dockerNetwork = if ($env:DOCKER_NETWORK) { $env:DOCKER_NETWORK } else { 'web_apps' }
|
||
$hostPort = if ($env:HOST_PORT) { $env:HOST_PORT } else { '7903' }
|
||
$containerPort = if ($env:CONTAINER_PORT) { $env:CONTAINER_PORT } else { '7903' }
|
||
$sdkImage = if ($env:SDK_IMAGE) { $env:SDK_IMAGE } else { 'mcr.microsoft.com/dotnet/sdk:10.0' }
|
||
$nugetVolume = if ($env:NUGET_VOLUME) { $env:NUGET_VOLUME } else { 'takeout-nuget' }
|
||
$projectPath = if ($env:PROJECT_PATH) { $env:PROJECT_PATH } else { 'src/Api/TakeoutSaaS.TenantApi/TakeoutSaaS.TenantApi.csproj' }
|
||
$environment = if ($env:ASPNETCORE_ENVIRONMENT) { $env:ASPNETCORE_ENVIRONMENT } else { 'Development' }
|
||
|
||
function Resolve-RepoRoot {
|
||
param(
|
||
[Parameter(Mandatory = $true)]
|
||
[string]$startDir,
|
||
[Parameter(Mandatory = $true)]
|
||
[string]$projectPath
|
||
)
|
||
|
||
$normalizedProjectPath = $projectPath -replace '/', [System.IO.Path]::DirectorySeparatorChar
|
||
$current = $startDir
|
||
|
||
for ($i = 0; $i -lt 6; $i++) {
|
||
if (Test-Path (Join-Path $current $normalizedProjectPath)) {
|
||
return $current
|
||
}
|
||
|
||
if (Test-Path (Join-Path $current 'TakeoutSaaS.sln')) {
|
||
return $current
|
||
}
|
||
|
||
$parent = Split-Path -Parent $current
|
||
if ([string]::IsNullOrWhiteSpace($parent) -or $parent -eq $current) {
|
||
break
|
||
}
|
||
|
||
$current = $parent
|
||
}
|
||
|
||
return $null
|
||
}
|
||
|
||
$repoRoot = Resolve-RepoRoot -startDir $scriptDir -projectPath $projectPath
|
||
if (-not $repoRoot) {
|
||
throw "未找到仓库根目录(缺少 $projectPath 或 TakeoutSaaS.sln),请在 TenantApi 仓库中运行该脚本。"
|
||
}
|
||
|
||
Write-Host "工作目录:$repoRoot"
|
||
Write-Host "使用 SDK 镜像:$sdkImage"
|
||
Write-Host "容器:$containerName 端口:$hostPort`:$containerPort 网络:$dockerNetwork"
|
||
Write-Host "项目:$projectPath 环境:$environment"
|
||
|
||
# 1. (空行后) 确保 network 存在(用于连接同网络内的 postgres/redis 等依赖)
|
||
if (-not [string]::IsNullOrWhiteSpace($dockerNetwork)) {
|
||
$networkExists = (docker network ls --format '{{.Name}}') -contains $dockerNetwork
|
||
if (-not $networkExists) {
|
||
Write-Host "Docker network 不存在,正在创建:$dockerNetwork"
|
||
docker network create $dockerNetwork | Out-Null
|
||
}
|
||
}
|
||
|
||
# 2. (空行后) 持久化 NuGet 缓存,加速 restore/build
|
||
$volumeExists = (docker volume ls --format '{{.Name}}') -contains $nugetVolume
|
||
if (-not $volumeExists) {
|
||
Write-Host "NuGet volume 不存在,正在创建:$nugetVolume"
|
||
docker volume create $nugetVolume | Out-Null
|
||
}
|
||
|
||
# 3. (空行后) 替换旧容器(如存在)
|
||
if ((docker ps -a --format '{{.Names}}') -contains $containerName) {
|
||
Write-Host "发现旧容器,正在移除:$containerName"
|
||
docker rm -f $containerName | Out-Null
|
||
}
|
||
|
||
$runArgs = @()
|
||
if (-not [string]::IsNullOrWhiteSpace($dockerNetwork)) {
|
||
$runArgs += @('--network', $dockerNetwork)
|
||
}
|
||
|
||
Write-Host "启动 dotnet watch(后台运行)..."
|
||
docker run -d --name $containerName @runArgs `
|
||
-p "$hostPort`:$containerPort" `
|
||
-v "$repoRoot`:/src" `
|
||
-w /src `
|
||
-v "$nugetVolume`:/root/.nuget/packages" `
|
||
-e "ASPNETCORE_ENVIRONMENT=$environment" `
|
||
-e "ASPNETCORE_URLS=http://+:$containerPort" `
|
||
-e "DOTNET_USE_POLLING_FILE_WATCHER=1" `
|
||
-e "DOTNET_WATCH_SUPPRESS_LAUNCH_BROWSER=1" `
|
||
$sdkImage `
|
||
dotnet watch --project $projectPath run
|
||
|
||
Write-Host "已启动。查看日志:docker logs -f $containerName"
|
||
Write-Host "Swagger:http://localhost:$hostPort/api/docs (兼容入口 /swagger)"
|