Entity Framework Coreが生成するSQLクエリを確認する
ASP.NET CoreでEntity Framework Coreが生成するSQLクエリをログに出力してみます。
ここでは.NET Coreの組み込みのログ機能を使いました。
実行環境
.NET Core 3.1
SQLクエリのパラメーターをログに含める
デフォルトでは、SQLクエリに渡されるパラメーターは表示されないようになっています。
これを表示させるように修正します。
Startup.cs
内のConfigureServices
メソッド内にあるEF Coreの設定が、以下のように構成されているとします。
public void ConfigureServices(IServiceCollection services) { services.AddRazorPages(); services.AddDbContext<SchoolContext>(options => options.UseSqlite(Configuration.GetConnectionString("SchoolContext"))); }
DbContextOptionsBuilderクラスのEnableSensitiveDataLoggingメソッドを追加すると有効化。
public void ConfigureServices(IServiceCollection services) { services.AddRazorPages(); services.AddDbContext<SchoolContext>(options => { options.EnableSensitiveDataLogging(); // new options.UseSqlite(Configuration.GetConnectionString("SchoolContext")); }); }
appsettings.jsonを修正
EF CoreのSQLがログに表示されるように、
appsettings.json
のLogLevel
に
"Microsoft.EntityFrameworkCore": "Information"
を追加します。
開発時のみ表示されればいいので、appsettings.Development.json
に記述しました。
{ "Logging": { "LogLevel": { "Default": "Debug", "Microsoft": "Warning", "Microsoft.Hosting.Lifetime": "Information", "Microsoft.EntityFrameworkCore": "Information" } } }
以上で設定は完了です。
SQLを確認
Webアプリを実行して、データベースを使う処理を実行します。
Visual Studio Codeでは「DEBUG CONSOLE」にSQLが出力されています。
info: Microsoft.EntityFrameworkCore.Database.Command[20101] Executed DbCommand (2ms) [Parameters=[@__Format_1='%Yan%' (Size = 5)], CommandType='Text', CommandTimeout='30'] SELECT COUNT(*) FROM "Student" AS "s" WHERE ("s"."LastName" LIKE @__Format_1) OR ("s"."FirstName" LIKE @__Format_1) info: Microsoft.EntityFrameworkCore.Database.Command[20101] Microsoft.EntityFrameworkCore.Database.Command: Information: Executed DbCommand (1ms) [Parameters=[@__Format_1='%Yan%' (Size = 5), @__p_3='3' (DbType = String), @__p_2='0' (DbType = String)], CommandType='Text', CommandTimeout='30'] SELECT "s"."ID", "s"."EnrollmentDate", "s"."FirstName", "s"."LastName" FROM "Student" AS "s" WHERE ("s"."LastName" LIKE @__Format_1) OR ("s"."FirstName" LIKE @__Format_1) ORDER BY "s"."LastName" LIMIT @__p_3 OFFSET @__p_2 Executed DbCommand (1ms) [Parameters=[@__Format_1='%Yan%' (Size = 5), @__p_3='3' (DbType = String), @__p_2='0' (DbType = String)], CommandType='Text', CommandTimeout='30'] SELECT "s"."ID", "s"."EnrollmentDate", "s"."FirstName", "s"."LastName" FROM "Student" AS "s" WHERE ("s"."LastName" LIKE @__Format_1) OR ("s"."FirstName" LIKE @__Format_1) ORDER BY "s"."LastName" LIMIT @__p_3 OFFSET @__p_2
デフォルトではパラメータが?
になっていますが、 EnableSensitiveDataLoggingを追加することで中身が表示されています。
EnableSensitiveDataLogging なし
[Parameters=[@__Format_1='?' (Size = 5)], CommandType='Text', CommandTimeout='30']
EnableSensitiveDataLogging あり
[Parameters=[@__Format_1='%Yan%' (Size = 5)], CommandType='Text', CommandTimeout='30']
おわりに
ORMはブラックボックスな部分が多いので、開発時はSQLが出力されるようになっているほうがいいですね。
ASP.NET CoreもEntity Framework Coreもデフォルトでログが出力されるようになっているので、設定はかなり楽でした。