{"record":{"id":"302bb4e84ca1f1ac","repo":"gitbutlerapp/gitbutler","slug":"askpass-broker-must-be-initialized-302bb4","errorCode":null,"errorMessage":"askpass broker must be initialized","messagePattern":"askpass broker must be initialized","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/gitbutler-git/src/context.rs","lineNumber":343,"sourceCode":"        .to_owned();\n    Ok((remote, short_name))\n}\n\nfn now_ms() -> u128 {\n    UNIX_EPOCH\n        .elapsed()\n        .expect(\"system time is set before the Unix epoch\")\n        .as_millis()\n}\n\nasync fn handle_git_prompt_push(\n    prompt: String,\n    askpass: Option<Option<StackId>>,\n) -> Option<String> {\n    if let Some(branch_id) = askpass {\n        tracing::info!(\"received prompt for branch push {branch_id:?}: {prompt:?}\");\n        askpass::get_broker()\n            .expect(\"askpass broker must be initialized\")\n            .submit_prompt(prompt, askpass::Context::Push { branch_id })\n            .await\n    } else {\n        tracing::warn!(\"received askpass push prompt but no broker was supplied; returning None\");\n        None\n    }\n}\n\nasync fn handle_git_prompt_fetch(prompt: String, askpass: Option<String>) -> Option<String> {\n    if let Some(action) = askpass {\n        tracing::info!(\"received prompt for fetch with action {action:?}: {prompt:?}\");\n        askpass::get_broker()\n            .expect(\"askpass broker must be initialized\")\n            .submit_prompt(prompt, askpass::Context::Fetch { action })\n            .await\n    } else {\n        tracing::warn!(\"received askpass fetch prompt but no broker was supplied; returning None\");\n        None","sourceCodeStart":325,"sourceCodeEnd":361,"githubUrl":"https://github.com/gitbutlerapp/gitbutler/blob/58e5313667b857ef39a730e380af31816a7b1768/crates/gitbutler-git/src/context.rs#L325-L361","documentation":"During a push, git credential prompts are routed to the askpass broker; handle_git_prompt_push expects askpass::get_broker() to return Some. If the broker was never initialized (the application startup step that installs the global broker didn't run), the expect panics with \"askpass broker must be initialized\".","triggerScenarios":"A push that triggers an authentication prompt (askpass) arrives while the global askpass broker hasn't been set up — i.e. askpass::get_broker() returns None at prompt time.","commonSituations":"Headless/CLI or test contexts where broker initialization was skipped; initialization order bug where the push starts before the broker is installed; asking for credentials on a private remote without stored credentials, forcing an interactive prompt.","solutions":["Ensure askpass broker initialization runs before any push (the app's startup/context-setup path that installs the global broker)","Add stored credentials for the remote (git credential store / SSH keys) so no interactive prompt is needed","Downgrade to graceful handling: if get_broker() is None, log and return None instead of panicking"],"exampleFix":"// before\naskpass::get_broker()\n    .expect(\"askpass broker must be initialized\")\n    .submit_prompt(prompt, askpass::Context::Push { branch_id })\n    .await\n// after\nmatch askpass::get_broker() {\n    Some(broker) => broker.submit_prompt(prompt, askpass::Context::Push { branch_id }).await,\n    None => {\n        tracing::warn!(\"askpass broker not initialized; cannot answer prompt\");\n        None\n    }\n}","handlingStrategy":"fallback","validationCode":"// Rust: verify the broker is ready before starting a push that may prompt\nif askpass::get_broker().is_none() {\n    tracing::warn!(\"askpass broker not initialized; pushes may fail to prompt for credentials\");\n}","typeGuard":"fn broker_ready() -> bool {\n    askpass::get_broker().is_some()\n}","tryCatchPattern":"match askpass::get_broker() {\n    Some(b) => b.submit_prompt(prompt, askpass::Context::Push { branch_id }).await,\n    None => { tracing::warn!(\"no askpass broker\"); None }\n}","preventionTips":["Initialize the global askpass broker during app startup before any git network operation","Configure SSH keys or a credential helper so pushes to private remotes don't need interactive prompts","Add an integration test that pushes without broker init to catch initialization-order regressions"],"tags":["rust","git","authentication","askpass","initialization-order"],"backgroundTag":"missing-credentials","analyzedSha":"58e5313667b857ef39a730e380af31816a7b1768","analyzedAt":"2026-09-18T06:50:32.052Z","contentChangedAt":"2026-09-18T06:50:32.052Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}