hashicorp/nomad · error
error changing owner/group: %w
Error message
error changing owner/group: %w
What it means
This error wraps a failure of os.Chown during the plugin Create operation on non-Windows platforms, after mkdir and chmod succeeded. Nomad attempts to set the requested uid/gid on the directory; on failure it removes the half-created directory (RemoveAll) and returns this wrapped error. The usual wrapped cause is EPERM: the nomad client process lacks the privileges (root or CAP_CHOWN) to change ownership to the requested uid/gid.
Source
Thrown at client/hostvolumemanager/host_volume_plugin.go:160
if err != nil {
log.Error("error setting directory permission mode", "error", err)
return nil, fmt.Errorf("error setting directory permission mode: %w", err)
}
if runtime.GOOS != "windows" {
// Chown note: A uid or gid of -1 means to not change that value.
if err = os.Chown(path, params.Uid, params.Gid); err != nil {
log.Error("error changing owner/group", "error", err, "uid", params.Uid, "gid", params.Gid)
// Failing to change ownership is fatal for this plugin. Since we have
// already created the directory, we should attempt to clean it.
// Otherwise, the operator must do this manually.
if err := os.RemoveAll(path); err != nil {
log.Error("failed to remove directory after create failure",
"error", err)
}
return nil, fmt.Errorf("error changing owner/group: %w", err)
}
}
log.Debug("plugin ran successfully")
return resp, nil
}
func decodeMkdirParams(in map[string]string) (HostVolumePluginMkdirParams, error) {
// default values if their associated keys are not in the input map
out := HostVolumePluginMkdirParams{
Mode: 0o700, // "0700"
Uid: -1, // this default translates to "do not set" in os.Chown
Gid: -1, // ditto
}
var err error
for param, val := range in {
switch param {View on GitHub (pinned to 482b49bf1a)
Solutions
- Run the nomad client as root or grant it CAP_CHOWN (setcap cap_chown+eip on the agent binary / run agent privileged) so chown of arbitrary uids succeeds.
- Request uid/gid values the agent user can set — either omit uid/gid (default to agent user) or align them with the agent's own uid/gid.
- Set client option to allow unprivileged chown is not possible: alternatively pre-create the directory with correct ownership outside Nomad and create the volume over it.
- Check the wrapped error for EPERM vs EINVAL to distinguish privilege vs argument problems.
Example fix
// before: agent runs as 'nomad' user, cannot chown Uid: 1000, Gid: 1000 // EPERM // after: run client with capability // sudo setcap cap_chown+eip /usr/bin/nomad (or run agent as root) // or omit ownership: Uid: -1, Gid: -1
Defensive patterns
Strategy: try-catch
Validate before calling
func canChown(uid, gid int) error {
if uid == -1 && gid == -1 {
return nil
}
if os.Geteuid() == 0 {
return nil
}
if uid != -1 && uid != os.Geteuid() {
return fmt.Errorf("running as uid %d; cannot chown to %d without CAP_CHOWN", os.Geteuid(), uid)
}
if gid != -1 && gid != os.Getegid() {
return fmt.Errorf("running as gid %d; cannot chgrp to %d without CAP_CHOWN", os.Getegid(), gid)
}
return nil
} Try / catch
var hvErr *hvapi.Error
if errors.As(err, &hvErr) && strings.Contains(hvErr.Error(), "error changing owner/group") {
if errors.Is(err, fs.ErrPermission) {
// run agent as root / grant CAP_CHOWN, or drop uid/gid from the request
}
} Prevention
- Run the nomad client agent as root or with CAP_CHOWN if volumes request specific uid/gid.
- Omit uid/gid (use -1) unless ownership changes are genuinely required.
- Pre-create directories with correct ownership outside Nomad when the agent is unprivileged.
- Validate requested uid/gid against what the agent user may set before submitting the request.
When it happens
Trigger: Plugin Create runs on Linux/Unix with nonzero params.Uid or params.Gid while the nomad agent runs as an unprivileged user: os.Chown(path, params.Uid, params.Gid) returns EPERM. Also fires on EINVAL if uid/gid are out of range, or if the path vanished between chmod and chown.
Common situations: Operator requests a volume owned by uid 1000/gid 1000 but the nomad client agent runs as the 'nomad' user without root; containers/nomad running without CAP_CHOWN; requesting a uid that only root may set.
Related errors
- Couldn't change owner/group of %v to (uid: %v, gid: %v): %w
- Failed to delete proc directory %q: %w
- error chowning directory %w
- error chowning file %w
- error creating directory: %w
AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04).
Data as JSON: /api/errors/79bb18a85dc0a30f.
Report an issue: GitHub.