EntityFrameworkを使用しているSaaSアプリケーションのSerilogをテストしています。オブジェクトのロード元のコンテキストが破棄されていない場合、SerilogはEFオブジェクトの破棄を処理できないことに気付きました。
Supplier supplier = context.Supplier.Find(6100);
Log.Information("This works and the cost for ToString() is negligible {supp}", supplier);
Log.Fatal("This will cause an Out of Memory error {@supp}", supplier);
Serilogはデータベース全体を遅延読み込みしようとしますが、アプリは1分間ハングし、クラッシュします。SerilogログファイルはOutOfMemoryExceptionを報告します
他の開発者が誤って次のようなことをして予期しないハング/クラッシュを引き起こすのを防ぐ方法は?
if(veryRarelyOccuringEvent)
Log.Information("Supplier {@supplier} just did something, supplier)
私がしたことは、すべての破壊を防ぐために破壊ポリシーを使用することでした。@を使用するよりも、開発者にToStringメソッドを明示的に宣言してもらいたいと思います。もちろん、@演算子を使用しないことを決定することはできますが、誰かが忘れてアプリがダウンした場合はどうなりますか?@は、コードレビューで見逃しがちです。@の使用を防ぐためだけに、Serilog操作のラッパーを作成したくありません。
以下は、@演算子の使用を防ぎます。
Log.Logger = new LoggerConfiguration()
.Destructure.With<PreventDestructure>()
...
そして、{}を返します。しかし、以下のコードよりも簡単な方法はありますか?
public class PreventDestructure : IDestructuringPolicy {
public bool TryDestructure(
object value,
ILogEventPropertyValueFactory propertyValueFactory,
out LogEventPropertyValue result) {
List<LogEventProperty> fieldsWithValues;
fieldsWithValues = new List<LogEventProperty>();
result = new StructureValue(fieldsWithValues);
return true;
}
}
2番目の質問:ロギングイベントに最大XXXmsを費やすようにSerilogに指示する方法はありますか?データベースシンクを使用していて、データベースがオフラインの場合はどうでしょうか。また、AIシンクを使用していて、ApplicationInsightsにアクセスできない場合などはどうなりますか?
エンティティのナビゲーションプロパティが原因でSerilogがハングし、データベース全体が簡単に読み込まれる可能性があると思います。同じ問題を説明しているように見えるSerilogプロジェクトの問題を見つけました。
その問題で彼らは言う:
Serilogにはすでに最大深度制限があります。デフォルトでは10に設定されていますが、Destructure.ToMaximumDepth(n)を使用して減らすことができます。
関連するエンティティが読み込まれないように、1に設定してみてください。しかし、個人的にはこれが望ましい解決策ではないと思います。
ログに記録したくないプロパティまたはフィールドの属性を使用できるようにするこのNuGetパッケージもありNotLogged
ます。これは機能しますが、どこかのナビゲーションプロパティで忘れると、見逃しがちです。
Serilogは、破壊の処理方法をカスタマイズするオプションを提供します。ロギングに費やす最大時間など、すべての要件を処理する独自のハンドラーを作成するか、オブジェクトをフェイルセーフとして非構造化しようとしていることを示すスタックトレースをログに記録させることができます。しかし、それはあなた次第です。
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加