elasticsearch-dsl-py icon indicating copy to clipboard operation
elasticsearch-dsl-py copied to clipboard

`DslBase.__init__()` typing won't accept dict unpacking

Open realsuayip opened this issue 1 year ago • 1 comments

DslBase.__init__() typing does not accept dict unpacking, hence all Query subclasses.

https://github.com/elastic/elasticsearch-dsl-py/blob/318ea9a9e4b792325556671e1537df9032ee4e65/elasticsearch_dsl/utils.py#L326

For example, Term(**my_dict) will result in following mypy error:

error: Argument 1 to "Term" has incompatible type "**Dict[str, str]"; expected "Optional[bool]

This is due to _expand__to_dot, mypy assumes all params have unified type. Maybe just use **params: Any and pop _expand__to_dot from there?

realsuayip avatar Sep 03 '24 12:09 realsuayip

This will be addressed after #1890 is merged. All query classes are going to have explicit arguments. Here is how Term is going to be defined:

class Term(Query):
    """
    Returns documents that contain an exact term in a provided field. To
    return a document, the query term must exactly match the queried
    field's value, including whitespace and capitalization.

    :arg _field: The field to use in this query.
    :arg _value: The query value for the field.
    """

    name = "term"

    def __init__(
        self,
        _field: Union[str, "InstrumentedField", "NotSet"] = NOT_SET,
        _value: Union["i.TermQuery", Dict[str, Any], "NotSet"] = NOT_SET,
        **kwargs: Any,
    ):
        if not isinstance(_field, NotSet):
            kwargs[str(_field)] = _value
        super().__init__(**kwargs)

If you want to take advantage of typing, then you would call Term(field, value), but you can also use the current form and do Term(**kwargs). The _expand__to_dot will still be supported.

miguelgrinberg avatar Sep 03 '24 13:09 miguelgrinberg