Skip to content

fix: Serialize datetime values as UTC with a Z suffix - #754

Open
gjtorikian wants to merge 1 commit into
mainfrom
fix/serialize-datetimes-as-utc-z
Open

gjtorikian wants to merge 1 commit into
mainfrom
fix/serialize-datetimes-as-utc-z

Conversation

@gjtorikian

Copy link
Copy Markdown
Contributor

Description

  • events.list_events(range_start=datetime.now(UTC).isoformat()) was rejected by the API with invalid_date_range_exception (Events range_start rejects datetime.isoformat() output #743). The API accepts only the Z form for date-time parameters, and generated resources type them as str and forward them untouched, so callers had to discover the exact format by trial and error.
  • Query strings and JSON bodies now accept datetime objects. _query_value and _encode_body in _base_client.py route them through _format_datetime, which now converts aware values to UTC and assumes naive values are UTC before emitting 2026-10-01T18:01:14.870Z.
  • Strings still pass through untouched, so existing callers are unaffected. _format_datetime also backs generated to_dict, so model fields set to non-UTC datetimes now serialize in the form the API accepts instead of carrying an offset.
  • Follow-ups land separately: the Events DTO gains format: date-time in the API repo, and the Python emitter will type date-time parameters as Union[datetime, str] so this path also type-checks. Until then it works at runtime but a type checker will flag the str annotation.

Closes #743

The API only accepts the `Z` form for date-time parameters, so
`range_start=datetime.now(UTC).isoformat()` was rejected with a 400
(#743). Generated resources type these params as `str` and forward
them untouched, which leaves callers to discover the exact format by
trial and error.

Accepting `datetime` objects in query strings and JSON bodies gives
callers a path that cannot produce a rejected timestamp. Aware values
are converted to UTC first and naive values are assumed to be UTC,
matching the API contract and the legacy `utcnow()` habit. Strings
still pass through untouched.

Refs #743
@gjtorikian
gjtorikian requested review from a team as code owners October 19, 2026 22:26
@greptile-apps

greptile-apps Bot commented Oct 19, 2026 •

Copy link
Copy Markdown
Contributor

RetriggerView in GreptileConfidence Score: 5/5

[Medium impact] The PR appears safe to merge; no actionable defects were found.

Summary

The PR sends datetime values as UTC strings ending in Z.

  • WorkOS requests send datetime values as UTC timestamps ending in Z.

gjtorikian explicitly deferred changing generated date parameter annotations from str to a later follow-up.

Diagram

%%{init: {'theme': 'neutral'}}%%
flowchart LR
  Query["Query datetime"] --> Q["_query_value"]
  Body["JSON datetime"] --> J["_json_default"]
  Model["Model datetime"] --> T["to_dict"]
  Q --> F["_format_datetime"]
  J --> F
  T --> F
  F --> UTC["UTC, milliseconds, Z suffix"]
Loading

Reviews (1) · Last reviewed commit: "fix: Serialize datetime values as UTC wi..." · Reviewed by Greptile

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

Events range_start rejects datetime.isoformat() output

1 participant