Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

typing.Hashable and typing.Sized error on inference #2272

Closed
leaprovenzano opened this issue Dec 13, 2019 · 2 comments
Closed

typing.Hashable and typing.Sized error on inference #2272

leaprovenzano opened this issue Dec 13, 2019 · 2 comments
Labels
bug

Comments

@leaprovenzano
Copy link
Contributor

@leaprovenzano leaprovenzano commented Dec 13, 2019

typing.Hashable and typing.Sized error on inference

Version: 4.53.2
Python : 3.7.4

heres an minimum example to reproduce the error:

from typing import Hashable
from hypothesis import given, infer


@given(key=infer)
def test_setitem_with_hashable(key: Hashable):
    d = dict()
    d[key] = 1
    assert d[key] == 1

expected behaviour: infer infers a strategy of hashable objects from my type hint OR errors gracefully and tells me I can't use typing.Hashable.

actual behaviour:

inferring a strategy based on typing.Hashable type fails when we try and to index an empty __args__ tuple in resolve_FrozenSet as you can see from the tailend of this traceback:

env/lib/python3.7/site-packages/hypothesis/strategies/_internal/core.py:1452: in from_type
    return types.from_typing_type(thing)
env/lib/python3.7/site-packages/hypothesis/strategies/_internal/types.py:182: in from_typing_type
    for k, v in mapping.items()
env/lib/python3.7/site-packages/hypothesis/strategies/_internal/types.py:183: in <listcomp>
    if sum(try_issubclass(k, T) for T in mapping) == 1
env/lib/python3.7/site-packages/hypothesis/strategies/_internal/types.py:340: in really_inner
    return func(thing)
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

thing = typing.Hashable

    @register(typing.FrozenSet, st.builds(frozenset))
    def resolve_FrozenSet(thing):
>       return st.frozensets(st.from_type(thing.__args__[0]))
E       IndexError: tuple index out of range

env/lib/python3.7/site-packages/hypothesis/strategies/_internal/types.py:377: IndexError

typing.Hashable does not accept type args via __class_getitem__ (it would make no sense) and typing.Hashable.__args__ exists but is an empty tuple ( which is also a bit silly but whatever).
to be clear this works just fine:

from collections.abc import Hashable
from hypothesis import given, infer


@given(key=infer)
def test_setitem_with_hashable(key: Hashable):
    d = dict()
    d[key] = 1
    assert d[key] == 1

which is good because typing.Hashable.__origin__ is collections.abc.Hashable.

I had a look for other things in the typing module with these properties and i can see that typing.Sized has precisely the same issue (and also works fine with from_type(typing.Sized.__origin__)).


how can I help?

I'm happy to put up a PR to patch these in to strategies._internal.types.py

Let me know if you're happy for me to go ahead i will get to work on a PR.

@Zac-HD

This comment has been minimized.

Copy link
Member

@Zac-HD Zac-HD commented Dec 13, 2019

Go for it - I think we'll want to take the first element of __args__ if it's non-empty, falling back to __origin__ otherwise. A helper function might make this easier!

@Zac-HD Zac-HD added the bug label Dec 13, 2019
@leaprovenzano

This comment has been minimized.

Copy link
Contributor Author

@leaprovenzano leaprovenzano commented Dec 13, 2019

Go for it - I think we'll want to take the first element of __args__ if it's non-empty, falling back to __origin__ otherwise. A helper function might make this easier!

cool. thanks for tip!

you can assign me to this issue if you like.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
2 participants
You can’t perform that action at this time.