hashicorp/nomad · error
failed to parse security_opt configuration: %v
Error message
failed to parse security_opt configuration: %v
What it means
The docker driver's security_opt option is validated by parseSecurityOpts before being handed to the Docker daemon. Entries that are not well-formed (e.g. missing key=value separation or disallowed forms) are rejected locally with this wrapper so jobs fail at config time rather than with an opaque Docker API error.
Source
Thrown at drivers/docker/driver.go:1391
hostConfig.PidMode = containerapi.PidMode(driverConfig.PidMode)
if utsErr := d.validateNamespace(d.config.AllowedModes.UTS, "uts_mode", driverConfig.UTSMode); utsErr != nil {
return c, utsErr
}
hostConfig.UTSMode = containerapi.UTSMode(driverConfig.UTSMode)
if usernsErr := d.validateNamespace(d.config.AllowedModes.Userns, "userns_mode", driverConfig.UsernsMode); usernsErr != nil {
return c, usernsErr
}
hostConfig.UsernsMode = containerapi.UsernsMode(driverConfig.UsernsMode)
hostConfig.ExtraHosts = driverConfig.ExtraHosts
hostConfig.SecurityOpt = driverConfig.SecurityOpt
hostConfig.Sysctls = driverConfig.Sysctl
hostConfig.SecurityOpt, err = parseSecurityOpts(driverConfig.SecurityOpt)
if err != nil {
return c, fmt.Errorf("failed to parse security_opt configuration: %v", err)
}
ulimits, err := sliceMergeUlimit(driverConfig.Ulimit)
if err != nil {
return c, fmt.Errorf("failed to parse ulimit configuration: %v", err)
}
hostConfig.Ulimits = ulimits
hostConfig.ReadonlyRootfs = driverConfig.ReadonlyRootfs
// set the docker network mode
hostConfig.NetworkMode = containerapi.NetworkMode(driverConfig.NetworkMode)
// if the driver config does not specify a network mode then try to use the
// shared alloc network
if hostConfig.NetworkMode == "" {
if task.NetworkIsolation != nil && task.NetworkIsolation.Path != "" {
// find the previously created parent container to join networks withView on GitHub (pinned to 482b49bf1a)
Solutions
- Use key=value syntax for every security_opt entry, e.g. "seccomp=unconfined", "apparmor=profile-name","no-new-privileges=true"
- Remove or fix the offending entry identified by the wrapped %v error
- Validate the seccomp JSON file path exists on the host if using seccomp=<path>
Example fix
// before
driver {
docker {
security_opt = ["seccomp:unconfined"]
}
}
// after
driver {
docker {
security_opt = ["seccomp=unconfined"]
}
} Defensive patterns
Strategy: validation
Validate before calling
for _, opt := range cfg.SecurityOpt {
if !strings.Contains(opt, "=") {
return fmt.Errorf("security_opt must be key=value, got %q", opt)
}
} Try / catch
err := client.StartTask(task); if err != nil && strings.Contains(err.Error(), "failed to parse security_opt") { logOffendingOpts(cfg.SecurityOpt) } Prevention
- Always use key=value syntax for security_opt
- Validate seccomp JSON paths exist on the host
- Lint HCL lists for accidental value splitting
When it happens
Trigger: StartTask -> createContainerConfig calls parseSecurityOpts(driverConfig.SecurityOpt) and the security_opt list contains a malformed entry such as a flag without '=' (e.g. 'seccomp:unconfined' style instead of 'seccomp=unconfined').
Common situations: Users copying --security-opt CLI syntax with colons instead of equals signs; security_opt entries that docker daemon would reject (apparmor profiles that don't exist, malformed seccomp JSON paths); quoting mistakes in HCL splitting a value into separate items.
Understand the failure class
Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- invalid value for cpu_cfs_period
- failed to parse ulimit configuration: %v
- Port %q not found, check network block
- failed to parse ipv4_address %q: %v
- host path must be set in configuration for devices
AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04).
Data as JSON: /api/errors/4daa33614098fa71.
Report an issue: GitHub.