test_exceptions.py 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190
  1. ##############################################################################
  2. #
  3. # Copyright (c) 2010 Zope Foundation and Contributors.
  4. # All Rights Reserved.
  5. #
  6. # This software is subject to the provisions of the Zope Public License,
  7. # Version 2.1 (ZPL). A copy of the ZPL should accompany this distribution.
  8. # THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
  9. # WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
  10. # WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
  11. # FOR A PARTICULAR PURPOSE.
  12. #
  13. ##############################################################################
  14. """ zope.interface.exceptions unit tests
  15. """
  16. import unittest
  17. def _makeIface():
  18. from zope.interface import Interface
  19. class IDummy(Interface):
  20. pass
  21. return IDummy
  22. class DoesNotImplementTests(unittest.TestCase):
  23. def _getTargetClass(self):
  24. from zope.interface.exceptions import DoesNotImplement
  25. return DoesNotImplement
  26. def _makeOne(self, *args):
  27. iface = _makeIface()
  28. return self._getTargetClass()(iface, *args)
  29. def test___str__(self):
  30. dni = self._makeOne()
  31. self.assertEqual(
  32. str(dni),
  33. "An object has failed to implement interface "
  34. "__tests__.tests.test_exceptions.IDummy: "
  35. "Does not declaratively implement the interface."
  36. )
  37. def test___str__w_candidate(self):
  38. dni = self._makeOne('candidate')
  39. self.assertEqual(
  40. str(dni),
  41. "The object 'candidate' has failed to implement interface "
  42. "__tests__.tests.test_exceptions.IDummy: "
  43. "Does not declaratively implement the interface."
  44. )
  45. class BrokenImplementationTests(unittest.TestCase):
  46. def _getTargetClass(self):
  47. from zope.interface.exceptions import BrokenImplementation
  48. return BrokenImplementation
  49. def _makeOne(self, *args):
  50. iface = _makeIface()
  51. return self._getTargetClass()(iface, 'missing', *args)
  52. def test___str__(self):
  53. dni = self._makeOne()
  54. self.assertEqual(
  55. str(dni),
  56. 'An object has failed to implement interface '
  57. '__tests__.tests.test_exceptions.IDummy: '
  58. "The 'missing' attribute was not provided.")
  59. def test___str__w_candidate(self):
  60. dni = self._makeOne('candidate')
  61. self.assertEqual(
  62. str(dni),
  63. 'The object \'candidate\' has failed to implement interface '
  64. '__tests__.tests.test_exceptions.IDummy: '
  65. "The 'missing' attribute was not provided.")
  66. def broken_function():
  67. """
  68. This is a global function with a simple argument list.
  69. It exists to be able to report the same information when
  70. formatting signatures.
  71. """
  72. class BrokenMethodImplementationTests(unittest.TestCase):
  73. def _getTargetClass(self):
  74. from zope.interface.exceptions import BrokenMethodImplementation
  75. return BrokenMethodImplementation
  76. message = 'I said so'
  77. def _makeOne(self, *args):
  78. return self._getTargetClass()('aMethod', self.message, *args)
  79. def test___str__(self):
  80. dni = self._makeOne()
  81. self.assertEqual(
  82. str(dni),
  83. "An object has failed to implement interface <Unknown>: "
  84. "The contract of 'aMethod' is violated because I said so."
  85. )
  86. def test___str__w_candidate_no_implementation(self):
  87. dni = self._makeOne('some_function', '<IFoo>', 'candidate')
  88. self.assertEqual(
  89. str(dni),
  90. "The object 'candidate' has failed to implement interface <IFoo>: "
  91. "The contract of 'aMethod' is violated because I said so."
  92. )
  93. def test___str__w_candidate_w_implementation(self):
  94. self.message = 'implementation is wonky'
  95. dni = self._makeOne(broken_function, '<IFoo>', 'candidate')
  96. self.assertEqual(
  97. str(dni),
  98. "The object 'candidate' has failed to implement interface <IFoo>: "
  99. "The contract of 'aMethod' is violated because "
  100. "'broken_function()' is wonky."
  101. )
  102. def test___str__w_candidate_w_implementation_not_callable(self):
  103. self.message = 'implementation is not callable'
  104. dni = self._makeOne(42, '<IFoo>', 'candidate')
  105. self.assertEqual(
  106. str(dni),
  107. "The object 'candidate' has failed to implement interface <IFoo>: "
  108. "The contract of 'aMethod' is violated because "
  109. "'42' is not callable."
  110. )
  111. def test___repr__w_candidate(self):
  112. dni = self._makeOne(None, 'candidate')
  113. self.assertEqual(
  114. repr(dni),
  115. "BrokenMethodImplementation("
  116. "'aMethod', 'I said so', None, 'candidate')"
  117. )
  118. class MultipleInvalidTests(unittest.TestCase):
  119. def _getTargetClass(self):
  120. from zope.interface.exceptions import MultipleInvalid
  121. return MultipleInvalid
  122. def _makeOne(self, excs):
  123. iface = _makeIface()
  124. return self._getTargetClass()(iface, 'target', excs)
  125. def test__str__(self):
  126. from zope.interface.exceptions import BrokenMethodImplementation
  127. excs = [
  128. BrokenMethodImplementation('aMethod', 'I said so'),
  129. Exception("Regular exception")
  130. ]
  131. dni = self._makeOne(excs)
  132. self.assertEqual(
  133. str(dni),
  134. "The object 'target' has failed to implement interface "
  135. "__tests__.tests.test_exceptions.IDummy:\n"
  136. " The contract of 'aMethod' is violated because I said so\n"
  137. " Regular exception"
  138. )
  139. def test__repr__(self):
  140. from zope.interface.exceptions import BrokenMethodImplementation
  141. excs = [
  142. BrokenMethodImplementation('aMethod', 'I said so'),
  143. # Use multiple arguments to normalize repr; versions of Python
  144. # prior to 3.7 add a trailing comma if there's just one.
  145. Exception("Regular", "exception")
  146. ]
  147. dni = self._makeOne(excs)
  148. self.assertEqual(
  149. repr(dni),
  150. "MultipleInvalid("
  151. "<InterfaceClass __tests__.tests.test_exceptions.IDummy>,"
  152. " 'target',"
  153. " (BrokenMethodImplementation('aMethod', 'I said so'),"
  154. " Exception('Regular', 'exception')))"
  155. )