package com.bcxin.rest.web.commons;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;

import java.util.Collection;
import java.util.stream.Collectors;

public class ResponseBuilder {
    public static <T> ResponseEntity build(HttpStatus status, T data) {
        String message = null;
        if (status != HttpStatus.OK && data != null) {
            message = String.valueOf(data);
        }

        if (data instanceof ValidationErrorResponse) {
            message = ((ValidationErrorResponse) data).getViolations().stream().map(ii -> ii.getMessage()).collect(Collectors.joining(","));
        }

        return ResponseEntity.status(status).body(new ResponseBody(status, data, message, null));
    }

    public static <T> ResponseEntity build(HttpStatus status, T data, String message, ErrorBody error) {
        return ResponseBuilder.build(status, data, "1000000000", message, error);
    }

    public static <T> ResponseEntity build(HttpStatus status, T data, String code, String message, ErrorBody error) {
        return ResponseEntity.status(status).body(new ResponseBody(status, data,code, message, error));
    }

    public static class ResponseBody<T> {
        private final HttpStatus httpStatus;
        private final String code;
        private final String message;
        private final ErrorBody error;
        private final T data;

        public ResponseBody(HttpStatus status,
                            T data,
                            String code,
                            String message, ErrorBody error) {
            this.httpStatus = status;
            this.message = message;
            this.error = error;
            this.data = data;
            this.code = code;
        }

        public ResponseBody(HttpStatus status,
                            T data, String message, ErrorBody error) {
            this(status, data, null, message, error);
        }

        public ResponseBody(HttpStatus status, T data, ErrorBody error) {
            this(status, data, null, error);
        }

        public ResponseBody(HttpStatus status, T data) {
            this(status, data, null, null);
        }

        public HttpStatus getHttpStatus() {
            return httpStatus;
        }

        public T getData() {
            return data;
        }

        public ErrorBody getError() {
            return error;
        }

        public String getMessage() {
            return message;
        }

        public int getStatus() {
            return httpStatus.value();
        }

        public String getCode() {
            return this.code;
        }
    }

    private static class ErrorBody {
        private final Collection<String> items;

        private ErrorBody(Collection<String> items) {
            this.items = items;
        }

        public Collection<String> getItems() {
            return items;
        }
    }
}
