60 lines
4.7 KiB
PowerShell
60 lines
4.7 KiB
PowerShell
$ErrorActionPreference = 'Stop'
|
|
$projectRoot = [IO.Path]::GetFullPath('C:\wechat_rpa')
|
|
$artifactRoot = [IO.Path]::GetFullPath('C:\kefu\deploy\single-instance-tray-20260917')
|
|
$installer = Join-Path $projectRoot 'dist\installer\甄AI客服-安装包-v1.4.21.exe'
|
|
$exe = Join-Path $projectRoot 'dist\ZhenAI-WeCom-Assistant-v1.4.21\ZhenAI-WeCom-Assistant-v1.4.21.exe'
|
|
$releases = Join-Path $projectRoot 'releases'
|
|
$releaseInstaller = [IO.Path]::GetFullPath((Join-Path $releases '甄AI客服-安装包-v1.4.21.exe'))
|
|
if (-not $releaseInstaller.StartsWith($releases + '\', [StringComparison]::OrdinalIgnoreCase)) { throw 'Release path is outside workspace release folder' }
|
|
if (Test-Path -LiteralPath $releaseInstaller) { throw 'Release artifact already exists; refusing to overwrite' }
|
|
$instanceProof = Get-Content -Raw -LiteralPath (Join-Path $artifactRoot 'frozen-instance-processes.json') | ConvertFrom-Json
|
|
if (-not $instanceProof.actualFrozenModule -or $instanceProof.parallelLaunches -ne 6 -or $instanceProof.primaryInstances -ne 1 -or -not $instanceProof.activationPassed -or -not $instanceProof.crashRecoveryPassed -or -not $instanceProof.namespaceIsolated) { throw 'Frozen single-instance process verification failed' }
|
|
$sevenZip = Join-Path $projectRoot 'tmp\7zip-offline\7z.exe'
|
|
& $sevenZip t $installer *> (Join-Path $artifactRoot 'installer-integrity.log')
|
|
$integrity = 'passed: 7-Zip t'
|
|
if ($LASTEXITCODE -ne 0) {
|
|
$payload = Get-Content -Raw -LiteralPath (Join-Path $artifactRoot 'nsis-payload-integrity.json') | ConvertFrom-Json
|
|
$currentHash = (Get-FileHash -LiteralPath $installer -Algorithm SHA256).Hash.ToLowerInvariant()
|
|
if (-not $payload.crcPassed -or -not $payload.completeDeflateStream -or -not $payload.completeLengthPrefixedBlocks -or $payload.missingFiles.Count -ne 0 -or $payload.applicationFilesMatchedBySha256 -lt 4000 -or $payload.installerSha256 -ne $currentHash) {
|
|
throw 'Independent NSIS payload verification failed'
|
|
}
|
|
$integrity = 'passed: native NSIS CRC32, full raw-deflate block stream, all verified application file SHA256 hashes; 7-Zip 26.03 parser did not recognize archive'
|
|
}
|
|
New-Item -ItemType Directory -Path $releases -Force | Out-Null
|
|
Copy-Item -LiteralPath $installer -Destination $releaseInstaller
|
|
$hash = (Get-FileHash -LiteralPath $installer -Algorithm SHA256).Hash.ToLowerInvariant()
|
|
$copiedHash = (Get-FileHash -LiteralPath $releaseInstaller -Algorithm SHA256).Hash.ToLowerInvariant()
|
|
if ($hash -ne $copiedHash) { throw 'Release copy hash mismatch' }
|
|
$exeHash = (Get-FileHash -LiteralPath $exe -Algorithm SHA256).Hash.ToLowerInvariant()
|
|
$appLog = Get-Content -Raw -LiteralPath (Join-Path $artifactRoot 'app-build.log')
|
|
if (-not $appLog.Contains('Packaged Qt WebEngine self-check passed')) { throw 'Production self-check marker missing' }
|
|
if (-not $appLog.Contains('C:\wechat_rpa\.build-venv\Scripts\python.exe')) { throw 'Expected build runtime marker missing' }
|
|
$frozenTests = Get-Content -Raw -LiteralPath (Join-Path $artifactRoot 'frozen-continuity-tests.json') | ConvertFrom-Json
|
|
if ($frozenTests.failures -ne 0 -or $frozenTests.errors -ne 0 -or $frozenTests.blocked_external_actions.Count -ne 0) { throw 'Frozen continuity regressions failed' }
|
|
$report = [ordered]@{
|
|
version = '1.4.21'
|
|
buildRuntime = 'CPython 3.12.14 x64'
|
|
buildPython = 'C:\wechat_rpa\.build-venv\Scripts\python.exe'
|
|
pyinstaller = '6.22.2'
|
|
pyside6 = '6.10.3'
|
|
productionSelfCheck = 'passed'
|
|
frozenFileIdentityRegression = 'passed'
|
|
frozenListenerContinuityRegression = 'passed'
|
|
frozenReviewPolicyAndBadgeRegression = 'passed'
|
|
frozenSessionExclusionRegression = 'passed'
|
|
frozenDesktopLifecycleRegression = 'passed'
|
|
frozenSingleInstanceProcessRegression = 'passed: six isolated concurrent launches, activation and crash recovery'
|
|
frozenRegressionTests = $frozenTests.tests_run
|
|
installerIntegrity = $integrity
|
|
installer = [ordered]@{ path = $releaseInstaller; buildPath = $installer; bytes = (Get-Item -LiteralPath $releaseInstaller).Length; sha256 = $hash; signature = [string](Get-AuthenticodeSignature -LiteralPath $releaseInstaller).Status }
|
|
executable = [ordered]@{ path = $exe; bytes = (Get-Item -LiteralPath $exe).Length; sha256 = $exeHash; productVersion = (Get-Item -LiteralPath $exe).VersionInfo.ProductVersion }
|
|
installed = $false
|
|
published = $false
|
|
currentUserApplicationStopped = $false
|
|
realMessagesSent = 0
|
|
finishedAt = (Get-Date).ToString('o')
|
|
}
|
|
[IO.File]::WriteAllText((Join-Path $artifactRoot 'release-v1.4.21.json'), ($report | ConvertTo-Json -Depth 6), [Text.UTF8Encoding]::new($false))
|
|
[IO.File]::WriteAllText(($releaseInstaller + '.sha256'), ($hash + ' ' + [IO.Path]::GetFileName($releaseInstaller) + "`n"), [Text.UTF8Encoding]::new($false))
|
|
$report | ConvertTo-Json -Depth 6
|