Skip to content

Return null, not throw, for stored JSON with no $type discriminator - #167

Merged
matt-edmondson merged 1 commit into
mainfrom
fix/164-missing-type-discriminator
Sep 27, 2026
Merged

matt-edmondson merged 1 commit into
mainfrom
fix/164-missing-type-discriminator

Conversation

@matt-edmondson

Copy link
Copy Markdown
Contributor

Fixes #164

What was wrong

When well-formed JSON has no $type property (for example {} or {"Token":"x"}), System.Text.Json's polymorphic deserializer throws NotSupportedException. CredentialSerialization.Deserialize and DeserializeFromString caught only JsonException. A corrupt, hand-edited or foreign entry in the Windows, macOS or Linux store therefore made CredentialCache.TryGet throw, even though the Try contract promises it returns false.

Change

Both methods now also catch NotSupportedException and return null, which matches their documented behaviour ("returns null if the bytes do not represent a known credential"). The library targets net9.0 and net10.0 only, so the older System.Text.Json InvalidOperationException variant mentioned in the triage doesn't apply.

Tests

New file UnknownPayloadTests:

  • Deserialize and DeserializeFromString return null for {}, {"Token":"x"}, {"$type":"Bogus"}, [] and 123.
  • TryGet returns false for a planted {} or {"Token":"x"} entry. The entry sits in a RawBlobCredentialStore, which reads raw bytes through DeserializeAndScrub the same way the native stores do.

With CredentialSerialization.cs reverted, the 6 missing-discriminator cases fail. With the fix, the suite passes: 61 passed, and 5 native-store tests skipped as inconclusive with no keyring on the runner.

🤖 Generated with Claude Code

https://claude.ai/code/session_014jCUYfoRMwhybsUaSa1NFm


Generated by Claude Code

…inator

System.Text.Json's polymorphic deserializer throws NotSupportedException for
well-formed JSON that lacks a $type property, such as {} or {"Token":"x"}.
Deserialize and DeserializeFromString caught only JsonException, so a
corrupt or foreign entry in a native store made CredentialCache.TryGet throw
instead of returning false. Both now treat that payload as unknown.

Fixes #164

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_014jCUYfoRMwhybsUaSa1NFm
@sonarqubecloud

Copy link
Copy Markdown

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.

TryGet throws NotSupportedException when a stored entry is JSON without a $type discriminator, instead of returning false

2 participants