# 22039 — sql_json_array_not_found

> Source-backed reference for PostgreSQL SQLSTATE 22039.
---

# 22039

## At a glance {#at-a-glance}
An array-only JSON path accessor or item method reached a non-array item without permitted auto-wrap or structural-error suppression. Fixed wildcard, indexed, and `.size()` paths expose separate array-type primaries; an out-of-bounds subscript is 22033.

<!-- BEGIN SQLSTATE FACTS: generated by scripts/generate.py; do not edit -->

| Field | Value |
| --- | --- |
| SQLSTATE | `22039` |
| Condition | `sql_json_array_not_found` |
| Status | `active` |
| Known present by | `12.0` |
| Locked snapshots | `12.22, 13.23, 14.24, 15.19, 16.15, 17.11, 18.6, 19beta3` |
| Macros | `ERRCODE_SQL_JSON_ARRAY_NOT_FOUND` |
| Aliases | `—` |

<!-- source facts: data/errcodes/22039.json -->
<!-- END SQLSTATE FACTS -->

## Messages {#messages}
Representative primary texts are:

| Guard | Primary |
| --- | --- |
| Wildcard array accessor receives a non-array | `jsonpath wildcard array accessor can only be applied to an array` |
| Indexed array accessor receives a non-array | `jsonpath array accessor can only be applied to an array` |
| `.size()` receives a non-array without permitted auto-wrap | `jsonpath item method .%s() can only be applied to an array` |

## Meaning {#meaning}
The `jpiAnyArray` wildcard, `jpiIndexArray` indexed accessor, and `.size()` item-method branches can each auto-wrap a non-array item when `jspAutoWrap(cxt)` is enabled by lax mode. If auto-wrap is not permitted, `jspIgnoreStructuralErrors` can suppress the structural mismatch; when neither applies, the corresponding array-only branch reports 22039. A valid array with an invalid index reaches the separate 22033 subscript guard, so 22039 does not mean an empty array or an out-of-range index.

## Diagnosis {#diagnosis}
Use the exact accessor or method named in the primary and inspect the item returned immediately before it. Separate a scalar/object input from a valid array whose index is outside its bounds, and check whether lax structural-error handling or auto-wrap/unwrap is part of the SQL/JSON path mode.

## Response {#response}
Make the path select an array, normalize the input shape, or choose a scalar-compatible operation. If variable documents are expected, handle the scalar/array branch explicitly instead of relying on a structural mismatch to become an empty result. If an ERROR occurred in an explicit transaction, roll back or roll back to the existing savepoint before retrying; autocommit can retry the corrected action.

## Versions {#versions}
The locked catalogue records this condition from 12.0; the fixed array accessor and `.size()` guards are PostgreSQL 18.6. No natural runtime observation is claimed for this page.

## Related {#related}
[`2203C`](../2203c/), [`2203A`](../2203a/), [`22033`](../22033/)

## Sources {#sources}
The wildcard, indexed, and auto-wrap checks are [`jsonpath_exec.c#L836-979`](https://github.com/postgres/postgres/blob/724edf9bde9d356724ad384a2e196edc3c9f80f7/src/backend/utils/adt/jsonpath_exec.c#L836); the `.size()` array check is [`#L1101-1117`](https://github.com/postgres/postgres/blob/724edf9bde9d356724ad384a2e196edc3c9f80f7/src/backend/utils/adt/jsonpath_exec.c#L1101). The strict/lax structural and throw-return macros are [`#L235-249`](https://github.com/postgres/postgres/blob/724edf9bde9d356724ad384a2e196edc3c9f80f7/src/backend/utils/adt/jsonpath_exec.c#L235). The structured [evidence record](../data/evidence/22039.json) binds the exact array messages and 22033 boundary; no natural runtime was run.
