[解決済み] 例外に情報を追加する?
質問
こんなことを実現したい
def foo():
try:
raise IOError('Stuff ')
except:
raise
def bar(arg1):
try:
foo()
except Exception as e:
e.message = e.message + 'happens at %s' % arg1
raise
bar('arg1')
Traceback...
IOError('Stuff Happens at arg1')
しかし、私が得たものは
Traceback..
IOError('Stuff')
これを実現するためのヒントがあれば教えてください。Python 2 と 3 の両方で行うにはどうしたらいいですか?
どのように解決するのですか?
私ならこのようにします。
foo()
で変更する必要はありません。
bar()
.
def foo():
try:
raise IOError('Stuff')
except:
raise
def bar(arg1):
try:
foo()
except Exception as e:
raise type(e)(e.message + ' happens at %s' % arg1)
bar('arg1')
Traceback (most recent call last):
File "test.py", line 13, in <module>
bar('arg1')
File "test.py", line 11, in bar
raise type(e)(e.message + ' happens at %s' % arg1)
IOError: Stuff happens at arg1
アップデート1
ここでは、元のトレースバックを保持するために若干の修正を加えています。
...
def bar(arg1):
try:
foo()
except Exception as e:
import sys
raise type(e), type(e)(e.message +
' happens at %s' % arg1), sys.exc_info()[2]
bar('arg1')
Traceback (most recent call last):
File "test.py", line 16, in <module>
bar('arg1')
File "test.py", line 11, in bar
foo()
File "test.py", line 5, in foo
raise IOError('Stuff')
IOError: Stuff happens at arg1
アップデート2
Python 3.x では、最初のアップデートのコードは構文的に正しくなく、さらに
message
属性に
BaseException
は
PEP 352の変更で撤回された
を2012-05-16に投稿しました(私の最初の更新は2012-03-12)。したがって、現在、とにかく Python 3.5.2 では、トレースバックを保持し、関数内の例外のタイプをハードコードしないために、次のような行を行う必要があります。
bar()
. また、行があることに注意してください。
During handling of the above exception, another exception occurred:
が、表示されるトレースバックメッセージに表示されます。
# for Python 3.x
...
def bar(arg1):
try:
foo()
except Exception as e:
import sys
raise type(e)(str(e) +
' happens at %s' % arg1).with_traceback(sys.exc_info()[2])
bar('arg1')
アップデート3
コメントで、Python 2 と 3 の両方で動作する方法はないのか、という質問がありました。構文の違いから答えは "No"と思われるかも知れませんが
は
のようなヘルパー関数を使用することで、それを回避することができます。
reraise()
の中に
six
アドオンモジュールです。そこで、何らかの理由でライブラリを使いたくないという方のために、以下は簡略化したスタンドアローン版です。
また、例外の発生は
reraise()
関数を呼び出すと、どのようなトレースバックが発生しても、最終的な結果はあなたが望むものになります。
import sys
if sys.version_info.major < 3: # Python 2?
# Using exec avoids a SyntaxError in Python 3.
exec("""def reraise(exc_type, exc_value, exc_traceback=None):
raise exc_type, exc_value, exc_traceback""")
else:
def reraise(exc_type, exc_value, exc_traceback=None):
if exc_value is None:
exc_value = exc_type()
if exc_value.__traceback__ is not exc_traceback:
raise exc_value.with_traceback(exc_traceback)
raise exc_value
def foo():
try:
raise IOError('Stuff')
except:
raise
def bar(arg1):
try:
foo()
except Exception as e:
reraise(type(e), type(e)(str(e) +
' happens at %s' % arg1), sys.exc_info()[2])
bar('arg1')
関連
-
[解決済み] Pythonで例外を手動で発生(スロー)させる
-
[解決済み] JUnit 4のテストで、ある例外が投げられたことをどのように断言しますか?
-
[解決済み] Pythonのsuper()は多重継承でどう動くのか?
-
[解決済み] Pythonの「名前付きタプル」とは何ですか?
-
[解決済み] Pythonで例外を表示するには?
-
[解決済み] Pythonの関数が例外を投げるかどうかをテストするにはどうすればよいですか?
-
[解決済み] 他のPythonファイルをインポートするには?
-
[解決済み] print()を使用してクラスのインスタンスを表示するには?
-
[解決済み】例外の説明と例外を発生させたスタックトレースを文字列で取得する。
-
[解決済み】Pythonでtry-except-elseを使用するのは良い習慣ですか?
最新
-
nginxです。[emerg] 0.0.0.0:80 への bind() に失敗しました (98: アドレスは既に使用中です)
-
htmlページでギリシャ文字を使うには
-
ピュアhtml+cssでの要素読み込み効果
-
純粋なhtml + cssで五輪を実現するサンプルコード
-
ナビゲーションバー・ドロップダウンメニューのHTML+CSSサンプルコード
-
タイピング効果を実現するピュアhtml+css
-
htmlの選択ボックスのプレースホルダー作成に関する質問
-
html css3 伸縮しない 画像表示効果
-
トップナビゲーションバーメニュー作成用HTML+CSS
-
html+css 実装 サイバーパンク風ボタン
おすすめ
-
Python interpreted model libraryによる機械学習モデル出力の可視化 Shap
-
パッケージングツールPyinstallerの使用と落とし穴の回避
-
[解決済み] [Solved] sklearn error ValueError: 入力に NaN、infinity または dtype('float64') に対して大きすぎる値が含まれている。
-
[解決済み】RuntimeWarning: 割り算で無効な値が発生しました。
-
[解決済み】Python elifの構文が無効です【終了しました
-
[解決済み] TypeError: 'DataFrame' オブジェクトは呼び出し可能ではない
-
[解決済み】django インポートエラー - core.managementという名前のモジュールがない
-
[解決済み】Pythonでカスタムメッセージで同じExceptionを発生させる方法は?
-
[解決済み] Python 2.6で非推奨となったBaseException.message
-
[解決済み] 既存の情報を保持したまま、異なる型とメッセージで例外を再提示する。