Add global exception handling

This commit is contained in:
litoral05
2026-05-07 13:37:41 +01:00
parent 8d065e4112
commit a09587950e
4 changed files with 88 additions and 3 deletions
@@ -0,0 +1,12 @@
package com.litoralregas.vpnprovisioner.common.exception;
import java.time.Instant;
public record ApiErrorResponse(
Instant timestamp,
int status,
String error,
String message,
String path
) {
}
@@ -0,0 +1,64 @@
package com.litoralregas.vpnprovisioner.common.exception;
import jakarta.servlet.http.HttpServletRequest;
import org.springframework.http.HttpStatus;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.*;
import java.time.Instant;
import java.util.stream.Collectors;
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(ResourceNotFoundException.class)
@ResponseStatus(HttpStatus.NOT_FOUND)
public ApiErrorResponse handleNotFound(
ResourceNotFoundException exception,
HttpServletRequest request
) {
return new ApiErrorResponse(
Instant.now(),
HttpStatus.NOT_FOUND.value(),
"Not Found",
exception.getMessage(),
request.getRequestURI()
);
}
@ExceptionHandler(MethodArgumentNotValidException.class)
@ResponseStatus(HttpStatus.BAD_REQUEST)
public ApiErrorResponse handleValidation(
MethodArgumentNotValidException exception,
HttpServletRequest request
) {
String message = exception.getBindingResult()
.getFieldErrors()
.stream()
.map(error -> error.getField() + ": " + error.getDefaultMessage())
.collect(Collectors.joining(", "));
return new ApiErrorResponse(
Instant.now(),
HttpStatus.BAD_REQUEST.value(),
"Bad Request",
message,
request.getRequestURI()
);
}
@ExceptionHandler(IllegalArgumentException.class)
@ResponseStatus(HttpStatus.BAD_REQUEST)
public ApiErrorResponse handleIllegalArgument(
IllegalArgumentException exception,
HttpServletRequest request
) {
return new ApiErrorResponse(
Instant.now(),
HttpStatus.BAD_REQUEST.value(),
"Bad Request",
exception.getMessage(),
request.getRequestURI()
);
}
}
@@ -0,0 +1,8 @@
package com.litoralregas.vpnprovisioner.common.exception;
public class ResourceNotFoundException extends RuntimeException {
public ResourceNotFoundException(String message) {
super(message);
}
}
@@ -5,6 +5,7 @@ import com.litoralregas.vpnprovisioner.router.dto.RouterResponse;
import com.litoralregas.vpnprovisioner.router.dto.UpdateRouterRequest; import com.litoralregas.vpnprovisioner.router.dto.UpdateRouterRequest;
import com.litoralregas.vpnprovisioner.router.entity.Router; import com.litoralregas.vpnprovisioner.router.entity.Router;
import com.litoralregas.vpnprovisioner.router.repository.RouterRepository; import com.litoralregas.vpnprovisioner.router.repository.RouterRepository;
import com.litoralregas.vpnprovisioner.common.exception.ResourceNotFoundException;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional; import org.springframework.transaction.annotation.Transactional;
@@ -43,7 +44,7 @@ public class RouterService {
@Transactional(readOnly = true) @Transactional(readOnly = true)
public RouterResponse findById(UUID id) { public RouterResponse findById(UUID id) {
Router router = routerRepository.findById(id) Router router = routerRepository.findById(id)
.orElseThrow(() -> new IllegalArgumentException("Router not found: " + id)); .orElseThrow(() -> new ResourceNotFoundException("Router not found: " + id));
return toResponse(router); return toResponse(router);
} }
@@ -51,7 +52,7 @@ public class RouterService {
@Transactional @Transactional
public RouterResponse update(UUID id, UpdateRouterRequest request) { public RouterResponse update(UUID id, UpdateRouterRequest request) {
Router router = routerRepository.findById(id) Router router = routerRepository.findById(id)
.orElseThrow(() -> new IllegalArgumentException("Router not found: " + id)); .orElseThrow(() -> new ResourceNotFoundException("Router not found: " + id));
router.updateDetails( router.updateDetails(
request.name(), request.name(),
@@ -65,7 +66,7 @@ public class RouterService {
@Transactional @Transactional
public void delete(UUID id) { public void delete(UUID id) {
Router router = routerRepository.findById(id) Router router = routerRepository.findById(id)
.orElseThrow(() -> new IllegalArgumentException("Router not found: " + id)); .orElseThrow(() -> new ResourceNotFoundException("Router not found: " + id));
routerRepository.delete(router); routerRepository.delete(router);
} }