Skip to content

fix(cli): handle 404 in versions command instead of crashing#143

Merged
Aaronontheweb merged 3 commits into
netclaw-dev:devfrom
Aaronontheweb:fix/versions-404-crash
Jul 22, 2026
Merged

fix(cli): handle 404 in versions command instead of crashing#143
Aaronontheweb merged 3 commits into
netclaw-dev:devfrom
Aaronontheweb:fix/versions-404-crash

Conversation

@Aaronontheweb

Copy link
Copy Markdown
Contributor

Root cause

skillserver versions <name> for a skill that isn't on the server crashed with an unhandled HttpRequestException on the server's 404 (Aborted (core dumped), exit 134), dumping a stack trace.

VersionsCommand.ExecuteAsync calls client.GetSkillVersionsAsync(name), which uses GetFromJsonAsync. That helper calls EnsureSuccessStatusCode() internally and throws HttpRequestException on a 404. Nothing caught it, so the process aborted. Sibling read commands (verify, download-subagent) already wrap their calls in a try/catch (HttpRequestException); versions was the outlier.

Fix

Catch HttpRequestException in VersionsCommand, matching the sibling pattern:

  • A 404 prints a clean Skill '<name>' not found. and exits 1.
  • Any other HttpRequestException falls through to ConsoleOutput.HandleHttpError, exiting 1.

The fix is scoped to the versions path. SkillServerClient is unchanged, so verify and download-subagent are unaffected.

Added VersionsCommandTests with two cases using the existing mock-HttpMessageHandler pattern: a 404 returns 1 without throwing (regression test for this bug), and a successful response returns 0 and lists versions.

Verification

Built the CLI from this branch and ran it against a real ghcr.io/netclaw-dev/skillserver:0.4.0 server.

Missing skill — now exits 1 with a readable message, no stack trace / no core dump:

$ skillserver versions no-such-skill
Skill 'no-such-skill' not found.
exit=1

Existing skill — still lists versions correctly (exit 0):

$ skillserver publish .../hello-greeter
Published [email protected]

$ skillserver versions hello-greeter
VERSION  PUBLISHED   LATEST  SHA256
1.0.0    2026-07-22  *       sha256:37e4bb27...
exit=0

Sibling commands still behave (exit 1, no crash) — client untouched, no regression:

$ skillserver verify .../k8s-log-triage        # not published to server
Error: Response status code does not indicate success: 404 (Not Found).
exit=1

$ skillserver download-subagent no-such-agent 1.0.0 out.md
Error: Response status code does not indicate success: 404 (Not Found).
exit=1

dotnet build (Release): 0 warnings, 0 errors. dotnet test (CLI test project): 114 passed, 0 failed.

Closes #142

skillserver versions <name> for a skill that isn't on the server crashed
with an unhandled HttpRequestException on the 404 (Aborted, exit 134).
GetSkillVersionsAsync uses GetFromJsonAsync, which throws on a non-success
status, and VersionsCommand had no catch around it.

Catch the 404 in VersionsCommand and print a clean "Skill '<name>' not
found." message, exiting 1 -- consistent with how VerifyCommand and
DownloadSubAgentCommand already handle a missing resource. Other
HttpRequestExceptions fall through to ConsoleOutput.HandleHttpError.

The fix is scoped to the versions path; the client is unchanged, so
verify and download-subagent are unaffected.

Closes netclaw-dev#142

@Aaronontheweb Aaronontheweb left a comment

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@Aaronontheweb
Aaronontheweb enabled auto-merge (squash) July 22, 2026 02:14
@Aaronontheweb
Aaronontheweb merged commit bb8eafd into netclaw-dev:dev Jul 22, 2026
7 checks passed
@Aaronontheweb
Aaronontheweb deleted the fix/versions-404-crash branch July 22, 2026 02:27
@Aaronontheweb Aaronontheweb mentioned this pull request Jul 22, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

skillserver versions <name> crashes (unhandled 404) instead of a clean not-found

1 participant