package com.eactive.eai.custom.adapter.http.dynamic.filter;

import java.security.KeyStore;
import java.util.Base64;
import java.util.Properties;

import javax.crypto.SecretKey;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.json.simple.JSONObject;
import org.springframework.http.HttpStatus;

import com.eactive.eai.adapter.http.dynamic.filter.FilterException;
import com.eactive.eai.adapter.http.dynamic.filter.HttpAdapterFilter;
import com.eactive.eai.common.hsm.HsmManager;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.util.HexaConverter;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;

public class HSMKeyCryptoFilter implements HttpAdapterFilter {

	private static final Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
	
	private static final ObjectMapper OBJECT_MAPPER = new ObjectMapper();

	@Override
	public Object doPreFilter(String adptGrpName, String adptName, Object message, Properties prop,
			HttpServletRequest request, HttpServletResponse response) throws Exception {
		try {
			ObjectNode rootNode = null;
			String jsonStr = null;
			if (message instanceof String) {
				jsonStr = (String) message;
			} else if (message instanceof JSONObject) {
				jsonStr = ((JSONObject) message).toJSONString();
			} else if (message instanceof ObjectNode) {
				rootNode = (ObjectNode) message;
			} else {
				return message;
			}
			
			if (rootNode == null)
				rootNode = (ObjectNode) OBJECT_MAPPER.readTree(jsonStr);

			JsonNode hsmKeyAlias = rootNode.get("hsmKeyAlias");
			if (hsmKeyAlias != null) {
				String hsmKeyAliasValue = hsmKeyAlias.textValue();
				KeyStore keyStore = HsmManager.getInstance().getKeyStore();
				
				java.security.Key key = keyStore.getKey(hsmKeyAliasValue, null);
				if (key instanceof SecretKey) {
					SecretKey secretKey = (SecretKey) key;
					byte[] encoded = secretKey.getEncoded();
					if (encoded != null) {
						String encBase64 = Base64.getEncoder().encodeToString(encoded);
						logger.debug("HsmManager] HSM - {} : [{}]", hsmKeyAliasValue, encBase64);
						rootNode.put("hsmKeyBase64", encBase64);
						rootNode.put("hsmKeyRaw", HexaConverter.binToHex(encoded));
					} else {
						logger.debug("HsmManager] HSM - secretKey null {} : [{}]", hsmKeyAliasValue, secretKey);
					}
				}
			}
			return rootNode;

		} catch (Exception e) {
			throw new FilterException("HSM key 가져오기 실패", ERROR_PRE_FAIL, HttpStatus.INTERNAL_SERVER_ERROR.value(), e);
		}
	}

	@Override
	public Object doPostFilter(String adptGrpName, String adptName, Object resultMessage, Properties prop,
			HttpServletRequest request, HttpServletResponse response) throws Exception {
		return resultMessage;
	}

}
