fix(tracer): exclude injected keys from cache vector text - #123
Conversation
The @vectorize decorator injects function_uuid, exec_source and trace_id into call kwargs. _perform_background_logging embedded the full kwargs, so a stored execution's vector carried those keys while the cache-lookup path embedded only the caller's own args. The two vectors never aligned — even an identical input capped near cosine 0.76 — so the semantic cache could not hit at the default 0.95 threshold, in both Pro and Lite mode. Strip the reserved keys before vectorizing so stored and looked-up inputs embed identically. Add a regression test that fails on the old behavior. Signed-off-by: Jun Yeong Kim <junyeonggim5@gmail.com>
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: bb8cf28c2f
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| # Keys the @vectorize decorator injects into call kwargs for its own bookkeeping. | ||
| # They must be excluded from the vectorized text so a stored execution embeds the | ||
| # same input as the cache-lookup path (which only sees the caller's own args). | ||
| _RESERVED_VECTOR_KEYS = frozenset({"function_uuid", "exec_source", "trace_id"}) |
There was a problem hiding this comment.
Preserve user trace_id when vectorizing cached inputs
When a @vectorize(semantic_cache=True) function actually declares trace_id as a parameter, _init_trace_root intentionally leaves that caller argument in kwargs, and the cache-lookup path embeds the original kwargs via _check_and_return_cached_result. Adding trace_id to this stripped set means the stored execution vector drops a legitimate input while lookup vectors still include it, so those functions either stop hitting the semantic cache or can compare against vectors that ignored an input the function may depend on. trace_id should only be stripped when it was consumed as tracer metadata, not from user-owned function arguments.
Useful? React with 👍 / 👎.
Summary
The semantic cache never hit — even an identical input capped near cosine 0.76, below the default 0.95 threshold — in both Pro and Lite mode. The storage path embedded the decorator's internal bookkeeping keys into the vector text while the cache-lookup path did not, so the two vectors never aligned.
Bug Fix
@vectorizeinjectsfunction_uuid,exec_source, andtrace_idinto call kwargs. Inmonitoring/tracer.py,_perform_background_loggingembedded the fullctx.kwargs, so a stored execution's vector text contained e.g.function_uuid: <uuid> exec_source: REALTIME. The cache-lookup path (utils/return_caching_utils.py) embeds only the caller's own args, so the stored and looked-up vectors diverged and the semantic cache could not hit at any sane threshold.Fix: strip a
_RESERVED_VECTOR_KEYS = {function_uuid, exec_source, trace_id}set from the kwargs before vectorizing on the storage path, so stored and looked-up inputs embed identically.Changes
src/vectorwave/monitoring/tracer.py_RESERVED_VECTOR_KEYS._perform_background_logging, buildclean_kwargs(kwargs minus reserved keys) and vectorize that instead of the rawctx.kwargs.src/tests/monitoring/test_tracer.pytest_reserved_keys_excluded_from_cache_vector: a spy vectorizer asserts the injected keys/values never appear in the embedded text and that the stored text equals what the lookup path builds from the caller's args. The test fails on the old behavior.Test Results
test_reserved_keys_excluded_from_cache_vectorfails without the fix, passes with it.pytest src/tests/monitoring/test_tracer.py src/tests/utils/test_return_caching.py— 14 passed.🤖 Generated with Claude Code