[fix] drain pending Gemini usage metadata before realtime session teardown - #3
Merged
Merged
Conversation
…rdown ## AS IS - Gemini Live 只在 generation 結束時送 usageMetadata;caller 在第一句話 講完前後掛斷時,close_on_disconnect 的 teardown 立刻 off 掉 metrics_collected listener 並 cancel receive loop,in-flight 的 usage event 永遠收不到 —— 單 turn 通話的 LLM token usage 直接歸零 - 每通 realtime 通話的最後一個 turn 都有同樣的 race ## TO BE - RealtimeSession 新增 drain_pending_metrics() hook(base 預設 no-op, fallback adapter 委派給 active child) - AgentActivity._close_session 在拆 listener 之前先 await 這個 hook, drain 出來的 usage event 仍會進 session.usage - Gemini plugin 實作:當前 generation 尚未收到 usageMetadata 時,最多等 LK_GOOGLE_USAGE_DRAIN_TIMEOUT(預設 2s);已收到 / 未連線 / 正在關閉 時不等,正常結束的通話零額外延遲 Co-Authored-By: Claude Fable 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01LLsDzcMV2NVcF9o8rN52u4
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.
修 pathorsAI/pathors#2204:realtime 通話中使用者在 AI 第一句話講完前後掛斷時,該通話的 Gemini usage metrics 完全收不到。
AS IS
Gemini Live 只在 generation 結束時送
usageMetadata。掛斷觸發的 teardown 裡AgentActivity._close_session()先off("metrics_collected")、再rt_session.aclose()砍 receive loop——in-flight 的 usage event 永遠到不了session.usage。單 turn 通話整通 LLM usage 歸零;多 turn 通話固定漏最後一個 turn。TO BE
兩層修正:
llm/realtime.py+voice/agent_activity.py):RealtimeSession新增drain_pending_metrics()hook(預設 no-op;fallback adapter 委派給 active child),_close_session()在拆 listener 之前 await 它——drain 出來的 usage event 因此仍會被收進session.usage。realtime_api.py):_ResponseGeneration追蹤_usage_received;drain_pending_metrics()在「當前 generation 的 usage 還沒到、連線還活著」時最多等LK_GOOGLE_USAGE_DRAIN_TIMEOUT(預設 2s,≤0 可關閉)。已收到 / 未連線 / 正在關閉時直接 return——正常結束的通話零額外延遲。timeout 時留 warning log,該 turn usage 維持缺失(同修正前),可觀測。掛斷時 SDK 會先送 interrupt(
activity_start),Gemini 隨即 flushturnComplete+ usage,2s 的 window 足以涵蓋絕大多數 case。測試
tests/test_realtime_usage_drain.py(unit ×8):drain 的各 no-op guard、等到 usage、timeout、LK_GOOGLE_USAGE_DRAIN_TIMEOUT=0關閉,以及 activity 層的順序測試(drain hook emit 的 metric 必須進session.usage——沒有_close_session的修改該測試會 fail)pytest --unit:1016 passed(base commit 對照跑,僅有的 1 failed + 9 errors 在 base 上完全相同,是測試環境 egress proxy 擋test.livekit.cloud造成,與本 PR 無關)ruff check/ruff format --check全 repo 過;scripts/check_types.py(mypy strict)618 檔全過對應的主 repo submodule bump:pathorsAI/pathors 的
claude/realtime-usage-metrics-disconnect-5x1xxbbranch。🤖 Generated with Claude Code
https://claude.ai/code/session_01LLsDzcMV2NVcF9o8rN52u4
Generated by Claude Code