From 21841cc2ef562593d89ea7d34b584be07df81453 Mon Sep 17 00:00:00 2001 From: Nikola Metulev <711864+nmetulev@users.noreply.github.com> Date: Fri, 31 Jul 2026 14:18:19 -0700 Subject: [PATCH 1/2] fix(winapp-pr): paginate the artifacts query so a busy run's package is findable winapp-pr walks recent runs looking for a downloadable msix-packages artifact. The query asked GitHub for a run's artifacts without --paginate, so it only ever saw the first 30. A run that uploads more than that pushes msix-packages onto page 2, where the query cannot see it -- and the failure is silent in the worst way: it is indistinguishable from a run that genuinely never produced a package, so the walk-back to an older run looks like it is working correctly and hands back a stale build. Observed on a run with 47 artifacts: without --paginate 30 returned msix-packages NOT present with --paginate 47 returned msix-packages present, non-expired The tool reported "no usable msix-packages artifact" for four consecutive good runs and resolved to a build from before the change under test. Nothing in the output suggested the query was the problem. This is a threshold bug, not a regression: the tool worked until a repo's per-run artifact count crossed 30. Any workflow that adds per-shard artifacts (logs, diagnostics, per-job uploads) will trip it, and it will look like the builds are broken. Also widens the diagnostic to report how many artifacts were actually examined -- "has no msix-packages artifact among its 30" makes a truncated page obvious, where the previous wording ("no usable ... artifact") reads as a fact about the run. Verified both directions against a real run: with the fix -> FOUND: msix-packages bytes=61019727 --paginate out -> NOT FOUND, "among its 30" (bug reproduced) The other gh api calls in this script pass an explicit per_page and are "most recent N" queries where truncation is the intent. This was the only "find this named item" query relying on the default page size. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> Copilot-Session: 70dbd3fe-4b72-4e07-a1c8-ac6a8758c4d5 --- scripts/winapp-pr.ps1 | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/scripts/winapp-pr.ps1 b/scripts/winapp-pr.ps1 index de988ab3..753d704c 100644 --- a/scripts/winapp-pr.ps1 +++ b/scripts/winapp-pr.ps1 @@ -616,15 +616,20 @@ function Get-MsixArtifact { param([string]$RepoName, [object[]]$Runs, [switch]$Quiet) foreach ($run in $Runs) { + # --paginate is load-bearing: the artifacts endpoint returns 30 per page, and a run that + # uploads more than that pushes msix-packages onto page 2, where an unpaginated query + # cannot see it. The symptom is indistinguishable from a run that genuinely never built a + # package -- the walk-back to an older run looks like it is working, and silently hands + # back a stale build. Do not remove this without checking .total_count on a busy run. $artifacts = Invoke-Gh @('api', "repos/$RepoName/actions/runs/$($run.id)/artifacts", - '--jq', '.artifacts') + '--paginate', '--jq', '.artifacts') $msix = $artifacts | Where-Object { $_.name -eq $ArtifactName -and -not $_.expired } | Select-Object -First 1 if ($msix) { return [pscustomobject]@{ Run = $run; Artifact = $msix } } if (-not $Quiet) { - Write-Detail "Run $($run.id) has no usable $ArtifactName artifact, trying older run..." + Write-Detail "Run $($run.id) has no $ArtifactName artifact among its $(($artifacts | Measure-Object).Count), trying older run..." } } return $null From 3612ce8b134665900edd31328b899514f2dc93da Mon Sep 17 00:00:00 2001 From: Nikola Metulev Date: Fri, 31 Jul 2026 14:31:18 -0700 Subject: [PATCH 2/2] Potential fix for pull request finding Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com> --- scripts/winapp-pr.ps1 | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/winapp-pr.ps1 b/scripts/winapp-pr.ps1 index 753d704c..de80901c 100644 --- a/scripts/winapp-pr.ps1 +++ b/scripts/winapp-pr.ps1 @@ -629,7 +629,7 @@ function Get-MsixArtifact { return [pscustomobject]@{ Run = $run; Artifact = $msix } } if (-not $Quiet) { - Write-Detail "Run $($run.id) has no $ArtifactName artifact among its $(($artifacts | Measure-Object).Count), trying older run..." + Write-Detail "Run $($run.id) has no usable $ArtifactName artifact among its $(($artifacts | Measure-Object).Count), trying older run..." } } return $null