Тестирование сбоя задания с помощью unittest
Один из моих атрибутов - это свойство, когда сеттер вызывает функцию проверки, которая вызывает исключение, если новое значение недействительно:
pos.offset = 0
# @offset.setter calls validate(offset=0)
# PositionError: Offset may not be 0.
Я пытаюсь добавить тест, чтобы убедиться, что это не удается. Однако я не могу понять, как заставить assertRaises работать с заданием.
Нормальный синтаксис assertRaises требует метода, а не атрибута/свойства:
self.assertRaises(PositionError, pos.offset, 0)
# TypeError: 'int' object is not callable
Другие формы, которые я пробовал, являются недопустимыми Python:
self.assertRaises(PositionError, pos.offset = 0)
# SyntaxError: Keyword can't be an expression
self.assertRaises(PositionError, lambda: pos.offset = 0)
# SyntaxError: lambda cannot contain assignment
Как проверить неудачу назначения свойства?
Примечание: Python 2.6, я знаю, что unittest имеет некоторые новые функции в 2.7
Ответы
Ответ 1
Если вы хотите использовать unittest
для проверки того, что исключение происходит в блоке кода, а не только вызове функции, вы можете использовать assertRaises
в качестве менеджера контекста:
with self.assertRaises(PositionError):
pos.offset = 0
Это использование можно найти в unittest docs.
Хотя это не доступно в Python 2.6 и не будет работать для вас как такового (я только что видел вашу заметку), я думаю, что это стоит включить в ответы, так как это, вероятно, более ясный способ сделать это для python 2.7 +.
Ответ 2
До Python 2.7, вы хотите использовать setattr(object, name, value)
(doc). Это позволяет установить значение для атрибута.
self.assertRaises(PositionError, setattr, pos, "offset", 0)
# ... ok
Это всегда должно работать, потому что, если атрибут является свойством и, таким образом, "тайно" вызывает функцию, он должен находиться внутри класса. Я не думаю, что стандартное назначение может завершиться неудачно (хотя выражение с правой стороны может выйти из строя, т.е. x = 1/0
).