package com.dla.dda.utils.rest.client;

import java.io.IOException;
import java.util.ArrayList;
import java.util.List;

import javax.ws.rs.core.MediaType;

import org.apache.cxf.jaxrs.client.WebClient;

import org.codehaus.jackson.jaxrs.JacksonJsonProvider;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.dla.dda.utils.json.JsonConverter;

/**
 * @see Cliente para consulta de Rest Services
 * 
 * 
 * @author nmontielh
 * @version 1.0
 */
public class RestServiceClient implements IRestClient {

	private static Logger logger = LoggerFactory.getLogger(RestServiceClient.class);

	private String uri;

	protected WebClient jsonClient;

	/**
	 * @see Metodo de inicializacion para que acepte JSON
	 * @param path
	 */
	public void initialize() {

		List<Object> providers = new ArrayList<Object>();
		providers.add(new JacksonJsonProvider());

		logger.info("Rest Service Client to [{}]", uri);

		jsonClient = WebClient.create(uri, providers);
		jsonClient.accept(MediaType.APPLICATION_JSON_TYPE);
		jsonClient.type(MediaType.APPLICATION_JSON_TYPE);
		jsonClient.header("Content-Type", MediaType.APPLICATION_JSON_TYPE);

	}

	@Override
	public <Response, Request> Response post(String path, Request request, Class<Response> responseClass)
			throws IOException {

		String json = null;
		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("POST:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());
		jsonClient.path(path);

		return jsonClient.post(json, responseClass);

	}

	@Override
	public <Response, Request> Response post(Request request, Class<Response> responseClass) throws IOException {

		String json = null;
		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("POST:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());

		return jsonClient.post(json, responseClass);

	}

	@Override
	public <Response, Request> Response post(String request, Class<Response> responseClass) throws IOException {

		logger.debug("POST:[{}]", request);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());

		return jsonClient.post(request, responseClass);

	}

	@SuppressWarnings("unchecked")
	@Override
	public <Response, Request> Response put(String path, Request request, Class<Response> responseClass)
			throws IOException {

		String json = null;
		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("PUT:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());

		jsonClient.path(path);

		return (Response) jsonClient.put(json);
	}

	/**
	 * 
	 * @param path
	 * @param request
	 */
	// TODO revisar si se usa por que no se pasa el json
	@Deprecated
	public <Request> void delete(String path, Request request) throws IOException {

		String json = null;

		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("DELETE:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());

		jsonClient.path(path);

		jsonClient.delete();

	}

	// TODO revisar si se usa por que no se pasa el json
	@Deprecated
	public <Response, Request> Response get(String path, Request request, Class<Response> responseClass)
			throws IOException {

		String json = null;
		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("GET:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());

		jsonClient.path(path);

		return jsonClient.get(responseClass);

	}

	@SuppressWarnings("unchecked")
	@Override
	public <Response, Request> Response put(Request request, Class<Response> responseClass) throws IOException {
		String json = null;
		try {
			json = JsonConverter.toJson(request);
		} catch (IOException e) {
			logger.error("Error to convert to Json : [{}]" + e.getMessage(), e);
			throw e;
		}

		logger.debug("PUT:[{}]", json);
		logger.debug("URL:[{}]", jsonClient.getBaseURI());
		return (Response) jsonClient.put(json);

	}

	public void setUri(String uri) {
		this.uri = uri;
	}

}