Files
google__adk-docs/examples/kotlin/snippets/context/CacheMetadataExample.kt
Shahin Saadati 718bcf5c6d Document how to check whether the context cache was used (#2120)
* Document how to check whether the context cache was used

The caching page explained how to turn caching on and never how to tell whether
it is working. CacheMetadata has been available since adk-kotlin 0.6.0 and is
undocumented: adk-python has fourteen code references to cache_metadata, while
adk-docs mentions it twice, both incidental -- a BigQuery schema table and a
bullet in the Live dev guide.

The snippet reads it from Event.cacheMetadata and covers both states the type
can be in, because the constructor enforces the split: cacheName, expireTime and
invocationsUsed must either all be set (an active cache) or all be null (the
fingerprint-only state used for prefix matching before a cache exists).

Notes that token counts live on LlmResponse.usageMetadata rather than here,
which the KDoc calls out to avoid duplication and a reader would otherwise
reasonably look for on CacheMetadata.

Badged Kotlin v0.6.0 and verified rather than assumed: the snippet compiles
against a temporary 0.6.0 pin as well as the current 0.7.0 one.

Transcluded and registered, so CI compiles and lints it. Exercised all four
paths with synthetic events: no metadata, fingerprint-only, active, and active
with expireSoon true.

* Correct when CacheMetadata is present on an event

The section claimed every event backed by an LLM response carries a
CacheMetadata. It does not: LlmResponse.cacheMetadata is null when caching
is disabled and also when the call produced no cache information, so the
claim was wrong even with caching on.

Say "can carry", name both null cases, and explain why the snippet checks
before reading. The snippet's own comment made the same overstatement.

* docs: clarify the behavior of expireSoon and cache status in documentation and snippets
2026-08-17 15:40:28 -07:00

47 lines
1.7 KiB
Kotlin

/*
* Copyright 2026 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.google.adk.kt.examples.context
import com.google.adk.kt.events.Event
// --8<-- [start:cache_metadata]
/** Reports whether the context cache was used for the LLM call behind [event]. */
fun logCacheUse(event: Event) {
// Null when caching is disabled, and on any event whose LLM call produced
// no cache information.
val cache = event.cacheMetadata ?: return
if (!cache.isActive) {
// Fingerprint-only: ADK measured the cacheable prefix but no cache is in
// use. That is the first turn, a prefix that changed since the last turn,
// or a cache ADK did not create -- most often because the cacheable
// prefix was below minTokens.
println("Not cached yet; fingerprinted ${cache.contentsCount} contents.")
return
}
println("Cache ${cache.cacheName} reused ${cache.invocationsUsed} time(s).")
if (cache.expireSoon) {
// Advisory only. ADK goes on reusing the cache until it actually expires,
// so this is a heads-up for your own code, not a prediction about the
// next turn.
println("Cache is at or near expiry.")
}
}
// --8<-- [end:cache_metadata]