diff --git a/src/main/java/com/eactive/eai/adapter/http/client/HttpClient5AdapterServiceSupport.java b/src/main/java/com/eactive/eai/adapter/http/client/HttpClient5AdapterServiceSupport.java index 98d890c..601b163 100644 --- a/src/main/java/com/eactive/eai/adapter/http/client/HttpClient5AdapterServiceSupport.java +++ b/src/main/java/com/eactive/eai/adapter/http/client/HttpClient5AdapterServiceSupport.java @@ -53,6 +53,8 @@ public abstract class HttpClient5AdapterServiceSupport implements HttpClientAdap private static boolean testMode = TestModeChecker.isTestMode(); + private static boolean httpHeaderLogMode = HttpAdapterExtraLogUtil.isHttpHeaderMode(); + public synchronized void close() { if(connectionManager != null) { connectionManager.close(); @@ -366,8 +368,20 @@ public abstract class HttpClient5AdapterServiceSupport implements HttpClientAdap } else { sslContext = SSLContextBuilder.create().loadTrustMaterial(new TrustAllStrategy()).build(); - SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext); - cmBuilder.setSSLSocketFactory(csf); + SSLConnectionSocketFactory sslSocketFactory = null; + if(testMode) { + // Hostname verifier 비활성화 (테스트용) + sslSocketFactory = new SSLConnectionSocketFactory( + sslContext + , NoopHostnameVerifier.INSTANCE + ); + } + else { + sslSocketFactory = new SSLConnectionSocketFactory( + sslContext + ); + } + cmBuilder.setSSLSocketFactory(sslSocketFactory); } } catch (KeyManagementException | NoSuchAlgorithmException | KeyStoreException @@ -384,6 +398,11 @@ public abstract class HttpClient5AdapterServiceSupport implements HttpClientAdap HttpRequestInterceptor requestLogInterceptor = (request, entity, context) -> { + if (!httpHeaderLogMode) { + logger.info("httpHeader logging off - use.http.header.log"); + return; + } + try { String uuid = (String) context.getAttribute(TransactionContextKeys.TRANSACTION_UUID); String contextAdapterGroupName = (String) context.getAttribute(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME); @@ -403,7 +422,12 @@ public abstract class HttpClient5AdapterServiceSupport implements HttpClientAdap }; HttpResponseInterceptor responseLogInterceptor = (response, entity, context) -> { - try{ + if (!httpHeaderLogMode) { + logger.info("httpHeader logging off - use.http.header.log"); + return; + } + + try{ HttpRequest request = (HttpRequest)context.getAttribute("http.request"); String url = request.getUri().toString(); String uuid = (String) context.getAttribute(TransactionContextKeys.TRANSACTION_UUID); diff --git a/src/main/java/com/eactive/eai/adapter/http/dynamic/HttpAdapterServiceSupport.java b/src/main/java/com/eactive/eai/adapter/http/dynamic/HttpAdapterServiceSupport.java index 8be66b3..6f68fe1 100644 --- a/src/main/java/com/eactive/eai/adapter/http/dynamic/HttpAdapterServiceSupport.java +++ b/src/main/java/com/eactive/eai/adapter/http/dynamic/HttpAdapterServiceSupport.java @@ -10,29 +10,35 @@ import org.apache.commons.lang3.StringUtils; import com.eactive.eai.adapter.AdapterGroupVO; import com.eactive.eai.adapter.AdapterManager; import com.eactive.eai.adapter.RequestDispatcher; +import com.eactive.eai.adapter.http.HttpStatusException; import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey; import com.eactive.eai.adapter.http.dynamic.filter.HttpAdapterFilter; import com.eactive.eai.adapter.http.dynamic.filter.HttpAdapterFilterFactoryKjb; import com.eactive.eai.adapter.http.dynamic.filter.HttpAdapterFilterType; +import com.eactive.eai.adapter.http.dynamic.filter.JwtAuthException; +import com.eactive.eai.common.util.Logger; public abstract class HttpAdapterServiceSupport implements HttpAdapterService, HttpAdapterServiceKey { + private static final String LOG_PREFIX = "HttpAdapterServiceSupport] "; protected long slowTranTime = 2000L; public static final String HEADER_NAME_CLIENT_ID = "x-elink-client-id"; public static final String PROPERTIES_NAME_CLIENT_ID = "clientId"; + static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER); public Object service(String adptGrpName, String adptName, Object message, Properties prop, HttpServletRequest request, HttpServletResponse response) throws Exception { + + String transactionId = request.getHeader(HttpClientAdapterServiceKey.TRANSACTION_ID); + if (StringUtils.isNotBlank(transactionId)) { + prop.put(HttpClientAdapterServiceKey.TRANSACTION_ID, transactionId); + } + try { String clientId = request.getHeader(HEADER_NAME_CLIENT_ID); if (StringUtils.isNotBlank(clientId)) { prop.put(PROPERTIES_NAME_CLIENT_ID, clientId); } - String transactionId = request.getHeader(HttpClientAdapterServiceKey.TRANSACTION_ID); - if (StringUtils.isNotBlank(transactionId)) { - prop.put(HttpClientAdapterServiceKey.TRANSACTION_ID, transactionId); - } - String instanceId = request.getHeader(HttpClientAdapterServiceKey.INSTANCE_ID); if (StringUtils.isNotBlank(instanceId)) { prop.put(HttpClientAdapterServiceKey.INSTANCE_ID, instanceId); @@ -40,9 +46,26 @@ public abstract class HttpAdapterServiceSupport implements HttpAdapterService, H } catch (Exception e) { } - message = doPreFilters(adptGrpName, adptName, message, prop, request, response); - Object obj = RequestDispatcher.getRequestDispatcher(adptGrpName).handle(adptName, message, prop); - obj = doPostFilters(adptGrpName, adptName, obj, prop, request, response); + Object obj = null; + try { + message = doPreFilters(adptGrpName, adptName, message, prop, request, response); + obj = RequestDispatcher.getRequestDispatcher(adptGrpName).handle(adptName, message, prop); + obj = doPostFilters(adptGrpName, adptName, obj, prop, request, response); + } catch (HttpStatusException e) { // inbound error + logger.warn(LOG_PREFIX + transactionId + "-" + adptGrpName + "-" + adptName + ">>" + e.getMessage(), e); + throw e; + } catch (JwtAuthException e) { // filter error + logger.error(LOG_PREFIX + transactionId + "-" + adptGrpName + "-" + adptName + ">>" + e.getMessage(), e); + UnkownMessageLogUtils.logUnkownMessage(adptGrpName, adptName, message, prop, request, response, + "RECEAIIRP202", e); + throw e; + } catch (Exception e) { // filter error + logger.error(LOG_PREFIX + transactionId + "-" + adptGrpName + "-" + adptName + ">>" + e.getMessage(), e); + UnkownMessageLogUtils.logUnkownMessage(adptGrpName, adptName, message, prop, request, response, + "RECEAIIRP201", e); + throw e; + } + if (obj == null) { return null; } else if (obj instanceof byte[]) { diff --git a/src/main/java/com/eactive/eai/adapter/http/dynamic/UnkownMessageLogUtils.java b/src/main/java/com/eactive/eai/adapter/http/dynamic/UnkownMessageLogUtils.java new file mode 100644 index 0000000..dcfd5a2 --- /dev/null +++ b/src/main/java/com/eactive/eai/adapter/http/dynamic/UnkownMessageLogUtils.java @@ -0,0 +1,149 @@ +package com.eactive.eai.adapter.http.dynamic; + +import java.io.UnsupportedEncodingException; +import java.nio.charset.Charset; +import java.util.Properties; + +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + +import org.apache.commons.lang3.StringUtils; + +import com.eactive.eai.adapter.AdapterGroupVO; +import com.eactive.eai.adapter.AdapterManager; +import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey; +import com.eactive.eai.common.exception.ExceptionUtil; +import com.eactive.eai.common.server.EAIServerManager; +import com.eactive.eai.common.util.DatetimeUtil; +import com.eactive.eai.common.util.InboundErrorLogger; +import com.eactive.eai.common.util.Logger; +import com.eactive.eai.common.util.UUIDGenerator; +import com.eactive.eai.inbound.error.InboundErrorInfoVO; +import com.eactive.eai.inbound.error.InboundErrorKeys; +import com.eactive.eai.util.HexaConverter; + +public class UnkownMessageLogUtils { + static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT); + + private UnkownMessageLogUtils() { + throw new IllegalStateException("Utility class"); + } + + public static void logUnkownMessage(String adptGrpName, String adptName, Object message, Properties prop, + HttpServletRequest request, HttpServletResponse response, String errCode, Exception e) { + try { + EAIServerManager eaiServerManager = EAIServerManager.getInstance(); + String serverName = eaiServerManager.getLocalServerName(); + String txId = prop.getProperty(HttpClientAdapterServiceKey.TRANSACTION_ID); + if(StringUtils.isEmpty(txId)) { + StringBuffer sb = new StringBuffer(); + + String instanceid1 = serverName.substring(0,2); + String instanceid2 = serverName.substring(serverName.length()-2, serverName.length()); + String instid = instanceid1 + instanceid2; + txId = instid + UUIDGenerator.getUUID(); + } + String clientId = prop.getProperty("clientId"); + String hexClientId = clientId != null ? HexaConverter.bytesToHexa(clientId.getBytes()) : ""; + String errorMsg = ExceptionUtil.make(e, errCode); + StringBuffer sb = new StringBuffer(); + sb.append(errorMsg).append("\n").append("Remote Addr : ").append(request.getRemoteAddr()).append("\n").append("Request URI : ") + .append(request.getRequestURI()).append("\n").append("clientId=").append(clientId).append(",hexClientId=").append(hexClientId).append(",txProp=").append(prop).append("\n").append("Exception : ").append(e.getMessage()); + UnkownMessageLogUtils.logUnknownMessage(txId, adptGrpName, adptName, + "", "", false, errCode, sb.toString(), System.currentTimeMillis(), + serverName, InboundErrorKeys.IN_UNKNOWN, message); + } catch (Exception ex) { + logger.warn("unkown log fail.", ex); + } + + } + +// public static void logUnkownMessage(String uuid, String adapterGroupName, String adapterName, String errCode, +// String errMsg, Object message) { +// UnkownMessageLogUtils.logUnknownMessage(uuid, adapterGroupName, adapterName, +// "", "", false, errCode, errMsg, System.currentTimeMillis(), +// EAIServerManager.getInstance().getInstId(), InboundErrorKeys.IN_UNKNOWN, message); +// } + + private static void logUnknownMessage(String uuid, String adapterGroupName, String adapterName, + String bzwkSvcKeyName, String eaiSvcCd, boolean isTasStarted, String errCode, String errMsg, long errTm, + String svcInstNm, String errDstCd, Object message) { + String msg = null; + + if(errDstCd == null || errDstCd.length() ==0) { + errDstCd = "ND"; + } + + if(isTasStarted) { + errDstCd = InboundErrorKeys.TAS_START; + } + + InboundErrorInfoVO errorInfoVO = new InboundErrorInfoVO(); + errorInfoVO.setEaiSvcSno(uuid); // EAI서비스일련번호 + errorInfoVO.setAdptBwkGrpNm(adapterGroupName); // 어댑터업무그룹명 + errorInfoVO.setEaiSvcCd(eaiSvcCd); + errorInfoVO.setErrCd(errCode); // 에러코드 + errorInfoVO.setErrTxt(errMsg); // 에러내용 + errorInfoVO.setErrTm(DatetimeUtil.getCurrentTime(errTm)); // 에러발생시각 + errorInfoVO.setErrDstcd(errDstCd); + errorInfoVO.setBzwkSvcKeyName(bzwkSvcKeyName); + + if(message == null) { + msg = "null"; + } + else { + if(message instanceof byte[]) { + AdapterManager adapterManager = AdapterManager.getInstance(); + AdapterGroupVO srcAdapterGrpVO = adapterManager.getAdapterGroupVO(adapterGroupName); + + // TAS 거래일 경우 NULL일 수 있음 + if(srcAdapterGrpVO == null) { + msg = new String((byte[])message); + } + else { +// String srcAdapterMsgType = srcAdapterGrpVO.getMessageType(); +// if( MessageUtil.isUTF8(srcAdapterMsgType) ) { +// try { +// msg = new String((byte[])message, UJSONMessage.encode); +// } catch (UnsupportedEncodingException e) { +// logger.warn("msg encode error", e); +// msg = new String((byte[])message); } +// } +// else { +// msg = new String((byte[])message); +// } + + String charset = StringUtils.defaultIfBlank(srcAdapterGrpVO.getMessageEncode(), Charset.defaultCharset().name()); + try { + msg = new String((byte[])message, charset); + } catch (UnsupportedEncodingException e) { + logger.warn("msg encode error", e); + msg = new String((byte[])message); + } + } + + } + else if(message instanceof String) { + msg = (String)message; + } + else { + msg = "invaild message ["+message.getClass().getName()+"] "+message.toString(); + } + } + + errorInfoVO.setBwkDataTxt(msg); // 업무데이터내용 + errorInfoVO.setEaiSvrInstNm(svcInstNm); // EAI서버인스턴스명 + + InboundErrorLogger.error(errorInfoVO); + + if (logger.isError()) { + logger.error("======================================================================" ); + logger.error(" RequestDispatcher] GET UNKNOWN MESSAGE"); + logger.error(" ADAPTER GROUP NAME [" + adapterGroupName + "]"); + logger.error(" EAISVCNAME [" + eaiSvcCd + "]"); + logger.error(" ADAPTER NAME [" + adapterName + "]"); + logger.error("======================================================================" ); + } + + } +} diff --git a/src/main/java/com/eactive/eai/adapter/http/dynamic/filter/ApiAuthFilter.java b/src/main/java/com/eactive/eai/adapter/http/dynamic/filter/ApiAuthFilter.java index 6b6db9e..97d4967 100644 --- a/src/main/java/com/eactive/eai/adapter/http/dynamic/filter/ApiAuthFilter.java +++ b/src/main/java/com/eactive/eai/adapter/http/dynamic/filter/ApiAuthFilter.java @@ -104,7 +104,8 @@ public class ApiAuthFilter implements HttpAdapterFilter { */ StandardMessage standardMessage = STDMessageManager.getInstance().getSTDMessage(apiId); String eaiSvcCd = StandardMessageManager.getInstance().getMapper().getEaiSvcCode(standardMessage); - if(!StringUtils.equals(eaiSvcCd, prop.getProperty("API_SERVICE_CODE"))) eaiSvcCd = prop.getProperty("API_SERVICE_CODE"); +// if (StringUtils.isNotEmpty(eaiSvcCd) && !StringUtils.equals(eaiSvcCd, )) +// eaiSvcCd = prop.getProperty("API_SERVICE_CODE"); EAIMessage eaiMessage = EAIMessageManager.getInstance().getEAIMessage(eaiSvcCd); if(StringUtils.isBlank(eaiMessage.getAuthType())){ @@ -305,7 +306,8 @@ public class ApiAuthFilter implements HttpAdapterFilter { } public static String extractBearerToken(HttpServletRequest request) throws JwtAuthException { - String authorization = request.getHeader("Authorization"); + String tokenHeaderName = PropManager.getInstance().getProperty("ApiConfig", "token.header.name", "Authorization"); + String authorization = request.getHeader(tokenHeaderName); if (StringUtils.isBlank(authorization)) { // QueryString으로 전달된 access_token 파라미터 확인 String tokenParamName = PropManager.getInstance().getProperty("ApiConfig", "token.param.name", "access_token"); @@ -313,13 +315,13 @@ public class ApiAuthFilter implements HttpAdapterFilter { if (StringUtils.isNotBlank(queryToken)) { return queryToken.trim(); } - throw new JwtAuthException(ERROR_AUTHENTICATION_FAIL, "No have header info: Authorization"); + throw new JwtAuthException(ERROR_AUTHENTICATION_FAIL, "No have header info: " + tokenHeaderName); } - String[] components = authorization.split("\\s"); + String[] components = authorization.trim().split("\\s+", 2); if (components.length != 2) { - throw new JwtAuthException(ERROR_AUTHENTICATION_FAIL, "Malformat [Authorization] content"); + throw new JwtAuthException(ERROR_AUTHENTICATION_FAIL, "Malformat [" + tokenHeaderName + "] content"); } if (!StringUtils.equalsIgnoreCase(components[0], "Bearer")) { diff --git a/src/main/java/com/eactive/eai/adapter/http/dynamic/impl/HttpAdapterServiceBypass.java b/src/main/java/com/eactive/eai/adapter/http/dynamic/impl/HttpAdapterServiceBypass.java index dd5ab69..e7af5f3 100644 --- a/src/main/java/com/eactive/eai/adapter/http/dynamic/impl/HttpAdapterServiceBypass.java +++ b/src/main/java/com/eactive/eai/adapter/http/dynamic/impl/HttpAdapterServiceBypass.java @@ -45,7 +45,7 @@ public class HttpAdapterServiceBypass extends HttpAdapterServiceSupport { public static final String HTTP_STATUS = "HTTP_STATUS"; public static final String PROPERTIES_NAME_HTTP_REQUEST_METHOD = "httpRequestMethod"; public static final String[] HOP_BY_HOP_HEADERS = new String[] { "Connection", "Keep-Alive", "Proxy-Authenticate", - "Proxy-Authorization", "TE", "Trailers", "Transfer-Encoding", "Upgrade" }; + "Proxy-Authorization", "TE", "Trailers", "Trailer", "Transfer-Encoding", "Upgrade" }; protected boolean doPreserveCookies = false; protected boolean doPreserveCookiePath = false; diff --git a/src/main/java/com/eactive/eai/common/util/HttpAdapterExtraLogUtil.java b/src/main/java/com/eactive/eai/common/util/HttpAdapterExtraLogUtil.java index 2797a88..722fb5b 100644 --- a/src/main/java/com/eactive/eai/common/util/HttpAdapterExtraLogUtil.java +++ b/src/main/java/com/eactive/eai/common/util/HttpAdapterExtraLogUtil.java @@ -21,6 +21,10 @@ import org.apache.commons.lang3.StringUtils; public class HttpAdapterExtraLogUtil { static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT); + + public static boolean isHttpHeaderMode() { + return StringUtils.equals(System.getProperty("use.http.header.log", "n"), "y"); + } public static void insertHttpAdapterExtraLog(String guid, int serviceProcessNumber, String adapterGroupName, String adapterName, Map headers, String url, String httpMethod){ insertHttpAdapterExtraLog(guid, serviceProcessNumber, adapterGroupName, adapterName, headers, url, httpMethod, 0); diff --git a/src/main/java/com/eactive/eai/common/util/MessageUtil.java b/src/main/java/com/eactive/eai/common/util/MessageUtil.java index 82e3980..9adfbf9 100644 --- a/src/main/java/com/eactive/eai/common/util/MessageUtil.java +++ b/src/main/java/com/eactive/eai/common/util/MessageUtil.java @@ -23,6 +23,7 @@ import org.w3c.dom.Document; import com.eactive.eai.common.EAIKeys; import com.eactive.eai.common.message.MessageType; import com.eactive.eai.common.monitor.EAIServiceMonitor; +import com.eactive.eai.common.property.PropManager; import com.eactive.eai.transformer.message.ISO8583Message; import com.eactive.eai.transformer.message.ISO8583MessageFactory; import com.eactive.eai.transformer.util.IConv; @@ -35,7 +36,8 @@ public final class MessageUtil { static Logger logger = LoggerFactory.getLogger(MessageUtil.class); //public static final String ERROR_MESSAGE_DEFAULT_FORMAT = "{\"error\":{\"code\":\"%s\",\"message\":\"%s\"}}"; - public static final String ERROR_MESSAGE_DEFAULT_FORMAT = "{\"code\":\"%s\",\"message\":\"%s\"}"; +// public static final String ERROR_MESSAGE_DEFAULT_FORMAT = "{\"code\":\"%s\",\"message\":\"%s\"}"; + public static final String ERROR_MESSAGE_DEFAULT_FORMAT = "{\"error\":\"%s\",\"error_description\":\"%s\"}"; public static final String ERROR_CODE_AP_ERROR = "E.GW.AP_ERROR"; public static final String ERROR_CODE_AUTH_FAIL = "E.GW.AUTH_FAIL"; @@ -516,7 +518,8 @@ public final class MessageUtil { public static String makeJsonErrorMessage(String code, String msg, String errorFormat) { if (StringUtils.isBlank(errorFormat)) { - errorFormat = ERROR_MESSAGE_DEFAULT_FORMAT; + errorFormat = PropManager.getInstance().getProperty("MessageUtil", + "ERROR_MESSAGE_DEFAULT_FORMAT", ERROR_MESSAGE_DEFAULT_FORMAT); } // errorFormat에 %s가 1개만 있으면 msg만, 2개 이상이면 code, msg 전달 diff --git a/src/main/java/com/eactive/eai/inbound/processor/RequestProcessor.java b/src/main/java/com/eactive/eai/inbound/processor/RequestProcessor.java index 0c491d0..6bb9fb9 100644 --- a/src/main/java/com/eactive/eai/inbound/processor/RequestProcessor.java +++ b/src/main/java/com/eactive/eai/inbound/processor/RequestProcessor.java @@ -4,6 +4,9 @@ import java.util.Calendar; import java.util.Properties; import java.util.Set; +import javax.servlet.http.HttpServletRequest; +import javax.servlet.http.HttpServletResponse; + import com.eactive.eai.common.TransactionContextKeys; import com.eactive.eai.common.context.ElinkTransactionContext; import com.eactive.eai.common.util.*; @@ -96,7 +99,9 @@ public class RequestProcessor extends RequestProcessorSupport { //isPEAIServer = eaiServerManager.isPEAIServer(); instid = eaiServerManager.getGroupInstId(); } - + + private static boolean httpHeaderLogMode = HttpAdapterExtraLogUtil.isHttpHeaderMode(); + private ProcessVO setVO(Properties prop,long msgRcvTm) throws RequestProcessorException{ String actionName = prop.getProperty(Processor.REQUEST_ACTION); String adapterGroupName = prop.getProperty(Processor.ADAPTER_GROUP_NAME); @@ -422,12 +427,16 @@ public class RequestProcessor extends RequestProcessorSupport { // INBOUND_HEADER 가 NULL인 경우는 HTTP가 아닌것으로 간주함. if(prop.get(HttpClientAdapterServiceKey.INBOUND_HEADER) != null) { - HttpAdapterExtraLogUtil.insertHttpAdapterExtraLog(vo.getUuid(), 100, - prop.getProperty(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME), - prop.getProperty(HttpClientAdapterServiceKey.ADAPTER_NAME), - (Properties) prop.get(HttpClientAdapterServiceKey.INBOUND_HEADER), - prop.getProperty(HttpClientAdapterServiceKey.INBOUND_EXTURI)+"?"+prop.getProperty(HttpClientAdapterServiceKey.INBOUND_EXTPARAMS), - prop.getProperty(HttpClientAdapterServiceKey.INBOUND_METHOD)); + if (!httpHeaderLogMode) { + logger.info("httpHeader logging off - use.http.header.log"); + } else { + HttpAdapterExtraLogUtil.insertHttpAdapterExtraLog(vo.getUuid(), 100, + prop.getProperty(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME), + prop.getProperty(HttpClientAdapterServiceKey.ADAPTER_NAME), + (Properties) prop.get(HttpClientAdapterServiceKey.INBOUND_HEADER), + prop.getProperty(HttpClientAdapterServiceKey.INBOUND_EXTURI)+"?"+prop.getProperty(HttpClientAdapterServiceKey.INBOUND_EXTPARAMS), + prop.getProperty(HttpClientAdapterServiceKey.INBOUND_METHOD)); + } } EAIMessage eaiMsg = null;