Hmbown/CodeWhale · critical
portable export refused credential-bearing config paths
Error message
portable export refused credential-bearing config paths: {} What it means
export_bundle refuses to produce a portable bundle when find_rejected_entries detects credential-bearing config paths (API keys, tokens, secrets) in the current configuration. Portable bundles are meant to be shared, so secret-shaped entries are stripped out of the allowed schema and their presence blocks the export, listing the offending keys.
Solutions
- Move the listed credentials out of the config paths named in the error (e.g. use environment variables or a secret store) and re-export.
- Remove the credential-shaped entries entirely if they are not needed on the target machine.
- Check which keys are flagged: the error lists them comma-separated; edit config.toml to clear or restructure them.
- Re-export and inspect the bundle for the sensitive keys before sharing.
Example fix
// before (config.toml) [providers.openai] api_key = "sk-..." // after [providers.openai] # api_key read from CODEWHALE_OPENAI_API_KEY env var; not stored in config export -> succeeds
Defensive patterns
Strategy: validation
Validate before calling
// Before exporting, scan your config for secret-shaped values: // grep -nEi '(api[_-]?key|token|secret|password)[[:space:]]*=' ~/.config/codewhale/config.toml // Move any hits to environment variables or a secret store.
Try / catch
match export_bundle(&store, &target) {
Ok(receipt) => println!("exported {}", receipt.path),
Err(e) if e.to_string().contains("credential-bearing config paths") => {
eprintln!("remove the listed keys from config, then re-export: {e:#}");
}
Err(e) => return Err(e),
} Prevention
- Keep API keys in environment variables, never in config.toml.
- Run a pre-export grep for key/token/secret patterns in config.
- After any manual config edit, re-export and inspect the bundle before sharing.
When it happens
Trigger: Running the bundle export command (run_export) while the live config contains secret-shaped values — e.g. an API key stored under a provider entry, or leftover redaction placeholders — that find_rejected_entries flags.
Common situations: A user stored an API key directly in config.toml and now tries to share the bundle; exporting after importing a bundle that itself carried credentials; CI configs with tokens inline in provider settings.
Related errors
- bundle redirects may not change URL scheme
- bundle URLs may not include credentials
- failed to delete stored credentials for
- plain http is only allowed for loopback hosts; use https
- Secret storage failed: . Refusing to write the API key in…
AI-assisted analysis of Hmbown/CodeWhale@73e0f67d83 (2026-09-22).
Data as JSON: /api/errors/d0f1b68d13a3432b.
Report an issue: GitHub.
Appendix: source
Thrown at crates/cli/src/config_bundles.rs:905
}
ExportSection::Drop => {}
}
}
}
let bundle = PortableBundle {
schema_version: BUNDLE_SCHEMA_VERSION,
kind: BUNDLE_KIND.to_string(),
metadata,
preferences,
profiles,
plugins: BundleTable::default(),
project,
global,
};
let rejected = find_rejected_entries(&bundle);
if !rejected.is_empty() {
bail!(
"portable export refused credential-bearing config paths: {}",
rejected
.iter()
.map(|entry| entry.key.as_str())
.collect::<Vec<_>>()
.join(", ")
);
}
Ok(bundle)
}
/// Serialize a bundle deterministically (sorted keys, TOML).
pub fn serialize_bundle(bundle: &PortableBundle) -> Result<String> {
toml::to_string_pretty(bundle).context("serializing portable bundle")
}
/// Config keys that name a machine-local location and must never be exported.
const MACHINE_SPECIFIC_KEYS: [&str; 14] = [View on GitHub (pinned to 73e0f67d83)