Я нашел решение своей проблемы.Сначала я определяю декоратор:
import traceback
def catch_exception(f):
def wrapper(*args, **kwargs):
try:
return f(*args, **kwargs)
except StopConsumer:
raise
except Exception as e:
print(traceback.format_exc().strip('\n'), '<--- from consumer')
raise
return wrapper
Затем я определяю базовый класс для всех моих потребителей, который использует этот декоратор следующим образом:
import inspect
class BaseConsumer(JsonWebsocketConsumer):
def __getattribute__(self, name):
value = object.__getattribute__(self, name)
if inspect.ismethod(value):
return catch_exception(value)
return value
Но сохраняются 2 проблемы:
- Обычно показанные исключения появляются дважды
- Другие исключения повторяются 3 или 4 раза!(как будто срабатывает каждый уровень иерархии классов)
Пример первого случая (KeyError):
Traceback (most recent call last):
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 31, in wrapper
result = f(owner, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 110, in refresh
data = super().refresh.__wrapped__(self)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 73, in refresh
pvalue = round(data['toto'] * 100, 1)
KeyError: 'toto' <--- from consumer
Exception in thread Thread-3:
Traceback (most recent call last):
File "/usr/lib/python3.6/threading.py", line 916, in _bootstrap_inner
self.run()
File "/usr/lib/python3.6/threading.py", line 864, in run
self._target(*self._args, **self._kwargs)
File "/home/alain/ADN/simutool/dbsimu/utils.py", line 193, in repeat
self.repeat_func()
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 31, in wrapper
result = f(owner, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 110, in refresh
data = super().refresh.__wrapped__(self)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 73, in refresh
pvalue = round(data['toto'] * 100, 1)
KeyError: 'toto'
Пример второго случая (переменная с ошибкой):
WebSocket CONNECT /ws/dbsimu/Simuflow_progress/ [127.0.0.1:55866]
Traceback (most recent call last):
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 57, in receive_json
return getattr(self, icommand)(**data)
NameError: name 'icommand' is not defined <--- from consumer
Traceback (most recent call last):
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/.local/lib/python3.6/site-packages/channels/generic/websocket.py", line 125, in receive
self.receive_json(self.decode_json(text_data), **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 57, in receive_json
return getattr(self, icommand)(**data)
NameError: name 'icommand' is not defined <--- from consumer
Traceback (most recent call last):
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/.local/lib/python3.6/site-packages/channels/generic/websocket.py", line 60, in websocket_receive
self.receive(text_data=message["text"])
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/.local/lib/python3.6/site-packages/channels/generic/websocket.py", line 125, in receive
self.receive_json(self.decode_json(text_data), **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 19, in wrapper
return f(*args, **kwargs)
File "/home/alain/ADN/simutool/dbsimu/consumers.py", line 57, in receive_json
return getattr(self, icommand)(**data)
NameError: name 'icommand' is not defined <--- from consumer
Если у кого-нибудь есть идея, чтобы исправить это, пожалуйста, сообщите.