{"record":{"id":"02d10a7a14b9286a","repo":"helix-editor/helix","slug":"no-diff-provider-returns-success","errorCode":null,"errorMessage":"no diff provider returns success","messagePattern":"no diff provider returns success","errorType":"exception","errorClass":"anyhow::Error","httpStatus":null,"severity":"warning","filePath":"helix-vcs/src/lib.rs","lineNumber":79,"sourceCode":"        })\n    }\n\n    /// Fire-and-forget changed file iteration. Runs everything in a background task. Keeps\n    /// iteration until `on_change` returns `false`.\n    pub fn for_each_changed_file(\n        self,\n        cwd: PathBuf,\n        trust_full: bool,\n        f: impl Fn(Result<FileChange>) -> bool + Send + 'static,\n    ) {\n        tokio::task::spawn_blocking(move || {\n            if self\n                .providers\n                .iter()\n                .find_map(|provider| provider.for_each_changed_file(&cwd, trust_full, &f).ok())\n                .is_none()\n            {\n                f(Err(anyhow!(\"no diff provider returns success\")));\n            }\n        });\n    }\n}\n\nimpl Default for DiffProviderRegistry {\n    fn default() -> Self {\n        // currently only git is supported\n        // TODO make this configurable when more providers are added\n        let providers = vec![\n            #[cfg(feature = \"git\")]\n            DiffProvider::Git,\n            DiffProvider::None,\n        ];\n        DiffProviderRegistry { providers }\n    }\n}\n","sourceCodeStart":61,"sourceCodeEnd":97,"githubUrl":"https://github.com/helix-editor/helix/blob/079a789e8cb08ead67f19e1971a1b7438b37354b/helix-vcs/src/lib.rs#L61-L97","documentation":"DiffProviderRegistry::for_each_changed_file runs every configured provider (git is the only built-in one) and uses find_map on their results. If no provider returned Ok — in practice, because gix failed to discover or open a repository for the cwd ('failed to discover git repo' when the directory is not inside any git repository, or an open/status failure on a corrupt .git) — the fallback callback is invoked with Err('no diff provider returns success'). Consumers surface it via status::report_blocking, e.g. the changed-files picker shows it in the statusline.","triggerScenarios":"Opening the changed-files picker (default `space` g) in a directory that is not inside any git repository; a corrupted/unreadable .git directory; a repo gix cannot open due to discovery errors.","commonSituations":"Using helix on non-git projects (the most common case — no VCS integration is configured for them); broken .git dirs after interrupted operations; repos with unreadable config.","solutions":["If the project is not under git, initialize or ignore the message — the picker just has nothing to list.","Verify `git status` runs cleanly in the same directory from a terminal; if it errors, repair the repository (e.g. `git fsck`, restore .git/config).","For non-git projects wanting picker parity, put the project under git (git init) or accept the empty picker."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"// preflight: is the cwd inside a git repo at all?\nlet in_repo = gix::discover::upward_opts(\n    &cwd,\n    gix::discover::upwards::Options { dot_git_only: true, ..Default::default() },\n).is_ok();\nif !in_repo { /* skip the changed-files picker / expect the fallback error */ }","typeGuard":null,"tryCatchPattern":"// the registry already funnels every provider failure into one Err callback\ncx.editor.diff_providers.clone().for_each_changed_file(cwd, trust, move |res| match res {\n    Ok(change) => injector.push(change).is_ok(),\n    Err(err) => { status::report_blocking(err); true } // degrade gracefully: empty picker\n});","preventionTips":["Expect this error on non-git projects — VCS integration is git-only today.","Run `git status` once in a project before wiring tooling on top of the changed-files API.","Treat provider failure as 'no data', not fatal: keep the picker functional with zero rows."],"tags":["git","vcs","fallback"],"backgroundTag":null,"analyzedSha":"079a789e8cb08ead67f19e1971a1b7438b37354b","analyzedAt":"2026-08-16T09:09:59.668Z","schemaVersion":2},"datasetVersion":"2026-08-16T13:17:31.715Z"}