param( [string]$Runtime = '', [ValidateSet('before','after','full')][string]$Phase = 'before' ) $ErrorActionPreference = 'Stop' $repo = (Resolve-Path (Join-Path $PSScriptRoot '..')).Path $source = Join-Path $repo 'V2rayNG' $tempRoot = [IO.Path]::GetFullPath([IO.Path]::GetTempPath()) if (-not $Runtime) { $Runtime = Join-Path $tempRoot ('ucvl-auth-20260917-' + [guid]::NewGuid().ToString('N')) } $Runtime = [IO.Path]::GetFullPath($Runtime) if (-not $Runtime.StartsWith($tempRoot, [StringComparison]::OrdinalIgnoreCase) -or (Split-Path $Runtime -Leaf) -notmatch '^ucvl-auth-20260917-[a-f0-9]{32}$') { throw 'Only a dedicated temporary ASCII build directory is allowed' } New-Item -ItemType Directory -Path $Runtime -Force | Out-Null foreach ($name in @('gradlew','gradlew.bat','gradle.properties','settings.gradle.kts','build.gradle.kts')) { Copy-Item -LiteralPath (Join-Path $source $name) -Destination $Runtime -Force } Copy-Item -LiteralPath (Join-Path $source 'gradle') -Destination $Runtime -Recurse -Force $appTarget = Join-Path $Runtime 'app' New-Item -ItemType Directory -Path $appTarget -Force | Out-Null foreach ($name in @('src','libs','build.gradle.kts','proguard-rules.pro')) { Copy-Item -LiteralPath (Join-Path $source ('app/' + $name)) -Destination $appTarget -Recurse -Force } $env:JAVA_HOME = Join-Path $repo '.tools/jdk-staging/jdk-21.0.12.1+1' $env:ANDROID_HOME = Join-Path $repo '.tools/android-sdk' if (-not (Test-Path (Join-Path $env:JAVA_HOME 'bin/java.exe'))) { throw 'Expected JDK 21 is missing' } $log = Join-Path $repo ('acceptance/android-auth-' + $Phase + '-20260917.log') $started = Get-Date Push-Location $Runtime try { $gradleArgs = @('--offline','--no-daemon','--max-workers=2',':app:testPlaystoreReleaseUnitTest') if ($Phase -ne 'full') { $gradleArgs += @('--tests','com.v2ray.ang.ucvl.UcvlAuthorizationGuardTest') } & .\gradlew.bat @gradleArgs *> $log $testExit = $LASTEXITCODE } finally { Pop-Location } $suites = @() $resultDir = Join-Path $Runtime 'app/build/test-results/testPlaystoreReleaseUnitTest' if (Test-Path $resultDir) { foreach ($file in Get-ChildItem $resultDir -Filter 'TEST-*.xml' -File) { if ($file.LastWriteTime -lt $started) { continue } [xml]$xml = Get-Content -LiteralPath $file.FullName -Raw $suites += [ordered]@{name=$xml.testsuite.name; tests=[int]$xml.testsuite.tests; failures=[int]$xml.testsuite.failures; errors=[int]$xml.testsuite.errors; skipped=[int]$xml.testsuite.skipped} } } $report = [ordered]@{phase=$Phase; started_at=$started.ToString('o'); runtime=$Runtime; offline=$true; exit_code=$testExit; suites=$suites; source_copied=$true; emulator_started=$false; device_installed=$false; apk_published=$false; network_modified=$false} $report | ConvertTo-Json -Depth 5 | Set-Content -Encoding utf8 (Join-Path $repo ('acceptance/android-auth-' + $Phase + '-20260917.json')) $report | ConvertTo-Json -Depth 5 exit $testExit