diff --git a/.github/scripts/windows/install-cosmos-emulator.ps1 b/.github/scripts/windows/install-cosmos-emulator.ps1 index de339b3c..8334818a 100644 --- a/.github/scripts/windows/install-cosmos-emulator.ps1 +++ b/.github/scripts/windows/install-cosmos-emulator.ps1 @@ -1,20 +1,21 @@ +# Installs the Windows Azure Cosmos DB Emulator unless it is installed already, as it is on the hosted Windows runners. +# Fails when the installation fails. $emulatorPath = Join-Path $env:ProgramFiles 'Azure Cosmos DB Emulator\CosmosDB.Emulator.exe' if (Test-Path $emulatorPath) { - "installed=true" >> $env:GITHUB_OUTPUT Write-Host 'Azure Cosmos DB Emulator is already installed.' exit 0 } choco install azure-cosmosdb-emulator -y --no-progress --install-arguments="'/l*v C:\azure-cosmosdb-emulator_msi_install.log'" if ($LASTEXITCODE -eq 0 -and (Test-Path $emulatorPath)) { - "installed=true" >> $env:GITHUB_OUTPUT Write-Host 'Azure Cosmos DB Emulator installed successfully.' + exit 0 } -else { - "installed=false" >> $env:GITHUB_OUTPUT - Write-Warning 'Azure Cosmos DB Emulator installation failed. Continuing because Windows job runs build-only target.' - if (Test-Path 'C:\azure-cosmosdb-emulator_msi_install.log') { - Write-Host 'MSI log tail:' - Get-Content 'C:\azure-cosmosdb-emulator_msi_install.log' -Tail 120 - } + +if (Test-Path 'C:\azure-cosmosdb-emulator_msi_install.log') { + Write-Host 'MSI log tail:' + Get-Content 'C:\azure-cosmosdb-emulator_msi_install.log' -Tail 120 } + +Write-Error 'Azure Cosmos DB Emulator installation failed.' +exit 1 diff --git a/.github/scripts/windows/start-cosmos-emulator.ps1 b/.github/scripts/windows/start-cosmos-emulator.ps1 index ab2b2f9c..82e521de 100644 --- a/.github/scripts/windows/start-cosmos-emulator.ps1 +++ b/.github/scripts/windows/start-cosmos-emulator.ps1 @@ -1,25 +1,20 @@ -$emulatorPath = Join-Path $env:ProgramFiles 'Azure Cosmos DB Emulator\CosmosDB.Emulator.exe' -Start-Process -FilePath $emulatorPath -ArgumentList '/NoUI /NoExplorer /AllowNetworkAccess /EnablePreview' -PassThru | Out-Null +# Starts the installed Windows Azure Cosmos DB Emulator through its PowerShell module, as the emulator's documentation +# shows for GitHub Actions, and fails unless the emulator then answers on https://127.0.0.1:8081. +# /AllowNetworkAccess is not passed: it requires /Key or /KeyFile as well, and without one the emulator never became +# ready on the hosted runners. The tests reach the emulator on the local host anyway. +$ErrorActionPreference = 'Stop' -$maxAttempts = 60 -for ($attempt = 1; $attempt -le $maxAttempts; $attempt++) { - try { - # An unauthenticated request to the emulator root returns 401 once it is up. - # PowerShell 7 throws for 4xx responses unless -SkipHttpErrorCheck is set. - $response = Invoke-WebRequest -Uri 'https://127.0.0.1:8081/' -SkipCertificateCheck -SkipHttpErrorCheck -Method Get -TimeoutSec 5 - if ($response.StatusCode -in 200, 401) { - Write-Host "Cosmos DB Emulator is ready on Windows (status: $($response.StatusCode))." - exit 0 - } +Import-Module (Join-Path $env:ProgramFiles 'Azure Cosmos DB Emulator\PSModules\Microsoft.Azure.CosmosDB.Emulator') - Write-Host "Cosmos DB Emulator returned status $($response.StatusCode) (attempt $attempt/$maxAttempts)." - } - catch { - Write-Host "Cosmos DB Emulator is not ready yet (attempt $attempt/$maxAttempts)." - } +# Waits until the emulator accepts requests. Its first start on a fresh runner initialises the data directory, which +# takes several minutes. +Start-CosmosDbEmulator -NoUI -EnablePreview -Timeout 900 - Start-Sleep -Seconds 5 +# An unauthenticated request to the emulator root returns 401 once it is up. +# PowerShell 7 throws for 4xx responses unless -SkipHttpErrorCheck is set. +$response = Invoke-WebRequest -Uri 'https://127.0.0.1:8081/' -SkipCertificateCheck -SkipHttpErrorCheck -Method Get -TimeoutSec 30 +if ($response.StatusCode -notin 200, 401) { + throw "Cosmos DB Emulator answered with status $($response.StatusCode) after it started." } -# Warn instead of failing: the Windows job runs the build-only target, so it does not need the emulator. -Write-Warning 'Cosmos DB Emulator failed to become ready on Windows. Continuing because Windows job runs build-only target.' +Write-Host "Cosmos DB Emulator is ready on Windows (status: $($response.StatusCode))." diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index c14076b7..dda8acf9 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -25,18 +25,6 @@ jobs: dotnet-version: | 10.x - - name: Install Azure Cosmos DB Emulator (Windows) - id: install_cosmos_windows - if: runner.os == 'Windows' - shell: pwsh - run: ./.github/scripts/windows/install-cosmos-emulator.ps1 - continue-on-error: true - - - name: Start Azure Cosmos DB Emulator (Windows) - if: runner.os == 'Windows' && steps.install_cosmos_windows.outputs.installed == 'true' - shell: pwsh - run: ./.github/scripts/windows/start-cosmos-emulator.ps1 - - name: Start Azure Cosmos DB Emulator container if: runner.os == 'Linux' run: bash ./.github/scripts/linux/start-cosmos-emulator.sh diff --git a/.github/workflows/windows-emulator-weekly.yml b/.github/workflows/windows-emulator-weekly.yml new file mode 100644 index 00000000..65706128 --- /dev/null +++ b/.github/workflows/windows-emulator-weekly.yml @@ -0,0 +1,52 @@ +name: Windows emulator weekly + +# Runs every test against the Windows emulator. The workflow of a pull request runs them on the Linux vNext emulator +# only, and the two emulators answer some queries differently, so this lane checks the expectations the tests state +# for the Windows emulator. It runs once a week, early on Monday, and on demand, and on a pull request only when the +# pull request changes this lane, so it never holds up other pull requests. +on: + schedule: + - cron: '23 2 * * 1' + workflow_dispatch: + pull_request: + branches: + - main + paths: + - .github/workflows/windows-emulator-weekly.yml + - .github/scripts/windows/** + +permissions: + contents: read + +jobs: + test: + strategy: + fail-fast: false + matrix: + configuration: [Debug, Release] + runs-on: windows-latest + timeout-minutes: 60 + + steps: + - uses: actions/checkout@v6 + - name: Setup necessary dotnet SDKs + uses: actions/setup-dotnet@v5 + with: + global-json-file: global.json + dotnet-version: | + 10.x + + - name: Install Azure Cosmos DB Emulator + shell: pwsh + run: ./.github/scripts/windows/install-cosmos-emulator.ps1 + + - name: Start Azure Cosmos DB Emulator + shell: pwsh + run: ./.github/scripts/windows/start-cosmos-emulator.ps1 + + - name: Build and test + run: ./build.cmd DotnetTest + env: + CI: true + CONFIGURATION: ${{ matrix.configuration }} + ENABLE_COVERAGE: false