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

Support multiple contract syntaxes #21

Open
dhouck opened this issue Feb 19, 2020 · 3 comments
Open

Support multiple contract syntaxes #21

dhouck opened this issue Feb 19, 2020 · 3 comments

Comments

@dhouck
Copy link

dhouck commented Feb 19, 2020

Is your feature request related to a problem? Please describe.
There are multiple runtime DBC packages for Python (e.g., PyContracts, dpcontracts, icontract, …). It would be nice to be able to use the same contracts for runtime checking with one of these tools, and compile-time checking with CrossHair.

Describe the solution you'd like
Being able to tell when one of these packages is imported and reading their annotations would probably be simplest. I don’t know how decorated functions are currently handled, but it might also be simpler than trying to statically analyze the functions those decorators return.

Describe alternatives you've considered
CrossHair could either support runtime checking on its own, or it could have a decorator that reads the docstring and applied the relevant decorators from one of these other systems. Both of these sound more complicated than my proposed solution, and they are less compatible with existing runtime-checked contracts.

@pschanely
Copy link
Owner

Love this idea.

And it might not be all that difficult to do; the stuff we'd need to change is relatively well encapsulated in get_fn_conditions and get_class_conditions in condition_parser.py. There are some details to consider, however, like whether it's ok for exceptions can be thrown and what kind of copy happens for previous/old value comparisons. I think class invariants also have some subtle behaviors that might vary between contract implementations.

If someone wanted to make this happen for their favorite syntax, I would be completely happy to shepherd it along.

Otherwise, internet, please post or thumbs-up your favorite tools: with enough votes, I could probably prioritize some of my own time to try and get an implementation out.

@Zac-HD
Copy link
Contributor

Zac-HD commented Mar 11, 2020

You know what would be amazing? Symbolically executing tests written for Hypothesis! For example:

@given(st.integers(min_value=0))
def test(x):
    assert x ** 2 >= x

# could be equivalent to

def test(x: int):
    """pre: x >= 0"""
    assert x ** 2 >= x

this is particularly interesting to me because (a) I'm a core dev of Hypothesis 😜, (b) Hypothesis tests have to precisely describe the domain of valid inputs, and (c) they have a high density of assertions about error-prone behaviour!

I don't have time to write this myself (at least in the next few months), but would be delighted to help anyone who wants to have a go.

@pschanely
Copy link
Owner

pschanely commented Feb 24, 2021

An update: at present we support: PEP316, icontract, deal, an assert-based mode, and hypothesis. See these docs for details.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants