Repository navigation
fix(count-codec): accept integral floats in Count response fields across SDKs - #369
Merged
Merged
Conversation
The generated Go decoders now understand a bare `Count` (u64) field carrying the `crate::codecs::count::deserialize` path. gen_go maps it to a public `uint64` with a raw `jsontext.Value` shadow, treats a missing or null value as a missing member, and emits a `decodeCount` call; an `Option<Count>` or `Vec<Count>` shape is rejected with a clear error because it has no Go shape yet. **Decode helper:** * Added `decodeCount` to `sdk/go/decode.go`, which accepts a non-negative JSON integer or a finite integral float such as `3.0` below `2^64`, as the provider intermittently sends, and reports a fractional, negative, out-of-range, or non-numeric value as a Decode error that never echoes the value. **Tests and docs:** * Added Rust tests covering the mapping, rendering, and rejection paths and Go tests exercising the accepted and rejected inputs. * Documented the count codec rule in ADR 0030.
Providers occasionally send a count as an integral JSON float such as `3.0` where an integer is documented, which previously failed to decode. Count response fields now accept a non-negative finite integral number from either the integer or float path, while still rejecting fractional, negative, non-finite, or out-of-range numbers and non-numbers. **Rust count codec:** * Added `crate::codecs::count` with `deserialize` and `deserialize_option` helpers that decode a `Count` from an integer or an integral float below `2^64`, with an error message that never echoes the offending value. * Applied the codec via `deserialize_with` to every `Count` response field across analyst, company, fundraising, funds, insider-trading, statement summary, and TipRanks models; serialization stays serde's default `u64`. * Documented the accepted range on the `Count` type alias and covered both the `from_str` and `from_value` decode paths with tests. **Regenerated Go models:** * Regenerated the Go SDK models so count shadow fields decode through `decodeCount`, matching the Rust codec they are generated from and keeping the go-sdk-tests hook satisfied in the same commit. Refs: #367
This commit adds coverage that verifies Count members accept integral floats such as 3.0 while rejecting fractional values such as 2.9. **Count source-scan test:** * Added `crates/libfmp/tests/count_fields.rs` to scan the Count source and enforce the decoding contract. **Decode tests across SDKs:** * Added a Rust test in `analyst_stock_grades_endpoints.rs` asserting `3.0` decodes to `3` and `2.9` raises a decode error for `grades-consensus`. * Added a Go test in `analyst_test.go` covering the same integral-float and fractional-count behaviour. * Added Python tests in `test_analyst.py` confirming `3.0` decodes to an `int` and `2.9` maps to `FmpDecodeError`. close #367
benbenbang
enabled auto-merge (rebase)
September 29, 2026 02:30
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.
Providers intermittently send count values as integral JSON floats such as
3.0where an integer is documented, which previously failed to decode. This change makes Count decoding tolerant of integral floats across the Rust, Go, and Python SDKs while still rejecting values that are not valid counts.deserializeanddeserialize_optionhelpers that decode aCountfrom an integer or a finite integral float below2^64, rejecting fractional, negative, non-finite, out-of-range, and non-numeric values without echoing the offending value.Countresponse field across analyst, company, fundraising, funds, insider-trading, statement summary, and TipRanks models, keeping serde's defaultu64serialization.Countfield to a publicuint64decoded via a newdecodeCounthelper, rejectingOption<Count>andVec<Count>shapes that have no Go equivalent yet.decodeCount, matching the Rust codec they are generated from.Counttype alias and the count codec rule in ADR 0030.Closes #367