feat: Add _strict=true to url_search_params_serializer - #617
Merged
Conversation
razor-x
pushed a commit
to seamapi/php
that referenced
this pull request
Aug 14, 2026
Mirror seamapi/python#617: serialize() and update() take a strict flag that appends _strict=true to any non-empty query, telling the Seam API to use strict, schema-aware parsing. The flag is appended after the sort so it always sits last, a caller-supplied _strict param is replaced rather than repeated, and a query with no serializable params stays empty. The SDK client always serializes in strict mode. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2
razor-x
pushed a commit
to seamapi/ruby
that referenced
this pull request
Aug 14, 2026
Match seamapi/python#617: the SDK serializes query params with strict mode enabled, appending _strict=true after the sorted pairs of any non-empty query so the Seam API uses strict, schema-aware parsing. The strict entry points live in strict_url_search_params_serializer so the base serializer stays a faithful port of the standard, and a query built entirely by the caller still passes through without it. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp
razor-x
pushed a commit
to seamapi/php
that referenced
this pull request
Aug 14, 2026
Mirror seamapi/python#617: the new StrictUrlSearchParamsSerializer wraps the base serializer and appends _strict=true to any non-empty query, telling the Seam API to use strict, schema-aware parsing. The flag is appended after the sort so it always sits last, a caller-supplied _strict param is replaced rather than repeated, and a query with no serializable params stays empty. The flag is Seam API behavior, not part of the serialization standard, so it is isolated in the wrapper and the base UrlSearchParamsSerializer stays a pure implementation of the standard. The SDK client serializes every request with the strict wrapper. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2
razor-x
added a commit
to seamapi/ruby
that referenced
this pull request
Aug 14, 2026
* feat: Add URL search params serializer Port @seamapi/url-search-params-serializer to Ruby: a UrlSearchParams pair collection with WHATWG form encoding and UTF-16 code unit sort, a serializer with ECMAScript number formatting and JavaScript toISOString date formatting, and the Seam::NULL sentinel distinguishing an explicit JSON null from an omitted parameter. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * feat: Serialize request params with the URL search params serializer Query params are built by a Faraday params encoder that applies the serializer, so requests carry the exact encoding, ordering, and number formatting the Seam API parses; Faraday's default encoder dropped the '=' from empty-array params, silently turning an empty filter into no filter. Request bodies replace the Seam::NULL sentinel with nil before JSON encoding, and generated methods now document nullable parameters with Seam::Null in their types, consuming the blueprint isNullable flag. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * test: Add URL search params conformance harness Verify the Ruby serializer byte for byte against the TypeScript reference implementation over hand-built, structural-fuzz, and float-fuzz fixtures, and round-trip the output through @seamapi/url-search-params-parser in strict mode. The harness needs Node and the reference implementation, so it lives in dev/conformance outside the shipped gem. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * chore: Remove the URL search params conformance harness The serializer standard is stable, so the Node-based comparison against the TypeScript reference and its devDependencies are not worth carrying. The RSpec suite covers the spec directly, including the exact ECMAScript exponent formatting and multi-byte encoding cases the harness verified. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * feat: Add _strict=true to url_search_params_serializer Match seamapi/python#617: the SDK serializes query params with strict mode enabled, appending _strict=true after the sorted pairs of any non-empty query so the Seam API uses strict, schema-aware parsing. The strict entry points live in strict_url_search_params_serializer so the base serializer stays a faithful port of the standard, and a query built entirely by the caller still passes through without it. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * chore: Trim comments to constraints the code cannot show Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * chore: Delete comments that restate tested behavior Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * docs: Match the URL search params section to the other SDKs Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017p9TwdqYv9ccnv7nGvpfsp * Move UrlSearchParamsEncoder down --------- Co-authored-by: Claude <noreply@anthropic.com>
razor-x
added a commit
to seamapi/php
that referenced
this pull request
Aug 14, 2026
* feat: implement the URL search params serialization standard Port @seamapi/url-search-params-serializer to PHP as Seam\UrlSearchParamsSerializer over a Seam\UrlSearchParams pair collection, byte-for-byte identical to the TypeScript reference implementation. The unit test suite mirrors the reference and Python SDK suites, covering every branch of the standard. PHP's own primitives each diverge from the standard, so the port implements them directly: urlencode() is RFC 3986 flavored (escapes *, keeps ~) where the WHATWG form encoding does the opposite; float casts render 1.0, switch to exponents at the wrong thresholds, and spell them E+21, so floats follow the ECMAScript Number::toString algorithm; sorting compares UTF-16 code units, not UTF-8 bytes; and dates always carry exactly three fractional digits and a literal Z. PHP has a single absence value, so the Seam\NullValue enum adds the explicit null sentinel: null means the safe option of omitting a param, and sending null is always spelled NullValue::NULL. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 * feat: apply the URL search params standard and type nullable params Wrap the Guzzle client in Seam\Http\SerializingClient so every request follows the serialization standard. Query params given as a map are serialized with UrlSearchParamsSerializer and handed to Guzzle as a raw query string, since Guzzle's own encoder escapes *, keeps ~, and drops an empty array entirely instead of sending name= (which the API reads as the empty array rather than an unfiltered request). NullValue::NULL sentinels in JSON bodies become JSON null, so the sentinel works on both transports. A query already given as a string passes through untouched, and nothing serialized means no query at all rather than a bare trailing ?. Consume the blueprint's isNullable flag in the codegen: a nullable param is typed string|NullValue|null and accepts the sentinel, while a merely optional one keeps ?string and rejects it, so the type system catches sending an accidental null where it would unset a value. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 * feat: add _strict=true to the URL search params serializer Mirror seamapi/python#617: the new StrictUrlSearchParamsSerializer wraps the base serializer and appends _strict=true to any non-empty query, telling the Seam API to use strict, schema-aware parsing. The flag is appended after the sort so it always sits last, a caller-supplied _strict param is replaced rather than repeated, and a query with no serializable params stays empty. The flag is Seam API behavior, not part of the serialization standard, so it is isolated in the wrapper and the base UrlSearchParamsSerializer stays a pure implementation of the standard. The SDK client serializes every request with the strict wrapper. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 * refactor: drop comments that narrate instead of constrain Keep a comment only when it says something the code cannot: a non-obvious why, an external constraint, or an invariant a future edit would break. Comments that narrate a test, restate an assertion, or argue the code is correct are deleted; the tests are the explanation. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 * docs: align the README sections with the other SDKs Setting a param to null becomes a top-level usage section and Serializing URL search params follows the structure of the Python and Ruby READMEs, including the note explaining why PHP spells the sentinel NullValue::NULL where the other SDKs spell it NULL with type Null: both names are reserved in PHP, so the type and the value live on one enum. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 * refactor: sort search params by stable byte order Drop the UTF-16 sort key: a stable sort is what the standard needs to keep array element order, and byte order matches URLSearchParams.sort() for every ASCII name, which all Seam param names are. Only a name beyond the Basic Multilingual Plane could order differently than the reference implementation, and then only against a name in U+E000 to U+FFFF. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01HMKbYgbsoFdKiiaxXB6jh2 --------- Co-authored-by: Claude <noreply@anthropic.com>
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.
No description provided.