Jguer/yay · error

unknown upgrade exclusion

Error message

unknown upgrade exclusion %q

What it means

Exclude entries that are strings but not in the validExcludes set (the packages actually offered for upgrade) produce 'unknown upgrade exclusion "<name>"'. The library throws this because excluding a package that is not part of this upgrade round indicates a stale or incorrect hook.

Solutions

  1. Correct the package name spelling to match the upgrade set
  2. Remove the stale entry from the exclude list
  3. Compute excludes dynamically from the event's package list instead of hardcoding
  4. Ignore the hook (remove the autocmd) if exclusions are no longer relevant

Example fix

-- before
return { exclude = { 'linux-lts-old' } }
-- after
return { exclude = { 'linux-lts' } }
Defensive patterns

Strategy: validation

Validate before calling

-- cross-check excludes against the packages offered in the event
for _, name in ipairs(result.exclude or {}) do
  local found = false
  for _, pkg in ipairs(event.packages or {}) do if pkg == name then found = true end end
  if not found then error('unknown exclusion: ' .. name) end
end

Prevention

When it happens

Trigger: Callback returns { exclude = { 'somepkg' } } where 'somepkg' is not among the packages in the current upgrade selection passed via validExcludes.

Common situations: Hardcoded exclude lists that outlive the package being removed/renamed; typos in package names; excludes written for a previous upgrade still running in later ones.

Understand the failure class

Background: Invalid enum value errors: "Unknown type", "Invalid scope", "must be one of" — when a string is not on the library's allowed list — this error's family across 23 libraries.

Related errors


AI-assisted analysis of Jguer/yay@328f4b4939 (2026-09-07). Data as JSON: /api/errors/28f1799a3e148d04. Report an issue: GitHub.

Appendix: source

Thrown at pkg/settings/lua/autocmd.go:384

		if !ok {
			return result, fmt.Errorf("exclude must be a table")
		}

		var parseErr error
		excludeTbl.ForEach(func(_ glua.LValue, val glua.LValue) {
			if parseErr != nil {
				return
			}

			lname, ok := val.(glua.LString)
			if !ok {
				parseErr = fmt.Errorf("exclude entries must be strings")
				return
			}

			name := string(lname)
			if !validExcludes.Contains(name) {
				parseErr = fmt.Errorf("unknown upgrade exclusion %q", name)
				return
			}

			result.Exclude = append(result.Exclude, name)
		})
		if parseErr != nil {
			return result, parseErr
		}
	}

	if skipMenuValue := tbl.RawGetString("skip_menu"); skipMenuValue != glua.LNil {
		skipMenu, ok := skipMenuValue.(glua.LBool)
		if !ok {
			return result, fmt.Errorf("skip_menu must be a boolean")
		}

		result.SkipMenu = bool(skipMenu)
	}

View on GitHub (pinned to 328f4b4939)