Поймать несколько исключений и отбросить общее исключение - PullRequest
6 голосов
/ 26 января 2009

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

Я бы предпочел не объявлять все четыре из этих исключений для моего вызывающего. Он, вероятно, никогда их не увидит. Я хотел бы просто перехватить все это и выдать еще одно исключение, чтобы сказать: «Произошла ошибка отражения Java; вероятно, библиотека была обновлена ​​и изменена способом, несовместимым с этим методом». Есть ли стандартное исключение Java, которое я могу выдать, которое указывает только на общую ошибку отражения? Должен ли я определить свой собственный? Или было бы лучше просто объявить, что этот метод может выдать все возможные исключения отражения?

Ответы [ 6 ]

6 голосов
/ 26 января 2009

Я обычно задаю себе эти вопросы:

  • Может ли тот, кто вызывает этот метод, обрабатывать эти различные типы исключений по-разному?
  • ... Или они к ним относятся одинаково?
  • Может ли абонент / пользователь даже восстановиться после этой ошибки?

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

2 голосов
/ 27 января 2009

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

} catch (InvocationTargetException e) {
    // Throw any exception in the current thread (even if it is a checked exception)
    Thread.currentThread().stop(e.getCause());
}
2 голосов
/ 26 января 2009

Во-первых, не используйте отражение, если вам действительно не нужно, потому что это зло. Предполагая, что вы должны:

Поскольку вы жестко кодируете все имена, он просто оставляет Method.invoke, Constructor.newInstance и Field.get/set. Я бы предложил просто перебросить проверенные исключения, с которыми вы можете иметь дело, в Error. Они не должны происходить, и если вы хотите иметь дело с этим, я предлагаю сделать проверку во время инициализации класса. InvocationTargetException, конечно, следует развернуть и обработать соответствующим образом (бросить упакованный Error для проверенного исключения, которое метод / конструктор не объявил).

2 голосов
/ 26 января 2009

Существует некоторое противоречие относительно проверенных и непроверенных исключений. Лично я считаю, что проверенные исключения являются худшей идеей в Java, но это всего лишь мнение (однако я не одинок в этом думаю)

В любом случае, я думаю, что важно было бы изменить их на одно непроверенное исключение. Чаще всего я использую одну, такую ​​как IllegalStateException или IllegalParameterException - с четким текстовым описанием, эти два исключения покрывают 90% всего дерьма, которое может пойти не так с методом.

1 голос
/ 16 сентября 2009

Как насчет того, чтобы эти классы Exception были расширены из GeneralException и перехватили это GeneralException?

Я попробую это прямо сейчас! :)

0 голосов
/ 26 января 2009

Я не думаю, что имеет смысл объявлять исключения в этом случае. Так что я бы поймал исключения из рефлексии, может записать трассировку стека и выдать некоторое RuntimeException, которое имеет то преимущество, что его не нужно объявлять. Вы можете просто использовать RuntimeException с подходящим сообщением, если вы ленивы.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...