hashicorp/nomad · warning
tag %q not found on job %q
Error message
tag %q not found on job %q
What it means
Unsetting a job version tag requires that the tag actually exists on some version of the job. The state store looks the tag up via JobVersionByTagName and, when nothing is bound, rejects the unset request with this error instead of silently succeeding.
Source
Thrown at nomad/state/state_store.go:4969
if err != nil {
return err
}
if versionCopy.Version == latestJob.Version {
if err := txn.Insert("jobs", versionCopy); err != nil {
return err
}
}
return s.upsertJobVersion(index, versionCopy, txn)
}
func (s *StateStore) unsetJobVersionTagImpl(index uint64, namespace, jobID string, name string, txn *txn) error {
job, err := s.JobVersionByTagName(nil, namespace, jobID, name)
if err != nil {
return err
}
if job == nil {
return fmt.Errorf("tag %q not found on job %q", name, jobID)
}
versionCopy := job.Copy()
versionCopy.VersionTag = nil
versionCopy.ModifyIndex = index
latestJob, err := s.JobByID(nil, namespace, jobID)
if err != nil {
return err
}
if versionCopy.Version == latestJob.Version {
if err := txn.Insert("jobs", versionCopy); err != nil {
return err
}
}
return s.upsertJobVersion(index, versionCopy, txn)
}
View on GitHub (pinned to 482b49bf1a)
Solutions
- Check current tags via GET /v1/job/:jobId/versions before unsetting
- Treat this error as success in idempotent delete/cleanup flows
- Correct the tag name (case-sensitive) and retry
Example fix
// before: blindly DELETE tag=prod on every deploy
// after
if tags := versionsWithTags(jobVersions); tags.contains("prod") {
unsetTag("prod")
} // else skip, already unset Defensive patterns
Strategy: validation
Validate before calling
versions, _, _ := client.Jobs().Versions(jobID, false, nil)
tagged := false
for _, v := range versions {
if v.VersionTag != nil && v.VersionTag.Name == name { tagged = true }
}
if !tagged { return nil } // nothing to unset Try / catch
err := unsetTag(jobID, name)
if err != nil && strings.Contains(err.Error(), "not found") {
return nil // already unset; idempotent success
} Prevention
- Verify the tag exists before unsetting
- Write idempotent cleanup scripts that treat not-found as success
- Check tag name spelling and case
When it happens
Trigger: Calling the unset tag endpoint (DELETE /v1/job/:jobId/versions/tag?tag=NAME / JobRevert-related unset RPC) with a tag name that no version carries, or that was already unset.
Common situations: Idempotent cleanup scripts running twice; typos in tag names; tags already removed by another operator or automation between listing and deletion.
Understand the failure class
Background: 'Could not be found', 'does not exist', 'not found in database': the resource-not-found family when an ID, slug, key, or URI lookup comes back empty — this error's family across 20 libraries.
Related errors
- job %q version %d not found
- eval not found
- variable doesn't exist
- unknown deployment %q
- job %q not found
AI-assisted analysis of hashicorp/nomad@482b49bf1a (2026-09-04).
Data as JSON: /api/errors/b51f2fed9bbcb1a0.
Report an issue: GitHub.