Repository navigation
fix(flags): serialize UUID values in flags request bodies - #1156
Merged
Merged
Conversation
The flags request body goes straight to DatetimeSerializer without clean(), so a UUID distinct id, group key, or flag property raised TypeError. The SDK swallowed it and returned missing flags without sending a request. Serialize UUIDs as strings, matching what clean() already does for captured events.
marandaneto
approved these changes
Nov 2, 2026
marandaneto
left a comment
Member
There was a problem hiding this comment.
The code looks good; no qualifying findings. Verdict: correct.
Member
|
thanks @luantaraschi |
marandaneto
enabled auto-merge (squash)
November 2, 2026 15:53
4 of 6 tasks
eli-r-ph
added a commit
that referenced
this pull request
Nov 4, 2026
* docs(mcp): clarify unsigned session token trust (#1151) (cherry picked from commit b4c2e47) * feat: send a flat body from emails.send (#1155) emails.send now posts template_id and distinct_id at the top level of the request body, for the sync and async clients. The server accepts both shapes, so this changes only the wire format. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Generated-By: PostHog Desktop Task-Id: e72a2c10-f145-4f7c-8754-a4fcc06a18be (cherry picked from commit f20066e) * chore: Release v7.81.2 [skip ci] (cherry picked from commit 0aec2d9) * Update generated references (cherry picked from commit 14b4d33) * feat: add a per-read send_feature_flag_events option to snapshot reads (#1148) (cherry picked from commit b10c38a) * fix: send flag id and version on locally evaluated $feature_flag_called (#1149) Locally evaluated flags in get_feature_flag(), feature_enabled() and get_feature_flag_result() sent $feature_flag_called without $feature_flag_id or $feature_flag_version, because both were read only from remote /flags metadata. Read them from the local flag definition that produced the value. evaluate_flags() already sent the id for local flags but dropped the definition's version; send it too. (cherry picked from commit e24100b) * chore: Release v7.82.0 [skip ci] (cherry picked from commit b6f8eaf) * Update generated references (cherry picked from commit 0a5417f) * fix(flags): treat concurrent fallback-cache eviction as a cache miss (#1167) * fix(flags): treat concurrent cache eviction as a cache miss * chore: add changeset for fallback cache eviction fix --------- Co-authored-by: Manoel Aranda Neto <marandaneto@gmail.com> (cherry picked from commit 9ebfb87) * fix(flags): stringify regex properties as compact JSON (#1157) Local regex and not_regex matching called str() on the property. (cherry picked from commit 5b50683) * fix(flags): serialize UUID values in flags request bodies (#1156) The flags request body goes straight to DatetimeSerializer without clean(), so a UUID distinct id, group key, or flag property raised TypeError. The SDK swallowed it and returned missing flags without sending a request. Serialize UUIDs as strings, matching what clean() already does for captured events. (cherry picked from commit a239479) * chore: Release v7.82.1 [skip ci] (cherry picked from commit 8c5e9df) * Update generated references (cherry picked from commit fbbd109) * fix(ai): count Gemini tool use prompt tokens as input tokens (#1164) * fix(ai): count Gemini tool use prompt tokens as input tokens Built-in tools (Google Search, URL context) report the retrieved content in tool_use_prompt_token_count, separately from prompt_token_count, so input tokens were under-reported on grounded responses. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> Signed-off-by: Alex Castillo <alex.castillog33@gmail.com> * chore: add changeset for Gemini tool use prompt tokens Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> Signed-off-by: Alex Castillo <alex.castillog33@gmail.com> * fix(ai): keep unbilled Google Search retrieval out of Gemini input tokens tool_use_prompt_token_count is only added to input tokens when the response carries url_context_metadata (billed as input); Search retrieval is not. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> * fix(ai): carry Gemini URL context flag across stream chunks URL context metadata can arrive on a different chunk than the final usage_metadata, so the tool-use prompt tokens were dropped in streaming. Track the flag across chunks in the sync and async clients. Co-Authored-By: Claude Sonnet 5.5 <noreply@anthropic.com> * fix(ci): format Gemini clients and refresh API snapshot --------- Signed-off-by: Alex Castillo <alex.castillog33@gmail.com> Co-authored-by: Claude Sonnet 5.5 <noreply@anthropic.com> Co-authored-by: Manoel Aranda Neto <marandaneto@gmail.com> (cherry picked from commit 57b9db8) * chore: Release v7.82.2 [skip ci] (cherry picked from commit 16e99f0) * Update generated references (cherry picked from commit 1dfca27) --------- Signed-off-by: Alex Castillo <alex.castillog33@gmail.com> Co-authored-by: Dustin Byrne <dustin@posthog.com> Co-authored-by: Harley Alexander <43975092+mayteio@users.noreply.github.com> Co-authored-by: releaser-posthog-python[bot] <262414804+releaser-posthog-python[bot]@users.noreply.github.com> Co-authored-by: Anders <754494+andehen@users.noreply.github.com> Co-authored-by: Sarbajit Sengupta <73594751+Sarbajit-Sengupta@users.noreply.github.com> Co-authored-by: Manoel Aranda Neto <marandaneto@gmail.com> Co-authored-by: Luan Taraschi <130802253+luantaraschi@users.noreply.github.com> Co-authored-by: alexcastgonz <82875882+pcbeingused333@users.noreply.github.com> Co-authored-by: Claude Sonnet 5.5 <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.
💡 Motivation and Context
When the distinct id is a
uuid.UUID,get_feature_flag,feature_enabled,get_all_flagsandevaluate_flagsreturn missing flags and no request reaches/flags.ID_TYPESincludesUUID, andcapture()handles it, because events go throughclean(), which turns UUIDs into strings. The flags request body skipsclean()and goes straight tojson.dumps(..., cls=DatetimeSerializer), which raisesTypeError: Object of type UUID is not JSON serializable. The SDK logs it and treats every flag as missing. A UUID group key or a UUID insideperson_propertiesorgroup_propertiesfails the same way, in bothClientandAsyncClient.DatetimeSerializer.defaultnow returnsstr(uuid)for UUIDs, which is whatclean()already does for captured events. I put the fix in the serializer instead of stringifying the distinct id at the call site so that group keys and flag properties are covered too, and the sync and async request paths share it.💚 How did you test it?
test_uuid_serializationfor the serializer,test_flags_sends_uuid_inputs_as_stringsfor syncflags()with a UUID distinct id, group key and person property, andtest_async_flags_sends_uuid_inputs_as_stringsforasync_flags. All three fail on main with theTypeErrorand pass with the fix.client.get_feature_flag("beta", some_uuid)returnsNoneand the server sees no/flagsrequest. With the fix it returnsTrueafter one request. Passingstr(some_uuid)givesTruebefore and after.ruff format --check,ruff check(0.12.2, the version inuv.lock), the mypy baseline andpython -W error -c "import posthog"are clean.python:3.12-slimcontainer: 5850 passed on main, 5853 passed with this change, no failures in either.📝 Checklist
If releasing new changes
sampo addto generate a changeset file🤖 Agent context
Autonomy: Human-driven (agent-assisted)
Claude Code with Claude Opus 5.5 found this while checking posthog-python against the server scenarios in PostHog/sdk-specs, reproduced it against a local mock server, and wrote the fix and the tests. Luan directed the work.