pathwaycom/pathway · error · TypeError

Object in {expression!r} has to be a JSON or sequence.

Error message

Object in {expression!r} has to be a JSON or sequence.

What it means

Pathway's type interpreter raises this TypeError when a JsonGet expression (column.get(...) / column[...]) is applied to a column whose dtype is neither JSON (or Optional[JSON]) nor a sequence type (Array, Tuple, List) nor ANY. The interpreter statically checks column dtypes before the pipeline runs, so this is a schema/type error, not a data error.

Source

Thrown at python/pathway/internals/type_interpreter.py:532

            # json
            if not dt.dtype_issubclass(default_dtype, dt.Optional(dt.JSON)):
                raise TypeError(
                    f"Default must be of type {Json | None}, found {default_dtype.typehint}."
                )
            if not expression._check_if_exists or default_dtype == dt.JSON:
                return _wrap(expression, dt.JSON)
            else:
                return _wrap(expression, dt.Optional(dt.JSON))
        elif object_dtype.equivalent_to(dt.Optional(dt.JSON)):
            # optional json
            raise TypeError(f"Cannot get from {Json | None}.")
        else:
            # sequence
            if (
                not isinstance(object_dtype, (dt.Array, dt.Tuple, dt.List))
                and object_dtype != dt.ANY
            ):
                raise TypeError(
                    f"Object in {expression!r} has to be a JSON or sequence."
                )
            if index_dtype != dt.INT:
                raise TypeError(f"Index in {expression!r} has to be an int.")

            if isinstance(object_dtype, dt.Array):
                return _wrap(expression, object_dtype.strip_dimension())
            if object_dtype == dt.ANY:
                return _wrap(expression, dt.ANY)

            if isinstance(object_dtype, dt.List):
                if expression._check_if_exists:
                    return _wrap(expression, dt.Optional(object_dtype.wrapped))
                else:
                    return _wrap(expression, object_dtype.wrapped)
            assert isinstance(object_dtype, dt.Tuple)
            if object_dtype == dt.ANY_TUPLE:
                return _wrap(expression, dt.ANY)

View on GitHub (pinned to fa2f74a464)

Solutions

  1. Declare the column as pw.Json in the connector schema so .get() is valid on it
  2. If the column holds a JSON string, parse it first (e.g. pw.parse_json(table.col)) before .get()
  3. If the column is a scalar, use the value directly instead of .get()
  4. Cast with .astype(pw.Json) or table.with_columns(col=pw.this.col.astype(pw.Json)) when you know the data is JSON-like

Example fix

// before
input_schema = pw.schema_from_types(value=str)
t = pw.io.csv.read(path, schema=input_schema)
out = t.select(res=t.value.get('key'))

// after
input_schema = pw.schema_from_types(value=pw.Json)
t = pw.io.csv.read(path, schema=input_schema)
out = t.select(res=t.value.get('key'))
Defensive patterns

Strategy: type-guard

Validate before calling

import pathway as pw

def can_json_get(col) -> bool:
    d = col._column.dtype
    return (
        d.equivalent_to(pw.Json)
        or d.equivalent_to(pw.Optional[pw.Json])
        or isinstance(d, (pw.Array, pw.Tuple, pw.List))
        or d == pw.ANY
    )

Type guard

from pathway.internals import dtype as dt

def is_json_or_sequence(dtype) -> bool:
    return (
        dtype.equivalent_to(dt.JSON)
        or dtype.equivalent_to(dt.Optional(dt.JSON))
        or isinstance(dtype, (dt.Array, dt.Tuple, dt.List))
        or dtype == dt.ANY
    )

Try / catch

try:
    out = t.select(res=t.value.get('key'))
except TypeError as e:
    if 'has to be a JSON or sequence' in str(e):
        t = t.with_columns(value=pw.this.value.astype(pw.Json))
        out = t.select(res=t.value.get('key'))
    else:
        raise

Prevention

When it happens

Trigger: Calling .get() or [] on a column typed as a scalar (e.g. int, str, float, Optional[int], Pointer, or a Duration/Date column). Example: table.select(res=table.value.get('key')) where table.value is int or str instead of pw.Json. Also happens after apply_with_type or io.schemas that declare the column as a non-JSON scalar.

Common situations: CSV/JSON connector schema declares the field as str instead of pw.Json; developer assumed .get() works on any column; reading JSON strings (not parsed objects) from Kafka/CSV and indexing them directly; column wrapped in Optional of a non-JSON type.

Related errors


AI-assisted analysis of pathwaycom/pathway@fa2f74a464 (2026-08-15). Data as JSON: /api/errors/a3bccd73cd0ac54b. Report an issue: GitHub.