2015-03-13 2 views
1

Я хотел поместить результаты pytest aserts в журнал.пользовательский sys.excepthook не работает с pytest

Сначала я попробовал это решение

def logged_assert(self, testval, msg=None): 
    if not testval: 
     if msg is None: 
      try: 
       assert testval 
      except AssertionError as e: 
       self.logger.exception(e) 
       raise e 
     self.logger.error(msg) 
     assert testval, msg 

Это работа прекрасно, но мне нужно, чтобы использовать свой собственный сбщ для каждого утверждают, вместо этого, если построить в. Проблема заключается в том, что testval оценивает, когда она перешла в функцию и ошибка тзд является

AssertionError: False 

Я нашел отличный способ решить проблему http://code.activestate.com/recipes/577074-logging-asserts/ здесь в первом комментарии.

И я написал эту функцию в моем модуле обертке регистратора

def logged_excepthook(er_type, value, trace): 
    print('HOOK!') 
    if isinstance(er_type, AssertionError): 
     current = sys.modules[sys._getframe(1).f_globals['__name__']] 
     if 'logger' in sys.modules[current]: 
      sys.__excepthook__(er_type, value, trace) 
      sys.modules[current].error(exc_info=(er_type, value, trace)) 
     else: 
      sys.__excepthook__(er_type, value, trace) 
    else: 
     sys.__excepthook__(er_type, value, trace) 

, а затем

sys.excepthook = logged_excepthook 

В модуле тестирования, где я есть утверждает выход

import sys 
print(sys.excepthook, sys.__excepthook__, logged_excepthook) 

является

<function logged_excepthook at 0x02D672B8> <built-in function excepthook> <function logged_excepthook at 0x02D672B8> 

Но на моем выходе нет сообщения «Крючок». А также сообщение ERROR в моих файлах журналов. Все работает как со встроенным sys.excepthook.

Я просмотрел источники pytest, но sys.excepthook там не изменился. Но если я прерываю выполнение кода с помощью Cntrl-C, я получаю сообщение «Hook» в stdout.

Главный вопрос: почему встроенный sys.excepthook называется isntead моей пользовательской функцией и как я могу это исправить. Но это также интересно мне, если существует другой способ регистрации ошибок утверждения.

Я использую python3.2 (32bit) в 64-битных окнах 8.1.

ответ

1

excepthook инициируется только в случае, если существует исключение , то есть тот, который обычно завершает вашу программу. Любые исключения в тесте обрабатываются платформой тестирования.

См. Asserting with the assert statement - pytest documentation о том, как функция предназначена для использования. Пользовательское сообщение указывается стандартным способом: assert condition, failure_message.

Если вы не удовлетворены тем, как pytest ручками assert с, вам необходимо либо

pytest использует крючок assert. Его логика находится в Lib\site-packages\_pytest\assertion (a stock plugin). Вероятно, достаточно обернуть/заменить несколько функций. Чтобы избежать исправления базы кода, вы можете использовать свой собственный плагин: заплатите плагин exceptions во время выполнения, или отключите его и повторно используйте его функции самостоятельно.

+1

Спасибо! Ваш ответ очистил мой разум. Я просто использовал 'pytest_assertrepr_compare' для добавления журнала. Это не идеальное решение по некоторым причинам, но приемлемое для меня. Проблемы - это Нет, возвращаемые 'util.assertrepr_compare' (что не является реальной проблемой - если нет объяснений по умолчанию, я могу определить свой собственный простой). Во-вторых, я не могу добавить msg в журналы ('assert testval, msg'). Но это тоже не проблема, я могу просто использовать мой метод logged_assert для этих случаев. – Aprectu

Смежные вопросы