package io.delphiplatform.api.security;

import org.springframework.http.HttpStatus;
import org.springframework.security.authentication.InsufficientAuthenticationException;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.oauth2.core.OAuth2AuthenticationException;
import org.springframework.security.web.AuthenticationEntryPoint;
import org.springframework.stereotype.Component;

import java.io.IOException;

import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import lombok.extern.slf4j.Slf4j;

@Slf4j
@Component
public class ErrorCodeAuthenticationEntryPoint implements AuthenticationEntryPoint {

    @Override
    public void commence(HttpServletRequest request, HttpServletResponse response,
        AuthenticationException authException) throws IOException, ServletException {
        String errorCode;
        String errorDescription;

        log.debug("Authentication failed with exception.", authException);

        if (authException instanceof OAuth2AuthenticationException) {
            response.setStatus(HttpStatus.UNAUTHORIZED.value());
            String message = authException.getMessage();
            errorCode = message.contains("expired") ? "token_expired" : "invalid_token";
            errorDescription = message;
        } else if (authException instanceof InsufficientAuthenticationException) {
            response.setStatus(HttpStatus.UNAUTHORIZED.value());
            errorCode = "insufficient_authentication";
            errorDescription = authException.getMessage();
        } else {
            response.setStatus(HttpStatus.UNAUTHORIZED.value());
            errorCode = "authorization_exception";
            errorDescription = "Authorization failed";
        }

        response.setHeader("Content-Type", "application/json");
        response.getOutputStream().println(String.format("{\"code\":\"%s\","
            + "\"description\":\"%s\"}", errorCode, errorDescription));
    }

}
