This document records the external crate and service contracts used by optional UsageKit features. Re-check the linked upstream documentation before changing a major version or wire format.
redis 1.5.0 with the async connection manager and Tokio Rustls.RedisTaskStore::connect_with_timeout.SET key value NX EX seconds preserves the first pre-priced task
attribution and expires abandoned tasks. TTLs are validated as positive
signed 64-bit seconds before the client parses a URL or opens a connection,
matching Redis integer expiry arguments.EVAL operation reads and deletes the attribution atomically.SET,
Redis signed integer representation,
Redis Rust client guidance,
and the redis connection manager API.PostgresTaskStore::with_timeout.DELETE ... RETURNING atomically consumes one completed task
attribution.crates/mcp-usage-store/schema/postgres.sql.mcp_usage_task_attribution. PostgresTaskStore::install rejects the old
shape instead of silently using it.opentelemetry 0.32.0 with metrics only.Meter; UsageKit does not
install an SDK, exporter, global provider, or network transport.Meter API.MeterEventProvider::submit receives a batch of unresolved AggregatedUsage
values in original order. It returns exactly one ordered MeterEventOutcome per
submitted aggregate, or one MeterEventProviderError when no per-event outcome
is available. A wrong outcome count is treated as a batch-wide failure and no
returned outcomes are applied.
Providers own authentication, endpoint selection, transport security, request
encoding, timestamp validation, response classification, and any asynchronous
notification receiver. They must use AggregatedUsage::identifier as the
provider-side idempotency identity because cancellation, panic, timeout, and
batch-wide failures can leave an accepted event ambiguous. Provider-specific
timestamp windows or asynchronous acceptance semantics belong in the provider,
not the generic exporter.
Outcome and error codes must be static, low-cardinality categories with no
credentials, customer data, event identifiers, URLs, response bodies, or other
identifying values. Accepted and PermanentRejection complete an event.
Permanent rejections enter a bounded reconciliation queue. RetryableFailure
leaves an event unresolved and causes the full pipeline batch to remain pending.
The exporter retains process-local partial progress and accepts only the
identical original batch until all events complete or the application calls
abandon_retry_progress. Retries submit only unresolved aggregates in original
order. Applications may pass a verified and correlated late provider rejection
to quarantine_async_rejection so synchronous and asynchronous rejection use
the same bounded, identifier-deduplicated reconciliation queue.
A provider adapter normally maps each aggregate to its own request payload and
keeps the stable identifier in that payload. A typical hosted meter payload
carries an event name, customer identifier, integer value, timestamp, and
idempotency identifier. The generic exporter does not construct that wire format
or apply its timestamp rules. The adapter sends the payloads,
preserves their order, and translates each response into one of:
Accepted when the provider confirms the event.RetryableFailure { code: "unavailable" } when the event remains unresolved.PermanentRejection { code: "invalid_event" } when only that event is invalid.If no per-event result exists, return a batch-wide
MeterEventProviderError::new("unavailable"). The complete adapter example,
including the boxed future shape, is in the
mcp-usage-export README.