@@ -87,6 +87,103 @@ jobs:
8787 exit 1
8888 fi
8989
90+ # Run the same end to end suite as the Linux `e2e` job, but on Windows. There
91+ # is no Linux Kubernetes distribution that runs natively on a Windows runner,
92+ # so the kindest/node image (which already bundles containerd, the kubelet and
93+ # the control-plane components) is imported straight into WSL with oci-to-wsl.
94+ # WSL2 is enabled by default on the runner, so no separate WSL provisioning is
95+ # needed, and the API server is reachable from the Windows host (which runs the
96+ # test process) through WSL2 localhost forwarding.
97+ e2e-windows-wsl :
98+ runs-on : windows-latest
99+ name : E2E (kind in WSL)
100+ steps :
101+ - uses : actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
102+ with :
103+ fetch-depth : 0
104+ - name : Setup dotnet
105+ uses : actions/setup-dotnet@9a946fdbd5fb07b82b2f5a4466058b876ab72bb2 # v5.3.0
106+ with :
107+ dotnet-version : |
108+ 8.0.x
109+ 9.0.x
110+ 10.0.x
111+ - name : Install oci-to-wsl
112+ shell : pwsh
113+ run : |
114+ $url = "https://github.com/tg123/oci-to-wsl/releases/download/v0.0.1/oci-to-wsl_windows_x86_64.zip"
115+ $expected = "79772846F1CE4A38E5B2841EA2406A070F4DB64F3DBF3EA32F04B519111FD003"
116+ Invoke-WebRequest $url -OutFile oci-to-wsl.zip
117+ $actual = (Get-FileHash oci-to-wsl.zip -Algorithm SHA256).Hash
118+ if ($actual -ne $expected) {
119+ throw "oci-to-wsl checksum mismatch: expected $expected, got $actual"
120+ }
121+ Expand-Archive -Force oci-to-wsl.zip -DestinationPath .
122+ - name : Start kind cluster in WSL
123+ shell : pwsh
124+ run : |
125+ # Import kindest/node into WSL as a systemd-enabled distro named "kind".
126+ .\oci-to-wsl.exe --profile .github/e2e/kind-wsl.yaml
127+
128+ # Reboot the distro so the systemd configuration written by the profile
129+ # takes effect.
130+ wsl --shutdown
131+
132+ # WSL terminates the lightweight VM once its last session exits, which
133+ # tears down the API server between steps and makes localhost:6443
134+ # connections fail with "actively refused". Hold an idle session open in
135+ # the background so the cluster (and WSL2 localhost forwarding) stay up
136+ # for the duration of the host-side test steps.
137+ Start-Process -FilePath wsl -ArgumentList '-d','kind','-u','root','--','sleep','infinity'
138+
139+ # Bring up the single node control plane in place.
140+ wsl -d kind -u root -- bash /usr/local/bin/bootstrap-kind.sh
141+
142+ # Export a kubeconfig for the Windows host. kubeadm points it at the WSL
143+ # eth0 address; rewrite it to localhost, which WSL2 forwards into WSL.
144+ wsl -d kind -u root -- cat /etc/kubernetes/admin.conf | Out-File -Encoding ascii kind.kubeconfig
145+ (Get-Content kind.kubeconfig) -replace 'server: https://[^ ]+', 'server: https://127.0.0.1:6443' | Set-Content kind.kubeconfig
146+
147+ # Wait until the API server is reachable from the Windows host through
148+ # the forwarded port before handing off to the test steps.
149+ $ok = $false
150+ foreach ($i in 1..60) {
151+ if ((Test-NetConnection -ComputerName 127.0.0.1 -Port 6443 -WarningAction SilentlyContinue).TcpTestSucceeded) {
152+ $ok = $true
153+ break
154+ }
155+ Start-Sleep -Seconds 5
156+ }
157+ if (-not $ok) {
158+ throw "API server on 127.0.0.1:6443 was not reachable from the Windows host"
159+ }
160+ - name : Test
161+ shell : pwsh
162+ env :
163+ K8S_E2E_MINIKUBE : " 1"
164+ KUBECONFIG : ${{ github.workspace }}\kind.kubeconfig
165+ run : |
166+ "" | Out-File -Encoding ascii skip.log
167+ dotnet test tests/E2E.Tests --logger "SkipTestLogger;file=$PWD/skip.log" -p:BuildInParallel=false
168+ if ((Get-Item skip.log).Length -gt 0) {
169+ Get-Content skip.log
170+ Write-Error "CASES MUST NOT BE SKIPPED"
171+ exit 1
172+ }
173+ - name : AOT Test
174+ shell : pwsh
175+ env :
176+ K8S_E2E_MINIKUBE : " 1"
177+ KUBECONFIG : ${{ github.workspace }}\kind.kubeconfig
178+ run : |
179+ "" | Out-File -Encoding ascii skip.log
180+ dotnet test tests/E2E.Aot.Tests --logger "SkipTestLogger;file=$PWD/skip.log" -p:BuildInParallel=false
181+ if ((Get-Item skip.log).Length -gt 0) {
182+ Get-Content skip.log
183+ Write-Error "CASES MUST NOT BE SKIPPED"
184+ exit 1
185+ }
186+
90187on :
91188 pull_request :
92189 types : [assigned, opened, synchronize, reopened]
0 commit comments