1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
//! The response-and-usage conversion a recorded model call writes.
//!
//! A [`ModelCallCompleted`](salvor_core::Event::ModelCallCompleted) event
//! carries two derived values: the response as a JSON [`Value`] and the
//! [`TokenUsage`] counted for the call. [`RunCtx`](crate::RunCtx) computes both
//! at the live IO edge, and the durable log's byte form depends on exactly how
//! it does so, so the conversion lives here as small public functions rather
//! than inline in `ctx.rs`.
//!
//! # Why it is its own module
//!
//! The server-performed model step (`salvor-server`'s client-driven runs) has
//! to record the *same* completion `RunCtx::model_call` records, because a run
//! must replay identically whether the runtime drove the model call natively or
//! the server performed it over the wire. Sharing this conversion, rather than
//! reimplementing it in the server, is what keeps the two paths byte-identical.
//! The functions are pure and side-effect-free: they read a
//! [`MessageResponse`] and return a value, touching no store, clock, or
//! provider.
use TokenUsage;
use MessageResponse;
use ;
/// Rebuilds the wire JSON of a response so the recorded value deserializes back
/// into an equal [`MessageResponse`]. Built by hand because the response type
/// is deserialize-only in `salvor-llm`.
///
/// This is the exact `response` field a `ModelCallCompleted` carries.
/// Narrows a provider-reported token count to the event log's `u32`,
/// saturating rather than failing on a count that cannot occur in practice.
/// The [`TokenUsage`] a completion records for `response`: its input and output
/// counts, each narrowed with [`clamp_tokens`]. This is the exact `usage` field
/// a `ModelCallCompleted` carries.