hasura/graphql-engine · error · MapFieldNamesError

Value did not match array type, was expecting {expected_type

Error message

Value did not match array type, was expecting {expected_type}

What it means

Thrown by MapFieldNamesError::ExpectedAnArray when mapping user-supplied argument values against the schema's array types during query planning. The planner encountered a value position the schema types as a list/array, but the runtime value (or its inferred type) does not match the expected element/list type. It almost always indicates a mismatch between the client-provided arguments and the NDC schema type mappings.

Source

Thrown at v3/crates/plan/src/query/arguments.rs:645

                    plan_expression(&predicate, relationships, remote_predicates, plan_state)?;

                Argument::BooleanExpression {
                    predicate: resolved_filter_expression,
                }
            }
            UnresolvedArgument::Literal { value } => Argument::Literal {
                value: value.clone(),
            },
        };
        resolved_arguments.insert(argument_name, resolved_argument_value.clone());
    }

    Ok(resolved_arguments)
}

#[derive(Debug, thiserror::Error)]
pub enum MapFieldNamesError {
    #[error("Value did not match array type, was expecting {expected_type}")]
    ExpectedAnArray {
        expected_type: QualifiedTypeReference,
    },
    #[error("Value did not match object type, was expecting {expected_type}")]
    ExpectedAnObject {
        expected_type: QualifiedTypeReference,
    },
    #[error("Type mappings not found for object type {object_type_name}")]
    TypeMappingsNotFound {
        object_type_name: Qualified<CustomTypeName>,
    },
    #[error("Field mapping {field_name} not found for object type {object_type_name}")]
    FieldMappingNotFound {
        object_type_name: Qualified<CustomTypeName>,
        field_name: FieldName,
    },
    #[error("Unknown fields found in object type {object_type_name}: {fields:?}")]
    UnknownFieldsInObject {

View on GitHub (pinned to 724551b9ae)

Solutions

  1. Check the failing argument in the request and wrap the value in a JSON array if the schema declares a list type
  2. Verify element types and nullability of the array against the schema (e.g. [String!] vs [String])
  3. Regenerate/refresh the client from the current schema if the argument type recently changed
  4. Inspect the NDC type mappings for the object to ensure the array type mapping is present and correct

Example fix

// before
variables: { "tags": "production" }
// after
variables: { "tags": ["production"] }
Defensive patterns

Strategy: validation

Validate before calling

// Before sending, check list-typed arguments against the schema
fn assert_list_arg(name: &str, v: &serde_json::Value) -> Result<(), String> {
    v.as_array().map(|_| ()).ok_or_else(|| format!("argument '{name}' must be an array"))
}

Type guard

const isJSONArray = (v: unknown): v is unknown[] => Array.isArray(v);

Try / catch

match plan { Err(e @ PlanError::MapFieldNames(MapFieldNamesError::ExpectedAnArray { expected_type })) => /* 400 with expected_type back to client */, ... }

Prevention

When it happens

Trigger: Calling a query/mutation with a list-typed argument where the value provided is a scalar/object instead of a JSON array, or whose elements don't match the array's declared element type, while map_field_names is resolving argument field names in v3/crates/plan/src/query/arguments.rs.

Common situations: Sending a single object where the API expects an array of objects; nested arrays with wrong inner types; stale client code after the schema changed a scalar argument into a list; inconsistent nullability of elements.

Related errors


AI-assisted analysis of hasura/graphql-engine@724551b9ae (2026-08-28). Data as JSON: /api/errors/6b22d6250f887a8d. Report an issue: GitHub.