mikefarah/yq · error

index [%v] out of range, array size is %v

Error message

index [%v] out of range, array size is %v

What it means

yq supports negative (from-the-end) indexing on arrays. After applying a negative offset, if the computed index is still below zero it means the requested position lies before the start of the array, so yq raises 'index out of range'. Positive indexes beyond the end are instead handled by padding/formatting logic, not this error.

Source

Thrown at pkg/yqlib/operator_traverse_path.go:239

		indexToUse := index
		contentLength := len(node.Content)
		for contentLength <= index {
			if contentLength == 0 {
				// default to nice yaml formatting
				node.Style = 0
			}

			valueNode := createScalarNode(nil, "null")
			node.AddChild(valueNode)
			contentLength = len(node.Content)
		}

		if indexToUse < 0 {
			indexToUse = contentLength + indexToUse
		}

		if indexToUse < 0 {
			return nil, fmt.Errorf("index [%v] out of range, array size is %v", index, contentLength)
		}

		newMatches.PushBack(node.Content[indexToUse])
	}
	return newMatches, nil
}

func keyMatches(key *CandidateNode, wantedKey string, exactKeyMatch bool) bool {
	if exactKeyMatch {
		// this is used for merge
		return key.Value == wantedKey
	}
	return matchKey(key.Value, wantedKey)
}

func traverseMap(context Context, matchingNode *CandidateNode, keyNode *CandidateNode, prefs traversePreferences, splat bool) (*list.List, error) {
	var newMatches = orderedmap.NewOrderedMap()
	err := doTraverseMap(newMatches, matchingNode, keyNode.Value, prefs, splat)

View on GitHub (pinned to 8b5af0694b)

Solutions

  1. Clamp the index in your expression, e.g. `.a[-1]` for the last element instead of a large negative offset
  2. Guard with a length check: `select(.a | length >= 3) | .a[-3]`
  3. Use optional traverse semantics (`.[...]?`) so out-of-range paths yield nothing instead of an error
  4. Fix the upstream data so the array actually contains the expected number of elements

Example fix

// before
yq '.a[-10]' file.yaml
// after
yq '.a[-1]' file.yaml
Defensive patterns

Strategy: validation

Validate before calling

// Guard negative index against array length before evaluating
if idx < 0 && -idx > arrayLen {
	return fmt.Errorf("index %d exceeds array length %d", idx, arrayLen)
}

Type guard

func indexInRange(idx, length int) bool { i := idx; if i < 0 { i += length }; return i >= 0 && i < length }

Try / catch

out, err := yqEval(".a[-1]", doc)
if err != nil && strings.Contains(err.Error(), "out of range") {
	// treat as missing element and continue
}

Prevention

When it happens

Trigger: Traversing with an index like `.a[-10]` on an array whose length is smaller than the absolute offset, so contentLength + index < 0. E.g. array size 2 with index -5.

Common situations: Assuming jq-style clamping of out-of-range negative indexes, scripts computing offsets dynamically (e.g. `.[-$n]`) where n exceeds array length, or input arrays that shrank between yq versions/config runs.

Related errors


AI-assisted analysis of mikefarah/yq@8b5af0694b (2026-09-05). Data as JSON: /api/errors/f1b8eaf47b8e46c0. Report an issue: GitHub.