Подтвердить что ты не робот

Как обрабатывать исключения в составе актера?

Существует ли стандартный шаблон для устранения исключений в субъектах Akka.NET?

Я видел несколько шаблонов для создания супервизоров, но кажется, что SupervisorStrategy - это способ справиться с вещами, которые не могут быть разрешены актером.

У меня есть актер, который получает много данных и должен хранить его на внешнем сервере. Внешняя база данных может быть недоступна. Если это так, сервер может перезагрузиться или сеть может быть отключена. Мне не нужно перезапускать актер или что-то еще, я просто хочу сообщить отправителю некоторую информацию о том, что происходит, чтобы он мог сохранить сообщение на диске и перенести его позже.

Отправитель не является родителем этого актера, подключающегося к базе данных. Должен ли я создать супервизора, чтобы справиться с этим? Или я должен инкапсулировать мои обработчики приема в блоки try/catch и просто использовать Tell для уведомления отправителей a с настраиваемым ответом, как если бы это было обычное сообщение?

Я знаю, что существует класс Failure, но я не уверен, что я должен использовать его для этой ситуации.

4b9b3361

Ответ 1

Да, есть. Прежде всего, всегда делегируйте опасную работу детям-актерам, дайте им все свои ножи, огнемет и тому подобное. если они сбой и сжигание, ваше состояние все еще остается нетронутым, и вы можете создавать новых детей.

Итак, для примера недостижимой базы данных; Выдвиньте БД-коммуникатора. Затем вы можете позволить этому актеру иметь два состояния: DB up и DB down, это можно моделировать как FSM или использовать Become/Unbecome.

Итак, когда приходит сообщение и запрашивает запрос БД, если что-то взорвано, агент-коммуникатор БД передает его в состояние DB-Down. Если какой-либо запрос получен в состоянии DB-Down, вы можете немедленно ответить с событием Failure.

Итак, как мы переходим от DB-Down до DB-Up снова? Актер DB-Communicator может выполнить ping сам, используя ScheduleOnce, например. передайте ему сообщение "CheckDBStatus" каждые x секунд. Когда сообщение CheckDBStatus получено, вы проверяете, снова ли DB снова, и если да, то вы вернетесь в состояние DB-Up.

Таким образом, вы не будете наводнять свою БД в сценариях, где он не может реагировать из-за высокой нагрузки, добавив больше нагрузки в этом случае, это только ухудшит ситуацию. Таким образом, этот автоматический выключатель предотвратит это.

Короче говоря:

В состоянии DB-Up:

Если получено сообщение DBQuery, попробуйте запустить запрос и отправить ответ. если что-то взорвалось, перейдите непосредственно в состояние DB-Down и ответьте на событие сбоя.

В состоянии DB-Down: если получено сообщение DBQuery, ответьте событием Failure непосредственно, не касаясь БД. Пинг себе каждые х секунд, чтобы увидеть, есть ли БД, и, если возможно, вернуться в состояние DB-Up.

В этом случае вы не будете использовать какой-либо супервизор для транзита состояния, нормального try/catch будет достаточно, чтобы справиться с этим.

Надеюсь, что это ясно.