Follow-up from #226 MVP (PR #402 lands /v1/embeddings).
Problem
`/v1/audio/transcriptions` and `/v1/audio/translations` (OpenAI Whisper-shape audio endpoints) do not emit `UsageEvent` to `ProxyState.usage_sink` on success. Same budget-ledger / /logs gap as embeddings.
Audio endpoints are billed differently from token-based endpoints — typically by audio duration in seconds. The `UsageEvent` shape will need adapting:
- `prompt_tokens` doesn't map cleanly. OpenAI's audio response does not return a usage block today.
- A custom telemetry field for `audio_seconds` may be needed cp-api-side, OR audio_seconds can be derived from the audio file's duration on the DP and emitted as `prompt_tokens` (cp-api recomputes cost from pricing catalog anyway).
Acceptance criteria
- On a successful 200 from /v1/audio/transcriptions or /v1/audio/translations, exactly one `UsageEvent` arrives on the configured sink
- Token/duration mapping documented in the PR (likely needs cp-api coordination on the receiving side)
- `model_id`, `api_key_id`, `inbound_protocol = "openai"` per chat.rs convention
References
Follow-up from #226 MVP (PR #402 lands /v1/embeddings).
Problem
`/v1/audio/transcriptions` and `/v1/audio/translations` (OpenAI Whisper-shape audio endpoints) do not emit `UsageEvent` to `ProxyState.usage_sink` on success. Same budget-ledger / /logs gap as embeddings.
Audio endpoints are billed differently from token-based endpoints — typically by audio duration in seconds. The `UsageEvent` shape will need adapting:
Acceptance criteria
References