ahmetb/kubectx · error
failed to save kubeconfig file: %w
Error message
failed to save kubeconfig file: %w
What it means
After mutating the namespace in memory, switchNamespace persists the kubeconfig to disk via kc.Save(). This error wraps any failure writing the kubeconfig file — I/O errors, permission problems, or serialization failures. The in-memory change succeeded but was not committed. Thrown at cmd/kubens/switch.go:91.
Source
Thrown at cmd/kubens/switch.go:91
}
ns = prev
}
if !force {
ok, err := namespaceExists(kc, ns)
if err != nil {
return "", fmt.Errorf("failed to query if namespace exists (is cluster accessible?): %w", err)
}
if !ok {
return "", fmt.Errorf("no namespace exists with name \"%s\"", ns)
}
}
if err := kc.SetNamespace(ctx, ns); err != nil {
return "", fmt.Errorf("failed to change to namespace \"%s\": %w", ns, err)
}
if err := kc.Save(); err != nil {
return "", fmt.Errorf("failed to save kubeconfig file: %w", err)
}
if curNS != ns {
if err := f.Save(curNS); err != nil {
return "", fmt.Errorf("failed to save the previous namespace to file: %w", err)
}
}
return ns, nil
}
func namespaceExists(kc *kubeconfig.Kubeconfig, ns string) (bool, error) {
// for tests
if os.Getenv("_MOCK_NAMESPACES") != "" {
return ns == "ns1" || ns == "ns2", nil
}
clientset, err := newKubernetesClientSet(kc)
if err != nil {
return false, fmt.Errorf("failed to initialize k8s REST client: %w", err)View on GitHub (pinned to 12ad6fb22e)
Solutions
- Fix ownership/permissions: sudo chown $USER ~/.kube/config && chmod 600 ~/.kube/config
- Check disk space and quota: df -h ~/.kube
- If the file is a read-only mount (secret/configmap), write to a writable copy and point KUBECONFIG at it
- Verify no policy blocks writes: check mount options (mount | grep kube) and SELinux denials
Example fix
// before -rw------- 1 root root ~/.kube/config # kubens cannot write as normal user // after sudo chown $USER:$USER ~/.kube/config kubens production
Defensive patterns
Strategy: validation
Validate before calling
cfgPath := kubeconfigPath()
if fi, err := os.Stat(cfgPath); err == nil {
if err := syscall.Access(cfgPath, os.O_RDWR); err != nil {
return fmt.Errorf("kubeconfig %s not writable by %s: %v", cfgPath, os.Getenv("USER"), err)
}
_ = fi
} Try / catch
if err := kc.Save(); err != nil {
var perr *os.PathError
if errors.As(err, &perr) {
return fmt.Errorf("cannot write %s (check ownership/permissions/disk space): %w", perr.Path, err)
}
return err
} Prevention
- Never run kubectl/kubens under sudo — it leaves root-owned config files
- Keep 0600/user-owned permissions on ~/.kube/config
- Monitor disk space on machines running cluster tooling
- In pods, do not mount kubeconfig from a read-only secret if tools must update it
When it happens
Trigger: kc.Save() errors because the kubeconfig file or its parent directory is not writable (read-only filesystem, wrong owner), disk is full, or an immutable attribute / LSM policy blocks the write.
Common situations: ~/.kube/config owned by root after running kubectl under sudo; read-only container filesystem; disk quota/full disk; the config file mounted read-only from a Kubernetes secret or ConfigMap in a pod; EACCES from SELinux/AppArmor.
Related errors
- failed to save kubeconfig file: %w
- failed to open file %q: %w
- kubeconfig error: %w
- failed to get current context: %w
- failed to read namespace of "%s": %w
AI-assisted analysis of ahmetb/kubectx@12ad6fb22e (2026-09-02).
Data as JSON: /api/errors/eb054f12beec3e8a.
Report an issue: GitHub.