Tutorial zur Entity Framework Core-Serie - 25-Entity Framework Core-Protokoll

Entity Framework Core-Protokolle

Wir müssen häufig SQL in EF Core aufzeichnen und die Trace-Informationen für das Debuggen ändern.
Die EF Core-Protokollierung wird automatisch in den Protokollierungsmechanismus von .NET Core integriert. Bevor Sie die Protokollierung von EF Core implizit verwenden, sollten Sie daher die Grundlagen der .NET Core-Protokollierung kennen.
Entity Framework Core ist in die .NET Core-Protokollierung integriert, um SQL aufzuzeichnen und Ablaufverfolgungsinformationen in verschiedene Ausgabeziele zu ändern. Installieren Sie zuerst das Nuget-Paket des Protokollierungsanbieters Ihrer Wahl und binden Sie dann den DbContext an die ILoggerFactory.
Lassen Sie uns das NuGet-Paket des Protokollierungsanbieters installieren. Hier werden die Protokolle auf der Konsole angezeigt. Installieren Sie daher das NuGet-Paket Microsoft.Extensions.Logging.Console über den NuGet-Paketmanager oder führen Sie den folgenden Befehl in der Paketmanagerkonsole aus:

Install-Package Microsoft.Extensions.Logging.Console

Das folgende Diagramm zeigt, wie DbContext mit der Protokollierungs-API und dem Konsolenprotokollierungsanbieter verwendet wird.
[Externe Kettenbildübertragung fehlgeschlagen, die Quellwebsite verfügt möglicherweise über einen Diebstahlschutzkettenmechanismus. Es wird empfohlen, das Bild zu speichern und direkt hochzuladen (img-afUjJAU3-1581165281344) (d: \ note \ efcore \ pic \ 27.png)]

Nach der Installation des Konsolenlogger-Anbieters müssen Sie eine statische / einzelne Instanz von LoggerFactory erstellen und diese dann wie unten gezeigt mit DbContext binden.

public class SchoolContext : DbContext
{
    //static LoggerFactory object
    public static readonly ILoggerFactory loggerFactory = new LoggerFactory(new[] {
              new ConsoleLoggerProvider((_, __) => true, true)
        });

    //or
    // public static readonly ILoggerFactory loggerFactory  = new LoggerFactory().AddConsole((_,___) => true);
    
    public SchoolContext():base()
    {

    }
    
    protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
    {
        optionsBuilder.UseLoggerFactory(loggerFactory)  //tie-up DbContext with LoggerFactory object
            .EnableSensitiveDataLogging()  
            .UseSqlServer(@"Server=.\SQLEXPRESS;Database=SchoolDB;Trusted_Connection=True;");
    }
        
    public DbSet<Student> Students { get; set; }
}

Im obigen Beispiel haben wir ein Objekt der Klasse LoggerFactory erstellt und es einer statischen Variablen vom Typ ILoggerFactory zugewiesen. Dann haben wir dieses Objekt in der optionsBuilder.UseLoggerFactory () -Methode der OnConfiguring () -Methode übergeben. Dadurch kann DbContext Informationen mit dem loggerFactory-Objekt teilen, das wiederum alle Protokollierungsinformationen auf der Konsole anzeigt.
Standardmäßig zeichnet EF Core keine vertraulichen Daten auf, z. B. Filterparameterwerte. Rufen Sie daher EnableSensitiveDataLogging () auf, um vertrauliche Daten aufzuzeichnen.
Hinweis: Das
EF-Team empfiehlt, während der gesamten Lebensdauer der Anwendung dasselbe Logger-Factory-Objekt mit allen Instanzen der DbContext-Klasse zu verwenden. Andernfalls kann es zu Speicherlecks und Leistungseinbußen kommen. Sie können auch eine separate Factory-Klasse erstellen, die Ihnen ein Singleton-Objekt der LoggerFactory-Klasse zur Verwendung mit DbContext bereitstellt.
Lassen Sie uns das obige Beispiel im Detail verstehen.
Zuerst haben wir ein Objekt der LoggerFactory-Klasse erstellt und es einer statischen Variablen vom Typ ILoggerFactory zugewiesen, wie unten gezeigt.

public static readonly ILoggerFactory loggerFactory = new LoggerFactory(
    new[] { new ConsoleLoggerProvider ((_, __) => true, true) }
);

LoggerFactory kann einen oder mehrere Protokolldatensatzanbieter enthalten, mit denen auf mehreren Medien gleichzeitig aufgezeichnet werden kann. Der Konstruktor von LoggerFactory akzeptiert eine Reihe verschiedener Logger-Provider-Objekte als neu [] {}. Wir möchten das Protokoll auf der Konsole anzeigen. Erstellen Sie daher ein Objekt für den Konsolenlogger-Anbieter ConsoleLoggerProvider.
ConsoleLoggerProvider verfügt über vier Konstruktoren. Verwenden Sie eine Methode, die Lambda-Ausdrücke (Func <>) für die Protokollfilterung zulässt, und verwenden Sie den booleschen Wert includeScope, wie unten gezeigt.

new ConsoleLoggerProvider((_, __) => true, true)

Hier möchten wir keine Informationen filtern, daher gibt der Lambda-Ausdruck immer true (_, __) => true zurück.

Verwenden Sie nach dem Erstellen des ILoggerFactory-Objekts DbContextOptionsBuilder, um DbContext und ILoggerFactory in der OnConfiguring () -Methode miteinander zu verbinden.

optionsBuilder.UseLoggerFactory(loggerFactory)

Daher binden wir den DbContext an die LoggerFactory, die den Konsolenlogger-Anbieter enthält. Immer wenn die DbContext-Instanz eine Operation ausführt, werden alle Protokolle auf der Konsole angezeigt.
Betrachten Sie das folgende Beispiel.

using (var context = new SchoolContext())
{
    var std = new Student(){ StudentName = "Steve" };
    context.Add(std);
                
    context.SaveChanges();
    Console.ReadLine();
}

Im obigen Beispiel werden die folgenden Protokolle auf der Konsole angezeigt:

dbug: Microsoft.EntityFrameworkCore.Infrastructure[100401]
An 'IServiceProvider' was created for internal use by Entity Framework.
info: Microsoft.EntityFrameworkCore.Infrastructure[100403]
Entity Framework Core 2.0.0-rtm-26452 initialized 'SchoolContext' using pr
ovider 'Microsoft.EntityFrameworkCore.SqlServer' with options: SensitiveDataLoggingEnabled
dbug: Microsoft.EntityFrameworkCore.Database.Connection[200000]
Opening connection to database 'SchoolDB' on server '.\SQLEXPRESS'.

dbug: Microsoft.EntityFrameworkCore.Database.Connection[200001]
Opened connection to database 'SchoolDB' on server '.\SQLEXPRESS'.
dbug: Microsoft.EntityFrameworkCore.Database.Transaction[200200]
Beginning transaction with isolation level 'ReadCommitted'.
warn: Microsoft.EntityFrameworkCore.Database.Command[100400]
Sensitive data logging is enabled. Log entries and exception messages may
include sensitive application data, this mode should only be enabled during development.
dbug: Microsoft.EntityFrameworkCore.Database.Command[200100]
Executing DbCommand [Parameters=[@p0='' (DbType = DateTime2), @p1='' (DbTy
pe = Int32), @p2='0', @p3='' (Size = 8000) (DbType = Binary), @p4='Steve' (Size = 4000), @p5='0'], CommandType='Text', CommandTimeout='30']
SET NOCOUNT ON;
INSERT INTO [Students] ([DateOfBirth], [GradeId], [Height], [Photo], [Stud
entName], [Weight])
VALUES (@p0, @p1, @p2, @p3, @p4, @p5);
SELECT [StudentID]
FROM [Students]
WHERE @@ROWCOUNT = 1 AND [StudentID] = scope_identity();
info: Microsoft.EntityFrameworkCore.Database.Command[200101]
Executed DbCommand (68ms) [Parameters=[@p0='' (DbType = DateTime2), @p1=''
(DbType = Int32), @p2='0', @p3='' (Size = 8000) (DbType = Binary), @p4='Steve'
(Size = 4000), @p5='0'], CommandType='Text', CommandTimeout='30']
SET NOCOUNT ON;
INSERT INTO [Students] ([DateOfBirth], [GradeId], [Height], [Photo], [Stud
entName], [Weight])
VALUES (@p0, @p1, @p2, @p3, @p4, @p5);
SELECT [StudentID]
FROM [Students]
WHERE @@ROWCOUNT = 1 AND [StudentID] = scope_identity();
dbug: Microsoft.EntityFrameworkCore.Database.Command[200300]
A data reader was disposed.
dbug: Microsoft.EntityFrameworkCore.Database.Transaction[200202]
Committing transaction.
dbug: Microsoft.EntityFrameworkCore.Database.Connection[200002]
Closing connection to database 'SchoolDB' on server '.\SQLEXPRESS'.

dbug: Microsoft.EntityFrameworkCore.Database.Connection[200003]
Closed connection to database 'SchoolDB' on server '.\SQLEXPRESS'.
dbug: Microsoft.EntityFrameworkCore.Database.Transaction[200204]
Disposing transaction.

Wie Sie sehen können, werden alle Informationen aufgezeichnet.

Protokolle filtern

Im obigen Beispiel zeichnet DbContext beim Speichern der Entität alle Informationen auf. Manchmal möchten Sie nicht alle Informationen aufzeichnen und unerwünschte Protokolle filtern. In EF Core können Sie Protokolle filtern, indem Sie die Protokollierungskategorie und die Protokollstufe angeben.

Protokollklassifizierung

EF Core 2.x enthält die DbLoggerCategory-Klasse, um die Entity Framework Core-Logger-Kategorie mithilfe ihrer Name-Eigenschaft abzurufen. In der folgenden Tabelle sind die verschiedenen Logger-Kategorien aufgeführt.

Protokollkategorie Beschreibung
Database.Command Der Typ des Protokollierers, den der Befehl ausführt, einschließlich der an die Datenbank gesendeten SQL.
Database.Connection Die Logger-Kategorie für Datenbankverbindungsvorgänge.
Database.Transaction Die Logger-Kategorie für Datenbanktransaktionen.
Infrastruktur Rekorderkategorie für andere Nachrichten in der EF-Infrastruktur.
Migration Migrierte Logger-Kategorie.
Modell Die für die Modellbildung und Metadaten verwendete Logger-Kategorie.
Abfrage Die Logger-Kategorie der Abfrage (ohne das generierte SQL).
Gerüst Arten von Rekordern für Gerüste und Reverse Engineering.
Aktualisieren Die Logger-Kategorie der Nachricht DbContext.SaveChanges ().

Protokollieren Sie SQL-Abfragen

Um nur SQL-Abfragen zu protokollieren, geben Sie die Kategorie DbLoggerCategory.Database.Command und LogLevel.Information im Lambda-Ausdruck des ConsoleLoggerProvider-Konstruktors an (siehe unten).

public static readonly ILoggerFactory consoleLoggerFactory  
            = new LoggerFactory(new[] {
                  new ConsoleLoggerProvider((category, level) =>
                    category == DbLoggerCategory.Database.Command.Name &&
                    level == LogLevel.Information, true)
                });

Oder rufen Sie standardmäßig einfach die AddConsole () -Methode in der LoggerFactory auf, um SQL-Abfragen zu protokollieren.

public static readonly ILoggerFactory consoleLoggerFactory
         = new LoggerFactory().AddConsole();

Hier werden nun die folgenden Abfrageinformationen aufgezeichnet, die DbContext zum Speichern einer Entität verwenden.

info: Microsoft.EntityFrameworkCore.Database.Command[200101]
Executed DbCommand (73ms) [Parameters=[@p0='' (DbType = DateTime2), @p1=''
(DbType = Int32), @p2='0', @p3='' (Size = 8000) (DbType = Binary), @p4='Steve'
(Size = 4000), @p5='0'], CommandType='Text', CommandTimeout='30']
SET NOCOUNT ON;
INSERT INTO [Students] ([DateOfBirth], [GradeId], [Height], [Photo], [Stud
entName], [Weight])
VALUES (@p0, @p1, @p2, @p3, @p4, @p5);
SELECT [StudentID]
FROM [Students]
WHERE @@ROWCOUNT = 1 AND [StudentID] = scope_identity();
Veröffentlichte 177 Originalartikel · 61 Lobpreisungen · 170.000 Aufrufe

Ich denke du magst

Origin blog.csdn.net/xingkongtianyuzhao/article/details/104227989
Empfohlen
Rangfolge