gastownhall/beads · error
failed to read config.yaml: %w
Error message
failed to read config.yaml: %w
What it means
setYamlConfigAtPath wraps any os.ReadFile failure on the target config.yaml path before updating a key. The wrapped cause (%w) is the underlying OS error, so the real reason (missing file, permissions, path) is in the %w suffix. bd throws it because YAML config writes require reading the existing file to merge the new key into it.
Source
Thrown at internal/config/yaml_config.go:515
if _, err := os.Stat(configPath); os.IsNotExist(err) {
if err := os.WriteFile(configPath, []byte{}, 0o600); err != nil {
return fmt.Errorf("failed to create user config.yaml: %w", err)
}
} else if err != nil {
return fmt.Errorf("failed to stat user config.yaml: %w", err)
}
return setYamlConfigAtPath(configPath, key, value)
}
func setYamlConfigAtPath(configPath, key, value string) error {
// Normalize key to canonical yaml format
normalizedKey := normalizeYamlKey(key)
// Read existing config
content, err := os.ReadFile(configPath) //nolint:gosec // configPath is from findProjectConfigYaml
if err != nil {
return fmt.Errorf("failed to read config.yaml: %w", err)
}
// Update or add the key
newContent, err := updateYamlKey(string(content), normalizedKey, value)
if err != nil {
return err
}
// Write back
if err := os.WriteFile(configPath, []byte(newContent), 0600); err != nil { //nolint:gosec // configPath is validated
return fmt.Errorf("failed to write config.yaml: %w", err)
}
return nil
}
// GetYamlConfig gets a configuration value from config.yaml.
// Returns empty string if key is not found or is commented out.View on GitHub (pinned to 71377f2769)
Solutions
- Run 'bd init' in the project (or in the directory BEADS_DIR points at) to create .beads/config.yaml
- Check the wrapped error in the %w suffix: if 'no such file or directory', create the file; if 'permission denied', fix ownership/permissions (chmod/chown)
- Verify BEADS_DIR points to the correct directory containing config.yaml, or unset it to use project resolution
- Ensure config.yaml is a regular readable file, not a directory, symlink, or FIFO
Example fix
// before (fails: file never created) BEADS_DIR=/tmp/myrepo bd config set dolt.mode embedded // after bd init /tmp/myrepo && bd config set dolt.mode embedded
Defensive patterns
Strategy: try-catch
Validate before calling
path, err := findProjectConfigYaml()
if err != nil { return err }
if _, err := os.Stat(path); err != nil {
return fmt.Errorf("config.yaml missing at %s: run 'bd init' first", path)
} Type guard
func configReadable(path string) bool {
fi, err := os.Stat(path)
return err == nil && fi.Mode().IsRegular()
} Try / catch
if err := SetYamlConfig(key, value); err != nil {
var perr *fs.PathError
if errors.As(err, &perr) && os.IsNotExist(err) {
// run bd init or create config.yaml, then retry
}
return err
} Prevention
- Always run 'bd init' before any config set/unset command
- Check BEADS_DIR points at an initialized directory in setup scripts
- Verify config.yaml exists and is readable before scripted config changes
When it happens
Trigger: Calling SetYamlConfig, SetYamlConfigInDir, or SetUserYamlConfig when the resolved config.yaml path does not exist (project not initialized) or cannot be opened (permissions, path is a directory, race where the file is deleted between resolution and read).
Common situations: Running 'bd config set' in a repo where 'bd init' was never run; BEADS_DIR pointing at a directory without config.yaml; config.yaml with restrictive ownership after switching users or cloning without the file.
Related errors
- failed to write config.yaml: %w
- server: NewDoltServer: doltBinExec is required
- server: NewDoltServer: rootDir is required
- server: NewDoltServer: configPath is required
- failed to find backup directory: %w
AI-assisted analysis of gastownhall/beads@71377f2769 (2026-08-30).
Data as JSON: /api/errors/fe58d5124da3808c.
Report an issue: GitHub.