impl From<lash_core::TokenLedgerEntry> for RemoteTokenLedgerEntry {
fn from(value: lash_core::TokenLedgerEntry) -> Self {
let lash_core::TokenLedgerEntry {
source,
model,
usage,
} = value;
Self {
source,
model,
usage: usage.into(),
}
}
}
impl From<RemoteTokenLedgerEntry> for lash_core::TokenLedgerEntry {
fn from(value: RemoteTokenLedgerEntry) -> Self {
let RemoteTokenLedgerEntry {
source,
model,
usage,
} = value;
Self {
source,
model,
usage: usage.into(),
}
}
}
impl RemoteTurnResult {
pub fn from_core(
session_id: impl Into<String>,
turn_id: impl Into<String>,
turn: lash_core::AssembledTurn,
activities: impl IntoIterator<Item = RemoteTurnActivity>,
) -> Self {
let lash_core::AssembledTurn {
state: _,
outcome,
assistant_output,
execution,
token_usage,
children_usage,
tool_calls,
errors,
} = turn;
let parent = RemoteUsage::from(token_usage);
let children = children_usage
.into_iter()
.map(RemoteTokenLedgerEntry::from)
.collect::<Vec<_>>();
let mut total = parent.clone();
for child in &children {
total.add(&child.usage);
}
let outcome = RemoteTurnOutcome::from(outcome);
let status = RemoteTurnStatus::from(&outcome);
Self {
protocol_version: REMOTE_PROTOCOL_VERSION,
session_id: session_id.into(),
turn_id: turn_id.into(),
status,
outcome,
assistant_output: assistant_output.into(),
usage: RemoteTurnUsageSummary {
parent,
children,
total,
},
execution: execution.into(),
tool_calls: tool_calls.into_iter().map(Into::into).collect(),
issues: errors.into_iter().map(Into::into).collect(),
activities: activities.into_iter().collect(),
metadata: HashMap::new(),
}
}
}
impl From<&RemoteTurnOutcome> for RemoteTurnStatus {
fn from(value: &RemoteTurnOutcome) -> Self {
match value {
RemoteTurnOutcome::Finished { .. } | RemoteTurnOutcome::AgentFrameSwitch { .. } => {
Self::Completed
}
RemoteTurnOutcome::Stopped {
stop: RemoteTurnStop::Cancelled,
} => Self::Cancelled,
RemoteTurnOutcome::Stopped { .. } => Self::Failed,
}
}
}
impl From<lash_core::TurnOutcome> for RemoteTurnOutcome {
fn from(value: lash_core::TurnOutcome) -> Self {
match value {
lash_core::TurnOutcome::Finished(finish) => Self::Finished {
finish: finish.into(),
},
lash_core::TurnOutcome::AgentFrameSwitch { frame_id, task } => {
Self::AgentFrameSwitch { frame_id, task }
}
lash_core::TurnOutcome::Stopped(stop) => Self::Stopped { stop: stop.into() },
}
}
}
impl From<lash_core::TurnFinish> for RemoteTurnFinish {
fn from(value: lash_core::TurnFinish) -> Self {
match value {
lash_core::TurnFinish::AssistantMessage { text } => Self::AssistantMessage { text },
lash_core::TurnFinish::SubmittedValue { value } => Self::SubmittedValue { value },
lash_core::TurnFinish::ToolValue { tool_name, value } => {
Self::ToolValue { tool_name, value }
}
}
}
}
impl From<lash_core::TurnStop> for RemoteTurnStop {
fn from(value: lash_core::TurnStop) -> Self {
match value {
lash_core::TurnStop::Cancelled => Self::Cancelled,
lash_core::TurnStop::Incomplete => Self::Incomplete,
lash_core::TurnStop::InvalidInput => Self::InvalidInput,
lash_core::TurnStop::MaxTurns => Self::MaxTurns,
lash_core::TurnStop::ToolFailure => Self::ToolFailure,
lash_core::TurnStop::ProviderError => Self::ProviderError,
lash_core::TurnStop::PluginAbort => Self::PluginAbort,
lash_core::TurnStop::RuntimeError => Self::RuntimeError,
lash_core::TurnStop::SubmittedError { value } => Self::SubmittedError { value },
lash_core::TurnStop::ToolError { tool_name, value } => {
Self::ToolError { tool_name, value }
}
}
}
}
impl From<lash_core::AssistantOutput> for RemoteAssistantOutput {
fn from(value: lash_core::AssistantOutput) -> Self {
let lash_core::AssistantOutput {
safe_text,
raw_text,
state,
} = value;
Self {
safe_text,
raw_text,
state: state.into(),
}
}
}
impl From<lash_core::OutputState> for RemoteAssistantOutputState {
fn from(value: lash_core::OutputState) -> Self {
match value {
lash_core::OutputState::Usable => Self::Usable,
lash_core::OutputState::EmptyOutput => Self::EmptyOutput,
lash_core::OutputState::TracebackOnly => Self::TracebackOnly,
lash_core::OutputState::RecoveredFromError => Self::RecoveredFromError,
}
}
}
impl From<lash_core::ExecutionSummary> for RemoteExecutionSummary {
fn from(value: lash_core::ExecutionSummary) -> Self {
let lash_core::ExecutionSummary {
had_tool_calls,
had_code_execution,
} = value;
Self {
had_tool_calls,
had_code_execution,
}
}
}
impl From<lash_core::ToolCallRecord> for RemoteToolCallSummary {
fn from(value: lash_core::ToolCallRecord) -> Self {
let lash_core::ToolCallRecord {
call_id,
tool,
args,
output,
duration_ms,
} = value;
Self {
call_id,
tool_name: tool,
args,
outcome: output.into(),
duration_ms,
}
}
}
impl From<lash_core::ToolCallOutput> for RemoteToolCallOutcome {
fn from(value: lash_core::ToolCallOutput) -> Self {
let lash_core::ToolCallOutput {
outcome,
control: _,
} = value;
match outcome {
lash_core::ToolCallOutcome::Success(value) => Self::Success(value.to_json_value()),
lash_core::ToolCallOutcome::Failure(value) => Self::Failure(value.to_json_value()),
lash_core::ToolCallOutcome::Cancelled(value) => Self::Cancelled(value.to_json_value()),
}
}
}
impl From<lash_core::TurnIssue> for RemoteTurnIssue {
fn from(value: lash_core::TurnIssue) -> Self {
let lash_core::TurnIssue {
kind,
code,
terminal_reason,
message,
raw,
} = value;
Self {
kind,
code,
terminal_reason: terminal_reason.map(Into::into),
message,
raw,
}
}
}