C# でいちど作成した Exception の Message プロパティは get のみで後からメッセージを変更することができません。
今回は一度作成した Exception オブジェクトの Message を変更したいと思います。
確認環境
- VisualStudio 2022
- .NET 6
- IDE上からDebug実行で確認
実装の説明
リフレクションを使って Exception オブジェクト内のフィールドを書き換えます。
public static void ChangeMessage(Exception ex, string newMessage) { BindingFlags flags = BindingFlags.NonPublic | BindingFlags.Instance; FieldInfo fi = ex.GetType().GetField("_message", flags); fi.SetValue(ex, newMessage); // これで書き換わる }
Message プロパティが内部的に private のフィールド変数 _message を使用しているためこれを強制的に書き換えています。
で、何でこんな事してるかというと、ジェネリックで例外オブジェクトを作成しようとするとあれ、設定できなくないと思ってこんなことしていました。
public static T CreateException<T>(string message) where T : MyException, new() { var ex = new T(); // 引数が指定できない BindingFlags flags = BindingFlags.NonPublic | BindingFlags.Instance; var fieldInfo = typeof(Exception).GetField("_message", flags); fieldInfo.SetValue(ex, message); // これで設定する return ex; }
で、最近まで思ってましたが Activator.CreateInstance を使用すればこんなことしないで済むみたいです。あらら。
public static T CreateException<T>(string message) where T : MyException, new() { return (T)Activator.CreateInstance(typeof(T), message); }