Visibility
An LLM Service emits identity-aware, inference-specific AccessLogs in real time. The common part identifies the User, Session, Device, Service, Namespace, authorization decision and policy match. The entry.info.llm part records the normalized inference exchange (read more about visibility here).
Body and Header Visibility
Prompt and completion bodies are disabled by default because they routinely contain secrets, personal information, source code and proprietary data. Enable only the required fields:
enableRequestBodyrecords the request body as bytes.enableRequestBodyMaprecords its serialized JSON representation.enableResponseBodyrecords a non-streamed response body as bytes.enableResponseBodyMaprecords its serialized JSON representation.includeRequestHeadersandincludeResponseHeadersselect individual headers.
All headers can be enabled with explicit exclusions:
Sensitive authentication and session headers are excluded even when all headers are enabled. Body and event capture is bounded, so a large body can be omitted. Streamed response bodies and body maps are not recorded through the response-body options.
Access-log visibility and semantic cache storage are independent. A Service that records no prompt or completion body still stores prompt-derived vectors, execution-context digests and generated responses while a semantic cache entry lives.
Entry Types
The type field describes the lifecycle of a response:
COMPLETEis a request with a finite response.STREAM_STARTis emitted when a streamed response starts.STREAM_ENDis the final record of that stream and carries accumulated response metadata and usage.
The source field identifies who produced the response:
UPSTREAMmeans the provider produced it and inference tokens were consumed.SEMANTIC_CACHEmeans an earlier response was reused without invoking the provider.OCTELIUMmeans Octelium produced it, including rejected requests.
isUpstreamInvoked is intentionally separate. A response guardrail can reject provider-generated output, resulting in source: OCTELIUM while isUpstreamInvoked: true and usage still show the tokens consumed.
Complete Response
The following is the LLM-specific part of an example non-streamed AccessLog. Common identity and policy fields are omitted for brevity:
Integer values whose protobuf type is 64-bit are represented as JSON strings.
Model and Reasoning
model distinguishes three names:
requestedis what the downstream asked for.effectiveis what Octelium sent to the provider.reportedis the provider's response value, which can resolve an alias or unpinned name.
Its source is unset when the requested model was preserved, or is CONFIG, PLUGIN or SEMANTIC_ROUTER. plugin names the model plugin when the source is PLUGIN.
reasoning is present when the Service decided the configuration. It contains isDisabled, a served ordinal effort, or a numeric tokenBudget. Octelium does not interpret a reasoning value controlled entirely by the downstream.
Provider Token Usage
usage contains provider-reported counts only. It is never populated with Octelium's estimate, and it is absent for a semantic cache hit. state is COMPLETE for final provider usage or PARTIAL when a stream ended before the final usage report.
inputTokens, outputTokens and totalTokens are accompanied by:
cacheReadInputTokens, which is a subset of input for OpenAI and additive for Anthropic.cacheWriteInputTokens, which Anthropic reports additively.reasoningOutputTokens, which OpenAI already includes in output.
Use estimatedInputTokens and estimateQuality when no provider usage is present, but never treat the estimate as billing truth.
Streamed Response
A streamed response emits a start record followed by an end record. The end record can include time to first token, event count, provider usage and finish reason:
An incomplete stream can have usage.state: PARTIAL and an unset finish reason. Its observed token counts are a floor rather than a final total.
Semantic Cache Hit
An exact or semantic hit has no provider usage and does not spend a token quota:
Cache results are EXACT_HIT, SEMANTIC_HIT, MISS, BYPASS or ERROR. ERROR means an embedding or vector-store failure; the request fails open to the provider. isStored shows whether the observed response was added to the cache.
Rejections
A token quota rejection identifies the plugin and scope that denied the request:
Each applied guardrail produces an entry with PASS, MODIFIED, DENIED or ERROR. ERROR distinguishes an inability to reach a verdict from content that matched a deny pattern.
Metrics and Export
AccessLogs are exported through OpenTelemetry and can be sent to an observability or SIEM backend. Useful dimensions include Service, User, requested and effective model, protocol, operation, route, finish reason, cache result, semantic route, guardrail result and quota result. Only sum usage when measuring provider consumption; it contains authoritative reported values and excludes cache hits.
Read more about the LLM configuration and LLM plugins.