Repository navigation
Show GitHub errors in build-monitor, mark running runs, and list org private repos [patch] - #350
Open
matt-edmondson wants to merge 3 commits into
Open
matt-edmondson wants to merge 3 commits into
matt-edmondson wants to merge 3 commits into
Conversation
…private repos [patch]
- Tick only caught HttpRequestException, but Octokit reports API
failures as ApiException. A bad token or unknown owner crashed the
first refresh, and a later failure (e.g. hitting the rate limit after
~50 minutes) faulted IntervalAction and froze the dashboard. The
dashboard is now rendered by RenderDashboardAsync, which shows rate
limit (with reset time), authorization and other API errors and is
retried on the next tick. One repository's API error marks only its
own row; a rate limit fails the whole refresh.
- GetWorkflowRunsAsync passed UpdatedAt as CompletedAt, so no run ever
showed "In progress...". CompletedAt is now set only for completed runs.
- GetRepositoriesAsync used /users/{owner}/repos, which lists only an
organization's public repositories. Organizations now go through
GetAllForOrg.
Fixes #207
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_017vfJW48r2AEHXkyMC1wF3i
main fails restore on NU1903 (GHSA-v76p-62qx-wwq2) against 3.1.12, so no PR can build. This ports the bump from #270. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017vfJW48r2AEHXkyMC1wF3i
Contributor
Author
|
CI: all three No fix can be ported here yet. The 3.2.0 bump from #270 fails the build in CI without a Six Labors license key, and no patched 3.1.x exists, so I reverted it. Details and the three options for a maintainer are in #348 (comment). Once one of them lands on Generated by Claude Code |
3.2.0 fails the build in CI without a Six Labors license key, so the bump is not a usable fix for NU1903. That decision belongs to the maintainer. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017vfJW48r2AEHXkyMC1wF3i
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #207
What was wrong
BuildMonitorServicecaught onlyHttpRequestException, but Octokit reports API failures asApiExceptionand its subclasses. On the first refresh, a mistyped token or an unknown owner escaped fromLiveas an unhandled exception. On a later refresh the exception faultedIntervalAction, which stopped polling and left the last table on screen indefinitely. This is what happens after about 50 minutes at the default--refresh 30for an org-sized owner, when the rate limit runs out.GetWorkflowRunsAsyncpassedr.UpdatedAtasCompletedAt.UpdatedAtis never null, soIn progress...was unreachable.GetRepositoriesAsynccalled/users/{owner}/repos, which for an organization lists only its public repositories.projectuses the same service, so it had the same gap.Change
New internal
RenderDashboardAsyncreturns either the table or a message, soTickcan't throw. It handles each error class:RateLimitExceededException: shows the hourly limit and when it resets.AuthorizationException: shows the status code and that GitHub rejected the token.ApiException, andHttpRequestException: shows the status and message.Each failure is retried on the next tick instead of ending the polling.
Per repository: an
ApiExceptionmarks only that repo's row asError. A rate-limit error is rethrown instead, so the whole refresh reports it once rather than as a table full of errors.GitHubService.CompletedAtOf: a run'sUpdatedAtbecomesCompletedAtonly when its status iscompleted, so queued, waiting and running runs showIn progress....GetRepositoriesAsynclooks up the owner withUser.Get, then usesGetAllForOrgfor an organization andGetAllForUserotherwise. This costs one extra request per refresh.GitHubServicenow holds anIGitHubClient, with an internal constructor for tests.KtsuTools.BuildMonitornow referencesOctokitdirectly, which the SDK's KTSU0006 rule requires.Not done: the optional warning when
--refresh× repository count would exceed the hourly limit. A user who is the authenticated account still goes throughGetAllForUser, which omits their own private repos.GetAllForCurrentwould fix that, but it is outside this issue's org case.Tests
New
BuildMonitorServiceTests, using Moq forIGitHubServiceandIGitHubClient, with Octokit models deserialized from JSON:In progress....CompletedAtOfis null forqueued,in_progressandwaiting, and isUpdatedAtforcompleted.GetAllForOrg, and a user throughGetAllForUser.With the old behaviour restored in
BuildMonitorService.csandGitHubService.cs(new signatures kept so the tests compile), 8 of the 10 tests fail. The other 2, the completed-run and user-endpoint cases, are guards that pass either way. Full suite with the fix: 395/395.Builds were run with
-p:WarningsNotAsErrors=NU1903, becausemaincurrently fails restore on the SixLabors.ImageSharp advisory (#270).Generated by Claude Code