pub struct AtomicTokenCounter { /* private fields */ }Expand description
Process-wide token counter. Cheap record on the hot path; richer
per-model stats guarded by an async-compatible mutex and accessed
best-effort via try_lock.
Prefer the super::super::TOKEN_USAGE singleton — constructing your
own instance is only useful in tests.
§Examples
use codetether_agent::telemetry::AtomicTokenCounter;
let c = AtomicTokenCounter::new();
c.record(100, 50);
let (p, o, t) = c.get();
assert_eq!((p, o, t), (100, 50, 150));Implementations§
Source§impl AtomicTokenCounter
impl AtomicTokenCounter
Sourcepub fn record_model_usage(&self, model: &str, prompt: u64, completion: u64)
pub fn record_model_usage(&self, model: &str, prompt: u64, completion: u64)
Record per-model usage without prompt-cache data.
Sourcepub fn record_model_usage_with_cache(
&self,
model: &str,
prompt: u64,
completion: u64,
cache_read: u64,
cache_write: u64,
)
pub fn record_model_usage_with_cache( &self, model: &str, prompt: u64, completion: u64, cache_read: u64, cache_write: u64, )
Record a completion’s usage including prompt-cache read/write tokens.
prompt is the non-cached input tokens billed at full price.
cache_read is billed at 10% of input price; cache_write at 125%
on Anthropic / Bedrock. See crate::provider::pricing.
§Examples
use codetether_agent::telemetry::AtomicTokenCounter;
let c = AtomicTokenCounter::new();
c.record_model_usage_with_cache("claude-sonnet-4", 500, 200, 1_000, 0);
assert_eq!(c.cache_usage_for("claude-sonnet-4"), (1_000, 0));
assert_eq!(c.last_prompt_tokens_for("claude-sonnet-4"), Some(1_500));Sourcepub fn cache_usage_for(&self, model: &str) -> (u64, u64)
pub fn cache_usage_for(&self, model: &str) -> (u64, u64)
Cumulative (cache_read, cache_write) token counts for a model.
Returns (0, 0) if the map is contended or the model is unknown.
Sourcepub fn last_prompt_tokens_for(&self, model: &str) -> Option<u64>
pub fn last_prompt_tokens_for(&self, model: &str) -> Option<u64>
Most recent turn’s full prompt token count (including cache) for a model.
This reflects the current in-flight context size (what the next
request will send), not cumulative lifetime tokens. Returns None
if no completion has been recorded for the model yet.
Source§impl AtomicTokenCounter
impl AtomicTokenCounter
Sourcepub fn record(&self, prompt: u64, completion: u64)
pub fn record(&self, prompt: u64, completion: u64)
Record a single completion. Increments all four global atomics relaxed-ordering — correctness only requires eventual visibility.
Sourcepub fn global_snapshot(&self) -> GlobalTokenSnapshot
pub fn global_snapshot(&self) -> GlobalTokenSnapshot
Snapshot the global counters into a plain-data struct.
Sourcepub fn model_snapshots(&self) -> Vec<TokenUsageSnapshot>
pub fn model_snapshots(&self) -> Vec<TokenUsageSnapshot>
Snapshot every tracked model’s usage. Returns an empty Vec if the
per-model map is currently contended.
Trait Implementations§
Source§impl Debug for AtomicTokenCounter
impl Debug for AtomicTokenCounter
Auto Trait Implementations§
impl !Freeze for AtomicTokenCounter
impl !RefUnwindSafe for AtomicTokenCounter
impl Send for AtomicTokenCounter
impl Sync for AtomicTokenCounter
impl Unpin for AtomicTokenCounter
impl UnsafeUnpin for AtomicTokenCounter
impl !UnwindSafe for AtomicTokenCounter
Blanket Implementations§
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self>
fn instrument(self, span: Span) -> Instrumented<Self>
Source§fn in_current_span(self) -> Instrumented<Self>
fn in_current_span(self) -> Instrumented<Self>
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self>
fn into_either(self, into_left: bool) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§impl<T> IntoRequest<T> for T
impl<T> IntoRequest<T> for T
Source§fn into_request(self) -> Request<T>
fn into_request(self) -> Request<T>
T in a tonic::Request