pydantic/pydantic · error · ConfigError

validator with no fields specified

Error message

validator with no fields specified

What it means

Raised by pydantic v1's @validator decorator when it is invoked with zero positional field arguments (e.g. @validator() or @validator(pre=True)). The decorator requires at least one target field name so it knows which model attribute to run the validator against; with no fields there is nothing to bind it to. pydantic raises this at decoration time (class creation) rather than at validation time so the mistake is caught early.

Source

Thrown at pydantic/v1/class_validators.py:72

    pre: bool = False,
    each_item: bool = False,
    always: bool = False,
    check_fields: bool = True,
    whole: Optional[bool] = None,
    allow_reuse: bool = False,
) -> Callable[[AnyCallable], 'AnyClassMethod']:
    """
    Decorate methods on the class indicating that they should be used to validate fields
    :param fields: which field(s) the method should be called on
    :param pre: whether or not this validator should be called before the standard validators (else after)
    :param each_item: for complex objects (sets, lists etc.) whether to validate individual elements rather than the
      whole object
    :param always: whether this method and other validators should be called even if the value is missing
    :param check_fields: whether to check that the fields actually exist on the model
    :param allow_reuse: whether to track and raise an error if another validator refers to the decorated function
    """
    if not fields:
        raise ConfigError('validator with no fields specified')
    elif isinstance(fields[0], FunctionType):
        raise ConfigError(
            "validators should be used with fields and keyword arguments, not bare. "  # noqa: Q000
            "E.g. usage should be `@validator('<field_name>', ...)`"
        )
    elif not all(isinstance(field, str) for field in fields):
        raise ConfigError(
            "validator fields should be passed as separate string args. "  # noqa: Q000
            "E.g. usage should be `@validator('<field_name_1>', '<field_name_2>', ...)`"
        )

    if whole is not None:
        warnings.warn(
            'The "whole" keyword argument is deprecated, use "each_item" (inverse meaning, default False) instead',
            DeprecationWarning,
        )
        assert each_item is False, '"each_item" and "whole" conflict, remove "whole"'
        each_item = not whole

View on GitHub (pinned to 2e5f0e2b42)

Solutions

  1. Pass at least one field name as a positional string, e.g. `@validator('name')`.
  2. To target every field, use the wildcard: `@validator('*')`.
  3. To target multiple fields, list them separately: `@validator('email', 'phone')`.

Example fix

# before
@validator(pre=True)
def normalize(cls, v):
    return v

# after
@validator('name', pre=True)
def normalize(cls, v):
    return v
Defensive patterns

Strategy: validation

Validate before calling

from pydantic.v1.class_validators import validator

def safe_validator(*fields, **kwargs):
    if not fields:
        raise ValueError('At least one field name is required')
    return validator(*fields, **kwargs)

Type guard

def has_field_arg(*fields) -> bool:
    return len(fields) > 0 and all(isinstance(f, str) for f in fields)

Try / catch

try:
    @validator('field')
    def v(cls, value): ...
except Exception as e:
    raise RuntimeError(f'Validator misconfigured: {e}') from e

Prevention

When it happens

Trigger: Calling `validator()` with only keyword args: `@validator(pre=True)` over a method; or calling `@validator()` with empty parens; or programmatically `validator(pre=True)(some_fn)`. The guard at class_validators.py:71 `if not fields:` fires before any field binding.

Common situations: Copy-pasting a validator and deleting the field-name string but leaving the parentheses; migrating code where a generic 'apply to all' intent was expected (use '*' for that); IDE autocomplete inserting `@validator()` as a stub.

Related errors


AI-assisted analysis of pydantic/pydantic@2e5f0e2b42 (2026-08-04). Data as JSON: /data/errors/f7a53fa0bc92b2c2.json. Report an issue: GitHub.