def test_correct_exceptions_raised_on_contract_fail(self): func = deal.pre(lambda x: x > 0)(lambda x: x) with pytest.raises(deal.PreContractError): func(-2) func = deal.pre(lambda x: x > 0, message='TEST')(lambda x: x) try: func(-2) except AssertionError as e: assert e.args[0] == 'TEST' func = deal.pre(lambda x: x > 0, exception=NameError)(lambda x: x) with pytest.raises(NameError): func(-2) func = deal.pre(lambda x: x > 0, exception=NameError('TEST'))(lambda x: x) with pytest.raises(NameError): func(-2) try: func(-2) except NameError as e: assert e.args[0] == 'TEST' func = deal.pre(lambda x: x > 0, message='TEST', exception=NameError)(lambda x: x) with pytest.raises(NameError): func(-2) try: func(-2) except NameError as e: assert e.args[0] == 'TEST'
def test_chain_all_contracts_fulfilled(correct, incorrect_min, incorrect_max): func = deal.pre(lambda x: x < 10)(lambda x: x) func = deal.pre(lambda x: x > 0)(func) assert func(correct) == correct with pytest.raises(deal.PreContractError): func(incorrect_min) with pytest.raises(deal.PreContractError): func(incorrect_max)
def test_chain(self): func = deal.pre(lambda x: x < 10)(lambda x: x) func = deal.pre(lambda x: x > 0)(func) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(-2) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(20)
def test_contract_state_switch_default_param(): func = deal.pre(lambda x: x > 0)(lambda x: x * 2) deal.disable() assert func(-2) == -4 deal.enable() with pytest.raises(deal.PreContractError): func(-2)
def test_contract_state_switch_custom_param(): func = deal.pre(lambda x: x > 0)(lambda x: x * 2) deal.disable() func(-2) deal.enable() with pytest.raises(deal.PreContractError): func(-2)
def test_contract_state_switch_custom_param(self): func = deal.pre(lambda x: x > 0, debug=True)(lambda x: x * 2) deal.switch(debug=False) func(-2) deal.switch(debug=True) with pytest.raises(deal.PreContractError): func(-2)
def test_contract_state_switch_default_param(self): func = deal.pre(lambda x: x > 0)(lambda x: x * 2) deal.switch(main=False) func(-2) deal.switch(main=True) with pytest.raises(deal.PreContractError): func(-2)
def test_main(self): func = pre(lambda x: x > 0)(lambda x: x) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(PreContractError): func(-2)
def test_debug(self): func = deal.pre(lambda x: x > 0, debug=True)(lambda x: x * 2) deal.switch(debug=False) with self.subTest(text='good'): func(-2) deal.switch(debug=True) with self.subTest(text='error'): with pytest.raises(deal.PreContractError): func(-2)
def test_main(self): func = deal.pre(lambda x: x > 0)(lambda x: x * 2) deal.switch(main=False) with self.subTest(text='good'): func(-2) deal.switch(main=True) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(-2)
def test_raise_error_with_param_on_contract_failure(self): func = deal.pre(lambda x: x > 0 or 'TEST')(lambda x: x) assert func(4) == 4 with pytest.raises(deal.PreContractError): func(-2) try: func(-2) except deal.PreContractError as e: assert e.args[0] == 'TEST'
def test_contract_returns_message(): func = deal.pre(lambda x: x > 0 or 'TEST')(lambda x: x) assert func(4) == 4 with pytest.raises(deal.PreContractError): func(-2) try: func(-2) except deal.PreContractError as e: assert e.args[0] == 'TEST'
def _test_validator(self, validator): func = deal.pre(validator)(lambda x: x) assert func(4) == 4 with pytest.raises(deal.PreContractError): func(-2) try: func(-2) except deal.PreContractError as e: assert e.args[0] == 'TEST'
def test_source_get_chain(): sum_contract = deal.chain( deal.pre(lambda a, b: a > 0), deal.pre(lambda a, b: b > 0), deal.post(lambda res: res > 0), ) @sum_contract def sum(a, b): return a + b with pytest.raises(deal.ContractError) as exc_info: sum(-2, 3) assert exc_info.value.source == 'a > 0' with pytest.raises(deal.ContractError) as exc_info: sum(2, -3) assert exc_info.value.source == 'b > 0' state.color = False assert str(exc_info.value) == 'expected b > 0 (where a=2, b=-3)' state.color = True
def test_error_returning(self): func = deal.pre(lambda x: x > 0 or 'TEST')(lambda x: x) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(-2) with self.subTest(text='error message'): try: func(-2) except deal.PreContractError as e: self.assertEqual(e.args[0], 'TEST')
def _test_validator(self, validator): func = deal.pre(validator)(lambda x: x) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(-2) with self.subTest(text='error message'): try: func(-2) except deal.PreContractError as e: self.assertEqual(e.args[0], 'TEST')
def test_django_style_without_attr(self): class Validator: def __init__(self, x): self.x = x def is_valid(self): if self.x <= 0: return False return True func = deal.pre(Validator)(lambda x: x) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(deal.PreContractError): func(-2)
def test_exception_hook(capsys): pre_path = str(Path('deal', '_decorators', 'pre.py')) f = deal.pre(lambda x: x > 0)(lambda x: x) with pytest.raises(deal.PreContractError) as exc_info: f(-2) # custom hook is registered assert sys.excepthook is exception_hook # the default hook shows the full traceback _excepthook(exc_info.type, exc_info.value, exc_info.tb) captured = capsys.readouterr() assert captured.out == '' assert pre_path in captured.err # the custom hook hides deal from the traceback exception_hook(exc_info.type, exc_info.value, exc_info.tb) captured = capsys.readouterr() assert captured.out == '' # the hook doesn't work on python 3.6 and below if sys.version_info[:2] >= (3, 7): assert pre_path not in captured.err
def test_init(self): with self.subTest(text='init has not raised any exceptions'): func = deal.pre(lambda x: x > 0) with self.subTest(text='validator'): func = deal.pre(lambda x: x > 0)(lambda x: x) with self.assertRaises(deal.PreContractError): func(-2) with self.subTest(text='message'): func = deal.pre(lambda x: x > 0, message='TEST')(lambda x: x) try: func(-2) except AssertionError as e: self.assertEqual(e.args[0], 'TEST') with self.subTest(text='exception'): func = deal.pre(lambda x: x > 0, exception=NameError)(lambda x: x) with self.assertRaises(NameError): func(-2) with self.subTest(text='exception with name'): func = deal.pre(lambda x: x > 0, exception=NameError('TEST'))(lambda x: x) with self.subTest(text='exception/exception'): with self.assertRaises(NameError): func(-2) with self.subTest(text='exception/message'): try: func(-2) except NameError as e: self.assertEqual(e.args[0], 'TEST') with self.subTest(text='exception+message'): func = deal.pre(lambda x: x > 0, message='TEST', exception=NameError)(lambda x: x) with self.subTest(text='exception+message/exception'): with self.assertRaises(NameError): func(-2) with self.subTest(text='exception+message/message'): try: func(-2) except NameError as e: self.assertEqual(e.args[0], 'TEST')
def test_django_style(self): class Validator(object): def __init__(self, x): self.x = x def is_valid(self): if self.x <= 0: self.errors = 'TEST' return False return True func = pre(Validator)(lambda x: x) with self.subTest(text='good'): self.assertEqual(func(4), 4) with self.subTest(text='error'): with self.assertRaises(PreContractError): func(-2) with self.subTest(text='error message'): try: func(-2) except PreContractError as e: self.assertEqual(e.args[0], 'TEST')
def test_pre_contract_fulfilled(self, correct, incorrect): func = deal.pre(lambda x: x > 0)(lambda x: x) assert func(correct) == correct with pytest.raises(deal.PreContractError): func(incorrect)