Strukturiertes Anwendungsprotokoll für Azure Spring Apps

Hinweis

Azure Spring Apps ist der neue Name für den Azure Spring Cloud-Dienst. Obwohl der Dienst umbenannt wurde, wird der alte Name noch an einigen Stellen verwendet, solange wir Ressourcen wie Screenshots, Videos und Diagramme aktualisieren.

Dieser Artikel gilt für: ✔️ Basic/Standard ✔️ Enterprise

In diesem Artikel wird erläutert, wie strukturierte Anwendungsprotokolldaten in Azure Spring Apps generiert und erfasst werden. Mit der richtigen Konfiguration bietet Azure Spring Apps nützliche Anwendungsprotokollabfragen und -analysen über Log Analytics.

Protokollschemaanforderungen

Um die Protokollabfrage zu verbessern, muss ein Anwendungsprotokoll im JSON-Format vorliegen und einem Schema entsprechen. Azure Spring Apps verwendet dieses Schema, um Ihre Anwendung zu analysieren und in Log Analytics zu streamen.

Hinweis

Wenn Sie das JSON-Protokollformat aktivieren, ist es schwierig, die Protokollstreamingausgabe aus der Konsole zu lesen. Um eine von Menschen lesbare Ausgabe zu erhalten, fügen Sie das --format-json-Argument an den CLI-Befehl az spring app logs an. Weitere Informationen finden Sie unter Formatieren strukturierter JSON-Protokolle.

JSON-Schemaanforderungen:

JSON-Schlüssel JSON-Werttyp Erforderlich Spalte in Log Analytics Beschreibung
timestamp Zeichenfolge Ja AppTimestamp Zeitstempel im UTC-Format
Protokollierungstool Zeichenfolge Nein Logger Protokollierungstool
level Zeichenfolge Nein CustomLevel log level
thread Zeichenfolge Nein Thread thread
message Zeichenfolge Nein `Message` Protokollnachricht
stackTrace Zeichenfolge Nein StackTrace Ausnahme Stapelüberwachung
exceptionClass Zeichenfolge Nein exceptionClass Name der Ausnahmeklasse
mdc Geschachteltes JSON Nein Zugeordneter Diagnosekontext
mdc.traceId Zeichenfolge Nein TraceId Ablaufverfolgungs-ID für verteilte Ablaufverfolgung
mdc.spanId Zeichenfolge Nein SpanId Spannen-ID für verteilte Ablaufverfolgung
  • Das Feld „timestamp“ ist erforderlich und sollte im UTC-Format vorliegen. Alle anderen Felder sind optional.
  • „traceid“ und „spanid“ im Feld „mdc“ werden für die Ablaufverfolgungszwecke verwendet.
  • Protokolliert jeden JSON-Datensatz in einer Zeile.

Beispiel für Protokolldatensatz

{"timestamp":"2021-01-08T09:23:51.280Z","logger":"com.example.demo.HelloController","level":"ERROR","thread":"http-nio-1456-exec-4","mdc":{"traceId":"c84f8a897041f634","spanId":"c84f8a897041f634"},"stackTrace":"java.lang.RuntimeException: get an exception\r\n\tat com.example.demo.HelloController.throwEx(HelloController.java:54)\r\n\","message":"Got an exception","exceptionClass":"RuntimeException"}

Begrenzungen

Jede Zeile der JSON-Protokolle weist höchstens 16 K Bytes auf. Wenn die JSON-Ausgabe eines einzelnen Protokolldatensatzes diesen Grenzwert überschreitet, wird sie in mehrere Zeilen unterteilt, und jede rohe Zeile wird in der Log Spalte erfasst, ohne strukturell analysiert zu werden.

Im Allgemeinen geschieht diese Situation bei der Ausnahmeprotokollierung mit deep stacktrace, insbesondere, wenn der In-Process-Agent von AppInsights aktiviert ist. Wenden Sie Grenzwerteinstellungen auf die Stacktrace-Ausgabe an (siehe die folgenden Konfigurationsbeispiele), um sicherzustellen, dass die endgültige Ausgabe ordnungsgemäß analysiert wird.

Generieren eines schemakompatiblen JSON-Protokolls

Für Spring-Anwendungen können Sie das erwartete JSON-Protokollformat mit allgemeinen Protokollierungsframeworks wie Logback und Log4j2 generieren.

Protokollieren mit logback

Bei Verwendung von Spring Boot Starters wird Logback standardmäßig verwendet. Verwenden Sie für Logback-Apps den Logstash-Encoder , um JSON-formatiertes Protokoll zu generieren. Diese Methode wird in Spring Boot Version 2.1 oder höher unterstützt.

Die Prozedur:

  1. Fügen Sie eine logstash-Abhängigkeit in Ihrer Datei pom.xml hinzu.

    <dependency>
        <groupId>net.logstash.logback</groupId>
        <artifactId>logstash-logback-encoder</artifactId>
        <version>6.5</version>
    </dependency>
    
  2. Aktualisieren Sie die Konfigurationsdatei logback-spring.xml, um das JSON-Format festzulegen.

    <configuration>
        <appender name="stdout" class="ch.qos.logback.core.ConsoleAppender">
            <encoder class="net.logstash.logback.encoder.LoggingEventCompositeJsonEncoder">
                <providers>
                    <timestamp>
                        <fieldName>timestamp</fieldName>
                        <timeZone>UTC</timeZone>
                    </timestamp>
                    <loggerName>
                        <fieldName>logger</fieldName>
                    </loggerName>
                    <logLevel>
                        <fieldName>level</fieldName>
                    </logLevel>
                    <threadName>
                        <fieldName>thread</fieldName>
                    </threadName>
                    <nestedField>
                        <fieldName>mdc</fieldName>
                        <providers>
                            <mdc />
                        </providers>
                    </nestedField>
                    <stackTrace>
                        <fieldName>stackTrace</fieldName>
                        <!-- maxLength - limit the length of the stack trace -->
                        <throwableConverter class="net.logstash.logback.stacktrace.ShortenedThrowableConverter">
                            <maxDepthPerThrowable>200</maxDepthPerThrowable>
                            <maxLength>14000</maxLength>
                            <rootCauseFirst>true</rootCauseFirst>
                        </throwableConverter>
                    </stackTrace>
                    <message />
                    <throwableClassName>
                        <fieldName>exceptionClass</fieldName>
                    </throwableClassName>
                </providers>
            </encoder>
        </appender>
        <root level="info">
            <appender-ref ref="stdout" />
        </root>
    </configuration>
    
  3. Wenn Sie die Protokollierungskonfigurationsdatei mit einem -spring-Suffix wie logback-spring.xml verwenden, können Sie die Protokollierungskonfiguration basierend auf dem aktiven Spring-Profil festlegen.

    <configuration>
        <springProfile name="dev">
            <!-- JSON appender definitions for local development, in human readable format -->
            <include resource="org/springframework/boot/logging/logback/defaults.xml" />
            <include resource="org/springframework/boot/logging/logback/console-appender.xml" />
            <root level="info">
                <appender-ref ref="CONSOLE" />
            </root>
        </springProfile>
    
        <springProfile name="!dev">
            <!-- JSON appender configuration from previous step, used for staging / production -->
            ...
        </springProfile>
    </configuration>
    

    Führen Sie für die lokale Entwicklung die Spring-Anwendung mit dem JVM-Argument -Dspring.profiles.active=dev aus. Anschließend werden lesbare Protokolle anstelle von Zeilen im JSON-Format angezeigt.

Protokollieren mit log4j2

Verwenden Sie für log4j2-Apps json-template-layout, um das JSON-formatierte Protokoll zu generieren. Diese Methode wird in Spring Boot, Version 2.1 und höher, unterstützt.

Die Prozedur:

  1. Schließen Sie spring-boot-starter-logging aus spring-boot-starter aus, und fügen Sie die Abhängigkeiten spring-boot-starter-log4j2, log4j-layout-template-json in der Datei pom.xml hinzu.

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
        <exclusions>
            <exclusion>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-starter-logging</artifactId>
            </exclusion>
        </exclusions>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-log4j2</artifactId>
    </dependency>
    <dependency>
        <groupId>org.apache.logging.log4j</groupId>
        <artifactId>log4j-layout-template-json</artifactId>
        <version>2.14.0</version>
    </dependency>
    
  2. Bereiten Sie eine JSON-Layoutvorlageandatei jsonTemplate.json in Ihrem Klassenpfad vor.

    {
        "mdc": {
            "$resolver": "mdc"
        },
        "exceptionClass": {
            "$resolver": "exception",
            "field": "className"
        },
        "stackTrace": {
            "$resolver": "exception",
            "field": "stackTrace",
            "stringified": true
        },
        "message": {
            "$resolver": "message",
            "stringified": true
        },
        "thread": {
            "$resolver": "thread",
            "field": "name"
        },
        "timestamp": {
            "$resolver": "timestamp",
            "pattern": {
                "format": "yyyy-MM-dd'T'HH:mm:ss.SSS'Z'",
                "timeZone": "UTC"
            }
        },
        "level": {
            "$resolver": "level",
            "field": "name"
        },
        "logger": {
            "$resolver": "logger",
            "field": "name"
        }
    }
    
  3. Verwenden Sie diese JSON-Layoutvorlage in Ihrer Konfigurationsdatei log4j2-spring.xml.

    <configuration>
        <appenders>
            <console name="Console" target="SYSTEM_OUT">
                <!-- maxStringLength - limit the length of the stack trace -->
                <JsonTemplateLayout eventTemplateUri="classpath:jsonTemplate.json" maxStringLength="14000" />
            </console>
        </appenders>
        <loggers>
            <root level="info">
                <appender-ref ref="Console" />
            </root>
        </loggers>
    </configuration>
    

Analysieren der Protokolle in Log Analytics

Nachdem Ihre Anwendung ordnungsgemäß eingerichtet wurde, wird das Anwendungskonsolenprotokoll in Log Analytics gestreamt. Die Struktur ermöglicht eine effiziente Abfrage in Log Analytics.

Überprüfen der Protokollstruktur in Log Analytics

Gehen Sie dazu wie folgt vor:

  1. Navigieren Sie zur Dienstübersichtsseite Ihrer Dienstinstanz.

  2. Wählen Sie den Eintrag Protokolle im Abschnitt Überwachung aus.

  3. Führen Sie die folgende Abfrage aus.

    AppPlatformLogsforSpring
    | where TimeGenerated > ago(1h)
    | project AppTimestamp, Logger, CustomLevel, Thread, Message, ExceptionClass, StackTrace, TraceId, SpanId
    
  4. Die Rückgabe von Anwendungsprotokollen wird in der folgenden Abbildung dargestellt:

    Screenshot of the Azure portal showing the log Results pane.

Anzeigen von Protokolleinträgen mit Fehlern

Um Protokolleinträge mit einem Fehler zu überprüfen, führen Sie die folgende Abfrage aus:

AppPlatformLogsforSpring
| where TimeGenerated > ago(1h) and CustomLevel == "ERROR"
| project AppTimestamp, Logger, ExceptionClass, StackTrace, Message, AppName
| sort by AppTimestamp

Verwenden Sie diese Abfrage, um Fehler zu finden, oder ändern Sie die Abfragebedingungen, um eine bestimmte Ausnahmeklasse oder Fehlercodes zu ermitteln.

Anzeigen von Protokolleinträgen für eine bestimmte traceId

Zum Überprüfen von Protokolleinträgen für eine bestimmte Ablaufverfolgungs-ID „trace_id“ führen Sie die folgende Abfrage aus:

AppPlatformLogsforSpring
| where TimeGenerated > ago(1h)
| where TraceId == "trace_id"
| project AppTimestamp, Logger, TraceId, SpanId, StackTrace, Message, AppName
| sort by AppTimestamp

Nächste Schritte