From 65785ed2600d936c98f944ffc627c1fc30f2eed1 Mon Sep 17 00:00:00 2001
From: Lars Johansson <lars.johansson@ess.eu>
Date: Thu, 24 Feb 2022 12:39:36 +0100
Subject: [PATCH] Added global exception handler

---
 .../GlobalControllerExceptionHandler.java     |  66 +++++
 .../openepics/names/util/ExceptionUtil.java   | 255 ++++++++++++++++++
 .../util/ServiceHttpStatusException.java      |  80 ++++++
 .../names/util/response/Response.java         |  70 +++++
 .../names/util/ExceptionUtilTest.java         | 145 ++++++++++
 5 files changed, 616 insertions(+)
 create mode 100644 src/main/java/org/openepics/names/rest/controller/GlobalControllerExceptionHandler.java
 create mode 100644 src/main/java/org/openepics/names/util/ExceptionUtil.java
 create mode 100644 src/main/java/org/openepics/names/util/ServiceHttpStatusException.java
 create mode 100644 src/main/java/org/openepics/names/util/response/Response.java
 create mode 100644 src/test/java/org/openepics/names/util/ExceptionUtilTest.java

diff --git a/src/main/java/org/openepics/names/rest/controller/GlobalControllerExceptionHandler.java b/src/main/java/org/openepics/names/rest/controller/GlobalControllerExceptionHandler.java
new file mode 100644
index 0000000..bad2608
--- /dev/null
+++ b/src/main/java/org/openepics/names/rest/controller/GlobalControllerExceptionHandler.java
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2022 European Spallation Source ERIC.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ */
+
+package org.openepics.names.rest.controller;
+
+import java.util.logging.Level;
+import java.util.logging.Logger;
+
+import org.apache.commons.lang3.StringUtils;
+import org.openepics.names.util.ExceptionUtil;
+import org.openepics.names.util.ServiceHttpStatusException;
+import org.openepics.names.util.response.Response;
+import org.springframework.http.HttpStatus;
+import org.springframework.http.ResponseEntity;
+import org.springframework.web.bind.annotation.ExceptionHandler;
+import org.springframework.web.bind.annotation.RestControllerAdvice;
+import org.springframework.web.context.request.WebRequest;
+import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler;
+
+/**
+ * Global exception handler to ensure exceptions are communicated to request origin in a uniform way.
+ *
+ * @author Lars Johansson
+ */
+@RestControllerAdvice
+public class GlobalControllerExceptionHandler extends ResponseEntityExceptionHandler {
+
+    // note
+    //     no logging here
+
+    private static final Logger LOGGER = Logger.getLogger(GlobalControllerExceptionHandler.class.getName());
+
+    @ExceptionHandler
+    protected ResponseEntity<Response> handleConflict(RuntimeException ex, WebRequest request) {
+        LOGGER.log(Level.INFO, "handleConflict, ex.getMessage: " + ex.getMessage());
+
+        Response response = new Response("", "");
+        response.setMessage(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED);
+
+        HttpStatus resultStatus = HttpStatus.INTERNAL_SERVER_ERROR;
+
+        if (ex instanceof ServiceHttpStatusException) {
+            response.setMessage(StringUtils.trimToEmpty(ex.getMessage()));
+            response.setDetails(StringUtils.trimToEmpty(((ServiceHttpStatusException) ex).getDetails()));
+            resultStatus = ((ServiceHttpStatusException) ex).getHttpStatus();
+        }
+
+        return new ResponseEntity<>(response, Response.HEADER_JSON, resultStatus);
+    }
+
+}
diff --git a/src/main/java/org/openepics/names/util/ExceptionUtil.java b/src/main/java/org/openepics/names/util/ExceptionUtil.java
new file mode 100644
index 0000000..e008c92
--- /dev/null
+++ b/src/main/java/org/openepics/names/util/ExceptionUtil.java
@@ -0,0 +1,255 @@
+/*
+ * Copyright (C) 2021 European Spallation Source ERIC.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ */
+
+package org.openepics.names.util;
+
+import org.springframework.http.HttpStatus;
+import org.springframework.web.server.ResponseStatusException;
+
+/**
+ * Utility class to assist in handling of exceptions.
+ * <br/><br/>
+ * Note
+ * <ul>
+ * <li>400 {@link HttpStatus#BAD_REQUEST}</li>
+ * <li>401 {@link HttpStatus#UNAUTHORIZED}</li>
+ * <li>403 {@link HttpStatus#FORBIDDEN}</li>
+ * <li>404 {@link HttpStatus#NOT_FOUND}</li>
+ * <li>409 {@link HttpStatus#CONFLICT}</li>
+ * <li>500 {@link HttpStatus#INTERNAL_SERVER_ERROR}</li>
+ * <li>501 {@link HttpStatus#NOT_IMPLEMENTED}</li>
+ * </ul>
+ *
+ * @author Lars Johansson
+ */
+public class ExceptionUtil {
+
+    public static final String ONE_OR_MORE_ELEMENTS_ARE_NOT_CORRECT = "One or more elements are not correct.";
+    public static final String OPERATION_COULD_NOT_BE_PERFORMED     = "Operation could not be performed.";
+
+    /**
+     * This class is not to be instantiated.
+     */
+    private ExceptionUtil() {
+        throw new IllegalStateException("Utility class");
+    }
+
+    /**
+     * Convert service http status exception to response status exception.
+     *
+     * @param e service http status exception
+     * @return response status exception
+     */
+    public static ResponseStatusException convertException(ServiceHttpStatusException e) {
+        switch (e.getHttpStatus()) {
+            case BAD_REQUEST:
+                throw ExceptionUtil.createResponseStatusExceptionBadRequest();
+            case UNAUTHORIZED:
+                throw ExceptionUtil.createResponseStatusExceptionUnauthorized();
+            case FORBIDDEN:
+                throw ExceptionUtil.createResponseStatusExceptionForbidden();
+            case NOT_FOUND:
+                throw ExceptionUtil.createResponseStatusExceptionNotFound();
+            case CONFLICT:
+                throw ExceptionUtil.createResponseStatusExceptionConflict();
+            case INTERNAL_SERVER_ERROR:
+                throw ExceptionUtil.createResponseStatusExceptionInternalServerError();
+            case NOT_IMPLEMENTED:
+                throw ExceptionUtil.createResponseStatusExceptionNotImplemented();
+            default:
+                throw ExceptionUtil.createResponseStatusExceptionInternalServerError();
+        }
+    }
+
+    /**
+     * Create response status exception.
+     * Intended for communication from server to client.
+     *
+     * @param status http status
+     * @param reason reason
+     * @param cause cause
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusException(HttpStatus status, String reason, Throwable cause) {
+        return new ResponseStatusException(status, reason, cause);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#BAD_REQUEST}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusExceptionBadRequest() {
+        return createResponseStatusException(HttpStatus.BAD_REQUEST, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#UNAUTHORIZED}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusExceptionUnauthorized() {
+        return createResponseStatusException(HttpStatus.UNAUTHORIZED, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#FORBIDDEN}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusExceptionForbidden() {
+        return createResponseStatusException(HttpStatus.FORBIDDEN, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#NOT_FOUND}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusExceptionNotFound() {
+        return createResponseStatusException(HttpStatus.NOT_FOUND, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#CONFLICT}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    protected static ResponseStatusException createResponseStatusExceptionConflict() {
+        return createResponseStatusException(HttpStatus.CONFLICT, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+
+    /**
+     * Create response status exception for {@link HttpStatus#INTERNAL_SERVER_ERROR}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    public static ResponseStatusException createResponseStatusExceptionInternalServerError() {
+        return createResponseStatusException(HttpStatus.INTERNAL_SERVER_ERROR, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create response status exception for {@link HttpStatus#NOT_IMPLEMENTED}.
+     * Intended for communication from server to client.
+     *
+     * @return response status exception
+     */
+    public static ResponseStatusException createResponseStatusExceptionNotImplemented() {
+        return createResponseStatusException(HttpStatus.NOT_IMPLEMENTED, OPERATION_COULD_NOT_BE_PERFORMED, null);
+    }
+
+    /**
+     * Create service http status exception.
+     * Intended for communication inside server.
+     *
+     * @param status http status
+     * @param message message
+     * @param details details
+     * @param userFriendly user friendly
+     * @param cause cause
+     * @return service http status exception
+     */
+    protected static ServiceHttpStatusException createServiceHttpStatusException(HttpStatus status, String message, String details, String userFriendly, Throwable cause) {
+        return new ServiceHttpStatusException(status, message, details, userFriendly, cause);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#BAD_REQUEST}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionBadRequest(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.BAD_REQUEST, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#UNAUTHORIZED}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionUnauthorized(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.UNAUTHORIZED, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#FORBIDDEN}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionForbidden(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.FORBIDDEN, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#NOT_FOUND}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionNotFound(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.NOT_FOUND, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#CONFLICT}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionConflict(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.CONFLICT, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#INTERNAL_SERVER_ERROR}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionInternalServerError(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.INTERNAL_SERVER_ERROR, message, details, userFriendly, null);
+    }
+
+    /**
+     * Create service http status exception for {@link HttpStatus#NOT_IMPLEMENTED}.
+     * Intended for communication inside server.
+     *
+     * @param message message
+     * @return service http status exception
+     */
+    public static ServiceHttpStatusException createServiceHttpStatusExceptionNotImplemented(String message, String details, String userFriendly) {
+        return createServiceHttpStatusException(HttpStatus.NOT_IMPLEMENTED, message, details, userFriendly, null);
+    }
+
+}
diff --git a/src/main/java/org/openepics/names/util/ServiceHttpStatusException.java b/src/main/java/org/openepics/names/util/ServiceHttpStatusException.java
new file mode 100644
index 0000000..f0b79ab
--- /dev/null
+++ b/src/main/java/org/openepics/names/util/ServiceHttpStatusException.java
@@ -0,0 +1,80 @@
+/*
+ * Copyright (C) 2021 European Spallation Source ERIC.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ */
+
+package org.openepics.names.util;
+
+import org.springframework.http.HttpStatus;
+
+/**
+ * Exception class to assist in handling of service layer exceptions.
+ *
+ * @author Lars Johansson
+ */
+public class ServiceHttpStatusException extends RuntimeException {
+
+    /**
+     *
+     */
+    private static final long serialVersionUID = 5346696855950320329L;
+
+    private final HttpStatus httpStatus;
+    private final String details;
+    private final String userFriendly;
+
+    /**
+     * Public constructor.
+     *
+     * @param httpStatus http status
+     * @param message message
+     * @param cause cause
+     */
+    public ServiceHttpStatusException(HttpStatus httpStatus, String message, String details, String userFriendly, Throwable cause) {
+        super(message, cause);
+        this.httpStatus = httpStatus;
+        this.details = details;
+        this.userFriendly = userFriendly;
+    }
+
+    /**
+     * Return http status of exception.
+     *
+     * @return http status
+     */
+    public HttpStatus getHttpStatus() {
+        return httpStatus;
+    }
+
+    /**
+     * Returns details of exception.
+     *
+     * @return details
+     */
+    public String getDetails() {
+        return details;
+    }
+
+    /**
+     * Return user friendly of exception.
+     *
+     * @return user friendly
+     */
+    public String getUserFriendly() {
+        return userFriendly;
+    }
+
+}
diff --git a/src/main/java/org/openepics/names/util/response/Response.java b/src/main/java/org/openepics/names/util/response/Response.java
new file mode 100644
index 0000000..491bb95
--- /dev/null
+++ b/src/main/java/org/openepics/names/util/response/Response.java
@@ -0,0 +1,70 @@
+/*
+ * Copyright (C) 2022 European Spallation Source ERIC.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ */
+
+package org.openepics.names.util.response;
+
+import org.springframework.http.HttpHeaders;
+
+/**
+ * This class is used to ensure response to request origin are handled in a uniform way.
+ *
+ * @author Lars Johansson
+ */
+public class Response {
+
+    private static final String CONTENT_TYPE = "Content-Type";
+    private static final String APP_JSON     = "application/json";
+
+    public static final HttpHeaders HEADER_JSON = new HttpHeaders();
+
+    private String message = null;
+    private String details = null;
+
+    public Response() {
+        HEADER_JSON.add(Response.CONTENT_TYPE, Response.APP_JSON);
+    }
+
+    public Response(String message) {
+        this();
+
+        this.message = message;
+        this.details = "";
+    }
+
+    public Response(String message, String details) {
+        this();
+
+        this.message = message;
+        this.details = details;
+    }
+
+    public String getMessage() {
+        return this.message;
+    }
+    public void setMessage(String message) {
+        this.message = message;
+    }
+
+    public String getDetails() {
+        return this.details;
+    }
+    public void setDetails(String details) {
+        this.details = details;
+    }
+
+}
diff --git a/src/test/java/org/openepics/names/util/ExceptionUtilTest.java b/src/test/java/org/openepics/names/util/ExceptionUtilTest.java
new file mode 100644
index 0000000..af5aae8
--- /dev/null
+++ b/src/test/java/org/openepics/names/util/ExceptionUtilTest.java
@@ -0,0 +1,145 @@
+/*
+ * Copyright (C) 2021 European Spallation Source ERIC.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version 2
+ * of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
+ */
+
+package org.openepics.names.util;
+
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertNull;
+
+import org.junit.jupiter.api.Test;
+import org.springframework.http.HttpStatus;
+import org.springframework.web.server.ResponseStatusException;
+
+/**
+ * Unit tests for ExceptionUtil class.
+ *
+ * @author Lars Johansson
+ *
+ * @see ExceptionUtil
+ */
+public class ExceptionUtilTest {
+
+    /**
+     * Test of create response status exception.
+     */
+    @Test
+    public void createResponseStatusException() {
+        ResponseStatusException exception = ExceptionUtil.createResponseStatusException(HttpStatus.I_AM_A_TEAPOT, null, null);
+        assertEquals(HttpStatus.I_AM_A_TEAPOT, exception.getStatus());
+        assertNull  (exception.getReason());
+        assertNull  (exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionBadRequest();
+        assertEquals(HttpStatus.BAD_REQUEST, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionUnauthorized();
+        assertEquals(HttpStatus.UNAUTHORIZED, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionForbidden();
+        assertEquals(HttpStatus.FORBIDDEN, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionNotFound();
+        assertEquals(HttpStatus.NOT_FOUND, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionConflict();
+        assertEquals(HttpStatus.CONFLICT, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionInternalServerError();
+        assertEquals(HttpStatus.INTERNAL_SERVER_ERROR, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createResponseStatusExceptionNotImplemented();
+        assertEquals(HttpStatus.NOT_IMPLEMENTED, exception.getStatus());
+        assertEquals(ExceptionUtil.OPERATION_COULD_NOT_BE_PERFORMED, exception.getReason());
+        assertEquals(null, exception.getCause());
+    }
+
+    /**
+     * Test of create service http status exception.
+     */
+    @Test
+    public void createServiceHttpStatusException() {
+        ServiceHttpStatusException exception = ExceptionUtil.createServiceHttpStatusException(null, null, null, null, null);
+        assertNull(exception.getHttpStatus());
+        assertNull(exception.getMessage());
+        assertNull(exception.getDetails());
+        assertNull(exception.getUserFriendly());
+        assertNull(exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionBadRequest(null, null, null);
+        assertEquals(HttpStatus.BAD_REQUEST, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionUnauthorized(null, null, null);
+        assertEquals(HttpStatus.UNAUTHORIZED, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionForbidden(null, null, null);
+        assertEquals(HttpStatus.FORBIDDEN, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionNotFound(null, null, null);
+        assertEquals(HttpStatus.NOT_FOUND, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionConflict(null, null, null);
+        assertEquals(HttpStatus.CONFLICT, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionInternalServerError(null, null, null);
+        assertEquals(HttpStatus.INTERNAL_SERVER_ERROR, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+
+        exception = ExceptionUtil.createServiceHttpStatusExceptionNotImplemented(null, null, null);
+        assertEquals(HttpStatus.NOT_IMPLEMENTED, exception.getHttpStatus());
+        assertEquals(null, exception.getMessage());
+        assertEquals(null, exception.getDetails());
+        assertEquals(null, exception.getUserFriendly());
+        assertEquals(null, exception.getCause());
+    }
+
+}
-- 
GitLab