Debugging ist ein essenzieller Bestandteil der Softwareentwicklung, um Fehler zu finden und die Funktionsweise einer Anwendung zu verstehen. In einer Spring Boot-Anwendung umfasst das Debugging nicht nur das Auffinden von logischen Fehlern, sondern auch das Verstehen der Interaktionen zwischen den verschiedenen Komponenten wie Beans, Konfigurationen, HTTP-Anfragen und dem Datenzugriff.
Dieses Kapitel gibt eine Übersicht über verschiedene Techniken und Werkzeuge, die Sie verwenden können, um Spring Boot-Anwendungen effektiv zu debuggen. Dabei wird sowohl auf die integrierten Debugging-Mechanismen als auch auf externe Tools und Best Practices eingegangen.
Spring Boot bietet eine einfache Möglichkeit, den Debug-Modus zu
aktivieren, der zusätzliche Informationen zur Laufzeit liefert,
insbesondere beim Starten der Anwendung. Der Debug-Modus kann durch
Hinzufügen der folgenden Zeile in der Datei
application.properties aktiviert werden:
debug=true
Oder in der Datei application.yml:
debug: trueWenn der Debug-Modus aktiviert ist, zeigt Spring Boot detaillierte Informationen über die Konfigurationen, die geladenen Beans und die Laufzeitumgebung an. Dies ist besonders hilfreich, um zu überprüfen, ob Beans korrekt erstellt und verdrahtet wurden.
Actuator zur
Laufzeitüberwachung und FehleranalyseSpring Boot Actuator ist ein leistungsstarkes Tool, das zusätzliche Metriken, Überwachung und Management-Endpunkte bereitstellt. Es bietet verschiedene Informationen zur Laufzeit der Anwendung, die für das Debugging nützlich sind, z. B.:
Fügen Sie die Abhängigkeit zu Ihrem pom.xml hinzu:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-actuator</artifactId>
</dependency>Aktivieren Sie anschließend Actuator-Endpunkte in
application.properties:
management.endpoints.web.exposure.include=*
Jetzt können Sie auf verschiedene Management-Endpunkte wie
/actuator/health oder /actuator/beans
zugreifen, um die Informationen zur Laufzeit zu überprüfen.
Logging ist eines der effektivsten Werkzeuge für das
Debugging von Anwendungen. Spring Boot verwendet SLF4J in Kombination
mit einer Logging-Implementierung wie Logback. Sie können den
Logging-Level in der application.properties-Datei
steuern:
logging.level.org.springframework=DEBUG
logging.level.com.example=TRACE
Die verschiedenen Logging-Level in Spring Boot sind:
Durch das Setzen des Logging-Levels auf DEBUG oder
TRACE können Sie detaillierte Informationen über den
Programmlauf erhalten.
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;
@Service
public class OrderService {
private static final Logger logger = LoggerFactory.getLogger(OrderService.class);
public void processOrder(String orderId) {
logger.debug("Verarbeite Bestellung: {}", orderId);
// Geschäftslogik hier
logger.info("Bestellung {} erfolgreich verarbeitet", orderId);
}
}Hier wird ein Logger verwendet, um Informationen zur Verarbeitung einer Bestellung auszugeben. Sie können den Log-Level leicht anpassen, um detaillierte Informationen oder nur kritische Fehler anzuzeigen.
Die meisten modernen IDEs, wie IntelliJ IDEA, Eclipse oder Visual Studio Code, unterstützen das Debuggen von Spring Boot-Anwendungen direkt. Durch das Setzen von Breakpoints können Sie den Code schrittweise durchlaufen, Variablen inspizieren und den Programmfluss verstehen.
Shift + F9
oder durch Klicken auf den Debug-Button).Step Over, Step Into usw.).Durch Breakpoints können Sie insbesondere in komplexen Interaktionen zwischen Beans und verschiedenen Schichten der Anwendung sehr effizient Fehler finden.
In vielen Fällen treten Fehler beim Zugriff auf die Datenbank auf. Spring Boot bietet verschiedene Tools, um Datenbankinteraktionen zu überwachen und Fehler zu erkennen.
Spring Boot ermöglicht es, alle SQL-Statements, die von JPA oder JDBC
ausgeführt werden, im Log anzuzeigen. Um SQL-Logging zu aktivieren,
fügen Sie diese Zeile in application.properties hinzu:
spring.jpa.show-sql=true
spring.jpa.properties.hibernate.format_sql=true
Dadurch werden alle SQL-Befehle im Log ausgegeben, was bei der Analyse von Datenbankfehlern hilfreich ist.
spring.datasource-PropertiesSie können zusätzlich die Ausführungsdauer von SQL-Abfragen protokollieren, um Engpässe oder ineffiziente Abfragen zu identifizieren:
spring.datasource.hikari.configuration.maximum-pool-size=10
spring.datasource.hikari.configuration.connection-timeout=30000
spring.datasource.hikari.configuration.leak-detection-threshold=2000
Diese Konfigurationen helfen dabei, Verbindungsprobleme und langsame Abfragen zu identifizieren, indem sie Schwellenwerte für die SQL-Abfragezeit festlegen.
Das Debugging von HTTP-Anfragen und -Antworten ist besonders wichtig bei Webanwendungen.
spring-web LoggingSpring Boot erlaubt es, detaillierte Informationen über HTTP-Anfragen
zu protokollieren, einschließlich der Anfragen, die an die Controller
gesendet werden, und der Antworten. Aktivieren Sie das Logging für den
org.springframework.web-Namespace:
logging.level.org.springframework.web=DEBUG
Um HTTP-Anfragen manuell zu testen und zu debuggen, können Sie Tools wie Postman oder cURL verwenden. Diese Werkzeuge ermöglichen es Ihnen, Anfragen mit verschiedenen Parametern, Headers und Payloads zu senden und die Antworten zu überprüfen.
Beispiel: cURL-Anfrage
curl -X POST http://localhost:8080/orders -H "Content-Type: application/json" -d '{"orderId": "12345"}'Mit Postman können Sie HTTP-Anfragen visualisieren und die Antworten leicht analysieren, was besonders hilfreich für das Debuggen von REST-APIs ist.
Der Actuator bietet den Endpunkt /actuator/mappings, der
eine Übersicht über alle definierten Controller-Mappings und die
entsprechenden Endpunkte liefert. Dies ist besonders nützlich, um zu
überprüfen, ob die richtigen Mappings für Ihre URLs definiert sind.
curl http://localhost:8080/actuator/mappingsSpring Boot verwendet standardmäßig die
BasicErrorController, um Fehler zu behandeln. Sie können
jedoch eigene Fehlerseiten für spezifische HTTP-Statuscodes definieren
oder globale Exception-Handler erstellen.
Beispiel: Globaler Exception-Handler
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.servlet.ModelAndView;
@ControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(Exception.class)
public ModelAndView handleException(Exception ex) {
ModelAndView mav = new ModelAndView("error");
mav.addObject("message", ex.getMessage());
return mav;
}
}In diesem Beispiel wird eine benutzerdefinierte Fehlerseite angezeigt, wenn eine Ausnahme auftritt.
Stack Traces sind oft die erste Informationsquelle beim Debuggen von Fehlern. Wenn eine Exception geworfen wird, zeigt der Stack Trace die Fehlerursache und den genauen Codeabschnitt, in dem der Fehler aufgetreten ist. Achten Sie besonders auf:
Verwenden Sie Logging sinnvoll: Nutzen Sie
verschiedene Logging-Level, um die richtige Menge an Informationen zu
erhalten. Verwenden Sie DEBUG und TRACE-Level
nur in Entwicklungsumgebungen, um überflüssige Logs in der Produktion zu
vermeiden.
Seien Sie präzise mit Breakpoints: Setzen Sie Breakpoints strategisch in Schlüsselbere
ichen des Codes, um den Programmablauf gezielt zu überprüfen.
Isolieren Sie Fehler: Testen Sie kleine Teile der Anwendung isoliert, um Fehler schneller zu finden. Verwenden Sie Unit-Tests, um einzelne Methoden zu überprüfen, und setzen Sie Integrationstests für das Zusammenspiel mehrerer Komponenten ein.
Verwenden Sie Actuator für Laufzeit-Insights: Actuator bietet viele nützliche Tools zur Laufzeitüberwachung und kann Ihnen helfen, Probleme in der Anwendung zu diagnostizieren, ohne den Code zu verändern.
Das Debugging in Spring Boot erfordert eine Kombination aus Logging, Breakpoints, Laufzeit-Überwachungs-Tools wie Actuator und externen Tools wie Postman oder cURL. Durch die Aktivierung des Debug-Modus und das richtige Setzen von Breakpoints in Ihrer IDE können Sie die Kontrolle über den Programmablauf gewinnen und Fehler effizient finden und beheben. Actuator-Endpunkte und SQL-Logging bieten zusätzliche Einblicke in die Anwendungslogik und die Interaktionen mit Datenbanken.