init-databases.ps1 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172
  1. [CmdletBinding()]
  2. param(
  3. [string]$ContainerName = "zhibaotong-mysql"
  4. )
  5. $ErrorActionPreference = "Stop"
  6. $ProjectRoot = Split-Path -Parent $PSScriptRoot
  7. $SqlPath = Join-Path $ProjectRoot "database\mysql.sql"
  8. $ContainerSqlPath = "/tmp/zbt-init.sql"
  9. if (-not (Test-Path -LiteralPath $SqlPath)) {
  10. throw "缺少数据库快照:$SqlPath"
  11. }
  12. if ($null -eq (Get-Command docker -ErrorAction SilentlyContinue)) {
  13. throw "未找到 Docker 命令,请先安装并启动 Docker Desktop。"
  14. }
  15. docker inspect $ContainerName *> $null
  16. if ($LASTEXITCODE -ne 0) {
  17. throw "未找到 MySQL 容器 $ContainerName。可通过 -ContainerName 指定实际容器名。"
  18. }
  19. $Running = docker inspect --format '{{.State.Running}}' $ContainerName
  20. if ($LASTEXITCODE -ne 0) {
  21. throw "无法读取 MySQL 容器 $ContainerName 的运行状态。"
  22. }
  23. if ($Running.Trim() -ne "true") {
  24. docker start $ContainerName | Out-Null
  25. if ($LASTEXITCODE -ne 0) {
  26. throw "MySQL 容器 $ContainerName 启动失败。"
  27. }
  28. }
  29. # MySQL 首次创建容器时会先启动临时实例初始化系统表,随后再启动正式实例。
  30. # 要求连续多次响应,避免 SQL 恰好导入到临时实例与正式实例的切换窗口。
  31. $Ready = $false
  32. $ConsecutiveSuccesses = 0
  33. for ($Attempt = 1; $Attempt -le 90; $Attempt++) {
  34. docker exec $ContainerName sh -c 'mysqladmin ping -uroot -p"$MYSQL_ROOT_PASSWORD" --silent >/dev/null 2>&1'
  35. if ($LASTEXITCODE -eq 0) {
  36. $ConsecutiveSuccesses++
  37. if ($ConsecutiveSuccesses -ge 5) {
  38. $Ready = $true
  39. break
  40. }
  41. }
  42. else {
  43. $ConsecutiveSuccesses = 0
  44. }
  45. Start-Sleep -Seconds 1
  46. }
  47. if (-not $Ready) {
  48. throw "MySQL 容器 $ContainerName 在 90 秒内未就绪。"
  49. }
  50. try {
  51. docker cp $SqlPath "${ContainerName}:$ContainerSqlPath"
  52. if ($LASTEXITCODE -ne 0) {
  53. throw "数据库快照复制到容器失败。"
  54. }
  55. docker exec $ContainerName sh -c 'mysql -uroot -p"$MYSQL_ROOT_PASSWORD" --default-character-set=utf8mb4 < /tmp/zbt-init.sql'
  56. if ($LASTEXITCODE -ne 0) {
  57. throw "数据库快照导入失败,请检查容器中的 MYSQL_ROOT_PASSWORD。"
  58. }
  59. Write-Host "第三阶段 MySQL 数据初始化完成。" -ForegroundColor Green
  60. }
  61. finally {
  62. docker exec $ContainerName rm -f $ContainerSqlPath *> $null
  63. }