forked from 1b-agent/fieldcraft-upstream
App: crash reports and a log file; Help › Report a Bug (#107)
The desktop app installs the crash reporter and a log file at start (both in a temporary folder in --control and CI runs, #266), journals the window's commands (background jobs included) and every control request's method, and ends the journal on a clean exit. A start after a crash asks: "FieldCraft closed unexpectedly", Report It… or Not Now. Help › Report a Bug (also Tools › Help and ui.start diagnostics.bug_report) shows exactly what the GitHub bug form will be filled with: the version, the OS, the last error, and for a crash where it happened. Share my session adds the replayable commands, Include the model file the model. Open GitHub Issue opens the form in the browser through the system's opener; files to attach are saved to bug-reports/<time>/ and a long session goes on the clipboard. Nothing is sent without that click and the user's submit on GitHub. The control channel answers the new prompts (crashed: report, close; report_bug: set, close) and ui.inspect shows the draft; it never opens the browser. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01UhhZMBTviDQxZvwnyP89fo
This commit is contained in:
1 parent
cb7e3a2711
commit
e06c85eb9e
9 files changed
+503
-8
No files matched your search
@@ -164,6 +164,8 @@ pub fn handle(app: &mut ModelApp, ctx: &egui::Context, req: &ControlRequest) ->
|
||||
let f = |k: &str| p.get(k).and_then(Value::as_f64).filter(|x| x.is_finite());
|
||||
let b = |k: &str| p.get(k).and_then(Value::as_bool).unwrap_or(false);
|
||||
let mods = || egui::Modifiers { shift: b("shift"), ctrl: b("ctrl"), command: b("ctrl"), alt: b("alt"), ..Default::default() };
|
||||
// A crash nothing catches (#248) still says which request came last.
|
||||
fieldcraft_engine::crash::activity(&format!("control {}", req.method));
|
||||
match req.method.as_str() {
|
||||
"engine.execute" => {
|
||||
let Some(id) = s("command") else { return err("missing `command`") };
|
||||
@@ -202,6 +204,8 @@ pub fn handle(app: &mut ModelApp, ctx: &egui::Context, req: &ControlRequest) ->
|
||||
crate::files::Prompt::Design(p) => json!({"design": p}),
|
||||
crate::files::Prompt::ReplaceMesh(r) => json!({"replace_mesh": r.question, "warnings": r.warnings}),
|
||||
crate::files::Prompt::Delete(d) => json!({"delete": d.question(), "kind": d.kind, "name": d.name, "users": d.users, "allowed": d.allowed()}),
|
||||
crate::files::Prompt::Crashed(r) => json!({"crashed": r}),
|
||||
crate::files::Prompt::ReportBug => json!({"report_bug": app.report.as_ref().and_then(|f| f.drafted_json())}),
|
||||
}),
|
||||
"recent": app.recent.paths,
|
||||
"version": crate::VERSION,
|
||||
@@ -374,6 +378,21 @@ pub fn handle(app: &mut ModelApp, ctx: &egui::Context, req: &ControlRequest) ->
|
||||
app.prompt = None;
|
||||
ok(Value::Null)
|
||||
}
|
||||
(crate::files::Prompt::Crashed(r), Some("report")) => {
|
||||
app.report_bug(r.first().map(|c| c.id.clone()));
|
||||
ok(json!({"prompt": "report_bug"}))
|
||||
}
|
||||
(crate::files::Prompt::Crashed(_), Some("close" | "cancel")) => {
|
||||
app.prompt = None;
|
||||
ok(Value::Null)
|
||||
}
|
||||
// The form's fields; sending opens the browser, which only a click does.
|
||||
(crate::files::Prompt::ReportBug, Some("set")) => wrap(app.set_report(p)),
|
||||
(crate::files::Prompt::ReportBug, Some("close" | "cancel")) => {
|
||||
app.prompt = None;
|
||||
app.report = None;
|
||||
ok(Value::Null)
|
||||
}
|
||||
(crate::files::Prompt::Recover, Some("recover")) => match s("id") {
|
||||
Some(id) => {
|
||||
app.recover(id);
|
||||
@@ -382,7 +401,7 @@ pub fn handle(app: &mut ModelApp, ctx: &egui::Context, req: &ControlRequest) ->
|
||||
None => err("missing `id` (from file.recovery.list)"),
|
||||
},
|
||||
(_, a) => err(format!(
|
||||
"`answer` {a:?} does not answer this prompt (unsaved: save, discard, cancel; design: new, keep, cancel; replace_mesh: replace, cancel; delete: delete, cancel; recover: recover with id, close; samples: open with name, close)"
|
||||
"`answer` {a:?} does not answer this prompt (unsaved: save, discard, cancel; design: new, keep, cancel; replace_mesh: replace, cancel; delete: delete, cancel; recover: recover with id, close; samples: open with name, close; crashed: report, close; report_bug: set with title/observed/share_session/include_model, close)"
|
||||
)),
|
||||
}
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user