Skip to content

Default type for Field.errors of tuple() is immediately overwritten #865

@miketheman

Description

@miketheman

The initial data type for Field.errors is set to a tuple:

errors = tuple()

which is reassigned to a list if there's any errors:

self.errors = list(self.process_errors)

which causes type checkers like mypy to be sad when you use the field in your own code directly.

Actual Behavior

in repro.py:

import wtforms

class MyForm(wtforms.Form):
    name = wtforms.StringField()

    def validate(self, extra_validators=None, *args, **kwargs):
        super().validate(extra_validators, *args, **kwargs)

        if self.name.data == 'repro':
            # note the use of `append()`, unavailable on a tuple.
            self.name.errors.append('Name cannot be "repro"')
$ mypy --check-untyped-defs repro.py
repro.py:10: error: "Sequence[str]" has no attribute "append"  [attr-defined]
Found 1 error in 1 file (checked 1 source file)

Expected Behavior

$ mypy --check-untyped-defs repro.py
Success: no issues found in 1 source file

Environment

  • Python version: 3.12
  • wtforms version: 3.2.1
  • mypy version: 1.12.1

Yes, this specific example could be solved another way with validate_name, but that's not the point. The point is that the error's initial datatype is incorrect.
Everywhere it's used, it's treated as a list.

I'd be happy to send a PR changing to an empty list, but I didn't know if there was some other reason to have the data type as a tuple initially.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions