hashicorp/nomad · error

Operator %q does not support an RTarget

Error message

Operator %q does not support an RTarget

What it means

The constraint's operand is "is_set" or "is_not_set", which test only for attribute presence, but an RTarget (right-hand value) was supplied. These operators take no comparison value, so providing one is flagged as a validation error.

Source

Thrown at nomad/structs/structs.go:10096

			mErr.Errors = append(mErr.Errors, fmt.Errorf("Version constraint is invalid: %v", err))
		}
	case ConstraintSemver:
		if _, err := semver.NewConstraint(c.RTarget); err != nil {
			mErr.Errors = append(mErr.Errors, fmt.Errorf("Semver constraint is invalid: %v", err))
		}
	case ConstraintDistinctProperty:
		// If a count is set, make sure it is convertible to a uint64
		if c.RTarget != "" {
			count, err := strconv.ParseUint(c.RTarget, 10, 64)
			if err != nil {
				mErr.Errors = append(mErr.Errors, fmt.Errorf("Failed to convert RTarget %q to uint64: %v", c.RTarget, err))
			} else if count < 1 {
				mErr.Errors = append(mErr.Errors, fmt.Errorf("Distinct Property must have an allowed count of 1 or greater: %d < 1", count))
			}
		}
	case ConstraintAttributeIsSet, ConstraintAttributeIsNotSet:
		if c.RTarget != "" {
			mErr.Errors = append(mErr.Errors, fmt.Errorf("Operator %q does not support an RTarget", c.Operand))
		}
	case "=", "==", "is", "!=", "not", "<", "<=", ">", ">=":
		if c.RTarget == "" {
			mErr.Errors = append(mErr.Errors, fmt.Errorf("Operator %q requires an RTarget", c.Operand))
		}
	default:
		mErr.Errors = append(mErr.Errors, fmt.Errorf("Unknown constraint type %q", c.Operand))
	}

	// If the constraint must have a "LTarget" (attribute in the job spec), then
	// ensure it is not an empty string and is valid.
	if requireLtarget {
		if c.LTarget == "" {
			mErr.Errors = append(mErr.Errors, errors.New("no attribute provided but is required by operator"))
		} else {
			if err := validateConstraintAttribute(c.LTarget); err != nil {
				mErr.Errors = append(mErr.Errors, err)
			}

View on GitHub (pinned to 482b49bf1a)

Solutions

  1. Remove the value/RTarget from the is_set / is_not_set constraint.
  2. If you need a value comparison, use an equality operand (=, !=) instead of is_set.
  3. Fix the generating template to omit the value field for these operands.

Example fix

// before
constraint {
  operand  = "is_set"
  attribute = "${meta.tls}"
  value    = "true"
}
// after
constraint {
  operand   = "is_set"
  attribute = "${meta.tls}"
}
Defensive patterns

Strategy: validation

Validate before calling

func constraintTargetAllowed(operand, rtarget string) bool {
  switch operand {
  case "is_set", "is_not_set":
    return rtarget == ""
  default:
    return true
  }
}

Try / catch

if (operand == "is_set" || operand == "is_not_set") && rtarget != "" {
  return fmt.Errorf("operand %q must not have a value", operand)
}

Prevention

When it happens

Trigger: Submitting a job with constraint { operand = "is_set" attribute = "${meta.foo}" ... } where an RTarget/value field is also set, e.g. value = "bar".

Common situations: Copy-pasting a comparison constraint and only changing the operand to is_set while leaving the old value; templated generation that always emits a value field; misunderstanding that is_set takes an argument.

Related errors


AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04). Data as JSON: /api/errors/50b4623ed2b25d90. Report an issue: GitHub.