Record another model provider
Place one invocation immediately around each actual provider request.
Use startInvocation and complete when an existing provider integration cannot
use LedgeLanguageModelSession. Your adapter supplies native request/response
data as JSON and preserves the provider result for the application.
import LedgeKit
func recordProviderRequest(
run: LedgeTraceHandle?,
input: LedgeJSONValue,
call: () async throws -> LedgeJSONValue
) async throws -> LedgeJSONValue {
let invocation = await run?.startInvocation(
agent: .init(name: "summarizer", version: 1), input: input
)
do {
let output = try await call()
await invocation?.complete(input: input, output: output)
return output
} catch is CancellationError {
await invocation?.complete(input: input, output: nil, status: .cancelled)
throw CancellationError()
} catch {
await invocation?.complete(
input: input, output: nil,
status: .failure, error: LedgeError(error)
)
throw error
}
}The caller starts and finalizes the run. call must wrap one real provider
request, with input/output matching that request. Supply model metadata at
start and native capture at completion when the provider exposes them. The
minimal JSON callback above illustrates the boundary; adapt it to return your
provider's original response type in a production adapter.
Preserve the model outcome
Finish the invocation before application parsing or validation. A later application error may fail the workflow, but should not rewrite the model result. Complete each invocation once; subsequent completion attempts cannot overwrite it.
startInvocation can return nil for an invalid definition, finished run, or
unknown relationship ID. Treat that as recording unavailable, or validate your
definitions explicitly when testing instrumentation.
Use relationships for parent, retry, and handoff IDs.