fix(robot): replace JSON serialization unwrap with graceful error handling
Replace serde_json::to_string(&output).unwrap() with match-based error handling across all robot-mode JSON printers. On serialization failure, the error is now written to stderr instead of panicking. This hardens the CLI against unexpected Serialize failures in production. Affected commands: count (2), embed, generate-docs, ingest (2), search, stats, sync (2), sync-status, timeline. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -257,7 +257,10 @@ pub fn print_event_count_json(counts: &EventCounts, elapsed_ms: u64) {
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_event_count(counts: &EventCounts) {
|
||||
@@ -325,7 +328,10 @@ pub fn print_count_json(result: &CountResult, elapsed_ms: u64) {
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_count(result: &CountResult) {
|
||||
|
||||
@@ -137,5 +137,8 @@ pub fn print_embed_json(result: &EmbedCommandResult, elapsed_ms: u64) {
|
||||
data: result,
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -259,7 +259,10 @@ pub fn print_generate_docs_json(result: &GenerateDocsResult, elapsed_ms: u64) {
|
||||
},
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@@ -982,7 +982,10 @@ pub fn print_ingest_summary_json(result: &IngestResult, elapsed_ms: u64) {
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_ingest_summary(result: &IngestResult) {
|
||||
@@ -1109,5 +1112,8 @@ pub fn print_dry_run_preview_json(preview: &DryRunPreview) {
|
||||
data: preview.clone(),
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -439,5 +439,8 @@ pub fn print_search_results_json(
|
||||
let expanded = crate::cli::robot::expand_fields_preset(f, "search");
|
||||
crate::cli::robot::filter_fields(&mut value, "results", &expanded);
|
||||
}
|
||||
println!("{}", serde_json::to_string(&value).unwrap());
|
||||
match serde_json::to_string(&value) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -585,5 +585,8 @@ pub fn print_stats_json(result: &StatsResult, elapsed_ms: u64) {
|
||||
},
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
@@ -746,7 +746,10 @@ pub fn print_sync_json(result: &SyncResult, elapsed_ms: u64, metrics: Option<&Me
|
||||
stages,
|
||||
},
|
||||
};
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug, Default, Serialize)]
|
||||
@@ -880,7 +883,10 @@ pub fn print_sync_dry_run_json(result: &SyncDryRunResult) {
|
||||
},
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
||||
@@ -268,7 +268,10 @@ pub fn print_sync_status_json(result: &SyncStatusResult, elapsed_ms: u64) {
|
||||
meta: RobotMeta { elapsed_ms },
|
||||
};
|
||||
|
||||
println!("{}", serde_json::to_string(&output).unwrap());
|
||||
match serde_json::to_string(&output) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
pub fn print_sync_status(result: &SyncStatusResult) {
|
||||
|
||||
@@ -374,7 +374,10 @@ pub fn print_timeline_json_with_meta(
|
||||
let expanded = crate::cli::robot::expand_fields_preset(f, "timeline");
|
||||
crate::cli::robot::filter_fields(&mut value, "events", &expanded);
|
||||
}
|
||||
println!("{}", serde_json::to_string(&value).unwrap());
|
||||
match serde_json::to_string(&value) {
|
||||
Ok(json) => println!("{json}"),
|
||||
Err(e) => eprintln!("Error serializing to JSON: {e}"),
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Serialize)]
|
||||
|
||||
Reference in New Issue
Block a user