This commit is contained in:
Rinjae
2025-09-05 18:57:45 +09:00
commit aacc1a389e
1229 changed files with 167963 additions and 0 deletions
+234
View File
@@ -0,0 +1,234 @@
gradle.properties
# Package Files #
*.war
src/main/generated
# Eclipse #
.metadata
bin/
tmp/
*.tmp
*.bak
*.swp
*~.nib
local.properties
.settings/
.loadpath
.recommenders
.classpath
.project
# External tool builders
.externalToolBuilders/
# Locally stored "Eclipse launch configurations"
*.launch
# PyDev specific (Python IDE for Eclipse)
*.pydevproject
# CDT-specific (C/C++ Development Tooling)
.cproject
# CDT- autotools
.autotools
# Java annotation processor (APT)
.factorypath
# PDT-specific (PHP Development Tools)
.buildpath
# sbteclipse plugin
.target
# Tern plugin
.tern-project
# TeXlipse plugin
.texlipse
# STS (Spring Tool Suite)
.springBeans
# Code Recommenders
.recommenders/
# Annotation Processing
.apt_generated/
.apt_generated_test/
# Scala IDE specific (Scala & Java development for Eclipse)
.cache-main
.scala_dependencies
.worksheet
# Uncomment this line if you wish to ignore the project description file.
# Typically, this file would be tracked if it contains build/dependency configurations:
#.project
### Intellij ###
.idea
# Covers JetBrains IDEs: IntelliJ, RubyMine, PhpStorm, AppCode, PyCharm, CLion, Android Studio and WebStorm
# Reference: https://intellij-support.jetbrains.com/hc/en-us/articles/206544839
# User-specific stuff
.idea/**/workspace.xml
.idea/**/tasks.xml
.idea/**/usage.statistics.xml
.idea/**/dictionaries
.idea/**/shelf
# Generated files
.idea/**/contentModel.xml
# Sensitive or high-churn files
.idea/**/dataSources/
.idea/**/dataSources.ids
.idea/**/dataSources.local.xml
.idea/**/sqlDataSources.xml
.idea/**/dynamic.xml
.idea/**/uiDesigner.xml
.idea/**/dbnavigator.xml
# Gradle
.idea/**/gradle.xml
.idea/**/libraries
# Gradle and Maven with auto-import
# When using Gradle or Maven with auto-import, you should exclude module files,
# since they will be recreated, and may cause churn. Uncomment if using
# auto-import.
# .idea/modules.xml
# .idea/*.iml
# .idea/modules
# *.iml
# *.ipr
# CMake
cmake-build-*/
# Mongo Explorer plugin
.idea/**/mongoSettings.xml
# File-based project format
*.iws
# IntelliJ
out/
# mpeltonen/sbt-idea plugin
.idea_modules/
# JIRA plugin
atlassian-ide-plugin.xml
# Cursive Clojure plugin
.idea/replstate.xml
# Crashlytics plugin (for Android Studio and IntelliJ)
com_crashlytics_export_strings.xml
crashlytics.properties
crashlytics-build.properties
fabric.properties
# Editor-based Rest Client
.idea/httpRequests
# Android studio 3.1+ serialized cache file
.idea/caches/build_file_checksums.ser
### Intellij Patch ###
# Comment Reason: https://github.com/joeblau/gitignore.io/issues/186#issuecomment-215987721
# *.iml
# modules.xml
# .idea/misc.xml
# *.ipr
# Sonarlint plugin
.idea/**/sonarlint/
# SonarQube Plugin
.idea/**/sonarIssues.xml
# Markdown Navigator plugin
.idea/**/markdown-navigator.xml
.idea/**/markdown-navigator/
### Java ###
# Compiled class file
*.class
# Log file
*.log
# BlueJ files
*.ctxt
# Mobile Tools for Java (J2ME)
.mtj.tmp/
# Package Files #
*.war
*.nar
*.ear
*.zip
*.tar.gz
*.rar
# virtual machine crash logs, see http://www.java.com/en/download/help/error_hotspot.xml
hs_err_pid*
### macOS ###
# General
.DS_Store
.AppleDouble
.LSOverride
# Icon must end with two \r
Icon
# Thumbnails
._*
# Files that might appear in the root of a volume
.DocumentRevisions-V100
.fseventsd
.Spotlight-V100
.TemporaryItems
.Trashes
.VolumeIcon.icns
.com.apple.timemachine.donotpresent
# Directories potentially created on remote AFP share
.AppleDB
.AppleDesktop
Network Trash Folder
Temporary Items
.apdisk
### Gradle ###
.gradle
build/
# Ignore Gradle GUI config
gradle-app.setting
# Avoid ignoring Gradle wrapper jar file (.jar files are usually ignored)
!gradle-wrapper.jar
# Cache of project
.gradletasknamecache
# # Work around https://youtrack.jetbrains.com/issue/IDEA-116898
# gradle/wrapper/gradle-wrapper.properties
### Gradle Patch ###
**/build/
# End of https://www.gitignore.io/api/java,macos,gradle,intellij
/EAISIMWeb/
/.apt_generated_tests/
+221
View File
@@ -0,0 +1,221 @@
plugins {
id 'java-library'
id 'maven-publish'
id 'eclipse-wtp'
id 'idea'
id 'com.diffplug.eclipse.apt' version '3.41.1'
}
group 'com.eactive'
version '4.5.1-SNAPSHOT'
def springVersion = "5.3.27"
def quartzVersion = "2.3.2"
def undertowVersion = "1.4.28.Final"
def queryDslVersion = "5.0.0"
def hibernateVersion = "5.6.15.Final"
def nexusUrl = "https://nexus.eactive.synology.me:8090"
def generatedJavaDir = "$buildDir/generated/java"
java {
toolchain {
languageVersion = JavaLanguageVersion.of(8)
}
}
compileJava {
options.encoding = 'UTF-8'
sourceSets.main.java { srcDir generatedJavaDir }
options.generatedSourceOutputDirectory = project.file(generatedJavaDir)
aptOptions {
processorArgs = [ 'querydsl.generatedAnnotationClass' : 'com.querydsl.core.annotations.Generated' ]
}
}
jar {
exclude '**/persistence.xml'
}
tasks.withType(JavaCompile) {
options.encoding = 'UTF-8'
}
dependencies {
annotationProcessor "org.projectlombok:lombok:1.18.28", "org.projectlombok:lombok-mapstruct-binding:0.2.0", "org.mapstruct:mapstruct-processor:1.5.5.Final"
annotationProcessor "com.querydsl:querydsl-apt:${queryDslVersion}:jpa", "jakarta.persistence:jakarta.persistence-api:2.2.3", "jakarta.annotation:jakarta.annotation-api:1.3.5"
//implementation project(':elink-online-core')
//implementation project(':elink-online-transformer')
api project(':elink-online-transformer')
compileOnly fileTree(dir: 'libs', include: ['*.jar'])
api (group: 'org.apache.activemq', name: 'activemq-console', version: '5.14.5'){
exclude group: 'com.fasterxml.jackson.core'
}
api group: 'org.apache.activemq', name: 'activemq-spring', version: '5.14.5'
api 'backport-util-concurrent:backport-util-concurrent:3.0'
api 'com.github.vladimir-bukhtoyarov:bucket4j-jcache:6.0.2'
api 'io.github.resilience4j:resilience4j-core:1.7.1'
api 'io.github.resilience4j:resilience4j-circuitbreaker:1.7.1'
api 'io.github.resilience4j:resilience4j-micrometer:1.7.1'
api 'io.micrometer:micrometer-core:1.5.17'
api 'io.micrometer:micrometer-registry-prometheus:1.5.17'
//api "com.eactive:mina-core-1.0.10-custom:1.0:custom@jar"
api ("org.apache.mina:mina-filter-ssl:1.0.10") {
exclude module: 'mina-core'
}
api group: 'commons-fileupload', name: 'commons-fileupload', version: '1.5'
api 'org.snmp4j:snmp4j:1.9.1f'
api group: 'com.lmax', name: 'disruptor', version: '3.4.4'
api group: 'commons-httpclient', name: 'commons-httpclient', version: '3.1'
// api group: 'log4j', name: 'log4j', version: '1.2.17'
api 'com.nimbusds:nimbus-jose-jwt:9.24.3'
api "io.undertow:undertow-servlet:${undertowVersion}"
api 'org.java-websocket:Java-WebSocket:1.3.9'
api 'javax.cache:cache-api:1.1.1'
api 'org.apache.ignite:ignite-slf4j:2.14.0'
api 'org.apache.ignite:ignite-kubernetes:2.14.0'
//api 'com.eactive:xc3:1.0'
//api 'com.eactive:xc2:1.0'
//api 'com.eactive:INICrypto:v4.1.22'
//api 'com.eactive:INISAFECore:v2.2.28'
//api 'com.eactive:INISAFENet:v7.2.51_NS'
//api 'com.eactive:INISAFEPKI:v1.1.33'
//api 'com.eactive:Egloan_aes:1.0'
//api 'com.eactive:ExafeiE2E:1.0'
//api 'com.eactive:tcseed:1.0'
//api "com.eactive:backport-util-concurrent:1.0"
api "org.quartz-scheduler:quartz:${quartzVersion}"
api group: 'commons-cli', name: 'commons-cli', version: '1.1'
api "org.springframework:spring-web:${springVersion}"
api "org.springframework:spring-jms:${springVersion}"
api "org.springframework.security.oauth:spring-security-oauth2:2.3.8.RELEASE"
api 'org.yaml:snakeyaml:1.30'
implementation 'org.codehaus.groovy:groovy:3.0.18'
api 'org.slf4j:jul-to-slf4j:1.7.35'
api 'org.slf4j:jcl-over-slf4j:1.7.35'
api 'org.slf4j:log4j-over-slf4j:1.7.35'
api 'org.slf4j:slf4j-api:1.7.35'
//compileOnly "tmax:webt:7.0.2.0-r11661-forJEUS8.0"
//compileOnly "tmax:webtasync:2.0.3.1-r11801-forJEUS8.1"
//compileOnly "tmax:jeus:1.0"
api 'org.apache.httpcomponents.client5:httpclient5:5.1'
api 'org.apache.httpcomponents.core5:httpcore5:5.1'
compileOnly group: 'javax.servlet', name: 'javax.servlet-api', version: '3.1.0'
compileOnly group: 'javax.servlet.jsp', name: 'javax.servlet.jsp-api', version: '2.3.3'
compileOnly 'javax.resource:javax.resource-api:1.7'
compileOnly 'javax.jms:javax.jms-api:2.0.1'
compileOnly group: 'com.fasterxml.jackson.dataformat', name: 'jackson-dataformat-xml', version: '2.13.1'
testRuntimeOnly 'com.h2database:h2:2.1.214'
testImplementation 'org.junit.jupiter:junit-jupiter-api:5.8.1'
testRuntimeOnly 'org.junit.jupiter:junit-jupiter-engine:5.8.1'
testImplementation 'org.springframework.boot:spring-boot-starter-test:2.6.15'
testImplementation 'junit:junit:4.4'
}
test {
useJUnitPlatform()
}
publishing {
repositories {
maven {
name = 'eactiveRepository'
def releasesRepoUrl = "${nexusUrl}/repository/maven-releases/"
def snapshotsRepoUrl = "${nexusUrl}/repository/maven-snapshots/"
url = version.endsWith('SNAPSHOT') ? snapshotsRepoUrl : releasesRepoUrl
credentials(PasswordCredentials)
}
}
publications {
mavenJava(MavenPublication) {
from components.java
pom {
description = "eLink common module"
licenses {
license {
name = "Commercial License"
url = "http://eactive.co.kr"
}
}
}
}
}
}
task sourcesJar(type: Jar, dependsOn: classes) {
archiveClassifier = 'sources'
from sourceSets.main.allSource
}
artifacts {
archives sourcesJar
}
configurations.all {
exclude group: 'org.apache.geronimo.specs', module: 'geronimo-jta_1.0.1B_spec'
// exclude group: 'javax.transaction', module: 'javax.transaction-api'
resolutionStrategy {
// 동적 버전 탐색을 10분 캐시
cacheDynamicVersionsFor 10, 'minutes'
// 변하는 모듈(Changing Module)을 캐시하지 않음
cacheChangingModulesFor 0, 'seconds'
}
}
task settingEclipseEncoding {
if (project.file('.settings').exists()) {
File f = file('.settings/org.eclipse.core.resources.prefs')
f.write('eclipse.preferences.version=1\n')
f.append('encoding/<project>=utf-8')
}
}
task initDirs() {
file(generatedJavaDir).mkdirs()
}
eclipse {
synchronizationTasks settingEclipseEncoding, initDirs
jdt {
apt {
// generated 된 패스 경로를 .setting/org.eclipse.jdt.apt.core.prefs 의 org.eclipse.jdt.apt.genSrcDir에 적용한다.
// project > properties > Java Compiler > Annoation Processing 화면에서 확인 가능하다.
genSrcDir = file(generatedJavaDir)
}
}
project {
natures = ['org.eclipse.buildship.core.gradleprojectnature',
'org.eclipse.jdt.core.javanature',
'org.eclipse.wst.common.project.facet.core.nature',
'org.eclipse.wst.common.modulecore.ModuleCoreNature',
'org.eclipse.jem.workbench.JavaEMFNature']
buildCommand 'org.eclipse.buildship.core.gradleprojectbuilder'
buildCommand 'org.eclipse.wst.validation.validationbuilder'
buildCommand 'org.eclipse.wst.common.project.facet.core.builder'
buildCommand 'org.eclipse.jdt.core.javabuilder'
}
}
Binary file not shown.
+6
View File
@@ -0,0 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.7-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
networkTimeout=10000
Vendored
+234
View File
@@ -0,0 +1,234 @@
#!/bin/sh
#
# Copyright © 2015-2021 the original authors.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# https://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#
##############################################################################
#
# Gradle start up script for POSIX generated by Gradle.
#
# Important for running:
#
# (1) You need a POSIX-compliant shell to run this script. If your /bin/sh is
# noncompliant, but you have some other compliant shell such as ksh or
# bash, then to run this script, type that shell name before the whole
# command line, like:
#
# ksh Gradle
#
# Busybox and similar reduced shells will NOT work, because this script
# requires all of these POSIX shell features:
# * functions;
# * expansions «$var», «${var}», «${var:-default}», «${var+SET}»,
# «${var#prefix}», «${var%suffix}», and «$( cmd )»;
# * compound commands having a testable exit status, especially «case»;
# * various built-in commands including «command», «set», and «ulimit».
#
# Important for patching:
#
# (2) This script targets any POSIX shell, so it avoids extensions provided
# by Bash, Ksh, etc; in particular arrays are avoided.
#
# The "traditional" practice of packing multiple parameters into a
# space-separated string is a well documented source of bugs and security
# problems, so this is (mostly) avoided, by progressively accumulating
# options in "$@", and eventually passing that to Java.
#
# Where the inherited environment variables (DEFAULT_JVM_OPTS, JAVA_OPTS,
# and GRADLE_OPTS) rely on word-splitting, this is performed explicitly;
# see the in-line comments for details.
#
# There are tweaks for specific operating systems such as AIX, CygWin,
# Darwin, MinGW, and NonStop.
#
# (3) This script is generated from the Groovy template
# https://github.com/gradle/gradle/blob/master/subprojects/plugins/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt
# within the Gradle project.
#
# You can find Gradle at https://github.com/gradle/gradle/.
#
##############################################################################
# Attempt to set APP_HOME
# Resolve links: $0 may be a link
app_path=$0
# Need this for daisy-chained symlinks.
while
APP_HOME=${app_path%"${app_path##*/}"} # leaves a trailing /; empty if no leading path
[ -h "$app_path" ]
do
ls=$( ls -ld "$app_path" )
link=${ls#*' -> '}
case $link in #(
/*) app_path=$link ;; #(
*) app_path=$APP_HOME$link ;;
esac
done
APP_HOME=$( cd "${APP_HOME:-./}" && pwd -P ) || exit
APP_NAME="Gradle"
APP_BASE_NAME=${0##*/}
# Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"'
# Use the maximum available, or set MAX_FD != -1 to use that value.
MAX_FD=maximum
warn () {
echo "$*"
} >&2
die () {
echo
echo "$*"
echo
exit 1
} >&2
# OS specific support (must be 'true' or 'false').
cygwin=false
msys=false
darwin=false
nonstop=false
case "$( uname )" in #(
CYGWIN* ) cygwin=true ;; #(
Darwin* ) darwin=true ;; #(
MSYS* | MINGW* ) msys=true ;; #(
NONSTOP* ) nonstop=true ;;
esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
# IBM's JDK on AIX uses strange locations for the executables
JAVACMD=$JAVA_HOME/jre/sh/java
else
JAVACMD=$JAVA_HOME/bin/java
fi
if [ ! -x "$JAVACMD" ] ; then
die "ERROR: JAVA_HOME is set to an invalid directory: $JAVA_HOME
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
else
JAVACMD=java
which java >/dev/null 2>&1 || die "ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
Please set the JAVA_HOME variable in your environment to match the
location of your Java installation."
fi
# Increase the maximum file descriptors if we can.
if ! "$cygwin" && ! "$darwin" && ! "$nonstop" ; then
case $MAX_FD in #(
max*)
MAX_FD=$( ulimit -H -n ) ||
warn "Could not query maximum file descriptor limit"
esac
case $MAX_FD in #(
'' | soft) :;; #(
*)
ulimit -n "$MAX_FD" ||
warn "Could not set maximum file descriptor limit to $MAX_FD"
esac
fi
# Collect all arguments for the java command, stacking in reverse order:
# * args from the command line
# * the main class name
# * -classpath
# * -D...appname settings
# * --module-path (only if needed)
# * DEFAULT_JVM_OPTS, JAVA_OPTS, and GRADLE_OPTS environment variables.
# For Cygwin or MSYS, switch paths to Windows format before running java
if "$cygwin" || "$msys" ; then
APP_HOME=$( cygpath --path --mixed "$APP_HOME" )
CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" )
JAVACMD=$( cygpath --unix "$JAVACMD" )
# Now convert the arguments - kludge to limit ourselves to /bin/sh
for arg do
if
case $arg in #(
-*) false ;; # don't mess with options #(
/?*) t=${arg#/} t=/${t%%/*} # looks like a POSIX filepath
[ -e "$t" ] ;; #(
*) false ;;
esac
then
arg=$( cygpath --path --ignore --mixed "$arg" )
fi
# Roll the args list around exactly as many times as the number of
# args, so each arg winds up back in the position where it started, but
# possibly modified.
#
# NB: a `for` loop captures its iteration list before it begins, so
# changing the positional parameters here affects neither the number of
# iterations, nor the values presented in `arg`.
shift # remove old arg
set -- "$@" "$arg" # push replacement arg
done
fi
# Collect all arguments for the java command;
# * $DEFAULT_JVM_OPTS, $JAVA_OPTS, and $GRADLE_OPTS can contain fragments of
# shell script including quotes and variable substitutions, so put them in
# double quotes to make sure that they get re-expanded; and
# * put everything else in single quotes, so that it's not re-expanded.
set -- \
"-Dorg.gradle.appname=$APP_BASE_NAME" \
-classpath "$CLASSPATH" \
org.gradle.wrapper.GradleWrapperMain \
"$@"
# Use "xargs" to parse quoted args.
#
# With -n1 it outputs one arg per line, with the quotes and backslashes removed.
#
# In Bash we could simply go:
#
# readarray ARGS < <( xargs -n1 <<<"$var" ) &&
# set -- "${ARGS[@]}" "$@"
#
# but POSIX shell has neither arrays nor command substitution, so instead we
# post-process each arg (as a line of input to sed) to backslash-escape any
# character that might be a shell metacharacter, then use eval to reverse
# that process (while maintaining the separation between arguments), and wrap
# the whole thing up as a single "set" statement.
#
# This will of course break if any of these variables contains a newline or
# an unmatched quote.
#
eval "set -- $(
printf '%s\n' "$DEFAULT_JVM_OPTS $JAVA_OPTS $GRADLE_OPTS" |
xargs -n1 |
sed ' s~[^-[:alnum:]+,./:=@_]~\\&~g; ' |
tr '\n' ' '
)" '"$@"'
exec "$JAVACMD" "$@"
Vendored
+89
View File
@@ -0,0 +1,89 @@
@rem
@rem Copyright 2015 the original author or authors.
@rem
@rem Licensed under the Apache License, Version 2.0 (the "License");
@rem you may not use this file except in compliance with the License.
@rem You may obtain a copy of the License at
@rem
@rem https://www.apache.org/licenses/LICENSE-2.0
@rem
@rem Unless required by applicable law or agreed to in writing, software
@rem distributed under the License is distributed on an "AS IS" BASIS,
@rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@rem See the License for the specific language governing permissions and
@rem limitations under the License.
@rem
@if "%DEBUG%" == "" @echo off
@rem ##########################################################################
@rem
@rem Gradle startup script for Windows
@rem
@rem ##########################################################################
@rem Set local scope for the variables with windows NT shell
if "%OS%"=="Windows_NT" setlocal
set DIRNAME=%~dp0
if "%DIRNAME%" == "" set DIRNAME=.
set APP_BASE_NAME=%~n0
set APP_HOME=%DIRNAME%
@rem Resolve any "." and ".." in APP_HOME to make it shorter.
for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi
@rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script.
set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m"
@rem Find java.exe
if defined JAVA_HOME goto findJavaFromJavaHome
set JAVA_EXE=java.exe
%JAVA_EXE% -version >NUL 2>&1
if "%ERRORLEVEL%" == "0" goto execute
echo.
echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH.
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:findJavaFromJavaHome
set JAVA_HOME=%JAVA_HOME:"=%
set JAVA_EXE=%JAVA_HOME%/bin/java.exe
if exist "%JAVA_EXE%" goto execute
echo.
echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME%
echo.
echo Please set the JAVA_HOME variable in your environment to match the
echo location of your Java installation.
goto fail
:execute
@rem Setup the command line
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %*
:end
@rem End local scope for the variables with windows NT shell
if "%ERRORLEVEL%"=="0" goto mainEnd
:fail
rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of
rem the _cmd.exe /c_ return code!
if not "" == "%GRADLE_EXIT_CONSOLE%" exit 1
exit /b 1
:mainEnd
if "%OS%"=="Windows_NT" endlocal
:omega
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
BIN
View File
Binary file not shown.
BIN
View File
Binary file not shown.
+29
View File
@@ -0,0 +1,29 @@
#-----------------------------------------------------------------------------
# comment start with #
# level; // 0 : root ~ n
# type; // 0: Message, 1: Field, 2:Group 3, Grid, 4 : Field Array, 9 : BIZ DATA
# size // 0 : variable, > 0 fixed
# fieldType; // 0: ELEMENT, 1: ATTRIBUTE,
# length;
# dataType; // 1: String, 2: Number,11: ZZ String, 12: LL Number
#-----------------------------------------------------------------------------
# name ,level ,type ,size ,fieldType ,length ,dataType ,,refPath, refValue,value
#-----------------------------------------------------------------------------
ElinkHeader ,0,0,1,0, 0,0,,,
Header ,1,2,1,1, 0,0,,,
StndCicsTrncd ,2,1,1,1,10,0,,,
StndIntnlStndTelgmLen,2,1,1,1,10,11,,,0
StndTranBaseYmd ,2,1,1,1,10,0,,,
Common ,1,2,0,0, 0,0,Header.StndCicsTrncd,JI6H,null
TranInfo ,2,2,1,0, 0,0,,,
StndCicsTrncd ,3,1,1,0, 3,0,,,
StndTelgmRecvTranCd ,3,1,1,0,10,0,,,
StndPrcssRtdTranCd ,3,1,1,0,10,0,,,
Array ,1,3,0,0, 3,0,,,
Item1 ,2,1,1,0,10,0,,,JI6H
Group ,2,3,1,0, 1,0,,,
gitem1 ,3,1,1,0,10,1,,,726
gitem2 ,3,1,1,0,10,0,,,20220905
FArray ,1,4,0,0,10,0,,,
bizData ,1,9,1,0, 0,0,,,
zzData ,1,1,1,0, 2,10,,,ZZ
1 #-----------------------------------------------------------------------------
2 # comment start with #
3 # level; // 0 : root ~ n
4 # type; // 0: Message, 1: Field, 2:Group 3, Grid, 4 : Field Array, 9 : BIZ DATA
5 # size // 0 : variable, > 0 fixed
6 # fieldType; // 0: ELEMENT, 1: ATTRIBUTE,
7 # length;
8 # dataType; // 1: String, 2: Number,11: ZZ String, 12: LL Number
9 #-----------------------------------------------------------------------------
10 # name ,level ,type ,size ,fieldType ,length ,dataType ,,refPath, refValue,value
11 #-----------------------------------------------------------------------------
12 ElinkHeader ,0,0,1,0, 0,0,,,
13 Header ,1,2,1,1, 0,0,,,
14 StndCicsTrncd ,2,1,1,1,10,0,,,
15 StndIntnlStndTelgmLen,2,1,1,1,10,11,,,0
16 StndTranBaseYmd ,2,1,1,1,10,0,,,
17 Common ,1,2,0,0, 0,0,Header.StndCicsTrncd,JI6H,null
18 TranInfo ,2,2,1,0, 0,0,,,
19 StndCicsTrncd ,3,1,1,0, 3,0,,,
20 StndTelgmRecvTranCd ,3,1,1,0,10,0,,,
21 StndPrcssRtdTranCd ,3,1,1,0,10,0,,,
22 Array ,1,3,0,0, 3,0,,,
23 Item1 ,2,1,1,0,10,0,,,JI6H
24 Group ,2,3,1,0, 1,0,,,
25 gitem1 ,3,1,1,0,10,1,,,726
26 gitem2 ,3,1,1,0,10,0,,,20220905
27 FArray ,1,4,0,0,10,0,,,
28 bizData ,1,9,1,0, 0,0,,,
29 zzData ,1,1,1,0, 2,10,,,ZZ
+41
View File
@@ -0,0 +1,41 @@
#-----------------------------------------------------------------------------
# comment start with #
# level; // 0 : root ~ n
# type; // 0: Message, 1: Field, 2:Group 3, Grid, 4 : Field Array, 9 : BIZ DATA
# size // 0 : variable, > 0 fixed
# fieldType; // 0: ELEMENT, 1: ATTRIBUTE,
# length;
# dataType; // 1: String, 2: Number,11: ZZ String, 12: LL Number
#-----------------------------------------------------------------------------
# name ,level ,type ,size ,fieldType ,length ,dataType ,,refPath, refValue,value
#-----------------------------------------------------------------------------
# name ,level ,type ,size ,fieldType ,length ,dataType ,refPath, refValue, value
STD_HNCPHEADER_REQ ,0 ,1 ,1 ,1 ,0 ,1 , , ,,표준헤더
msg_len ,1 ,2 ,1 ,1 ,6 ,12 , , ,199,전문길이
global_id ,1 ,2 ,1 ,1 ,29 ,1 , , ,GIDNO00000000001111,Global아이디
service_id ,1 ,2 ,1 ,1 ,10 ,1 , , ,ELINKSVC01,거래코드
service_cmt ,1 ,2 ,1 ,1 ,100 ,1 , , ,ELINK TEST Service,거래코드설명
service_tn ,1 ,2 ,1 ,1 ,1 ,1 , , ,1,거래구분
Session_id ,1 ,2 ,1 ,1 ,100 ,1 , , ,SESSIONID001,Session아이디
encrypt_yn ,1 ,2 ,1 ,1 ,2 ,1 , , ,NO,전문암호화여부
http_url ,1 ,2 ,1 ,1 ,100 ,1 , , ,,HTTPURL정보
screen_id ,1 ,2 ,1 ,1 ,13 ,1 , , ,SCREEN0000001,화면ID
scr_no ,1 ,2 ,1 ,1 ,30 ,1 , , ,000000000100000000020000000003,화면번호
scr_dsc ,1 ,2 ,1 ,1 ,100 ,1 , , ,,화면명
usr_id ,1 ,2 ,1 ,1 ,10 ,1 , , ,USER000001,사용자ID
ip_addr ,1 ,2 ,1 ,1 ,47 ,1 , , ,,IPAddress
ip_mac ,1 ,2 ,1 ,1 ,12 ,1 , , ,,ClientMAC Address
com_code ,1 ,2 ,1 ,1 ,4 ,1 , , ,EACT,그룹사코드
head_code ,1 ,2 ,1 ,1 ,7 ,1 , , ,EACT001,본부코드
dept_cd ,1 ,2 ,1 ,1 ,7 ,1 , , ,ELINK01,부서코드
conn_tp ,1 ,2 ,1 ,1 ,2 ,1 , , ,CH,요청채널구분
Inter_chn ,1 ,2 ,1 ,1 ,2 ,1 , , ,EA,시스템구분
recv_tm ,1 ,2 ,1 ,1 ,17 ,1 , , ,20220928000000000,전문수신시간
send_tm ,1 ,2 ,1 ,1 ,17 ,1 , , ,,전문송신시간
return_gubun ,1 ,2 ,1 ,1 ,1 ,1 , , ,S,전문응답구분
return_value ,1 ,2 ,1 ,1 ,1 ,1 , , ,,처리결과
msg_id ,1 ,2 ,1 ,1 ,7 ,1 , , ,,오류코드
msg_nm ,1 ,2 ,1 ,1 ,250 ,1 , , ,,오류메시지
filler ,1 ,2 ,1 ,1 ,125 ,1 , , ,,Filler
bizData ,1 ,9 ,0 ,1 ,0 ,1 , , ,,업무데이터
zzData ,1 ,2 ,0 ,1 ,2 ,11 , , ,,ZZ플래그
1 #-----------------------------------------------------------------------------
2 # comment start with #
3 # level; // 0 : root ~ n
4 # type; // 0: Message, 1: Field, 2:Group 3, Grid, 4 : Field Array, 9 : BIZ DATA
5 # size // 0 : variable, > 0 fixed
6 # fieldType; // 0: ELEMENT, 1: ATTRIBUTE,
7 # length;
8 # dataType; // 1: String, 2: Number,11: ZZ String, 12: LL Number
9 #-----------------------------------------------------------------------------
10 # name ,level ,type ,size ,fieldType ,length ,dataType ,,refPath, refValue,value
11 #-----------------------------------------------------------------------------
12 # name ,level ,type ,size ,fieldType ,length ,dataType ,refPath, refValue, value
13 STD_HNCPHEADER_REQ ,0 ,1 ,1 ,1 ,0 ,1 , , ,,표준헤더
14 msg_len ,1 ,2 ,1 ,1 ,6 ,12 , , ,199,전문길이
15 global_id ,1 ,2 ,1 ,1 ,29 ,1 , , ,GIDNO00000000001111,Global아이디
16 service_id ,1 ,2 ,1 ,1 ,10 ,1 , , ,ELINKSVC01,거래코드
17 service_cmt ,1 ,2 ,1 ,1 ,100 ,1 , , ,ELINK TEST Service,거래코드설명
18 service_tn ,1 ,2 ,1 ,1 ,1 ,1 , , ,1,거래구분
19 Session_id ,1 ,2 ,1 ,1 ,100 ,1 , , ,SESSIONID001,Session아이디
20 encrypt_yn ,1 ,2 ,1 ,1 ,2 ,1 , , ,NO,전문암호화여부
21 http_url ,1 ,2 ,1 ,1 ,100 ,1 , , ,,HTTPURL정보
22 screen_id ,1 ,2 ,1 ,1 ,13 ,1 , , ,SCREEN0000001,화면ID
23 scr_no ,1 ,2 ,1 ,1 ,30 ,1 , , ,000000000100000000020000000003,화면번호
24 scr_dsc ,1 ,2 ,1 ,1 ,100 ,1 , , ,,화면명
25 usr_id ,1 ,2 ,1 ,1 ,10 ,1 , , ,USER000001,사용자ID
26 ip_addr ,1 ,2 ,1 ,1 ,47 ,1 , , ,,IPAddress
27 ip_mac ,1 ,2 ,1 ,1 ,12 ,1 , , ,,ClientMAC Address
28 com_code ,1 ,2 ,1 ,1 ,4 ,1 , , ,EACT,그룹사코드
29 head_code ,1 ,2 ,1 ,1 ,7 ,1 , , ,EACT001,본부코드
30 dept_cd ,1 ,2 ,1 ,1 ,7 ,1 , , ,ELINK01,부서코드
31 conn_tp ,1 ,2 ,1 ,1 ,2 ,1 , , ,CH,요청채널구분
32 Inter_chn ,1 ,2 ,1 ,1 ,2 ,1 , , ,EA,시스템구분
33 recv_tm ,1 ,2 ,1 ,1 ,17 ,1 , , ,20220928000000000,전문수신시간
34 send_tm ,1 ,2 ,1 ,1 ,17 ,1 , , ,,전문송신시간
35 return_gubun ,1 ,2 ,1 ,1 ,1 ,1 , , ,S,전문응답구분
36 return_value ,1 ,2 ,1 ,1 ,1 ,1 , , ,,처리결과
37 msg_id ,1 ,2 ,1 ,1 ,7 ,1 , , ,,오류코드
38 msg_nm ,1 ,2 ,1 ,1 ,250 ,1 , , ,,오류메시지
39 filler ,1 ,2 ,1 ,1 ,125 ,1 , , ,,Filler
40 bizData ,1 ,9 ,0 ,1 ,0 ,1 , , ,,업무데이터
41 zzData ,1 ,2 ,0 ,1 ,2 ,11 , , ,,ZZ플래그
@@ -0,0 +1,11 @@
layout.file.type=CSV
layout.file.path=./resources/standard-layout-sample.csv
mapper.class=com.eactive.eai.message.test.TestInterfaceMapper
mapper.definition=./resources/standard-message-mapping-config.properties
reader.JSON=com.eactive.eai.message.parser.JsonReader
reader.JSN=com.eactive.eai.message.parser.JsonReader
reader.UJN=com.eactive.eai.message.parser.JsonReader
reader.XML=com.eactive.eai.message.parser.XmlReader
reader.UXL=com.eactive.eai.message.parser.XmlReader
reader.ASC=com.eactive.eai.message.parser.FlatReader
reader.FLAT=com.eactive.eai.message.parser.FlatReader
@@ -0,0 +1,20 @@
# layout : StandardMessage layout definition
layout.file.type=CSV
layout.file.path=./resources/standard-layout.csv
layout.filter.FLAT=com.eactive.eai.message.filter.FlatMessageFilter
# mapper : StandardMessage's fields getter/setter interface
mapper.class=com.eactive.eai.message.service.DefaultInterfaceMapper
mapper.definition=./resources/standard-message-mapping-config.properties
# reader : parsing input data to StandardMessage
reader.JSON=com.eactive.eai.message.parser.JsonReader
reader.JSN=com.eactive.eai.message.parser.JsonReader
reader.UJN=com.eactive.eai.message.parser.JsonReader
reader.XML=com.eactive.eai.message.parser.XmlReader
reader.UXL=com.eactive.eai.message.parser.XmlReader
reader.ASC=com.eactive.eai.message.parser.FlatReader
reader.FLAT=com.eactive.eai.message.parser.FlatReader
encode.flat=euc-kr
encode.value=euc-kr
encode.xml=utf-8
# version.layout.name=VERSION_SAMPLE
# version.mapper.definition=./resources/version-message-mapping-config.properties
@@ -0,0 +1,28 @@
REQ_SYS_CODE=systemHeader.DMND_SYS_CD
CHANNEL_TYPE_CD=stdcommon.chnlTycd
CHANNEL_DETAIL_CD=stdcommon.chnlDtlsClcd
SEND_TIME=stdheader.send_tm
GUID=stdheader.global_id
SYSTEM_TYPE=stdheader.Inter_chn
RECV_TIME=stdheader.recv_tm
RETURN_VALUE=stdheader.return_value
GUID_ORG=stdcommon.ortrGuid
GUID_SEQ=stdheader.global_id
#SERVICE_ID=stdheader.service_id
SERVICE_ID=service_id
RETURN_SERVICE_ID=stdcommon.procsRsltRcmsSrvcId
INTERFACE_ID=stdheader.service_id
SESSION_ID=stdheader.Session_id
#SEND_RECV_DIVISION=stdheader.return_gubun
SEND_RECV_DIVISION=service_tn
IN_EX_DIVISION=stdcommon.hmabDvcd
OPERATION_ENV=stdcommon.sysOprtEnvDvcd
FIRST_REQ_IP=stdheader.ip_addr
RECOVER_YN=stdcommon.ortrRestrYn
INST_CODE=stdheader.com_code
TIMEOUT=stdheader.gnrzTmotTktm
ERROR_CODE=stdheader.msg_id
ERROR_MSG=stdheader.msg_nm
USER_ID=stdheader.usr_id
RESPONSE_TYPE=stdcommon.procsRsltDvcd
SYNC_ASYNC_TYPE=stdcommon.txSynzDvcd
@@ -0,0 +1,26 @@
REQ_SYS_CODE=Inter_chn
CHANNEL_TYPE_CD=
CHANNEL_DETAIL_CD=conn_tp
SEND_TIME=send_tm
GUID=global_id
SYSTEM_TYPE=service_tn
RECV_TIME=recv_tm
RETURN_VALUE=return_value
GUID_ORG=stdcommon.ortrGuid
GUID_SEQ=stdheader.global_id
SERVICE_ID=service_id
RETURN_SERVICE_ID=stdcommon.procsRsltRcmsSrvcId
INTERFACE_ID=service_id
SESSION_ID=Session_id
SEND_RECV_DIVISION=service_tn
IN_EX_DIVISION=stdcommon.hmabDvcd
OPERATION_ENV=stdcommon.sysOprtEnvDvcd
FIRST_REQ_IP=ip_addr
RECOVER_YN=stdcommon.ortrRestrYn
INST_CODE=stdheader.com_code
TIMEOUT=stdheader.gnrzTmotTktm
ERROR_CODE=msg_id
ERROR_MSG=msg_nm
USER_ID=usr_id
RESPONSE_TYPE=stdcommon.procsRsltDvcd
SYNC_ASYNC_TYPE=stdcommon.txSynzDvcd
@@ -0,0 +1,4 @@
service_id=header.if_id
global_id=header.guid
service_tn=header.req_type
bizData=bizData
+9
View File
@@ -0,0 +1,9 @@
rootProject.name = 'elink-online-common'
include 'elink-online-core-jpa'
include 'elink-online-core'
include 'elink-online-transformer'
project (':elink-online-core-jpa').projectDir = new File(settingsDir, "../elink-online-core-jpa")
project (':elink-online-core').projectDir = new File(settingsDir, "../elink-online-core")
project (':elink-online-transformer').projectDir = new File(settingsDir, "../elink-online-transformer")
+9
View File
@@ -0,0 +1,9 @@
<?xml version="1.0" encoding="UTF-8"?>
<persistence version="2.2"
xmlns="http://xmlns.jcp.org/xml/ns/persistence"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/persistence http://xmlns.jcp.org/xml/ns/persistence/persistence_2_2.xsd">
<persistence-unit name="common">
</persistence-unit>
</persistence>
@@ -0,0 +1,82 @@
package com.eactive.eai.adapter;
import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.eactive.eai.adapter.loader.AdapterGroupLoader;
import com.eactive.eai.adapter.loader.AdapterLoader;
import com.eactive.eai.adapter.mapper.AdapterGroupMapper;
import com.eactive.eai.adapter.mapper.AdapterMapper;
import com.eactive.eai.common.dao.BaseDAO;
import com.eactive.eai.common.dao.DAOException;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.server.EAIServerManager;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.data.entity.onl.adapter.Adapter;
import com.eactive.eai.data.entity.onl.adapter.AdapterGroup;
@Service
@Transactional
public class AdapterDAO extends BaseDAO {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
@Autowired
private AdapterGroupLoader adapterGroupLoader;
@Autowired
private AdapterLoader adapterLoader;
@Autowired
private AdapterGroupMapper adapterGroupMapper;
@Autowired
private AdapterMapper adapterMapper;
public List<AdapterGroupVO> getAllAdapterGroups() throws DAOException {
try {
List<AdapterGroup> adapterGroups = adapterGroupLoader.selectAllGroups();
return adapterGroups.stream().map(adapterGroupMapper::toVo).collect(Collectors.toList());
} catch (Exception e) {
throw new DAOException(ExceptionUtil.getErrorCode(e, "RECEAIAAC001"));
}
}
public List<AdapterVO> getAllAdapters(String adapterGroupName) throws DAOException {
List<AdapterVO> al = new ArrayList<>();
try {
Iterable<Adapter> adapters = adapterLoader.selectAdaptersByGroup(
com.eactive.eai.common.server.Keys.DEFAULT_SERVER, adapterGroupName,
EAIServerManager.getInstance().getLocalServerName());
for (Adapter adapter : adapters) {
AdapterVO vo = adapterMapper.toVo(adapter);
al.add(vo);
}
return al;
} catch (Exception e) {
throw new DAOException(ExceptionUtil.getErrorCode(e, "RECEAIAAC002"));
}
}
public AdapterGroupVO getAdapterGroup(String adapterGroupName) throws DAOException {
try {
AdapterGroup adapterGroup = adapterGroupLoader.getById(adapterGroupName);
AdapterGroupVO gvo = adapterGroupMapper.toVo(adapterGroup);
List<AdapterVO> adapterVos = adapterGroup.getAdapters().stream().map(adapterMapper::toVo)
.collect(Collectors.toList());
adapterVos.forEach(gvo::addAdapterVO);
return gvo;
} catch (Exception e) {
throw new DAOException(ExceptionUtil.getErrorCode(e, "RECEAIAAC009"));
}
}
}
@@ -0,0 +1,569 @@
package com.eactive.eai.adapter;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.Vector;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicInteger;
import org.apache.commons.lang3.StringUtils;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.lifecycle.Lifecycle;
import com.eactive.eai.common.lifecycle.LifecycleException;
import com.eactive.eai.common.lifecycle.LifecycleListener;
import com.eactive.eai.common.lifecycle.LifecycleSupport;
import com.eactive.eai.common.util.Logger;
public class AdapterGroupVO implements Serializable, Lifecycle {
private static final long serialVersionUID = -8613631838169562236L;
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private String name; // 어뎁터업무그룹명[TSEAIAD01.ADPTRBZWKGROUPNAME]
private String adptrMsgPtrnCd; // 어댑터메시지유형코드[TSEAIAD01.ADPTRMSGPTRNCD] //[K, N, S] 값을 가짐
private String eaiBizCode; // EAI업무구분코드[TSEAIAD01.EAIBZWKDSTCD]
private String type; // 어댑터코드[TSEAIAD01.ADPTRCD]
private String messageType; // 어댑터메시지구분코드[TSEAIAD01.ADPTRMSGDSTCD]
private String messageEncode; // 어댑터메시지구분코드[TSEAIAD01.MSGENCODE]
private String gubun; // 어뎁터입출력구분코드[TSEAIAD01.ADPTRIODSTCD]
private String refClass; // 참고클래스명[TSEAIAD01.REFCLSNAME]
private boolean srLogFlag; // 송수신시각로그여부[TSEAIAD01.SNDRCVHMSLOGYN]
private boolean usedFlag; // 어댑터사용여부[TSEAIAD01.ADPTRUSEYN]
private boolean spcfcLUUseYn; // 특정LU사용여부[TSEAIAD01.SPCFCLUUSEYN] -> 용도변경 : 로그밸런싱 방식으로 사용 RR/LC
private String description; // 어댑터업무그룹설명[TSEAIAD01.ADPTRBZWKGROUPDESC]
private String osidInstiNo; // 대외기관번호[TSEAIAD01.OSIDINSTINO]
// KESA F/W사용여부[TSEAIAD01.KESAUSEYN]
// 0 : KESA 미사용, 1: nKESA 사용, 2: uKESA 사용, 3: zKESA 사용
private String kesaUseYn;
// 0 : 기본어댑터, 1: TAS어댑터, 2: TAS참조대표어댑터
private String testMasterYn;
private String adptrNickName;
private Map<String, AdapterVO> adapters;
private Vector<AdapterVO> actives;
private Vector<AdapterVO> disables;
private List<String> adapterNames;
private String companyCodeData; // 업체코드데이터 (업체코드 추출정보 등록)
private String adptrInstiCode; // 어댑터업체코드
private String bidInterface; // MCI에서 bid 거래시의 대표 인터페이스
private AtomicInteger idx = new AtomicInteger(0);
private boolean started;
private LifecycleSupport lifecycle = new LifecycleSupport(this);
private int currentTx;
private long successTx;
private long errorTx;
private String linkedAdapterGroup;
private String sameSessionYn;
private String pairAdapterYn;
private String clientId;
private boolean weighted = false;
public AdapterGroupVO() {
this("");
}
public AdapterGroupVO(String name) {
this.name = name;
this.adapters = new ConcurrentHashMap<>();
this.actives = new Vector<>();
this.disables = new Vector<>();
this.adapterNames = new ArrayList<>();
}
public boolean isWeighted() {
return weighted;
}
public void setWeighted(boolean weighted) {
this.weighted = weighted;
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return this.name;
}
public void setEaiBizCode(String eaiBizCode) {
this.eaiBizCode = eaiBizCode;
}
public String getEaiBizCode() {
return this.eaiBizCode;
}
public void setType(String type) {
this.type = type;
}
public String getType() {
return this.type;
}
public void setGubun(String gubun) {
this.gubun = gubun;
}
public String getGubun() {
return this.gubun;
}
public void setMessageType(String messageType) {
this.messageType = messageType;
}
public String getMessageType() {
return this.messageType;
}
public String getMessageEncode() {
return messageEncode;
}
public void setMessageEncode(String messageEncode) {
this.messageEncode = messageEncode;
}
public void setRefClass(String refClass) {
this.refClass = refClass;
}
public String getRefClass() {
return this.refClass;
}
public void setSrLogFlag(boolean srLogFlag) {
this.srLogFlag = srLogFlag;
}
public boolean isSrLogFlag() {
return this.srLogFlag;
}
public void setUsedFlag(boolean usedFlag) {
this.usedFlag = usedFlag;
}
public boolean isUsedFlag() {
return this.usedFlag;
}
public void setDescription(String description) {
this.description = description;
}
public String getDescription() {
return this.description;
}
public void setSpcfcLUUseYn(boolean spcfcLUUseYn) {
this.spcfcLUUseYn = spcfcLUUseYn;
}
public boolean isSpcfcLUUseYn() {
return this.spcfcLUUseYn;
}
public void setAdptrMsgPtrnCd(String adptrMsgPtrnCd) {
this.adptrMsgPtrnCd = adptrMsgPtrnCd;
}
public String getAdptrMsgPtrnCd() {
return this.adptrMsgPtrnCd;
}
public String getOsidInstiNo() {
return osidInstiNo;
}
public void setOsidInstiNo(String osidInstiNo) {
this.osidInstiNo = osidInstiNo;
}
public String getKesaUseYn() {
return kesaUseYn;
}
public void setKesaUseYn(String kesaUseYn) {
this.kesaUseYn = kesaUseYn;
}
public String getTestMasterYn() {
return testMasterYn;
}
public void setTestMasterYn(String testMasterYn) {
this.testMasterYn = testMasterYn;
}
public String getAdptrNickName() {
return adptrNickName;
}
public void setAdptrNickName(String adptrNickName) {
this.adptrNickName = adptrNickName;
}
public String getCompanyCodeData() {
return companyCodeData;
}
public void setCompanyCodeData(String companyCodeData) {
this.companyCodeData = companyCodeData;
}
public String getAdptrInstiCode() {
return adptrInstiCode;
}
public void setAdptrInstiCode(String adptrInstiCode) {
this.adptrInstiCode = adptrInstiCode;
}
public String getBidInterface() {
return bidInterface;
}
public void setBidInterface(String bidInterface) {
this.bidInterface = bidInterface;
}
public String getClientId() { return clientId; }
public void setClientId(String clientId) {
this.clientId = clientId;
}
public synchronized void addAdapterVO(AdapterVO avo) {
this.adapters.put(avo.getName(), avo);
this.adapterNames.add(avo.getName());
}
public AdapterVO getAdapterVO(String adapterName) {
return adapters.get(adapterName);
}
public synchronized void increase() {
++currentTx;
}
public synchronized void decrease() {
--currentTx;
}
public int currentTx() {
return this.currentTx;
}
// GW관련 어댑터 카운터 추가-시작
public synchronized void increaseSuccess() {
++successTx;
}
public synchronized void increaseError() {
++errorTx;
}
public long successTx() {
return this.successTx;
}
public long errorTx() {
return this.errorTx;
}
public synchronized void resetCount() {
this.successTx = 0;
this.errorTx = 0;
}
// GW관련 어댑터 카운터 추가-종료
public String getLinkedAdapterGroup() {
return linkedAdapterGroup;
}
public void setLinkedAdapterGroup(String linkedAdapterGroup) {
this.linkedAdapterGroup = linkedAdapterGroup;
}
public String getSameSessionYn() {
return sameSessionYn;
}
public void setSameSessionYn(String sameSessionYn) {
this.sameSessionYn = sameSessionYn;
}
public String getPairAdapterYn() {
return pairAdapterYn;
}
public void setPairAdapterYn(String pairAdapterYn) {
this.pairAdapterYn = pairAdapterYn;
}
public void start() throws LifecycleException {
if (started)
throw new LifecycleException("RECEAIAAC030");
// Notify our interested LifecycleListeners
lifecycle.fireLifecycleEvent(STARTING_EVENT, this);
if (!this.usedFlag) {
String code = "RECEAIAAC040";
String[] msgArgs = new String[1];
msgArgs[0] = name;
String errText = ExceptionUtil.make(code, msgArgs);
if (logger.isError())
logger.error(errText);
throw new LifecycleException(errText);
}
setWeighted(false);
idx.set(0);
AdapterVO avo = null;
Iterator<AdapterVO> it = adapters.values().iterator();
while (it.hasNext()) {
avo = it.next();
if (avo instanceof Lifecycle) {
try {
LifecycleListener[] listeners = this.lifecycle.findLifecycleListeners();
if (listeners != null) {
for (int j = 0; j < listeners.length; j++) {
avo.addLifecycleListener(listeners[j]);
}
}
// 어댑터 프라퍼티에 active_onstartup = false 일 경우
// EAI 서버 기동시에 Adapter를 start하지 않는다.
boolean activeOnstartup = true;
AdapterPropManager manager = AdapterPropManager.getInstance();
String activeOnstartupValue = manager.getProperty(avo.getPropGroupName(), "active_onstartup");
if (activeOnstartupValue != null && "false".equals(activeOnstartupValue.trim())) {
activeOnstartup = false;
}
String lbWeight = manager.getProperty(avo.getPropGroupName(), Keys.LB_WEIGHT);
if(StringUtils.isNoneEmpty(lbWeight)) {
int weight = 1;
try {
weight = Integer.parseInt(lbWeight);
}
catch(NumberFormatException ex) {
weight = 1;
}
if(weight > 1) setWeighted(true);
avo.setWeight(weight);
}
avo.setAdapterGroupVO(this);
if (activeOnstartup) {
avo.start();
} else {
disable(avo);
}
} catch (Exception e) {
disable(avo);
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAIAAC031") + " : " + this.name, e);
}
}
}
started = true;
lifecycle.fireLifecycleEvent(STARTED_EVENT, this);
}
public void stop() throws LifecycleException {
if (!started)
throw new LifecycleException("RECEAIAAC032");
lifecycle.fireLifecycleEvent(STOPING_EVENT, this);
AdapterVO avo = null;
Iterator<AdapterVO> it = adapters.values().iterator();
while (it.hasNext()) {
avo = it.next();
if (!avo.isStarted())
continue;
if (avo instanceof Lifecycle) {
try {
avo.stop();
} catch (Exception e) {
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAIAAC033") + " : " + this.name, e);
}
}
}
started = false;
lifecycle.fireLifecycleEvent(STOPPED_EVENT, this);
}
public boolean isStarted() {
return this.started;
}
public void active(AdapterVO vo) {
if (!this.actives.contains(vo) && vo.isStatus()) {
this.actives.add(vo);
this.disables.remove(vo);
}
}
public void disable(AdapterVO vo) {
if (!this.disables.contains(vo) && !vo.isStatus()) {
this.disables.add(vo);
this.actives.remove(vo);
}
}
public boolean isAlive() {
return !this.actives.isEmpty();
}
public void addLifecycleListener(LifecycleListener listener) {
lifecycle.addLifecycleListener(listener);
}
public LifecycleListener[] findLifecycleListeners() {
return lifecycle.findLifecycleListeners();
}
public void removeLifecycleListener(LifecycleListener listener) {
lifecycle.removeLifecycleListener(listener);
}
public Iterator<AdapterVO> getAdapters() {
return this.adapters.values().iterator();
}
public String[] getAdapterNames() {
String[] names = new String[this.adapterNames.size()];
for (int i = 0; i < names.length; i++) {
names[i] = this.adapterNames.get(i);
}
return names;
}
public synchronized AdapterVO nextAdapterVO() {
if (this.actives.isEmpty()) {
return null;
}
if (this.actives.size() == 1) {
return this.actives.get(0);
}
if(spcfcLUUseYn) {
if(logger.isDebug()) logger.debug("nextAdapterVO selectWithLeastConnection");
return selectWithLeastConnection();
}
else {
if(isWeighted()) {
if(logger.isDebug()) logger.debug("nextAdapterVO selectWithWeightedRoundRobin");
return selectWithWeightedRoundRobin();
}
else {
if(logger.isDebug()) logger.debug("nextAdapterVO selectWithRoundRobin");
return selectWithRoundRobin();
}
}
}
private AdapterVO selectWithRoundRobin() {
try {
if (idx.get() >= this.actives.size())
idx.set(0);
return this.actives.get(idx.getAndIncrement());
} catch (Exception e) {
if (this.actives.isEmpty())
return null;
idx.set(0);
return this.actives.get(idx.getAndIncrement());
}
}
private AdapterVO selectWithWeightedRoundRobin() {
try {
int totalWeight = actives.stream().mapToInt(AdapterVO::getWeight).sum();
int currentIndex = idx.getAndIncrement() % totalWeight;
for (AdapterVO adapter : actives) {
currentIndex -= adapter.getWeight();
if (currentIndex < 0) {
return adapter;
}
}
return this.actives.get(0);
} catch (Exception e) {
if (this.actives.isEmpty())
return null;
idx.set(0);
return this.actives.get(idx.getAndIncrement());
}
}
private AdapterVO selectWithLeastConnection() {
try {
AdapterVO selected = this.actives.get(0);
for (AdapterVO adapter : this.actives) {
if (adapter.getRequestCount() < selected.getRequestCount()) {
selected = adapter;
}
}
return selected;
} catch (Exception e) {
if (this.actives.isEmpty())
return null;
return this.actives.get(0);
}
}
public synchronized void removeAdapterVO(String name) {
adapters.remove(name);
this.adapterNames.remove(name);
}
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("AdapterGroupVO[ name=").append(name);
sb.append(", adptrMsgPtrnCd=").append(adptrMsgPtrnCd);
sb.append(", eaiBizCode=").append(eaiBizCode);
sb.append(", type=").append(type);
sb.append(", messageType=").append(messageType);
sb.append(", messageEncode=").append(messageEncode);
sb.append(", gubun=").append(gubun);
sb.append(", refClass=").append(refClass);
sb.append(", srLogFlag=").append(srLogFlag);
sb.append(", usedFlag=").append(usedFlag);
sb.append(", spcfcLUUseYn=").append(spcfcLUUseYn);
sb.append(", description=").append(description);
sb.append(", osidInstiNo=").append(osidInstiNo);
sb.append(", kesaUseYn=").append(kesaUseYn);
sb.append(", testMasterYn=").append(testMasterYn);
sb.append(", adptrNickName=").append(adptrNickName);
sb.append(", companyCodeData=").append(companyCodeData);
sb.append(", adptrInstiCode=").append(adptrInstiCode);
sb.append(", bidInterface=").append(bidInterface);
sb.append(", actives=").append(this.actives.size());
sb.append(", disables=").append(this.disables.size());
sb.append(", AdapterList=").append(adapters);
sb.append(", clientId=").append(clientId);
sb.append(" ]");
return sb.toString();
}
}
@@ -0,0 +1,217 @@
package com.eactive.eai.adapter;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import com.eactive.eai.common.dao.DAOException;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.lifecycle.Lifecycle;
import com.eactive.eai.common.lifecycle.LifecycleException;
import com.eactive.eai.common.lifecycle.LifecycleListener;
import com.eactive.eai.common.lifecycle.LifecycleSupport;
import com.eactive.eai.common.util.ApplicationContextProvider;
import com.eactive.eai.common.util.Logger;
@Component
public class AdapterManager implements Lifecycle {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private boolean started;
private HashMap<String, AdapterGroupVO> adapterGroups = new HashMap<>();
private LifecycleSupport lifecycle = new LifecycleSupport(this);
@Autowired
private AdapterDAO adapterDAO;
public static AdapterManager getInstance() {
return ApplicationContextProvider.getContext().getBean(AdapterManager.class);
}
public void start() throws LifecycleException {
if (started)
throw new LifecycleException("RECEAIAAC015");
lifecycle.fireLifecycleEvent(STARTING_EVENT, this);
this.adapterGroups.clear();
List<AdapterGroupVO> groups = null;
try {
adapterDAO = ApplicationContextProvider.getContext().getBean(AdapterDAO.class);
groups = adapterDAO.getAllAdapterGroups();
} catch (Exception e) {
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAIAAC016"));
}
for (AdapterGroupVO gvo : groups) {
List<AdapterVO> adapterVos = null;
try {
adapterVos = adapterDAO.getAllAdapters(gvo.getName());
for (AdapterVO vo : adapterVos) {
gvo.addAdapterVO(vo);
}
} catch (DAOException e) {
if (logger.isError())
logger.error(ExceptionUtil.getErrorCode(e, "RECEAIAAC017"));
continue;
}
if (logger.isDebug()) {
String[] msgArgs = new String[1];
msgArgs[0] = gvo.toString();
logger.debug(ExceptionUtil.make("RDCEAIAAC018", msgArgs));
}
addAdapterGroupVO(gvo);
try {
LifecycleListener[] listeners = this.lifecycle.findLifecycleListeners();
if (listeners != null) {
for (int j = 0; j < listeners.length; j++) {
gvo.addLifecycleListener(listeners[j]);
}
}
if (!gvo.isUsedFlag()) {
if (logger.isDebug())
logger.debug("Not Used Adapter>> " + gvo);
continue;
}
gvo.start();
} catch (Exception e) {
if (logger.isError())
logger.error(ExceptionUtil.getErrorCode(e, "RECEAIAAC019"));
}
}
started = true;
lifecycle.fireLifecycleEvent(STARTED_EVENT, this);
}
public void stop() throws LifecycleException {
if (!started)
throw new LifecycleException("RECEAIAAC020");
lifecycle.fireLifecycleEvent(STOPING_EVENT, this);
logger.warn("Stop Inbound Adapters ...");
for (Iterator<AdapterGroupVO> it = this.adapterGroups.values().iterator(); it.hasNext();) {
AdapterGroupVO vo = it.next();
if ("I".equals(vo.getGubun())) {
try {
if (!vo.isStarted()) {
logger.warn("AdapterGroup not started skip stop. - " + vo);
continue;
}
if (vo instanceof Lifecycle) {
vo.stop();
}
} catch (LifecycleException e) {
String[] msgArgs = { vo.toString() };
String errText = ExceptionUtil.make("RECEAIAAC021", msgArgs);
if (logger.isError())
logger.error(errText);
}
}
}
logger.warn("Stop Outbound Adapters ...");
for (Iterator<AdapterGroupVO> it = this.adapterGroups.values().iterator(); it.hasNext();) {
AdapterGroupVO vo = it.next();
if (!"I".equals(vo.getGubun())) {
try {
if (!vo.isStarted())
continue;
if (vo instanceof Lifecycle) {
vo.stop();
}
} catch (LifecycleException e) {
String[] msgArgs = new String[1];
msgArgs[0] = vo.toString();
String errText = ExceptionUtil.make("RECEAIAAC021", msgArgs);
if (logger.isError())
logger.error(errText);
}
}
}
started = false;
lifecycle.fireLifecycleEvent(STOPPED_EVENT, this);
}
public boolean isStarted() {
return this.started;
}
public void addLifecycleListener(LifecycleListener listener) {
lifecycle.addLifecycleListener(listener);
}
public LifecycleListener[] findLifecycleListeners() {
return lifecycle.findLifecycleListeners();
}
public void removeLifecycleListener(LifecycleListener listener) {
lifecycle.removeLifecycleListener(listener);
}
public AdapterVO getAdapterVO(String adapterGroupName, String adapterName) {
AdapterGroupVO gvo = adapterGroups.get(adapterGroupName);
if (gvo == null)
return null;
return gvo.getAdapterVO(adapterName);
}
public AdapterGroupVO getAdapterGroupVO(String adapterGroupName) {
return adapterGroups.get(adapterGroupName);
}
public AdapterGroupVO getAdapterGroup(String adapterGroupName) throws DAOException {
return adapterGroups.get(adapterGroupName);
}
public AdapterGroupVO loadAdapterGroup(String adapterGroupName) throws DAOException {
return adapterDAO.getAdapterGroup(adapterGroupName);
}
public void addAdapterGroupVO(AdapterGroupVO vo) {
if (vo != null) {
adapterGroups.put(vo.getName(), vo);
}
}
public HashMap<String, AdapterGroupVO> getAllAdapterGroupVO() {
return adapterGroups;
}
public List<String> getAllAdapterGroupNames() {
ArrayList<String> al = new ArrayList<>();
Iterator<String> it = this.adapterGroups.keySet().iterator();
while (it.hasNext()) {
al.add(it.next());
}
Collections.sort(al);
return al;
}
public void updateAdapterGroupVO(AdapterGroupVO vo) {
if (vo != null)
adapterGroups.put(vo.getName(), vo);
}
public void removeAdapterGroupVO(String name) {
adapterGroups.remove(name);
}
public void print() {
if (logger.isDebug())
logger.debug("AdapterManager] All Adapter List>> " + this.adapterGroups);
}
}
@@ -0,0 +1,65 @@
package com.eactive.eai.adapter;
import java.util.HashMap;
import java.util.Map;
import java.util.stream.Collectors;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import com.eactive.eai.adapter.loader.AdapterPropGroupLoader;
import com.eactive.eai.common.dao.BaseDAO;
import com.eactive.eai.common.dao.DAOException;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.data.entity.onl.adapter.AdapterPropGroup;
@Service
@Transactional
public class AdapterPropGroupDAO extends BaseDAO {
private static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
@Autowired
private AdapterPropGroupLoader adapterPropGroupLoader;
public Map<String, AdapterPropGroupVO> getAllProperties() throws DAOException {
Map<String, AdapterPropGroupVO> adapterPropGroupVos = new HashMap<>();
try {
logger.info("[ @@ Load Adapter Properties Configuration - starting >>>>>>>>>>>>>>>>> ]");
Iterable<AdapterPropGroup> adapterPropGroups = adapterPropGroupLoader
.loadAll()
.collect(Collectors.toList());
for (AdapterPropGroup adapterPropGroup : adapterPropGroups) {
AdapterPropGroupVO adapterPropGroupVO = getProperties(adapterPropGroup);
adapterPropGroupVos.put(adapterPropGroup.getPrptygroupname(), adapterPropGroupVO);
}
logger.info("[>>Load Adapter Properties Configuration - ended ]");
return adapterPropGroupVos;
} catch (Exception e) {
throw new DAOException(ExceptionUtil.getErrorCode(e, "RECEAICPM101"));
}
}
private AdapterPropGroupVO getProperties(AdapterPropGroup adapterPropGroup) {
AdapterPropGroupVO adapterPropGroupVO = new AdapterPropGroupVO(adapterPropGroup.getPrptygroupname());
adapterPropGroup.getAdapterProps().forEach(adapterProp -> adapterPropGroupVO
.addProperty(adapterProp.getId().getPrptyname(), adapterProp.getPrpty2val()));
return adapterPropGroupVO;
}
public AdapterPropGroupVO getProperties(String grpNm) throws DAOException {
try {
AdapterPropGroup adapterPropGroup = adapterPropGroupLoader.getById(grpNm);
return getProperties(adapterPropGroup);
} catch (Exception e) {
throw new DAOException(ExceptionUtil.make("RECEAICPM103", grpNm));
}
}
}
@@ -0,0 +1,106 @@
package com.eactive.eai.adapter;
import java.io.Serializable;
import java.util.Arrays;
import java.util.Iterator;
import java.util.Properties;
import com.eactive.eai.common.util.NullControl;
/**
* 1. 기능 : 어뎁터 프라퍼티 정보를 를 정의한 Java Value Object 클래스
* 2. 처리 개요 : 어뎁터 프라퍼티 정보를 정의한다.
* * -
* 3. 주의사항
*
* @author :
* @version : v 1.0.0
* @see : 관련 기능을 참조
* @since :
* :
*/
public class AdapterPropGroupVO implements Serializable
{
private String name; //어뎁터 프라퍼티 그룹명[TSEAIAD14.PrptyGroupName]
private String description; //어뎁터 프라퍼티 그룹설명[TSEAIAD14.PrptyGroupDesc]
private Properties props; //어뎁터 프라퍼티 명, 프라퍼티2값[TSEAIAD15.PrptyName, TSEAIAD15.Prpty2Val]
public AdapterPropGroupVO() {
this("");
}
public AdapterPropGroupVO(String name) {
this(name,"");
}
public AdapterPropGroupVO(String name, String description) {
this.name = name;
this.description = description;
this.props = new Properties();
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return this.name;
}
public void setDescription(String description) {
this.description = description;
}
public String getDescription() {
return NullControl.trimSpace(this.description);
}
public String getProperty(String key) {
return (String)props.get(key);
}
public String getProperty(String key, String defaultValue) {
String value = (String)props.get(key);
return (value==null) ? defaultValue : value;
}
public void addProperty(String key, String value) {
props.put(key, NullControl.trimSpace(value));
}
public void setProperty(String key, String value) {
props.put(key,value);
}
public void removeProperty(String key) {
props.remove(key);
}
public String[] keys() {
Iterator it = this.props.keySet().iterator();
String[] propKeys = new String[this.props.size()];
for(int i = 0; it.hasNext(); i++){
propKeys[i] = (String)it.next();
}
Arrays.sort(propKeys);
return propKeys;
}
public Properties getProperties() {
return props;
}
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("AdapterPropGroupVO[ name=").append(name);
sb.append(", description=").append(description);
sb.append(", Properties=").append(props);
sb.append(" ]");
return sb.toString();
}
public void setProperties(Properties prop){
this.props = prop;
}
}
@@ -0,0 +1,185 @@
package com.eactive.eai.adapter;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.beans.PropertyChangeSupport;
import java.util.Arrays;
import java.util.Iterator;
import java.util.Map;
import java.util.Properties;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.lifecycle.Lifecycle;
import com.eactive.eai.common.lifecycle.LifecycleException;
import com.eactive.eai.common.lifecycle.LifecycleListener;
import com.eactive.eai.common.lifecycle.LifecycleSupport;
import com.eactive.eai.common.util.ApplicationContextProvider;
import com.eactive.eai.common.util.Logger;
@Component
public class AdapterPropManager implements Lifecycle {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private LifecycleSupport lifecycle = new LifecycleSupport(this);
private PropertyChangeSupport property = new PropertyChangeSupport(this);
private Map<String, AdapterPropGroupVO> groups;
private boolean started;
@Autowired
private AdapterPropGroupDAO adapterPropGroupDAO;
public static AdapterPropManager getInstance() {
return ApplicationContextProvider.getContext().getBean(AdapterPropManager.class);
}
public void addPropertyChangeListener(PropertyChangeListener listener) {
property.addPropertyChangeListener(listener);
}
public void removePropertyChangeListener(PropertyChangeListener listener) {
property.removePropertyChangeListener(listener);
}
private PropertyChangeEvent createEvent(AdapterPropGroupVO source, String propertyName, Object oldValue,
Object newValue) {
return new PropertyChangeEvent(source, propertyName, oldValue, newValue);
}
public boolean isStarted() {
return this.started;
}
public void start() throws LifecycleException {
if (started)
throw new LifecycleException("RECEAICPM201");
lifecycle.fireLifecycleEvent(STARTING_EVENT, this);
try {
init();
} catch (Exception e) {
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAICPM201"));
}
started = true;
if (logger.isWarn()) {
logger.warn("AdapterPropManager] It is started.");
}
lifecycle.fireLifecycleEvent(STARTED_EVENT, this);
}
private void init() throws Exception {
this.groups = adapterPropGroupDAO.getAllProperties();
}
public synchronized void reload() throws Exception {
if (logger.isWarn()) {
logger.warn("AdapterPropManager] reload all Started ...");
}
init();
if (logger.isWarn()) {
logger.warn("AdapterPropManager] reload all finished ...");
}
}
public synchronized void reload(String keyName) throws Exception {
AdapterPropGroupVO vo = adapterPropGroupDAO.getProperties(keyName);
if (vo != null) {
this.groups.put(keyName, vo);
} else {
throw new Exception("AdapterPropManager not found in Database : key[" + keyName + "]");
}
}
public void stop() throws LifecycleException {
if (!started)
throw new LifecycleException("RECEAICPM203");
lifecycle.fireLifecycleEvent(STOPING_EVENT, this);
started = false;
if (logger.isWarn()) {
logger.warn("AdapterPropManager] It is stopped.");
}
lifecycle.fireLifecycleEvent(STOPPED_EVENT, this);
}
public void addLifecycleListener(LifecycleListener listener) {
lifecycle.addLifecycleListener(listener);
}
public LifecycleListener[] findLifecycleListeners() {
return lifecycle.findLifecycleListeners();
}
public void removeLifecycleListener(LifecycleListener listener) {
lifecycle.removeLifecycleListener(listener);
}
public void addAdapterPropGroupVO(String name, String description) {
groups.put(name, new AdapterPropGroupVO(name, description));
}
public AdapterPropGroupVO getAdapterPropGroupVO(String name) {
return groups.get(name);
}
public String getProperty(String key) {
return getProperty(com.eactive.eai.common.server.Keys.DEFAULT_SERVER, key);
}
public String getProperty(String group, String key) {
AdapterPropGroupVO vo = groups.get(group);
if (vo == null)
return null;
return vo.getProperty(key);
}
public Properties getProperties(String group) {
AdapterPropGroupVO vo = groups.get(group);
if (vo == null)
throw new RuntimeException("Cannot find the Property Group in AdapterPropManager. - " + group);
if (vo.getProperties() == null) {
return new Properties();
}
return (Properties) vo.getProperties().clone();
}
public void setProperty(String group, String key, String value) {
AdapterPropGroupVO gvo = groups.get(group);
String oldValue = gvo.getProperty(key);
gvo.setProperty(key, value);
if (oldValue != null && !oldValue.equals(value)) {
property.firePropertyChange(createEvent(gvo, key, oldValue, value));
}
}
public void setAdapterPropGroupVO(String group, AdapterPropGroupVO vo) {
groups.put(group, vo);
}
public void removeAdapterPropGroupVO(String name) {
groups.remove(name);
}
public String[] getAllPropGroupNames() {
Iterator<String> it = this.groups.keySet().iterator();
String[] name = new String[this.groups.size()];
for (int i = 0; it.hasNext(); i++) {
name[i] = it.next();
}
Arrays.sort(name);
return name;
}
}
@@ -0,0 +1,271 @@
package com.eactive.eai.adapter;
import java.io.Serializable;
import org.apache.commons.lang3.StringUtils;
import com.eactive.eai.adapter.listener.AdapterException;
import com.eactive.eai.adapter.listener.AdapterListener;
import com.eactive.eai.adapter.listener.ListenerUtil;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.lifecycle.Lifecycle;
import com.eactive.eai.common.lifecycle.LifecycleException;
import com.eactive.eai.common.lifecycle.LifecycleListener;
import com.eactive.eai.common.lifecycle.LifecycleSupport;
import com.eactive.eai.common.testcall.TestCallManager;
import com.eactive.eai.common.util.Logger;
public class AdapterVO implements Serializable, Lifecycle {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private AdapterGroupVO adapterGroupVO; // 어댑터 그룹
private String adapterGroupName; // 어뎁터업무그룹명[TSEAIAD02.AdptrBzwkGroupName]
private String name; // 어뎁터업무명[TSEAIAD02.AdptrBzwkName]
private String eaiSevrInstncName; // 서버인스탄스명[TSEAIAD02.EAISevrInstncName] - migration added.
private String listenerClass; // 리스너클래스명[TSEAIAD02.LstnerClsName]
private String testCallClass; // 테스터클래스명[TSEAIAD02.TestClsName]
private String propGroupName; // 프라퍼티그룹명[TSEAIAD02.PrptyGroupName]
private String description; // 어댑터설명[TSEAIAD02.AdptrDesc]
private String propGroupDesc; // 프라퍼티그룹설명
private boolean status;
private transient AdapterListener adapterListener;
private boolean started;
private LifecycleSupport lifecycle = new LifecycleSupport(this);
private int requestCount;
private int weight;
public int getWeight() {
return weight;
}
public void setWeight(int weight) {
this.weight = weight;
}
public int getRequestCount() {
return requestCount;
}
public synchronized void incrementRequestCount() {
requestCount++;
}
public synchronized void decrementRequestCount() {
requestCount--;
}
public AdapterVO() {
this.requestCount = 0;
this.weight = 1;
}
public AdapterVO(String name) {
this.name = name;
this.requestCount = 0;
this.weight = 1;
}
public boolean isStarted() {
return this.started;
}
public void setAdapterGroupName(String adapterGroupName) {
this.adapterGroupName = adapterGroupName;
}
public String getAdapterGroupName() {
return this.adapterGroupName;
}
public void setName(String name) {
this.name = name;
}
public String getName() {
return this.name;
}
public void setListenerClass(String listenerClass) {
this.listenerClass = listenerClass;
}
public String getListenerClass() {
return this.listenerClass;
}
public void setTestCallClass(String testCallClass) {
this.testCallClass = testCallClass;
}
public String getTestCallClass() {
return this.testCallClass;
}
public void setPropGroupName(String propGroupName) {
this.propGroupName = propGroupName;
}
public String getPropGroupName() {
return this.propGroupName;
}
public void setAdapterGroupVO(AdapterGroupVO group) {
this.adapterGroupVO = group;
}
public AdapterGroupVO getAdapterGroupVO() {
return this.adapterGroupVO;
}
private void setStatus(boolean status, boolean checkTestCall) {
this.status = status;
if (checkTestCall && !this.status && this.testCallClass != null && !this.testCallClass.equals("")) {
TestCallManager tmanager = TestCallManager.getInstance();
try {
tmanager.addTester(this);
String[] msgArgs = new String[1];
msgArgs[0] = this.toString();
if (logger.isInfo())
logger.info(ExceptionUtil.make("RICEAIAAC034", msgArgs));
} catch (Exception e) {
throw new RuntimeException(ExceptionUtil.getErrorCode(e, "RICEAIAAC035"), e);
}
}
if (this.status) {
this.adapterGroupVO.active(this);
} else {
this.adapterGroupVO.disable(this);
}
}
public synchronized void setStatus(boolean status) {
setStatus(status, true);
}
public synchronized void setStatusForcely(boolean status) {
setStatus(status, false);
}
public synchronized boolean isStatus() {
return this.status;
}
public void start() throws LifecycleException {
if (started)
throw new LifecycleException("RECEAIAAC036");
lifecycle.fireLifecycleEvent(STARTING_EVENT, this);
if (StringUtils.isEmpty(listenerClass)) {
listenerClass = ListenerUtil.getDefaultListenerClass(adapterGroupVO.getType(), adapterGroupVO.getGubun());
if(logger.isWarn() && StringUtils.isNotEmpty(listenerClass)) {
logger.warn("Use DefaultListenerClass {} - {}",adapterGroupVO.getName(), listenerClass);
}
}
if (StringUtils.isNotEmpty(listenerClass)) {
try {
adapterListener = (AdapterListener) Class.forName(listenerClass).newInstance();
adapterListener.setAdapterInfo(this);
adapterListener.start();
} catch (Exception e) {
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAIAAC037"), e);
}
}
started = true;
// SocketAdapter 기동시에 설정하므로
// socket2일 때는 status 를 setting 하지 않음.
if (adapterListener == null) {
status = true;
this.adapterGroupVO.active(this);
} else {
if (!(adapterListener instanceof com.eactive.eai.adapter.socket2.SocketAdapterListener)) {
status = true;
} else {
this.adapterGroupVO.active(this);
}
}
lifecycle.fireLifecycleEvent(STARTED_EVENT, this);
if(logger.isWarn()) {
logger.warn("Adapter started {} {} - {}",adapterGroupVO.getName(), getName(), listenerClass);
}
}
public void stop() throws LifecycleException {
if (!started)
throw new LifecycleException("RECEAIAAC038");
lifecycle.fireLifecycleEvent(STOPING_EVENT, this);
try {
if (adapterListener != null)
adapterListener.stop();
} catch (AdapterException e) {
throw new LifecycleException(ExceptionUtil.getErrorCode(e, "RECEAIAAC039"), e);
}
started = false;
status = false;
this.adapterGroupVO.disable(this);
lifecycle.fireLifecycleEvent(STOPPED_EVENT, this);
}
public void addLifecycleListener(LifecycleListener listener) {
lifecycle.addLifecycleListener(listener);
}
public LifecycleListener[] findLifecycleListeners() {
return lifecycle.findLifecycleListeners();
}
public void removeLifecycleListener(LifecycleListener listener) {
lifecycle.removeLifecycleListener(listener);
}
public void setDescription(String description) {
this.description = description;
}
public String getDescription() {
return this.description;
}
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("AdapterVO[ name=").append(name);
sb.append(", adapterGroupName=").append(adapterGroupName);
sb.append(", eaiSevrInstncName=").append(eaiSevrInstncName);
sb.append(", listenerClass=").append(listenerClass);
sb.append(", testCallClass=").append(testCallClass);
sb.append(", propGroupName=").append(propGroupName);
sb.append(", description=").append(description);
sb.append(", status=").append(status);
sb.append(", requestCount=").append(requestCount);
sb.append(" ]");
return sb.toString();
}
public void setEaiSevrInstncName(String eaiSevrInstncName) {
this.eaiSevrInstncName = eaiSevrInstncName;
}
public String getEaiSevrInstncName() {
return this.eaiSevrInstncName;
}
public void setPropGroupDesc(String propGroupDesc) {
this.propGroupDesc = propGroupDesc;
}
public String getPropGroupDesc() {
return this.propGroupDesc;
}
}
@@ -0,0 +1,26 @@
package com.eactive.eai.adapter;
public class EAIException extends Exception {
private String code;
public EAIException(String code, String msg) {
super(msg);
this.code = code;
}
public EAIException(String msg) {
this("", msg);
}
public EAIException(Throwable cause) {
super(cause);
}
public EAIException(String msg, Throwable cause) {
super(msg, cause);
}
public String getExceptionCode() {
return this.code;
}
}
@@ -0,0 +1,11 @@
package com.eactive.eai.adapter;
import java.util.Properties;
// EAI 엔진에서 어댑터을 common하게 접근하기 위한 Interface
public interface ElinkAdapter {
public Object callService(String adapterGroupName, Properties prop, Object message, Properties tempProp)
throws Exception;
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception;
}
@@ -0,0 +1,75 @@
package com.eactive.eai.adapter;
import java.util.concurrent.ConcurrentHashMap;
import com.eactive.eai.adapter.amq.AMQSenderAdapter;
import com.eactive.eai.adapter.app.BusinessApplicationAdapter;
import com.eactive.eai.adapter.http.client.HttpClientAdapterMain;
import com.eactive.eai.adapter.jtc.JtcClientAdapter;
import com.eactive.eai.adapter.socket2.SocketAdapterFacade;
import com.eactive.eai.adapter.wca.SNAAdapterClient;
import com.eactive.eai.adapter.websocket.WebSocketAdapterFacade;
import com.eactive.eai.adapter.webt.WebTClientAdapter;
import com.eactive.eai.common.util.Logger;
public class ElinkAdapterFactory {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private static final ElinkAdapterFactory factory = new ElinkAdapterFactory();
private ConcurrentHashMap<String, ElinkAdapter> adapterMap;
private ElinkAdapterFactory() {
adapterMap = new ConcurrentHashMap<>();
}
public static ElinkAdapterFactory newInstance() {
return factory;
}
public ElinkAdapter getElinkAdapter(String adapterTypeName) throws Exception {
ElinkAdapter adapter = adapterMap.get(adapterTypeName);
if (adapter == null) {
adapter = createAdapter(adapterTypeName);
}
if (adapter == null) {
throw new RuntimeException("등록된 어댑터 타입을 찾을 수 없습니다. - " + adapterTypeName);
}
return adapter;
}
private ElinkAdapter createAdapter(String adapterTypeName) throws Exception {
if (adapterTypeName == null) {
return null;
}
ElinkAdapter adapter = null;
if (adapterTypeName.equals(Keys.TYPE_HTTP)) {
adapter = new HttpClientAdapterMain();
adapterMap.put(Keys.TYPE_HTTP, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_NET2)) {
adapter = SocketAdapterFacade.getInstance();
adapterMap.put(Keys.TYPE_NET2, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_WSK)) {
adapter = WebSocketAdapterFacade.getInstance();
adapterMap.put(Keys.TYPE_WSK, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_WBT)) {
adapter = new WebTClientAdapter();
adapterMap.put(Keys.TYPE_WBT, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_JTC)) {
adapter = new JtcClientAdapter();
adapterMap.put(Keys.TYPE_JTC, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_APP)) {
adapter = new BusinessApplicationAdapter();
adapterMap.put(Keys.TYPE_APP, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_SNA)) {
adapter = new SNAAdapterClient();
adapterMap.put(Keys.TYPE_SNA, adapter);
} else if (adapterTypeName.equals(Keys.TYPE_AMQ)) {
adapter = new AMQSenderAdapter();
adapterMap.put(Keys.TYPE_SNA, adapter);
} else {
logger.warn("Unknown adapter type : " + adapterTypeName);
}
return adapter;
}
}
@@ -0,0 +1,65 @@
package com.eactive.eai.adapter;
import java.net.SocketTimeoutException;
import java.nio.charset.Charset;
import java.util.Properties;
import org.apache.commons.lang3.StringUtils;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.Logger;
public class ElinkDefaultAdapter implements ElinkAdapter {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private AdapterManager manager;
public ElinkDefaultAdapter() {
this.manager = AdapterManager.getInstance();
}
public Object callService(String adapterGroupName, Properties prop, Object message, Properties tempProp)
throws Exception {
String adapterName = tempProp.getProperty(com.eactive.eai.adapter.Keys.OUT_ADAPTER_NAME);
AdapterGroupVO group = this.manager.getAdapterGroupVO(adapterGroupName);
if (group == null) {
String code = "RECEAIAAC027";
String[] msgArgs = new String[1];
msgArgs[0] = adapterGroupName;
String errText = ExceptionUtil.make(code, msgArgs);
if (logger.isError())
logger.error(errText);
throw new Exception(errText);
}
AdapterVO adapterVO = null;
if(StringUtils.isNotEmpty(adapterName)) {
adapterVO = group.getAdapterVO(adapterName);
}
group.increase();
tempProp.setProperty(com.eactive.eai.adapter.Keys.OUT_ADAPTER_GROUP_NAME, adapterGroupName);
// set AdapterGroup charset
tempProp.setProperty(com.eactive.eai.adapter.Keys.CHARSET_KEY_OUT,
StringUtils.defaultIfBlank(group.getMessageEncode(), Charset.defaultCharset().name()));
try {
if(adapterVO != null) adapterVO.incrementRequestCount();
return execute(prop, message, tempProp);
} catch (SocketTimeoutException ste) {
throw ste;
} catch (HttpStatusException hse) {
throw hse;
} catch (Exception e) {
throw e;
} finally {
group.decrease();
if(adapterVO != null) adapterVO.decrementRequestCount();
}
}
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception {
throw new java.lang.UnsupportedOperationException("RECEAIAAC029");
}
}
@@ -0,0 +1,48 @@
package com.eactive.eai.adapter;
// adapter 패키지에서 사용하는 상수를 정의한 Interface
public interface Keys {
public static final String OUT_ADAPTER_GROUP_NAME = "OUT_ADAPTER_GROUP_NAME";
public static final String OUT_ADAPTER_NAME = "OUT_ADAPTER_NAME";
public static final String GUBUN_IN = "INBOUND";
public static final String GUBUN_OUT = "OUTBOUND";
public static final String LB_WEIGHT = "LB_WEIGHT";
// inbound adapter charset
public static final String CHARSET_KEY_IN = "CHARSET_IN";
// outbound adapter charset
public static final String CHARSET_KEY_OUT = "CHARSET_OUT";
public static final String TYPE_HTTP = "HTT";
//HTTP custom port - undertow
public static final String TYPE_HTTP_CUSTOM = "HTC";
public static final String TYPE_REST = "RST";
public static final String TYPE_NET2 = "NET";
public static final String TYPE_SNA = "SNA";
public static final String TYPE_WSK = "WSK";
public static final String TYPE_WBT = "WBT";
public static final String TYPE_JTC = "JTC";
public static final String TYPE_JCO = "JCO";
public static final String TYPE_APP = "APP";
public static final String TYPE_AMQ = "AMQ";
public static final String IF_NONSTANDARD = "N";
public static final String IF_STANDARD = "K";
public static final String IF_SUBSTANDARD = "B";
public static final String TESTMASTER_DEFAULT = "0";
public static final String TESTMASTER_TAS = "1";
public static final String TESTMASTER_TAS_INFO = "2";
public static final String ADAPTRER_IN = "I";
public static final String ADAPTER_OUT = "O";
public static final String NO_KESA = "0";
public static final String N_KESA = "1";
public static final String U_KESA = "2";
public static final String Z_KESA = "3";
public static final String CARD_KESA = "C";
}
@@ -0,0 +1,136 @@
package com.eactive.eai.adapter;
import java.nio.charset.Charset;
import java.util.Properties;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.commons.lang3.StringUtils;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.message.MessageType;
import com.eactive.eai.common.server.EAIServerManager;
import com.eactive.eai.common.state.ElinkState;
import com.eactive.eai.common.state.ElinkStateException;
import com.eactive.eai.common.state.ElinkStateManager;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.inbound.processor.Processor;
import com.eactive.eai.inbound.processor.ProcessorFactory;
public class RequestDispatcher {
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private static boolean isTASEnabledEAIServer = true;
static {
EAIServerManager eaiServerManager = EAIServerManager.getInstance();
isTASEnabledEAIServer = eaiServerManager.isTASEnabledEAIServer();
}
private static ConcurrentHashMap<String, RequestDispatcher> dispatchers = new ConcurrentHashMap<>();
private String adapterGroupName;
private Processor processor;
private RequestDispatcher(String adapterGroupName) {
this.adapterGroupName = adapterGroupName;
processor = ProcessorFactory.newInstance();
}
public static RequestDispatcher getRequestDispatcher(String adapterGroupName) {
return dispatchers.computeIfAbsent(adapterGroupName, k -> new RequestDispatcher(adapterGroupName));
}
public Object handle(String adapterName, Object message, Properties prop) throws Exception {
AdapterManager manager = AdapterManager.getInstance();
String inAdapterGroupName = this.adapterGroupName;
String actionClass = "";
String adptrMsgPtrnCd = "";
String messageType = MessageType.ASC;
AdapterGroupVO group = manager.getAdapterGroupVO(inAdapterGroupName);
if (group == null) {
String code = "RECEAIAAC042";
String[] msgArgs = new String[2];
msgArgs[0] = adapterGroupName;
msgArgs[1] = adapterName;
String errText = ExceptionUtil.make(code, msgArgs);
if (logger.isError()) {
logger.error(errText);
}
throw new Exception(errText);
}
AdapterVO adapter = group.getAdapterVO(adapterName);
if (adapter == null) {
String code = "RECEAIAAC022";
String[] msgArgs = { adapterGroupName, adapterName, group.toString() };
String errText = ExceptionUtil.make(code, msgArgs);
if (logger.isError()) {
logger.error(errText);
}
throw new Exception(errText);
}
if (prop == null) {
prop = new Properties();
}
actionClass = group.getRefClass();
adptrMsgPtrnCd = group.getAdptrMsgPtrnCd();
messageType = group.getMessageType();
try {
prop.put(Processor.ADAPTER_GROUP_NAME, inAdapterGroupName);
prop.put(Processor.ADAPTER_NAME, adapterName);
prop.put(Processor.STD_MESSAGE, adptrMsgPtrnCd);
prop.put(Processor.REQUEST_ACTION, actionClass);
prop.put(Processor.MESSAGE_TYPE, messageType);
// set Inbound AdapterGroup charset
prop.setProperty(com.eactive.eai.adapter.Keys.CHARSET_KEY_IN,
StringUtils.defaultIfBlank(group.getMessageEncode(), Charset.defaultCharset().name()));
} catch (Exception e) {
throw new Exception(ExceptionUtil.getErrorCode(e, "RECEAIAAC024"));
}
Object obj = null;
// Check Elink lifecycle is STARTED
// otherwise reject this request
if(ElinkStateManager.getInstance().getState() != ElinkState.STARTED) {
logger.error("Elink STATE FAIL - " + ElinkStateManager.getInstance().getState());
throw new ElinkStateException("Elink STATE FAIL - " + ElinkStateManager.getInstance().getState());
}
try {
ElinkStateManager.getInstance().startRequest();
group.increase();
adapter.incrementRequestCount();
obj = processor.execute(message, prop);
group.increaseSuccess();
} catch (HttpStatusException e) {
group.increaseError();
throw e;
} catch (Exception e) {
group.increaseError();
throw new Exception(ExceptionUtil.getErrorCode(e, "RECEAIAAC025"));
} finally {
group.decrease();
adapter.decrementRequestCount();
ElinkStateManager.getInstance().completeRequest();
}
if (obj != null) {
return obj;
}
else {
if (message instanceof byte[]) {
return new byte[0];
} else if (message instanceof String) {
return "";
} else {
return new Object();
}
}
}
}
@@ -0,0 +1,30 @@
package com.eactive.eai.adapter.amq;
public class AMQAdapterConstants {
// adapter properties
public static final String PROP_BROKER_URL = "BROKER_URL";
public static final String PROP_USER_NAME = "BROKER_USER_NAME";
public static final String PROP_PASSWORD = "BROKER_PASSWORD";
public static final String PROP_POOL_MAX_CONNECTIONS = "POOL_MAX_CONNECTIONS";
public static final String PROP_POOL_IDLE_TIMEOUT = "POOL_IDLE_TIMEOUT";
public static final String PROP_POOL_EXPIRY_TIMEOUT = "POOL_EXPIRY_TIMEOUT";
public static final String PROP_REQUEST_QUEUE_NAME = "REQUEST_QUEUE_NAME";
public static final String PROP_REPLY_QUEUE_NAME = "REPLY_QUEUE_NAME";
public static final String PROP_MESSAGE_TIME_TO_LIVE = "MESSAGE_TIME_TO_LIVE";
public static final String PROP_MESSAGE_RECEIVE_TIMEOUT = "REPLY_MESSAGE_RECEIVE_TIMEOUT";
public static final String PROP_RECEIVE_QUEUE_NAME = "RECEIVE_QUEUE_NAME";
public static final String PROP_RECEIVE_MAX_CONCURRENT_CONSUMERS = "RECEIVE_MAX_CONCURRENT_CONSUMERS";
public static final String PROP_REPLY_POOL_MAX_CONNECTIONS = "REPLY_POOL_MAX_CONNECTIONS";
public static final String PROP_REPLY_POOL_IDLE_TIMEOUT = "REPLY_POOL_IDLE_TIMEOUT";
public static final String PROP_REPLY_POOL_EXPIRY_TIMEOUT = "REPLY_POOL_EXPIRY_TIMEOUT";
public static final String PROP_RELAY_PROPERTY_GROUP = "RELAY_PROPERTY_GROUP";
public static final String PROP_RELAY_REQUEST_PROPERTY_KEYS = "RELAY_REQUEST_PROPERTY_KEYS";
public static final String PROP_RELAY_RESPONSE_PROPERTY_KEYS = "RELAY_RESPONSE_PROPERTY_KEYS";
public static final String TEMP_INTERFACE_RESPONSE_TYPE = "INTERFACE_RESPONSE_TYPE";
public static final String TEMP_MESSAGE_TYPE = "MESSAGE_TYPE";
public static final int DEFAULT_POOL_MAX_CONNECTIONS = 8;
public static final long DEFAULT_MESSAGE_RECEIVE_TIMEOUT = 30;
}
@@ -0,0 +1,53 @@
package com.eactive.eai.adapter.amq;
import com.eactive.eai.adapter.listener.AdapterException;
import com.eactive.eai.adapter.listener.AdapterListenerSupport;
import com.eactive.eai.common.util.Logger;
/**
* @formatter:off
* ActiveMQ 어댑터 LISTENER 클래스
* ActiveMQ 어댑터를 기동/중지한다
* @formatter:on
*/
public class AMQAdapterListener extends AdapterListenerSupport {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
@Override
public void start() throws AdapterException {
if (logger.isInfo()) {
logger.info("= AMQAdapterListener start.........");
}
try {
if (info == null) {
throw new Exception("AMQAdapterListener | AdapterVO가 NULL입니다.");
}
AMQAdapterManager manager = AMQAdapterManager.getInstance();
info.setStatus(true);
manager.start(info);
} catch (Throwable e) {
logger.error("[" + info.getName() + "] 구동 실패", e);
}
}
@Override
public void stop() throws AdapterException {
if (logger.isInfo()) {
logger.info("= AMQAdapterListener stop.........");
}
try {
if (info == null) {
throw new Exception("AMQAdapterListener | AdapterVO가 NULL입니다.");
}
AMQAdapterManager manager = AMQAdapterManager.getInstance();
manager.stop(info);
info.setStatus(false);
} catch (Throwable e) {
logger.error("[" + info.getName() + "] 중지 실패", e);
}
}
}
@@ -0,0 +1,127 @@
package com.eactive.eai.adapter.amq;
import java.util.Properties;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.activemq.ActiveMQConnectionFactory;
import org.apache.activemq.jms.pool.PooledConnectionFactory;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterPropManager;
import com.eactive.eai.adapter.AdapterVO;
import com.eactive.eai.agent.command.CommandException;
import com.eactive.eai.common.util.Logger;
public class AMQAdapterManager {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
private static AMQAdapterManager instance = new AMQAdapterManager();
// adapterName - Outbound Queue PooledConnectionFactory
private ConcurrentHashMap<String, PooledConnectionFactory> adapterConFacMap = new ConcurrentHashMap<>();
// adapterName - Inbound Queue Listener
private ConcurrentHashMap<String, AMQReceiverAdapter> receiverAdapterMap = new ConcurrentHashMap<>();
public static AMQAdapterManager getInstance() {
return instance;
}
public PooledConnectionFactory getOutboundPooledConnectionFactory(String adapterName) {
return adapterConFacMap.get(adapterName);
}
public void start(AdapterVO adapterVO) throws Exception {
if (logger.isDebug()) {
logger.debug("= AMQAdapterManager.start...");
}
AdapterGroupVO adapterGroupVO = adapterVO.getAdapterGroupVO();
AdapterPropManager propManager = AdapterPropManager.getInstance();
Properties queueProp = propManager.getProperties(adapterVO.getPropGroupName());
String brokerUrl = queueProp.getProperty(AMQAdapterConstants.PROP_BROKER_URL);
if (StringUtils.isBlank(brokerUrl)) {
throw new CommandException(AMQAdapterConstants.PROP_BROKER_URL + " is a required.");
}
if (StringUtils.equals(adapterGroupVO.getGubun(), "I")) {
AMQReceiverAdapter receiverAdapter = new AMQReceiverAdapter(adapterVO);
receiverAdapter.start();
receiverAdapterMap.put(adapterVO.getName(), receiverAdapter);
// Sync 거래일 경우 응답 Queue 연결
String replyQueue = queueProp.getProperty(AMQAdapterConstants.PROP_REPLY_QUEUE_NAME);
if (StringUtils.isNotBlank(replyQueue)) {
String userName = queueProp.getProperty(AMQAdapterConstants.PROP_USER_NAME);
String password = queueProp.getProperty(AMQAdapterConstants.PROP_PASSWORD);
String maxConnections = queueProp.getProperty(AMQAdapterConstants.PROP_REPLY_POOL_MAX_CONNECTIONS);
String idleTimeout = queueProp.getProperty(AMQAdapterConstants.PROP_REPLY_POOL_IDLE_TIMEOUT);
String expiryTimeout = queueProp.getProperty(AMQAdapterConstants.PROP_REPLY_POOL_EXPIRY_TIMEOUT);
adapterConFacMap.put(adapterVO.getName(), getPooledConnectionFactory(brokerUrl, userName, password,
maxConnections, idleTimeout, expiryTimeout));
}
} else {
String userName = queueProp.getProperty(AMQAdapterConstants.PROP_USER_NAME);
String password = queueProp.getProperty(AMQAdapterConstants.PROP_PASSWORD);
String maxConnections = queueProp.getProperty(AMQAdapterConstants.PROP_POOL_MAX_CONNECTIONS);
String idleTimeout = queueProp.getProperty(AMQAdapterConstants.PROP_POOL_IDLE_TIMEOUT);
String expiryTimeout = queueProp.getProperty(AMQAdapterConstants.PROP_POOL_EXPIRY_TIMEOUT);
adapterConFacMap.put(adapterVO.getName(), getPooledConnectionFactory(brokerUrl, userName, password,
maxConnections, idleTimeout, expiryTimeout));
}
}
public void stop(AdapterVO adapterVO) throws Exception {
AdapterGroupVO adapterGroupVO = adapterVO.getAdapterGroupVO();
if (StringUtils.equals(adapterGroupVO.getGubun(), "I")) {
AMQReceiverAdapter receiverAdapter = receiverAdapterMap.get(adapterVO.getName());
if (receiverAdapter != null) {
receiverAdapterMap.remove(adapterVO.getName());
receiverAdapter.stop();
}
// Sync 거래일 경우 응답 Queue 연결 해제
PooledConnectionFactory connectionFactory = adapterConFacMap.get(adapterVO.getName());
if (connectionFactory != null) {
adapterConFacMap.remove(adapterVO.getName());
connectionFactory.clear();
}
} else {
PooledConnectionFactory connectionFactory = adapterConFacMap.get(adapterVO.getName());
if (connectionFactory != null) {
adapterConFacMap.remove(adapterVO.getName());
connectionFactory.clear();
}
}
if (logger.isDebug()) {
logger.debug("= AMQAdapterManager.stoped...");
}
}
private PooledConnectionFactory getPooledConnectionFactory(String brokerUrl, String userName, String password,
String maxConnections, String idleTimeout, String expiryTimeout) throws Exception {
// Queue Connection pool 생성
ActiveMQConnectionFactory activeMQConnectionFactory = new ActiveMQConnectionFactory(brokerUrl);
if (StringUtils.isNotBlank(userName)) {
activeMQConnectionFactory.setUserName(userName);
activeMQConnectionFactory.setPassword(StringUtils.defaultString(password));
}
activeMQConnectionFactory.setTrustAllPackages(true);
PooledConnectionFactory connectionFactory = new PooledConnectionFactory();
connectionFactory.setConnectionFactory(activeMQConnectionFactory);
connectionFactory
.setMaxConnections(NumberUtils.toInt(maxConnections, AMQAdapterConstants.DEFAULT_POOL_MAX_CONNECTIONS));
if (NumberUtils.isParsable(idleTimeout)) {
connectionFactory.setIdleTimeout(NumberUtils.toInt(idleTimeout) * 1000);
}
if (NumberUtils.isParsable(expiryTimeout)) {
connectionFactory.setExpiryTimeout(NumberUtils.toLong(expiryTimeout) * 1000);
}
return connectionFactory;
}
}
@@ -0,0 +1,220 @@
package com.eactive.eai.adapter.amq;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageListener;
import javax.jms.Session;
import javax.jms.TextMessage;
import org.apache.activemq.ActiveMQConnectionFactory;
import org.apache.activemq.jms.pool.PooledConnectionFactory;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import org.springframework.jms.core.JmsTemplate;
import org.springframework.jms.core.MessageCreator;
import org.springframework.jms.listener.DefaultMessageListenerContainer;
import com.eactive.eai.adapter.AdapterPropManager;
import com.eactive.eai.adapter.AdapterVO;
import com.eactive.eai.adapter.RequestDispatcher;
import com.eactive.eai.adapter.http.dynamic.HttpAdapterServiceKey;
import com.eactive.eai.agent.command.CommandException;
import com.eactive.eai.common.message.MessageType;
import com.eactive.eai.common.util.Logger;
public class AMQReceiverAdapter {
private static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
private AdapterVO adapterVo;
DefaultMessageListenerContainer listenerContainer = null;
public AMQReceiverAdapter(AdapterVO adapterVo) {
this.adapterVo = adapterVo;
}
public void start() throws Exception {
AdapterPropManager propManager = AdapterPropManager.getInstance();
Properties queueProp = propManager.getProperties(adapterVo.getPropGroupName());
String brokerUrl = queueProp.getProperty(AMQAdapterConstants.PROP_BROKER_URL);
if (StringUtils.isBlank(brokerUrl)) {
throw new CommandException(AMQAdapterConstants.PROP_BROKER_URL + " is a required.");
}
String userName = queueProp.getProperty(AMQAdapterConstants.PROP_USER_NAME);
String password = queueProp.getProperty(AMQAdapterConstants.PROP_PASSWORD);
String receiveQueue = queueProp.getProperty(AMQAdapterConstants.PROP_RECEIVE_QUEUE_NAME);
if (StringUtils.isBlank(receiveQueue)) {
throw new Exception("No have receive Queue name");
}
String concurrency = queueProp.getProperty(AMQAdapterConstants.PROP_RECEIVE_MAX_CONCURRENT_CONSUMERS);
String replyQueue = queueProp.getProperty(AMQAdapterConstants.PROP_REPLY_QUEUE_NAME);
String relayPropertyGroup = queueProp.getProperty(AMQAdapterConstants.PROP_RELAY_PROPERTY_GROUP);
String relayRequestPropertyKeys = queueProp.getProperty(AMQAdapterConstants.PROP_RELAY_REQUEST_PROPERTY_KEYS);
// Queue Connection pool 생성
ActiveMQConnectionFactory connectionFactory = new ActiveMQConnectionFactory(brokerUrl);
if (StringUtils.isNotBlank(userName)) {
connectionFactory.setUserName(userName);
connectionFactory.setPassword(StringUtils.defaultString(password));
}
connectionFactory.setTrustAllPackages(true);
listenerContainer = new DefaultMessageListenerContainer();
listenerContainer.setConnectionFactory(connectionFactory);
listenerContainer.setDestinationName(receiveQueue);
if (NumberUtils.isParsable(concurrency)) {
listenerContainer.setConcurrency(concurrency);
}
listenerContainer.setMessageListener(new MessageListener() {
@Override
public void onMessage(Message message) {
try {
if (message instanceof TextMessage) {
if (logger.isDebug()) {
logger.debug("Received from " + receiveQueue + ": " + ((TextMessage) message).getText());
}
String receivedMsg = convertMessageToString(message);
Properties prop = new Properties();
// RestDataAdapterGroupParseRequestAction 오류 방지 위해 set
prop.setProperty(HttpAdapterServiceKey.INBOUND_METHOD, "QUEUE");
Object returnObject = RequestDispatcher.getRequestDispatcher(adapterVo.getAdapterGroupName())
.handle(adapterVo.getName(), receivedMsg, prop);
// reply queue가 설정되어 있으면(Sync) 전송
if (StringUtils.isNotBlank(replyQueue)) {
replyMessage((String) returnObject, replyQueue, relayPropertyGroup);
}
} else {
logger.error("Only supports TextMessage.");
throw new IllegalArgumentException(
"Only supports TextMessage: " + message.getClass().getName());
}
} catch (Exception e) {
logger.error(e.getMessage());
throw new RuntimeException(e);
}
}
@SuppressWarnings({ "deprecation", "unchecked" })
private String convertMessageToString(Message message) throws Exception {
String strMsg = ((TextMessage) message).getText();
// Queue property relay
if (MessageType.JSON.equals(adapterVo.getAdapterGroupVO().getMessageType())
&& StringUtils.isNotBlank(relayPropertyGroup)
&& StringUtils.isNotBlank(relayRequestPropertyKeys)) {
JSONObject jsonMessage = (JSONObject) JSONValue.parse(StringUtils.defaultString(strMsg));
JSONObject propertyJson = new JSONObject();
if (StringUtils.equalsIgnoreCase(relayRequestPropertyKeys, "ALL")) {
Enumeration<String> propertyNames = message.getPropertyNames();
while (propertyNames.hasMoreElements()) {
try {
String propertyName = propertyNames.nextElement();
propertyJson.put(propertyName, message.getStringProperty(propertyName));
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
}
} else {
String[] relayKeyArr = org.springframework.util.StringUtils
.tokenizeToStringArray(relayRequestPropertyKeys, ",");
for (String key : relayKeyArr) {
try {
String propertyValue = message.getStringProperty(key);
if (StringUtils.isNotBlank(propertyValue)) {
propertyJson.put(key, propertyValue);
}
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
}
}
if (propertyJson.size() > 0) {
jsonMessage.put(relayPropertyGroup, propertyJson);
strMsg = jsonMessage.toJSONString();
}
}
return strMsg;
}
private void replyMessage(String replyMessage, String replyQueue, String relayPropertyGroup)
throws Exception {
PooledConnectionFactory connectionFactory = AMQAdapterManager.getInstance()
.getOutboundPooledConnectionFactory(adapterVo.getName());
JmsTemplate jmsTemplate = new JmsTemplate(connectionFactory);
jmsTemplate.setExplicitQosEnabled(true);
jmsTemplate.setDeliveryPersistent(false);
jmsTemplate.send(replyQueue, new MessageCreator() {
@SuppressWarnings("deprecation")
public Message createMessage(Session session) throws JMSException {
String strMsg = replyMessage;
// relay to Queue property
HashMap<String, String> properties = new HashMap<>();
if (MessageType.JSON.equals(adapterVo.getAdapterGroupVO().getMessageType())
&& StringUtils.isNotBlank(relayPropertyGroup)
&& StringUtils.contains(replyMessage, relayPropertyGroup)) {
try {
JSONObject dataObject = (JSONObject) JSONValue.parse(replyMessage);
JSONObject propertyObject = (JSONObject) dataObject.get(relayPropertyGroup);
if (propertyObject != null) {
for (Object key : propertyObject.keySet()) {
Object obj = propertyObject.get(key);
if ((obj instanceof JSONObject) || (obj instanceof JSONArray)) {
continue;
}
properties.put((String) key, (String) obj);
}
dataObject.remove(relayPropertyGroup);
strMsg = dataObject.toJSONString();
}
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
}
Message ms = session.createTextMessage(strMsg);
for (Map.Entry<String, String> entry : properties.entrySet()) {
ms.setStringProperty(entry.getKey(), entry.getValue());
}
return ms;
}
});
}
});
listenerContainer.afterPropertiesSet();
listenerContainer.start();
}
public void stop() throws Exception {
if (listenerContainer != null) {
listenerContainer.stop();
listenerContainer.shutdown();
}
}
}
@@ -0,0 +1,358 @@
package com.eactive.eai.adapter.amq;
import java.nio.charset.Charset;
import java.util.Enumeration;
import java.util.Properties;
import java.util.UUID;
import javax.jms.Destination;
import javax.jms.JMSException;
import javax.jms.Message;
import javax.jms.MessageConsumer;
import javax.jms.MessageProducer;
import javax.jms.Session;
import javax.jms.TextMessage;
import org.apache.activemq.jms.pool.PooledConnectionFactory;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import org.springframework.jms.core.JmsTemplate;
import org.springframework.jms.core.MessageCreator;
import org.springframework.jms.core.SessionCallback;
import org.springframework.jms.support.JmsUtils;
import org.springframework.jms.support.destination.DestinationResolver;
import com.eactive.eai.adapter.ElinkDefaultAdapter;
import com.eactive.eai.adapter.Keys;
import com.eactive.eai.common.message.EAIMessageKeys;
import com.eactive.eai.common.message.MessageType;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.env.ElinkConfig;
public class AMQSenderAdapter extends ElinkDefaultAdapter {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
public static final String ADAPTER_NAME = "ADAPTER_NAME";
private static final class ProducerConsumer implements SessionCallback<Message> {
private final String msg;
private final DestinationResolver destinationResolver;
private final String queue;
private final String receiveQueue;
private final Long receiveTimeoutSeconds;
private final Long timeToLiveSeconds;
private final String messageType;
private final String relayPropertyGroup;
public ProducerConsumer(final String msg, String queue, String receiveQueue,
final DestinationResolver destinationResolver, Long receiveTimeoutSeconds, Long timeToLiveSeconds,
String messageType, String relayPropertyGroup) {
this.msg = msg;
this.queue = queue;
this.receiveQueue = receiveQueue;
this.destinationResolver = destinationResolver;
this.receiveTimeoutSeconds = receiveTimeoutSeconds;
this.timeToLiveSeconds = timeToLiveSeconds;
this.messageType = messageType;
this.relayPropertyGroup = relayPropertyGroup;
}
public Message doInJms(final Session session) throws JMSException {
MessageConsumer consumer = null;
MessageProducer producer = null;
try {
final String correlationId = UUID.randomUUID().toString();
if (logger.isDebug()) {
logger.debug("correlationId=====" + correlationId);
}
final Destination requestQueue = destinationResolver.resolveDestinationName(session, queue, false);
final Destination replyQueue = destinationResolver.resolveDestinationName(session, receiveQueue, false);
// Create the consumer first!
consumer = session.createConsumer(replyQueue, "JMSCorrelationID = '" + correlationId + "'");
JSONObject propObject = new JSONObject();
String strMsg = AMQSenderAdapter.extractRequestProperties(propObject, msg, messageType,
relayPropertyGroup);
final Message textMessage = session.createTextMessage(strMsg);
textMessage.setJMSCorrelationID(correlationId);
textMessage.setJMSReplyTo(replyQueue);
AMQSenderAdapter.assignRequestProperties(textMessage, propObject);
// Send the request second!
producer = session.createProducer(requestQueue);
if (timeToLiveSeconds != null) {
producer.setTimeToLive(timeToLiveSeconds.longValue() * 1000);
}
producer.send(requestQueue, textMessage);
// Block on receiving the response with a timeout
if (receiveTimeoutSeconds != null && receiveTimeoutSeconds.longValue() > 0) {
return consumer.receive(receiveTimeoutSeconds.longValue() * 1000);
} else {
return consumer.receive(AMQAdapterConstants.DEFAULT_MESSAGE_RECEIVE_TIMEOUT * 1000);
}
} catch (JMSException jmse) {
throw jmse;
} catch (Exception e) {
throw new JMSException(e.getMessage());
} finally {
JmsUtils.closeMessageConsumer(consumer);
JmsUtils.closeMessageProducer(producer);
}
}
}
@Override
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception {
String syncAsync = tempProp.getProperty(AMQAdapterConstants.TEMP_INTERFACE_RESPONSE_TYPE);
if (StringUtils.equals(syncAsync, EAIMessageKeys.ASYNC_SVC)) {
return executeAsync(prop, message, tempProp);
}
String sendQueue = prop.getProperty(AMQAdapterConstants.PROP_REQUEST_QUEUE_NAME);
if (StringUtils.isBlank(sendQueue)) {
throw new Exception("No have send Queue name");
}
String replyQueue = prop.getProperty(AMQAdapterConstants.PROP_REPLY_QUEUE_NAME);
if (StringUtils.isBlank(replyQueue)) {
throw new Exception("No have reply Queue name");
}
String timeToLive = prop.getProperty(AMQAdapterConstants.PROP_MESSAGE_TIME_TO_LIVE);
Long timeToLiveSeconds = null;
if (NumberUtils.isParsable(timeToLive)) {
timeToLiveSeconds = new Long(timeToLive);
}
String receiveTimeout = prop.getProperty(AMQAdapterConstants.PROP_MESSAGE_RECEIVE_TIMEOUT);
Long receiveTimeoutSeconds = AMQAdapterConstants.DEFAULT_MESSAGE_RECEIVE_TIMEOUT;
if (NumberUtils.isParsable(receiveTimeout)) {
receiveTimeoutSeconds = new Long(receiveTimeout);
}
// 인터페이스 정보에 설정된 타임아웃이 우선
String interfaceTimeout = tempProp.getProperty(com.eactive.eai.common.routing.Process.INTERFACE_TIME_OUT);
if (NumberUtils.isParsable(interfaceTimeout)) {
long miliseconds = NumberUtils.toLong(interfaceTimeout);
if (miliseconds >= 1000) {
receiveTimeoutSeconds = new Long(miliseconds / 1000);
}
}
String encode = tempProp.getProperty(Keys.CHARSET_KEY_OUT, Charset.defaultCharset().name());
String sendMsg = "";
if (message instanceof String) {
sendMsg = (String) message;
} else if (message instanceof byte[]) {
sendMsg = new String((byte[]) message, encode);
}
String relayPropertyGroup = prop.getProperty(AMQAdapterConstants.PROP_RELAY_PROPERTY_GROUP);
String relayResponsePropertyKeys = prop.getProperty(AMQAdapterConstants.PROP_RELAY_RESPONSE_PROPERTY_KEYS);
String messageType = tempProp.getProperty(AMQAdapterConstants.TEMP_MESSAGE_TYPE);
String adapterName = tempProp.getProperty(ADAPTER_NAME);
try {
PooledConnectionFactory connectionFactory = AMQAdapterManager.getInstance()
.getOutboundPooledConnectionFactory(adapterName);
JmsTemplate jmsTemplate = new JmsTemplate(connectionFactory);
jmsTemplate.setExplicitQosEnabled(true);
jmsTemplate.setDeliveryPersistent(false);
jmsTemplate.setReceiveTimeout(receiveTimeoutSeconds.longValue() * 1000);
if (timeToLiveSeconds != null) {
jmsTemplate.setTimeToLive(timeToLiveSeconds.longValue() * 1000);
}
Message receiveMessage = jmsTemplate
.execute(new ProducerConsumer(sendMsg, sendQueue, replyQueue, jmsTemplate.getDestinationResolver(),
receiveTimeoutSeconds, timeToLiveSeconds, messageType, relayPropertyGroup), true);
String returnMsg = "";
if (receiveMessage != null) {
returnMsg = assignResponseProperties(receiveMessage, messageType, relayPropertyGroup,
relayResponsePropertyKeys);
if (logger.isDebugEnabled()) {
logger.debug("AMQSenderAdapter] Received message: {}", returnMsg);
}
} else {
throw new JMSException(
"Received NULL(The timeout expires or this message consumer is concurrently closed)");
}
return returnMsg;
} catch (Exception e) {
logger.error("AMQSenderAdapter] Exception (" + adapterName + ") : " + e.getMessage(), e);
throw e;
} catch (Throwable t) {
logger.error("AMQSenderAdapter] Throwable (" + adapterName + ") : " + t.getMessage(), t);
throw t;
}
}
@SuppressWarnings({ "unchecked", "deprecation" })
private String assignResponseProperties(Message receiveMessage, String messageType, String relayPropertyGroup,
String relayResponsePropertyKeys) throws Exception {
if (!(receiveMessage instanceof TextMessage)) {
return receiveMessage.toString();
}
String returnMsg = ((TextMessage) receiveMessage).getText();
// Queue property to JSON
try {
if (MessageType.JSON.equals(messageType) && StringUtils.isNotBlank(relayPropertyGroup)
&& StringUtils.isNotBlank(relayResponsePropertyKeys)) {
String[] relayKeyArr = org.springframework.util.StringUtils
.tokenizeToStringArray(relayResponsePropertyKeys, ",");
JSONObject propertyJson = new JSONObject();
if (StringUtils.equalsIgnoreCase(relayResponsePropertyKeys, "ALL")) {
Enumeration<String> propertyNames = receiveMessage.getPropertyNames();
while (propertyNames.hasMoreElements()) {
String propertyName = propertyNames.nextElement();
propertyJson.put(propertyName, receiveMessage.getStringProperty(propertyName));
}
} else {
for (String key : relayKeyArr) {
String value = receiveMessage.getStringProperty(key);
if (value != null) {
propertyJson.put(key, value);
}
}
}
if (propertyJson.size() <= 0) {
return returnMsg;
}
JSONObject bodyJson = null;
if (StringUtils.isBlank(returnMsg)) {
bodyJson = new JSONObject();
} else {
bodyJson = (JSONObject) JSONValue.parse(returnMsg);
}
// malformed json message
if (bodyJson == null) {
return returnMsg;
}
bodyJson.put(relayPropertyGroup, propertyJson);
return bodyJson.toJSONString();
}
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
return returnMsg;
}
private Object executeAsync(Properties prop, Object message, Properties tempProp) throws Exception {
String sendQueue = prop.getProperty(AMQAdapterConstants.PROP_REQUEST_QUEUE_NAME);
if (StringUtils.isBlank(sendQueue)) {
throw new Exception("No have send Queue name");
}
String relayPropertyGroup = prop.getProperty(AMQAdapterConstants.PROP_RELAY_PROPERTY_GROUP);
String messageType = tempProp.getProperty(AMQAdapterConstants.TEMP_MESSAGE_TYPE);
String timeToLive = prop.getProperty(AMQAdapterConstants.PROP_MESSAGE_TIME_TO_LIVE);
String encode = tempProp.getProperty(Keys.CHARSET_KEY_OUT, Charset.defaultCharset().name());
final String sendMsg;
if (message instanceof String) {
sendMsg = (String) message;
} else if (message instanceof byte[]) {
sendMsg = new String((byte[]) message, encode);
} else {
sendMsg = "";
}
String adapterName = tempProp.getProperty(ADAPTER_NAME);
try {
PooledConnectionFactory connectionFactory = AMQAdapterManager.getInstance()
.getOutboundPooledConnectionFactory(adapterName);
JmsTemplate jmsTemplate = new JmsTemplate(connectionFactory);
jmsTemplate.setExplicitQosEnabled(true);
jmsTemplate.setDeliveryPersistent(false);
if (NumberUtils.isParsable(timeToLive)) {
jmsTemplate.setTimeToLive(NumberUtils.toLong(timeToLive) * 1000);
}
jmsTemplate.send(sendQueue, new MessageCreator() {
public Message createMessage(Session session) throws JMSException {
JSONObject propObject = new JSONObject();
String strMsg = AMQSenderAdapter.extractRequestProperties(propObject, sendMsg, messageType,
relayPropertyGroup);
Message ms = session.createTextMessage(strMsg);
AMQSenderAdapter.assignRequestProperties(ms, propObject);
return ms;
}
});
return ElinkConfig.getAsyncDummyData(null);
} catch (Exception e) {
logger.error("AMQSenderAdapter Async] Exception (" + adapterName + ") : " + e.getMessage(), e);
throw e;
} catch (Throwable t) {
logger.error("AMQSenderAdapter Async] Throwable (" + adapterName + ") : " + t.getMessage(), t);
throw t;
}
}
@SuppressWarnings({ "deprecation", "unchecked" })
protected static String extractRequestProperties(JSONObject propObject, String sendMsg, String messageType,
String relayPropertyGroup) {
String strMsg = sendMsg;
if (MessageType.JSON.equals(messageType) && StringUtils.isNotBlank(relayPropertyGroup)
&& StringUtils.contains(strMsg, relayPropertyGroup)) {
try {
JSONObject dataObject = (JSONObject) JSONValue.parse(strMsg);
JSONObject tmpPropObject = (JSONObject) dataObject.get(relayPropertyGroup);
if (tmpPropObject != null) {
propObject.putAll(tmpPropObject);
dataObject.remove(relayPropertyGroup);
strMsg = dataObject.toJSONString();
}
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
}
return strMsg;
}
protected static void assignRequestProperties(Message ms, JSONObject propObject) {
if (propObject == null || propObject.size() == 0) {
return;
}
for (Object key : propObject.keySet()) {
Object obj = propObject.get(key);
if ((obj instanceof JSONObject) || (obj instanceof JSONArray)) {
continue;
}
try {
ms.setStringProperty((String) key, (String) obj);
} catch (Exception e) {
if (logger.isWarn()) {
logger.warn(e.getMessage());
}
}
}
}
}
@@ -0,0 +1,9 @@
package com.eactive.eai.adapter.app;
import java.util.Properties;
public interface BusinessApplication {
public static final String EAI_SVC_NAME = "eaiSvcName";
public Object executeApplication(Properties prop, Object message, Properties tempProp) throws Exception;
}
@@ -0,0 +1,45 @@
package com.eactive.eai.adapter.app;
import com.eactive.eai.adapter.ElinkDefaultAdapter;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey;
import com.eactive.eai.common.util.Logger;
import org.apache.commons.lang3.StringUtils;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import java.util.Properties;
public class BusinessApplicationAdapter extends ElinkDefaultAdapter {
public static final String ADAPTER_PROP_CLASS_NAME = "BUSINESS_CLASS_NAME";
public static final String REST_OPTION_CLASS_NAME = "businessClassName";
@Override
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception {
String restOption = prop.getProperty(HttpClientAdapterServiceKey.REST_OPTION);
JSONObject restOptionObject = parseJson(restOption);
String businessClassName = null;
if (restOptionObject != null) {
businessClassName = (String) restOptionObject.get(REST_OPTION_CLASS_NAME);
}
if (StringUtils.isBlank(businessClassName)) {
businessClassName = prop.getProperty(ADAPTER_PROP_CLASS_NAME);
if (StringUtils.isBlank(businessClassName)) {
throw new Exception(ADAPTER_PROP_CLASS_NAME + " is not set.");
}
}
BusinessApplication app = BusinessApplicationFactory.createApplication(businessClassName);
return app.executeApplication(prop, message, tempProp);
}
@SuppressWarnings("deprecation")
private JSONObject parseJson(String message) {
if (StringUtils.isBlank(message)) {
return null;
}
return (JSONObject) JSONValue.parse(message);
}
}
@@ -0,0 +1,26 @@
package com.eactive.eai.adapter.app;
import java.util.concurrent.ConcurrentHashMap;
public class BusinessApplicationFactory {
static private ConcurrentHashMap<String, BusinessApplication> h = new ConcurrentHashMap<String, BusinessApplication>();
@SuppressWarnings("rawtypes")
public static BusinessApplication createApplication(String className) throws Exception {
if (h.containsKey(className)) {
return (BusinessApplication) h.get(className);
}
BusinessApplication app = null;
try {
Class cl = Class.forName(className);
app = (BusinessApplication) cl.newInstance();
if (app != null) {
h.put(className, app);
}
} catch (Exception e) {
throw new Exception("Cannot create a BusinessApplication. - " + className);
}
return app;
}
}
@@ -0,0 +1,84 @@
package com.eactive.eai.adapter.app.impl;
import java.io.BufferedWriter;
import java.io.File;
import java.io.FileWriter;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import org.apache.commons.lang3.StringUtils;
import org.json.simple.JSONObject;
import com.eactive.eai.adapter.app.BusinessApplication;
import com.eactive.eai.common.util.DatetimeUtil;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.common.util.StringUtil;
public class OnlineToFileWriter implements BusinessApplication {
private static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
public static final String CLASS_PROPS = "BUSINESS_CLASS_PROPS";
public static final String CLASS_PROPS_BASE_FILE_PATH = "baseFilePath";
public static final String CLASS_PROPS_ENCODE = "encode";
public static final String CLASS_PROPS_FILE_PATH_EXT = "fileExt";
/**
* @formatter:off
* Adapter property ¼³Á¤: BUSINESS_CLASS_PROPS
* - ex) baseFilePath=/data/onlineToJson, fileExt=json
* @formatter:on
*/
@Override
public Object executeApplication(Properties prop, Object message, Properties tempProp) throws Exception {
String classPropsStr = prop.getProperty(CLASS_PROPS);
Properties classProp = StringUtil.getProperties(classPropsStr);
String baseFilePath = classProp.getProperty(CLASS_PROPS_BASE_FILE_PATH);
if (StringUtils.isBlank(baseFilePath)) {
throw new Exception(String.format("Property(%s) is not setted", CLASS_PROPS_BASE_FILE_PATH));
}
String encode = classProp.getProperty(CLASS_PROPS_ENCODE, "UTF-8");
String fileExt = classProp.getProperty(CLASS_PROPS_FILE_PATH_EXT, "txt");
String eaiSvcName = tempProp.getProperty(BusinessApplication.EAI_SVC_NAME);
if (StringUtils.isBlank(eaiSvcName)) {
throw new Exception("Can not find serviceId");
}
String dirStr = StringUtils.removeEnd(baseFilePath, "/") + "/" + eaiSvcName;
File dir = new File(dirStr);
if (!dir.exists()) {
dir.mkdirs();
}
String fileName = DatetimeUtil.getFormattedDate("yyyyMMdd-HHmmssSSS") + "." + fileExt;
File file = new File(dir, fileName);
Map<String, String> resultMap = new HashMap<>();
try (
FileWriter fw = new FileWriter(file);
BufferedWriter bw = new BufferedWriter(fw);
){
if (message == null) {
logger.warn("message is null");
} else if (message instanceof byte[]) {
byte[] buff = (byte[]) message;
bw.write(new String(buff, encode));
} else {
bw.write(message.toString());
}
bw.flush();
resultMap.put("RESULTCD", "000");
resultMap.put("RESULTMSG", "Success");
resultMap.put("FILENAME", fileName);
} catch (Exception e) {
logger.error("OnlineToFileWriter error", e);
throw e;
}
JSONObject resultJsonObject = new JSONObject();
resultJsonObject.putAll(resultMap);
return resultJsonObject.toJSONString().getBytes();
}
}
@@ -0,0 +1,29 @@
package com.eactive.eai.adapter.db;
public class DBAdapterKeys {
public static final String ADAPTER_GROUPNAME = "adapterGroupName";
public static final String ADAPTER_NAME = "adapterName";
public static final String ADAPTER_PROPGN = "propGroupName";
// jdbc common
public static final String DRIVER = "jdbc.driver";
public static final String URL = "jdbc.url";
public static final String USER = "jdbc.user";
public static final String PVAL = "jdbc.pval";
public static final String DATASOURCE = "jdbc.datasource"; // optional
public static final String ENCODE = "encode"; // optional
// inbound query
public static final String SELECT = "jdbc.select"; // select query
public static final String UPDATE = "jdbc.update"; // update query
// inbound scheduler
public static final String RUN_CRONEXP = "run.cronexp"; // Quartz [ 0/10 * * * * ? ]
public static final String RUN_INTVL = "run.interval"; // 0...N
public static final String RUN_RETRY = "run.retry"; // Y|N
public static final String RUN_RETRYCNT = "run.retrycnt"; // 0...N
public static final String RUN_RETRYINTVL = "run.retryinterval"; //ms
public static final String RUN_MSGTYPE = "run.msgtype"; // XML | JSON
// Outbound
public static final String QUERY = "query";
}
@@ -0,0 +1,50 @@
package com.eactive.eai.adapter.db.sql;
import com.eactive.eai.adapter.AdapterPropManager;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.Properties;
public class AdapterUtils {
public static void main(String[] args) {
String updateSql = "update EAIINF01 set RFLAG = 'C' where UNID = '%UNID%'";
LinkedHashMap<String, Object> map = new LinkedHashMap<String, Object>();
map.put("Unid", "ID00000001");
String prefix = "%", surfix = "%";
System.out.println(updateSql);
System.out.println(getUpdateQuery(updateSql, map, prefix, surfix));
}
public static Properties getAdapterProerties(String propGroupName) {
AdapterPropManager pmanager = AdapterPropManager.getInstance();
Properties prop = null;
if(pmanager == null) {
prop = new Properties();
}
else {
prop = pmanager.getProperties(propGroupName);
}
return prop;
}
public static String getUpdateQuery(String updateSql, HashMap<String, Object> map) {
return getUpdateQuery(updateSql, map, "%", "%");
}
public static String getUpdateQuery(String updateSql, HashMap<String, Object> map, String prefix, String surfix) {
String convertedSql = updateSql;
String paramName = null;
for(String colName : map.keySet()) {
paramName = prefix+colName.toUpperCase()+surfix;
if(updateSql.indexOf(paramName) > -1) {
convertedSql = convertedSql.replaceAll(paramName, (String)map.get(colName));
}
}
return convertedSql;
}
}
@@ -0,0 +1,284 @@
package com.eactive.eai.adapter.db.sql;
import com.eactive.eai.adapter.AdapterVO;
import com.eactive.eai.adapter.RequestDispatcher;
import com.eactive.eai.adapter.db.DBAdapterKeys;
import com.eactive.eai.adapter.wca.jdbc.JDBCException;
import com.eactive.eai.common.message.EAIMessageKeys;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.common.util.ServiceLocator;
import javax.sql.DataSource;
import java.sql.*;
import java.util.LinkedHashMap;
import java.util.Properties;
public class DBInboudSqlAdapter {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
private boolean isLocalTest = false;
private String logPrefix = "";
private boolean isRunning = false;
private boolean stopRunning = false;
private AdapterVO vo;
private Properties configProperties = null;
public boolean isRunningState() {
return isRunning;
}
public void setAdapterVO(AdapterVO vo) {
this.vo = vo;
}
public void setProperties(Properties p) {
this.configProperties = p;
}
public void stop() {
stopRunning = true;
}
public DBInboudSqlAdapter(AdapterVO vo, Properties configProperties) {
super();
this.vo = vo;
this.configProperties = configProperties;
if(vo == null) {
logPrefix = this.getClass().getSimpleName() +"] ";
}
else {
logPrefix = vo.getName() +"] ";
}
String isLocal = System.getProperty("isLocal");
if(isLocal != null && "true".equalsIgnoreCase(isLocal)) {
isLocalTest = true;
}
System.out.println("$$$ DBInboudSqlAdapter] isLocalTest = " + isLocalTest);
}
public boolean execute() {
isRunning = true;
int chunkSize = 15;
Connection con = null;
PreparedStatement pstmt = null;
PreparedStatement pstmtUpdate = null;
ResultSet rs = null;
String datasoureName = configProperties.getProperty(DBAdapterKeys.DATASOURCE) ;
String selectQuery = configProperties.getProperty(DBAdapterKeys.SELECT) ;
String updateQuery = configProperties.getProperty(DBAdapterKeys.UPDATE) ;
int runInterval = 0;
String runIntervalStr = configProperties.getProperty(DBAdapterKeys.RUN_INTVL) ;
try {
runInterval = Integer.parseInt(runIntervalStr);
}
catch(Exception e) {
runInterval = 0;
}
String runRetry = configProperties.getProperty(DBAdapterKeys.RUN_RETRY, "N") ; // Y | N
int runRetryCnt = 0;
String runRetryCntStr = configProperties.getProperty(DBAdapterKeys.RUN_RETRYCNT, "0") ;
try {
runRetryCnt = Integer.parseInt(runRetryCntStr);
}
catch(Exception e) {
runRetryCnt = 0;
}
int runRetryInterval = 0;
String runRetryIntervalStr = configProperties.getProperty(DBAdapterKeys.RUN_RETRYINTVL, "0") ;
try {
runRetryInterval = Integer.parseInt(runRetryIntervalStr);
}
catch(Exception e) {
runRetryInterval = 0;
}
int rowIndex = 0;
int colCount = 0;
try {
if(datasoureName != null && datasoureName.trim().length() > 0) {
con = getDataSourceConnection(datasoureName);
}
else {
con = getJDBCConnection(configProperties);
}
// default : row unit commit
con.setAutoCommit(true);
// select chunk record
pstmt = con.prepareStatement(selectQuery);
rs = pstmt.executeQuery();
rowIndex = 0;
colCount = rs.getMetaData().getColumnCount();
debug(String.format("$$$ RUNNING Query [%s] - colCount = %s", selectQuery, colCount) );
String rowString = null;
// LOOP - Inbound Call
LinkedHashMap<String, Object> map = new LinkedHashMap<String, Object>();
boolean isSuccess = false;
int retryExecCounter = 0;
boolean retryFailed = false;
while(rs.next() && !retryFailed){
debug(String.format("==> run [%s]", (rowIndex+1)) );
if(stopRunning) {
debug(String.format("$$$ STOP RUNNING stopRunning[%s]", stopRunning) );
break;
}
for(int i = 1; i <= colCount; i++){
String key = rs.getMetaData().getColumnName(i);
String value = rs.getString(i);
if(value == null){
value = "";
}
map.put(key, value);
}
if("JSON".equals(configProperties.getProperty(DBAdapterKeys.RUN_MSGTYPE))) {
rowString = ResultParser.toJsonString(map);
}
if("XML".equals(configProperties.getProperty(DBAdapterKeys.RUN_MSGTYPE))) {
rowString = ResultParser.toXmlString(map);
}
debug(String.format("==> run [%s] : ", (rowIndex+1)) + rowString);
//-- start sudo test code
// debug(String.format("Sleep 1 secs - run [%s/%s]", (rowIndex+1), chunkSize) );
//-- end sudo test code
byte[] request = rowString.getBytes();
byte[] response = null;
String elinkResponseCode = null;
while(true) {
try {
isSuccess = false;
RequestDispatcher dispatcher = RequestDispatcher.getRequestDispatcher(vo.getAdapterGroupName());
response = (byte[]) dispatcher.handle(vo.getName(), request, this.configProperties);
elinkResponseCode = configProperties.getProperty(EAIMessageKeys.ELINK_RET_CODE);
debug("RequestProcessor.ELINK_RET_CODE ["+ elinkResponseCode +"]" );
// Sunncess check with elink F/W response code ESBEAI111111
if(EAIMessageKeys.EAI_SUCCESS_CODE.equals(elinkResponseCode)
|| EAIMessageKeys.EAI_DEFAULT_CODE.equals(elinkResponseCode)) {
isSuccess = true;
}
} catch (Exception e) {
logger.error("RequestDispatcher call error",e);
}
if(isSuccess) {
// check response
if(response != null) debug("Response Message : " + new String(response));
// if success, update CHK column
String mappedUpdate = AdapterUtils.getUpdateQuery(updateQuery, map);
debug("mappedUpdate - "+ mappedUpdate);
pstmtUpdate = con.prepareStatement(mappedUpdate);
int cnt = pstmtUpdate.executeUpdate();
debug("mappedUpdate result - "+ cnt);
// if success, skip retry
break;
}
else {
// if failed, retry or break, check retry options
if("Y".equals(runRetry)) {
debug(String.format(">> RETRY [%s / %s]", retryExecCounter, runRetryCnt) );
if(retryExecCounter < runRetryCnt) {
debug(String.format(">> RETRY runRetry=%s", runRetry) );
++retryExecCounter;
if(runRetryInterval > 0) {
debug("Sleep run.retryinterval - " +runRetryInterval);
Thread.sleep(runRetryInterval);
}
continue;
}
else {
debug(String.format(">> RETRY COMPLETED [%s / %s], STOP JOB", retryExecCounter, runRetryCnt) );
retryFailed = true;
break;
}
}
else {
debug(String.format(">> RETRY Disabled, runRetry=%s", runRetry) );
retryFailed = true;
break;
}
}
} // end retry LOOP
rowIndex++;
if(runInterval > 0) {
debug("Sleep run.interval - " +runInterval);
Thread.sleep(runInterval);
}
}
// end row LOOP
}
catch(Exception ex) {
ex.printStackTrace();
}
isRunning = false;
debug(String.format("JOB Completed. isRunning=%s, executed ROWCount=%s", isRunning, rowIndex) );
return isRunning;
}
private Connection getJDBCConnection(Properties p) throws SQLException {
try {
Class.forName(p.getProperty(DBAdapterKeys.DRIVER));
Connection con = DriverManager.getConnection(p.getProperty(DBAdapterKeys.URL),
p.getProperty(DBAdapterKeys.USER), p.getProperty(DBAdapterKeys.PVAL));
return con;
} catch (Exception e) {
throw new SQLException("DBAdapter] Cannot create a JDBC Connection. - " + e.getMessage());
}
}
private Connection getDataSourceConnection(String dataSourceName) throws JDBCException
{
DataSource dataSource = null;
try {
ServiceLocator sl = ServiceLocator.getInstance();
dataSource = sl.getDataSource(dataSourceName);
return dataSource.getConnection();
}
catch(Exception e) {
e.printStackTrace();
throw new JDBCException("["+dataSourceName+"]을 얻을 수 없습니다.");
}
}
private java.sql.Date toDate(String sDate) throws Exception {
java.sql.Date s = null;
if(sDate.length() == 10 && sDate.indexOf("-") > 0) {
s = java.sql.Date.valueOf(sDate);
}
else if(sDate.length() == 8) {
java.util.Date d = new java.text.SimpleDateFormat("yyyyMMdd").parse(sDate);
s = new java.sql.Date(d.getTime());
}
else {
throw new Exception("Invalid Date String - "+sDate);
}
return s;
}
private void debug(String msg) {
if(isLocalTest) {
System.out.println (logPrefix + msg);
}
else {
logger.info(logPrefix + msg);
}
}
}
@@ -0,0 +1,62 @@
package com.eactive.eai.adapter.db.sql;
import com.eactive.eai.adapter.db.DBAdapterKeys;
import com.eactive.eai.common.util.Logger;
import org.quartz.Job;
import org.quartz.JobExecutionContext;
import org.quartz.JobExecutionException;
import org.quartz.utils.Key;
public class DBInboudSqlAdapterJob implements Job {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
private static boolean isLocalTest = false;
static {
String isLocal = System.getProperty("isLocalTest");
if(isLocal != null && "true".equalsIgnoreCase(isLocal)) {
isLocalTest = true;
}
}
private void debug(String msg) {
if(isLocalTest) {
System.out.println (msg);
}
else {
logger.info(msg);
}
}
// private DBInboudSqlAdapter adapter = null;
public void execute(JobExecutionContext context) throws JobExecutionException {
// JobKey jobKey = context.getJobDetail().getKey();
Key jobKey = context.getJobDetail().getKey();
String data = "";
for (String key : context.getJobDetail().getJobDataMap().getKeys()) {
data = data + key + "=" + context.getJobDetail().getJobDataMap().getString(key) + ",";
}
debug( jobKey + " start data(" + data + ")");
logger.warn(">> " + jobKey + " start data(" + data + ")");
String jobKeyName = jobKey.getName();
String adapterName = context.getJobDetail().getJobDataMap().getString(DBAdapterKeys.ADAPTER_NAME);
String propGroupName = context.getJobDetail().getJobDataMap().getString(DBAdapterKeys.ADAPTER_PROPGN);
debug("adapterName=" + adapterName + ", propGroupName"+ propGroupName );
DBInboudSqlAdapter adapter = DBInboudSqlAdapterManager.getInstance().get(adapterName);
if(adapter == null) {
debug(jobKey + " : @@@@ Adapter not found in JobDataMap");
}
else {
if(adapter.isRunningState()) {
debug(jobKey + " : Adapter already RUNNING with previous scledule");
}
else {
debug(jobKey + " : Adapter Called.");
adapter.execute();
}
}
}
}
@@ -0,0 +1,208 @@
package com.eactive.eai.adapter.db.sql;
import com.eactive.eai.adapter.db.DBAdapterKeys;
import com.eactive.eai.adapter.listener.AdapterException;
import com.eactive.eai.adapter.listener.AdapterListenerSupport;
import com.eactive.eai.common.exception.ExceptionUtil;
import org.quartz.*;
import org.quartz.impl.StdSchedulerFactory;
import java.util.Date;
import java.util.Properties;
import static org.quartz.CronScheduleBuilder.cronSchedule;
import static org.quartz.JobBuilder.newJob;
import static org.quartz.TriggerBuilder.newTrigger;
public class DBInboudSqlAdapterListener extends AdapterListenerSupport {
String className = this.getClass().getName();
Scheduler scheduler = null;
private static boolean isLocalTest = false;
private String SCHE_GROUP_NAME = "DBQ_GROUP";
public boolean startScheduler(Properties prop) {
boolean isStart = false;
try {
debug(className + " Scheduler start");
logger.warn(className + " Scheduler start");
if(scheduler != null) {
logger.warn("Scheduler shutdown previous RUN !");
scheduler.shutdown();
}
String adapterName = prop.getProperty("adapterName");
scheduler = new StdSchedulerFactory().getScheduler();
String jobName = "DBInboudSqlAdapterJob";
String jobClassName = "com.eactive.eai.adapter.db.sql.DBInboudSqlAdapterJob";
String cronExp = prop.getProperty( DBAdapterKeys.RUN_CRONEXP ); // "0/10 * * * * ?";
registJob(jobName, jobClassName, cronExp, prop);
scheduler.start();
isStart = true;
}
catch(SchedulerException se) {
logger.error("Scheduler start failed", se);
}
catch(Exception e) {
logger.error("Scheduler start failed", e);
}
return isStart;
}
private String getTriggerName(String jobName) {
return jobName + "-trigger";
}
public boolean registJob(String jobName, String jobClassName, String cronExp, Properties p) {
try {
//configure the scheduler time
Class jobClass = Class.forName(jobClassName);
JobBuilder jobBuilder = newJob(jobClass);
jobBuilder = jobBuilder.withIdentity(jobName, Scheduler.DEFAULT_GROUP);
// pass adapter name : not used this time
jobBuilder.usingJobData(DBAdapterKeys.ADAPTER_NAME, p.getProperty(DBAdapterKeys.ADAPTER_NAME));
jobBuilder.usingJobData(DBAdapterKeys.ADAPTER_PROPGN, p.getProperty(DBAdapterKeys.ADAPTER_PROPGN));
JobDetail job = jobBuilder.build();
CronTrigger trigger = newTrigger().withIdentity( getTriggerName(jobName), SCHE_GROUP_NAME )
.withSchedule(cronSchedule(cronExp))
.build();
Date ft = scheduler.scheduleJob(job, trigger);
logger.warn(String.format("%s has been scheduled to run at: %s and repeat based on expression: %s", job.getKey(), ft,
trigger.getCronExpression()) );
return true;
}
catch(Exception e) {
logger.warn("registJob failed", e);
return false;
}
}
private void printProperties(Properties prop) throws Exception {
if(prop == null) {
debug("printProperties - Properties is null");
return;
}
for (Object key: prop.keySet()) {
debug(key + ": " + prop.getProperty(key.toString()));
}
// prop.forEach((key, value) -> debug("Key : " + key + ", Value : " + value));
}
private void init(Properties prop) throws Exception {
debug("Start init");
printProperties(prop);
startScheduler(prop);
}
public void start() throws AdapterException {
Properties prop = null;
String adapterName = null;
if(info != null) {
String propGroupName = info.getPropGroupName();
prop = AdapterUtils.getAdapterProerties(propGroupName);
adapterName = info.getName();
prop.setProperty(DBAdapterKeys.ADAPTER_PROPGN, propGroupName);
}
// TODO : Application Test Code.
// in real system, remove this block
else {
prop = new Properties();
prop.setProperty(DBAdapterKeys.RUN_CRONEXP, "0/10 * * * * ?");
prop.setProperty(DBAdapterKeys.RUN_INTVL, "1000");
prop.setProperty(DBAdapterKeys.RUN_RETRY, "N");
prop.setProperty(DBAdapterKeys.RUN_RETRYCNT, "2");
prop.setProperty(DBAdapterKeys.RUN_RETRYINTVL, "5000");
prop.setProperty(DBAdapterKeys.RUN_MSGTYPE, "JSON");
prop.setProperty(DBAdapterKeys.DRIVER, "oracle.jdbc.driver.OracleDriver");
prop.setProperty(DBAdapterKeys.URL, "jdbc:oracle:thin:@localhost:1521:XE");
prop.setProperty(DBAdapterKeys.USER, "eai");
prop.setProperty(DBAdapterKeys.PVAL, "eaiadmin");
// prop.setProperty(DBAdapterKeys.SELECT, "select * from APIJOBSCHE");
prop.setProperty(DBAdapterKeys.SELECT, "select * from EAIINF01 where RFLAG IS null ORDER BY UNID");
prop.setProperty(DBAdapterKeys.UPDATE, "update EAIINF01 set RFLAG = 'C' where UNID = '%UNID%' ");
debug("Start Scheduler");
adapterName = "_EAI_IN_DBQ_SyC";
}
// TODO : Application Test Code End.
prop.setProperty(DBAdapterKeys.ADAPTER_NAME, adapterName);
// Start Scheduler
try{
logger.warn(className + " STARTING");
init(prop);
DBInboudSqlAdapterManager maanger = DBInboudSqlAdapterManager.getInstance();
// init adapter configuration values
DBInboudSqlAdapter adapter = new DBInboudSqlAdapter(info, prop);
maanger.put(adapterName, adapter);
} catch(Exception e) {
e.printStackTrace();
}
}
public void stop() throws AdapterException {
try {
String adapterName = "";
if (info == null) {
adapterName = "_EAI_IN_DBQ_SyC";
// throw new Exception(this.getClass().getName() +" | AdapterVO°¡ NULLÀÔ´Ï´Ù.");
}
else {
adapterName = info.getName();
}
if(scheduler != null) {
try {
DBInboudSqlAdapterManager manager = DBInboudSqlAdapterManager.getInstance();
DBInboudSqlAdapter adapter = manager.get(adapterName);
logger.warn("stop adapter - " + adapterName);
adapter.stop();
// Stop Scheduler
logger.warn("stop scheduler - " + scheduler.getSchedulerName());
JobKey key = new JobKey(adapterName, SCHE_GROUP_NAME );
scheduler.deleteJob(key);
scheduler.shutdown();
}
catch(SchedulerException se) {
logger.error("stop scheduler failed", se);
}
}
} catch (Exception e) {
String errCode = ExceptionUtil.getErrorCode(e, "RECEAIOIA009");
throw new AdapterException(errCode);
}
}
private void debug(String msg) {
if(isLocalTest) {
System.out.println (msg);
}
else {
logger.info(msg);
}
}
public static void main(String[] args) {
try {
isLocalTest = true;
System.setProperty("isLocal", "true");
DBInboudSqlAdapterListener listener = new DBInboudSqlAdapterListener();
int testSecs = 60;
System.out.println (String.format(">> Test while %s secs ...", testSecs));
listener.start();
Thread.sleep(testSecs * 1000);
System.out.println ("<< Test end.");
listener.stop();
}
catch(Exception ex) {
ex.printStackTrace();
}
}
}
@@ -0,0 +1,21 @@
package com.eactive.eai.adapter.db.sql;
import java.util.concurrent.ConcurrentHashMap;
public class DBInboudSqlAdapterManager {
private static DBInboudSqlAdapterManager instance = new DBInboudSqlAdapterManager();
private static ConcurrentHashMap<String, DBInboudSqlAdapter> adapters = new ConcurrentHashMap<String, DBInboudSqlAdapter>();
public static DBInboudSqlAdapterManager getInstance() {
return instance;
}
public synchronized void put(String adapterName, DBInboudSqlAdapter adapter) {
adapters.put(adapterName, adapter);
}
public synchronized DBInboudSqlAdapter get(String adapterName) {
return adapters.get(adapterName);
}
}
@@ -0,0 +1,27 @@
package com.eactive.eai.adapter.db.sql;
import org.json.simple.JSONObject;
import java.util.LinkedHashMap;
public class ResultParser {
public static String toJsonString(LinkedHashMap<String, Object> map) {
JSONObject jsonObject = new JSONObject();
for (String key : map.keySet()) {
jsonObject.put(key, map.get(key));
}
return jsonObject.toJSONString();
}
public static String toXmlString(LinkedHashMap<String, Object> map) {
StringBuilder sb = new StringBuilder();
sb.append("<row>");
for (String key : map.keySet()) {
sb.append("<").append(key).append(">");
sb.append(map.get(key));
sb.append("</").append(key).append(">");
}
sb.append("</row>");
return sb.toString();
}
}
@@ -0,0 +1,10 @@
package com.eactive.eai.adapter.handler;
import java.util.Properties;
import com.eactive.eai.message.StandardMessage;
public interface AdapterErrorMessageHandler {
public Object generateNonStandardErrorResponseMessage(String inboudnAdapterGroupName, String inboudnAdapterName, Properties callProp, Object outboundRequestData, StandardMessage resStandardMessage) throws Exception;
}
@@ -0,0 +1,31 @@
package com.eactive.eai.adapter.handler;
import java.util.concurrent.ConcurrentHashMap;
import com.eactive.eai.common.util.Logger;
public class AdapterErrorMessageHandlerFactory {
static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
static private ConcurrentHashMap<String, AdapterErrorMessageHandler> h = new ConcurrentHashMap<String, AdapterErrorMessageHandler>();
@SuppressWarnings("rawtypes")
public static AdapterErrorMessageHandler createHandler(String handlerClassName) {
if (h.containsKey(handlerClassName)) {
return (AdapterErrorMessageHandler) h.get(handlerClassName);
}
AdapterErrorMessageHandler handler = null;
try {
Class cl = Class.forName(handlerClassName);
handler = (AdapterErrorMessageHandler) cl.newInstance();
} catch (Exception e) {
logger.error("Cannot create a AdapterErrorMessageHandler. - {}", handlerClassName);
}
if (handler != null) {
h.put(handlerClassName, handler);
return handler;
} else {
return null;
}
}
}
@@ -0,0 +1,15 @@
package com.eactive.eai.adapter.handler;
import java.util.Properties;
import com.eactive.eai.message.StandardMessage;
public class DefaultAdapterErrorMessageHandler implements AdapterErrorMessageHandler {
@Override
public Object generateNonStandardErrorResponseMessage(String inboudnAdapterGroupName, String inboudnAdapterName,
Properties callProp, Object outboundRequestData, StandardMessage resStandardMessage) throws Exception {
return null;
}
}
@@ -0,0 +1,18 @@
package com.eactive.eai.adapter.http;
import org.apache.commons.httpclient.methods.EntityEnclosingMethod;
public class EntityEnclosingDeleteMethod extends EntityEnclosingMethod {
public EntityEnclosingDeleteMethod() {
}
public EntityEnclosingDeleteMethod(String uri) {
super(uri);
}
@Override
public String getName() {
return "DELETE";
}
}
@@ -0,0 +1,25 @@
package com.eactive.eai.adapter.http;
import org.apache.commons.httpclient.methods.EntityEnclosingMethod;
import com.eactive.eai.common.util.Logger;
public class EntityEnclosingGetMethod extends EntityEnclosingMethod {
public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
public EntityEnclosingGetMethod() {
setFollowRedirects(true);
}
public EntityEnclosingGetMethod(String uri) {
super(uri);
if (logger.isDebugEnabled()) {
logger.debug("enter GetMethod(String)");
}
}
@Override
public String getName() {
return "GET";
}
}
@@ -0,0 +1,154 @@
//package com.eactive.eai.adapter.http;
//
//import java.net.URLDecoder;
//import java.net.URLEncoder;
//import java.util.Properties;
//import javax.naming.Context;
//import javax.naming.InitialContext;
//import javax.servlet.ServletException;
//import javax.servlet.http.HttpServlet;
//import javax.servlet.http.HttpServletRequest;
//import javax.servlet.http.HttpServletResponse;
//
//import com.eactive.eai.adapter.RequestDispatcher;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.util.LogKeys;
//import com.eactive.eai.common.util.Logger;
//import com.eactive.eai.common.util.StringUtil;
//
///**
//* 1. 기능 : HTTP 웹 요청을 수신해 EAI 프레임웍에 전달하는 HTTP 어댑터
//* 2. 처리 개요 :
//* * - 약속된 URL 파라미터(“_message_”)의 값을 얻어 RequestDispatcher의 handle() 메서드를 호출한다.
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : EAIHttpAdapter.java, RequestDispatcher.java
//* @since :
//* :
//*/
//public class HttpAdapter extends HttpServlet
//{
// /*
// * URL 파리미터 이름
// */
// static final String PARAMETER_MESSAGE = "_message_";
// /*
// * Http Adapter 이름
// */
// static final String HTTP_ADAPTER_NAME = "HTTP_ADAPTER_NAME";
// /*
// * Http Adapter Group 이름
// */
// static final String HTTP_ADAPTER_GROUP_NAME = "HTTP_ADAPTER_GROUP_NAME";
//
// private String adapterGroupName;
// private String adapterName;
// /*
// * Adapter Logger
// */
// static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
//
// /**
// * 1. 기능 : Http Adapter의 property 속성을 설정한다.
// * 2. 처리 개요 :
// * -
// * 3. 주의사항
// *
// **/
// public void init() {
// //-------------------------------------------------------
// // Edited 2007.09.12 : DHLEE
// //-------------------------------------------------------
// this.adapterName = this.getInitParameter(HTTP_ADAPTER_NAME);
// this.adapterGroupName = this.getInitParameter(HTTP_ADAPTER_GROUP_NAME);
// //-------------------------------------------------------
//
// if(this.adapterName == null) this.adapterName = "IN_HTTP_STD_Sync01";
// if(this.adapterGroupName == null) this.adapterGroupName = "HttpAdapter{STD}";
//
// String[] msgArgs = new String[2];
// msgArgs[0] = this.adapterGroupName;
// msgArgs[1] = this.adapterName;
// String resMsg = ExceptionUtil.make("RDCEAIAHA004", msgArgs);
// if(logger.isDebug()){
// logger.debug("HttpAdapter] " + resMsg);
// }
// }
//
// /**
// * 1. 기능 : 로컬 서비스 호출하는 비지니스 로직
// * 2. 처리 개요 :
// * - 로컬 서비스를 호출 하여 업무를 처리하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param message 요청 메시지
// * @return prop Http Adapter 속성 정보
// * @exception Exception 리턴 Object의 타입이 틀릴 경우
// **/
// protected byte[] service(byte[] message, Properties prop) throws Exception {
// Object obj = RequestDispatcher.getRequestDispatcher(this.adapterGroupName).handle(adapterName,message,prop);
// if(obj == null) return null;
// if(obj instanceof byte[]) {
// return (byte[])obj;
// } else if(obj instanceof String) {
// return ((String)obj).getBytes();
// } else {
// throw new Exception("RECEAIAHA001");
// }
// }
//
// /**
// * 1. 기능 : Http Servlet service 구현 메소드
// * 2. 처리 개요 :
// * - 로컬 서비스 호출
// * 3. 주의사항
// *
// * @param request Http Servlet Request
// * @return response Http Servlet Response
// * @exception Exception PARAMETER_MESSAGE가 null 이거나 로컬 서비스 호출 중 오류가 발생할 경우
// **/
// public void service(HttpServletRequest request, HttpServletResponse response) {
// try {
//
// String paramValue = request.getParameter(PARAMETER_MESSAGE);
// if(paramValue==null)
// throw new ServletException("RECEAIAHA002");
//
// //byte[] message = StringUtil.hex2Bytes(hexMessage);
// String message = URLDecoder.decode(paramValue);
// //logger.info("HttpAdapter] "+this.adapterGroupName+" (RCEV) - "+message);
// String[] msgArgs = new String[2];
// msgArgs[0] = this.adapterGroupName;
// msgArgs[1] = message;
// String resMsg = ExceptionUtil.make("RICEAIAHA005", msgArgs);
//
// if(logger.isInfo()){
// logger.info("HttpAdapter] " + resMsg);
// }
//
// Properties prop = new Properties();
// // 로컬 서비스 호출
// byte[] result = service(message.getBytes(),prop);
// if(message != null) {
// //response.getWriter().print(message);
// //hexMessage = StringUtil.bytes2Hex(message);
// paramValue = URLEncoder.encode(new String(result));
// response.getWriter().print(paramValue);
// }
//
// } catch (Exception e) {
// logger.error("HttpAdapter] "+adapterGroupName+"-"+adapterName+">>"+e.getMessage(),e);
// response.setStatus(500);
// try {
// response.getWriter().println(e.getMessage());
// String errCode = ExceptionUtil.getErrorCode(e, "RECEAIAHA003");
// throw new Exception(errCode);
// } catch (Exception ex) {
// // IGNORE
// }
// }
//
// }
//}
@@ -0,0 +1,82 @@
package com.eactive.eai.adapter.http;
import com.eactive.eai.adapter.*;
import com.eactive.eai.common.property.PropManager;
import com.eactive.eai.common.testcall.TestCallException;
import com.eactive.eai.common.testcall.TestCallManager;
import com.eactive.eai.common.testcall.TestCallSupport;
import com.eactive.eai.common.util.Logger;
import java.util.Properties;
public class HttpAdapterTestCall extends TestCallSupport
{
public static final String MESSAGE = "EAI TestCall Message";
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
public boolean isAlive() throws TestCallException
{
// int nConnected = 0 ;
try {
ElinkAdapterFactory factory = ElinkAdapterFactory.newInstance();
ElinkAdapter adapter = factory.getElinkAdapter(Keys.TYPE_HTTP);
AdapterVO vo = this.getAdapterInfo();
String pgoName = vo.getPropGroupName();
//PropManager manager = PropManager.getInstance();
AdapterPropManager manager = AdapterPropManager.getInstance();
Properties prop = (Properties)(manager.getProperties(pgoName)).clone();
String testCallUrl = (String)prop.get("TEST_CALL_URL");
// MFC_FAILOVER : FAILOVER = Y 일 경우 무조건 2센터로 테스트콜을 처리한다 (2020-10-16)
PropManager pmanager = PropManager.getInstance();
String mfcFailOver = pmanager.getProperty("MFC_FAILOVER", "FAILOVER");
if(mfcFailOver != null && "Y".equals(mfcFailOver.toUpperCase())) {
String testCallUrl2Grp = (String)prop.get("TEST_CALL_URL_2GRP");
if (testCallUrl2Grp != null && testCallUrl2Grp.trim().length() > 0) {
testCallUrl = testCallUrl2Grp;
if (logger.isWarn()) logger.warn(pgoName + " - USE TEST_CALL_URL_2GRP - " + testCallUrl );
}
}
// MFC_FAILOVER : FAILOVER = Y 일 경우 무조건 2센터로 테스트콜을 처리한다 (2020-10-16)
if (testCallUrl != null && testCallUrl.trim().length() > 0) {
prop.put("URL", testCallUrl);
}
Properties testCallProp = PropManager.getInstance().getProperties(TestCallManager.PROP_GROUP);
String responseType = testCallProp.getProperty(TestCallManager.RESPONSE_TYPE, "SYNC");
String httpTimeout = testCallProp.getProperty(TestCallManager.HTTP_TIME_OUT, "5000");
String connectionTimeout = testCallProp.getProperty(TestCallManager.CONNECTION_TIMEOUT, "3000");
prop.setProperty(TestCallManager.RESPONSE_TYPE,responseType);
prop.setProperty(TestCallManager.HTTP_TIME_OUT, httpTimeout);
prop.setProperty(TestCallManager.CONNECTION_TIMEOUT, connectionTimeout);
Properties tempProp = new Properties();
tempProp.setProperty(TestCallManager.TESTCALL_YN, "Y");
if(logger.isWarn()) {
logger.warn("HttpAdapterTestCall] TestCall ["+vo.getAdapterGroupName()+"] URL = " + prop.getProperty("URL") );
logger.warn("HttpAdapterTestCall] TestCall ["+vo.getAdapterGroupName()+"] " + TestCallManager.RESPONSE_TYPE +" = " + prop.getProperty(TestCallManager.RESPONSE_TYPE) );
logger.warn("HttpAdapterTestCall] TestCall ["+vo.getAdapterGroupName()+"] " + TestCallManager.HTTP_TIME_OUT +" = " + prop.getProperty(TestCallManager.HTTP_TIME_OUT) );
logger.warn("HttpAdapterTestCall] TestCall ["+vo.getAdapterGroupName()+"] " + TestCallManager.CONNECTION_TIMEOUT +" = " + prop.getProperty(TestCallManager.CONNECTION_TIMEOUT) );
logger.warn("HttpAdapterTestCall] TestCall ["+vo.getAdapterGroupName()+"] " + TestCallManager.TESTCALL_YN +" = " + tempProp.getProperty(TestCallManager.TESTCALL_YN) );
}
Object result = adapter.callService(vo.getAdapterGroupName(),prop,MESSAGE.getBytes(), tempProp);
if(logger.isWarn()) {
logger.warn("HttpAdapterTestCall] TestCall["+vo.getAdapterGroupName()+"], result ="+ result );
}
return true;
} catch(HttpStatusException hse) {
logger.warn("HttpAdapterTestCall] Error - "+hse.getClass().getName()+" : "+hse.getMessage());
return true;
} catch(Exception e) {
//e.printStackTrace();
logger.warn("HttpAdapterTestCall] Error - "+e.getClass().getName()+" : "+e.getMessage());
return false;
}
}
}
@@ -0,0 +1,915 @@
//
//package com.eactive.eai.adapter.http;
//
//import java.net.ConnectException;
//import java.net.SocketTimeoutException;
//import java.util.Properties;
//import org.apache.commons.httpclient.HttpClient;
//import org.apache.commons.httpclient.HttpMethod;
//import org.apache.commons.httpclient.HttpMethodRetryHandler;
//import org.apache.commons.httpclient.HttpStatus;
//import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
//import org.apache.commons.httpclient.NoHttpResponseException;
//import org.apache.commons.httpclient.methods.ByteArrayRequestEntity;
//import org.apache.commons.httpclient.methods.GetMethod;
//import org.apache.commons.httpclient.methods.PostMethod;
//import org.apache.commons.httpclient.params.HttpClientParams;
//import org.apache.commons.httpclient.params.HttpMethodParams;
//
//import com.eactive.eai.adapter.WLIDefaultAdapter;
//import com.eactive.eai.common.errorcode.ErrorCodeHandler;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.property.PropManager;
//import com.eactive.eai.common.util.Logger;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 강길수차장요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapter extends WLIDefaultAdapter
//{
// public static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
//
// public static final String URL = "URL";
// public static final String METHOD = "METHOD";
// public static final String PARAMETER_NAME = "PARAMETER_NAME";
//
// // encode 추가 : 20071207
// public static final String ENCODE = "ENCODE";
//
// public static final String METHOD_GET = "GET";
// public static final String METHOD_POST = "POST";
//
// //-------------------------------------------------
// // 전자무역 상태조회 :
// // 2009.01.09
// public static final String METHOD_SOAP = "SOAP";
// public static final String METHOD_SOAP_ACTION = "SOAPAction";
// //-------------------------------------------------
//
// public static final String HTTP_CONNECTION_STALE_CHECKING_ENABLED = "HTTP_CONNECTION_STALE_CHECKING_ENABLED";
// /*
// * 호스트 마다 최대 연결 수
// */
// public static final String HTTP_MAX_CONNECTION_PER_HOST = "HTTP_MAX_CONNECTION_PER_HOST";
// /*
// * 최대 HTTP 연결 수
// */
// public static final String HTTP_MAX_TOTAL_CONNECTIONS = "HTTP_MAX_TOTAL_CONNECTIONS";
//
// static final String PARAMETER_MESSAGE = "_message_";
//
// private HttpClient client;
//
// // 2008.01.21 이동훈
// // HttpClient 2.0 Timeout Setting
// public static final String HTTP_TIME_OUT = "HTTP_TIME_OUT";
// public static final int DEFAULT_TIME_OUT = 30 *1000;
// // HttpClient 2.0 Timeout Setting
//
// /**
// * 1. 기능 : HttpClientAdapter default 생성자
// * 2. 처리 개요 :
// * - property 정보를 가져와 MultiThreadedHttpConnectionManager 속성 설정
// * - HttpClient의 instance 생성
// * 3. 주의사항
// *
// **/
// public HttpClientAdapter() {
// MultiThreadedHttpConnectionManager cm = new MultiThreadedHttpConnectionManager();
// PropManager manager = PropManager.getInstance();
// String enabled = manager.getProperty(HTTP_CONNECTION_STALE_CHECKING_ENABLED);
//
// if(enabled==null) {
//
// enabled="true";
//
// String code = "RWCEAIAHA006";
// String msg = ErrorCodeHandler.getMessage(code);
// if(logger.isWarn()){
// logger.warn(ExceptionUtil.make(code, msg));
// }
// }
//
//
// try {
//
// cm.getParams().setStaleCheckingEnabled(new Boolean(enabled).booleanValue());
//
// } catch(Exception e) {
// e.printStackTrace();
// String errCode = ExceptionUtil.getErrorCode(e, "RECEAIAHA007");
// throw new RuntimeException(errCode);
// }
//
//
// String connPerHost = manager.getProperty(HTTP_MAX_CONNECTION_PER_HOST);
//
// if(connPerHost==null) {
// connPerHost = "10";
// String code = "RWCEAIAHA008";
// String msg = ErrorCodeHandler.getMessage(code);
// if(logger.isWarn()){
// logger.warn(ExceptionUtil.make(code, msg));
// }
// }
//
//
// try {
// //cm.setMaxConnectionsPerHost(new Integer(connPerHost).intValue());
// cm.getParams().setDefaultMaxConnectionsPerHost(new Integer(connPerHost).intValue());
// } catch(Exception e) {
// String errCode = ExceptionUtil.getErrorCode(e, "RECEAIAHA009");
// throw new RuntimeException(errCode);
// }
//
//
// String totalConnections = manager.getProperty(HTTP_MAX_TOTAL_CONNECTIONS);
// if(totalConnections==null) {
// totalConnections = "50";
// String code = "RWCEAIAHA010";
// String msg = ErrorCodeHandler.getMessage(code);
// if(logger.isWarn()){
// logger.warn(ExceptionUtil.make(code, msg));
// }
// }
//
//
// try {
// //cm.setMaxTotalConnections(new Integer(totalConnections).intValue());
// cm.getParams().setMaxTotalConnections(new Integer(totalConnections).intValue());
// } catch(Exception e) {
// String errCode = ExceptionUtil.getErrorCode(e, "RECEAIAHA011");
// throw new RuntimeException(errCode);
// }
//
// this.client = new HttpClient(cm);
//
//
// }
//
// /**
// * 1. 기능 : 현재 사용중인 Connection 수
// * 2. 처리 개요 :
// * -
// * 3. 주의사항
// *
// * @return int 사용중인 Connection 수
// **/
// public int getConnectionsInPool() {
// MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager)this.client.getHttpConnectionManager();
// return mgr.getConnectionsInPool();
// }
//
// /**
// * 1. 기능 : 생성된 총 Connection 수
// * 2. 처리 개요 :
// * -
// * 3. 주의사항
// *
// * @return int 총 Connection 수
// **/
// public int getMaxTotalConnections() {
// MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager)this.client.getHttpConnectionManager();
// return mgr.getParams().getMaxTotalConnections();
// }
//
// /**
// * 1. 기능 : 호스트 당 할당된 총 Connection 수
// * 2. 처리 개요 :
// * -
// * 3. 주의사항
// *
// * @return int 총 Connection 수
// **/
// public int getMaxConnectionsPerHost() {
// MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager)this.client.getHttpConnectionManager();
// return mgr.getParams().getDefaultMaxConnectionsPerHost();
// }
//
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, Object message) throws Exception
// {
//
// byte[] data = null;
// if(message instanceof byte[]) {
// data = (byte[])message;
// } else if( message instanceof String) {
// data = ((String)message).getBytes();
// } else {
// throw new Exception("RECEAIAHA011");
// }
// String url = prop.getProperty(URL);
// String parameterName = prop.getProperty(PARAMETER_NAME);
// String httpMethod = prop.getProperty(METHOD);
// String encode = prop.getProperty(ENCODE);
// String httpTimeOut = prop.getProperty(HTTP_TIME_OUT);
//
// String soapAction = prop.getProperty(METHOD_SOAP_ACTION);
//
// //-------------------------------------------
// // trim 처리 : 2009.03.27
// //-------------------------------------------
// if(url != null) {
// url = url.trim();
// }
//
// if(parameterName != null) {
// parameterName = parameterName.trim();
// }
//
// if(httpMethod != null) {
// httpMethod = httpMethod.trim();
// }
//
// if(encode != null) {
// encode = encode.trim();
// }
//
// if(soapAction != null) {
// soapAction = soapAction.trim();
// }
//
// //----------------------------------
// // 2008.02.15 이동훈
// // 설정값이 없을 경우 무한대로 기다리도록
// // 0 으로 설정하도록 함
// //----------------------------------
// if(httpTimeOut == null) {
// httpTimeOut = "0";
// }
// else {
// httpTimeOut = httpTimeOut.trim();
// }
//
// int timeout = -1;
// try {
// timeout = new Integer(httpTimeOut).intValue();
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] HTTP TIMEOUT SET ["+httpTimeOut+"]");
// }
// } catch(Exception e) {
// if(logger.isWarn()){
// logger.warn("HttpClientAdapter] HTTP TIMEOUT 설정값을 확인하세요. ["+httpTimeOut+"]");
// }
// }
//
//
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] Send("+httpMethod+") Data ["+new String(data)+"]");
// }
//
// if(httpMethod!=null && httpMethod.equals(METHOD_POST)) {
// return callPostService(url, parameterName, data, encode, timeout);
// }
// else if(httpMethod!=null && httpMethod.equals(METHOD_SOAP)) {
// return callSoapService(url, soapAction, data, encode, timeout);
// }
// else if(httpMethod!=null && httpMethod.equals("MEMO")) {
// return callMemoService(url, data, encode, timeout);
// }
// else if(httpMethod!=null && httpMethod.equals("ANN")) {
// return callAnnounceService(url, data, encode, timeout);
// }
// else if(httpMethod!=null && httpMethod.equals("POPUP")) {
// return callPopupService(url, data, encode, timeout);
// }
// else if(httpMethod!=null && httpMethod.equals("CDSVC")) {
// return callChangeDateService(url, data, encode, timeout);
// }
// else {
// return callGetService(url, parameterName, data, encode, timeout);
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Post 방식으로 서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param parameterName URL 파리미터 이름
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callPostService(String url, String parameterName, byte[] data, String encode, int timeout)
// throws Exception {
// PostMethod method = new PostMethod(url);
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// //method.setRequestHeader("Content-Type","text/html; charset=euc-kr");
//
// String sendData = null;
// HttpClient mclient = new HttpClient(new MultiThreadedHttpConnectionManager());
//
// if(encode != null && encode.length() > 0) {
//
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] ENCODE("+encode+") ");
// }
//
// try {
// mclient.getParams().setContentCharset(encode);
// sendData = new String(data,encode);
// } catch(Exception e) {
// if(logger.isError()){
// logger.error("HttpClientAdapter] ENCODE("+encode+") ERROR : "+ e.toString());
// logger.error("HttpClientAdapter] ENCODE("+encode+") SKIP ");
// }
// sendData = new String(data);
// }
// }
// else {
// //신용보증기금에 필요 분기 - 조현덕 추가(2008.11.04)
// if(parameterName.equals("SHINBO")){
// ;
// }else{
// sendData = java.net.URLEncoder.encode(new String(data));
// }
// }
//
//
// if(parameterName==null || parameterName.equals("")) {
// method.addParameter(PARAMETER_MESSAGE, sendData);
//
// //신용보증기금에 필요 분기 - 조현덕 추가(2008.05.06)
// } else if(parameterName.equals("SHINBO")){
// method.setRequestBody(sendData);
// } else {
// method.addParameter(parameterName, sendData);
// }
//
//
// int status = -1;
//
//
// try {
// status = mclient.executeMethod(method);
// //----------------------------------------------------------
// // 2008.01.23 : 응답이 깨지는 것 수정
// //----------------------------------------------------------
// //String responseMessage = method.getResponseBodyAsString();
// String responseMessage = new String(method.getResponseBody());
// //----------------------------------------------------------
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Get 방식으로 서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param parameterName URL 파리미터 이름
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callGetService(String url, String parameterName, byte[] data, String encode, int timeout)
// throws Exception {
// GetMethod method = new GetMethod(url);
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// String sendData = null;
//
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] GET Method URLEncoder");
// }
// sendData = java.net.URLEncoder.encode(new String(data));
//
// /*
// if(encode != null && encode.length() > 0) {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] ENCODE("+encode+") ");
// }
//
// try {
// sendData = new String(data, encode);
// } catch(Exception e) {
// if(logger.isError()){
// logger.error("HttpClientAdapter] ENCODE("+encode+") ERROR : "+ e.toString());
// logger.error("HttpClientAdapter] ENCODE("+encode+") SKIP ");
// }
// sendData = new String(data);
// }
// }
// else {
// sendData = new String(data);
//
// }
// */
//
// method.setQueryString(parameterName+"=" + sendData);
//
// int status = -1;
// try {
// status = client.executeMethod(method);
// //----------------------------------------------------------
// // 2008.01.23 : 응답이 깨지는 것 수정
// //----------------------------------------------------------
// //String responseMessage = method.getResponseBodyAsString();
// String responseMessage = new String(method.getResponseBody());
// //----------------------------------------------------------
// return responseMessage.getBytes();
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status!=HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA014", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 SOAP 방식으로 서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param soapAction soapAction 이름
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callSoapService(String url, String soapAction, byte[] data, String encode, int timeout)
// throws Exception {
// PostMethod method = new PostMethod(url);
//
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// ByteArrayRequestEntity entity = new ByteArrayRequestEntity(data);
//
// method.setRequestEntity(entity);
// method.setRequestHeader("SOAPAction", soapAction);
//
// int status = -1;
//
//
// try {
// status = client.executeMethod(method);
// //----------------------------------------------------------
// // 2008.01.23 : 응답이 깨지는 것 수정
// //----------------------------------------------------------
// //String responseMessage = method.getResponseBodyAsString();
// String responseMessage = new String(method.getResponseBody());
// //----------------------------------------------------------
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Post 방식으로 메신저 연계서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callMemoService(String url, byte[] data, String encode, int timeout)
// throws Exception {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callMemoService called ");
// }
//
// PostMethod method = new PostMethod(url);
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// // 2009.08.24 강길수차장 요청
// // MEMO Data Size : 161 Bytes -> 587 (항목 및 길이가 변경됨)
// int memoMinSize = 587;
//
// if(data.length >= memoMinSize) {
// if(encode != null && encode.length() > 0) {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callMemoService ENCODE("+encode+") ");
// }
// method.addParameter("SRV_CODE", new String(data, 0, 6, encode) );
// method.addParameter("SER_TYPE", new String(data, 6, 1, encode) );
// method.addParameter("RECIPIENT", new String(data, 7, 7, encode) );
// method.addParameter("SEND", new String(data, 14, 7, encode) );
// method.addParameter("TITLE", new String(data, 21, 40, encode) );
// method.addParameter("BODY", new String(data, 61,500, encode) );
// method.addParameter("URGENT", new String(data,561, 1, encode) );
// method.addParameter("SAVEOPTION", new String(data,562, 1, encode) );
// method.addParameter("RCV_IP", new String(data,563, 24, encode) );
// }
// else {
// method.addParameter("SRV_CODE", new String(data, 0, 6) );
// method.addParameter("SER_TYPE", new String(data, 6, 1) );
// method.addParameter("RECIPIENT", new String(data, 7, 7) );
// method.addParameter("SEND", new String(data, 14, 7) );
// method.addParameter("TITLE", new String(data, 21, 40) );
// method.addParameter("BODY", new String(data, 61,500) );
// method.addParameter("URGENT", new String(data,561, 1) );
// method.addParameter("SAVEOPTION", new String(data,562, 1) );
// method.addParameter("RCV_IP", new String(data,563, 24) );
// }
// }
// else {
// if(logger.isError()){
// logger.error("HttpClientAdapter] callMemoService Invalid Data Length (" + data.length + ") < "+memoMinSize);
// }
// throw new Exception("HttpClientAdapter.callMemoService Error : MessageSize("+(data.length)+" Bytes) too small < "+memoMinSize);
// }
//
// int status = -1;
//
//
// try {
// HttpClient mclient = new HttpClient(new MultiThreadedHttpConnectionManager());
// mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// String responseMessage = new String(method.getResponseBody());
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Post 방식으로 메신저 연계서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callAnnounceService(String url, byte[] data, String encode, int timeout)
// throws Exception {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callAnnounceService called ");
// }
//
// PostMethod method = new PostMethod(url);
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// // Announce Data Size : 113 Bytes
// int annMinSize = 113;
//
// if(data.length >= annMinSize) {
// if(encode != null && encode.length() > 0) {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callAnnounceService ENCODE("+encode+") ");
// }
// method.addParameter("SRV_CODE", new String(data, 0, 6, encode) );
// method.addParameter("RECIPIENT", new String(data, 6, 7, encode) );
// method.addParameter("BODY", new String(data, 13,100, encode) );
// if(data.length > 153) {
// method.addParameter("URL", new String(data, 113, data.length-annMinSize,encode) );
// }
// }
// else {
// method.addParameter("SRV_CODE", new String(data, 0, 6) );
// method.addParameter("RECIPIENT", new String(data, 6, 7) );
// method.addParameter("BODY", new String(data, 13,100) );
// if(data.length > 153) {
// method.addParameter("URL", new String(data,113, data.length-annMinSize) );
// }
// }
// }
// else {
// if(logger.isError()){
// logger.error("HttpClientAdapter] callAnnounceService Invalid Data Length (" + data.length + ") < "+annMinSize);
// }
// throw new Exception("HttpClientAdapter.callAnnounceService Error : MessageSize("+(data.length)+" Bytes) too small < "+annMinSize);
// }
//
// int status = -1;
//
//
// try {
// HttpClient mclient = new HttpClient(new MultiThreadedHttpConnectionManager());
// mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// String responseMessage = new String(method.getResponseBody());
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Post 방식으로 메신저 연계서비스 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callPopupService(String url, byte[] data, String encode, int timeout)
// throws Exception {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callPopupService called ");
// }
//
// PostMethod method = new PostMethod(url);
//
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// // Popup Data Size : 153 Bytes
// int popupMinSize = 153;
//
// if(data.length >= popupMinSize) {
// if(encode != null && encode.length() > 0) {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callPopupService ENCODE("+encode+") ");
// }
// method.addParameter("SRV_CODE", new String(data, 0, 6, encode) );
// method.addParameter("RECIPIENT", new String(data, 6, 7, encode) );
// method.addParameter("TITLE", new String(data, 13, 40, encode) );
// method.addParameter("BODY", new String(data, 53,100, encode) );
// }
// else {
// method.addParameter("SRV_CODE", new String(data, 0, 6) );
// method.addParameter("RECIPIENT", new String(data, 6, 7) );
// method.addParameter("TITLE", new String(data, 13, 40) );
// method.addParameter("BODY", new String(data, 53,100) );
// }
// }
// else {
// if(logger.isError()){
// logger.error("HttpClientAdapter] callPopupService Invalid Data Length (" + data.length + ") < "+popupMinSize);
// }
// throw new Exception("HttpClientAdapter.callPopupService Error : MessageSize("+(data.length)+" Bytes) too small < "+popupMinSize);
// }
//
// int status = -1;
//
//
// try {
// HttpClient mclient = new HttpClient(new MultiThreadedHttpConnectionManager());
// mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// String responseMessage = new String(method.getResponseBody());
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//
// /**
// * 1. 기능 : 수동 시스템에 Post 방식으로 일자전환이벤트 호출
// * 2. 처리 개요 :
// * - 수동 시스템에 서비스 요청 하고 결과를 리턴 한다.
// * 3. 주의사항
// *
// * @param url 수동 시스템 웹 컴포넌트 URL
// * @param data 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// private byte[] callChangeDateService(String url, byte[] data, String encode, int timeout)
// throws Exception {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callChangeDateService called ");
// }
//
// PostMethod method = new PostMethod(url);
//
// //2008.02.15 : Timeout 처리로직 변경 (0 : 무한대 설정가능하게 함)
// if(timeout > -1) {
// method.getParams().setSoTimeout(timeout);
// }
//
// // Data Size : 15 Bytes
// int popupMinSize = 15;
//
// if(data.length >= popupMinSize) {
// if(encode != null && encode.length() > 0) {
// if(logger.isDebug()){
// logger.debug("HttpClientAdapter] callChangeDateService ENCODE("+encode+") ");
// }
// method.addParameter("req", new String(data, 0, 7, encode).trim() );
// method.addParameter("date", new String(data, 7, 8, encode) );
// }
// else {
// method.addParameter("req", new String(data, 0, 7).trim() );
// method.addParameter("date", new String(data, 7, 8) );
// }
// }
// else {
// if(logger.isError()){
// logger.error("HttpClientAdapter] callChangeDateService Invalid Data Length (" + data.length + ") < "+popupMinSize);
// }
// throw new Exception("HttpClientAdapter.callChangeDateService Error : MessageSize("+(data.length)+" Bytes) too small < "+popupMinSize);
// }
//
// int status = -1;
//
//
// try {
// HttpClient mclient = new HttpClient(new MultiThreadedHttpConnectionManager());
// mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// String responseMessage = new String(method.getResponseBody());
//
// return responseMessage.getBytes();
//
// } catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// ste.printStackTrace();
// System.out.println("HttpClientAdapter] SocketTimeoutException : " + ste.toString() );
// throw ste;
// } catch(ConnectException ce) {
// ce.printStackTrace();
// System.out.println("HttpClientAdapter] Connection Exception : " + ce.toString() );
// throw ce;
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if(logger.isDebug()){
// logger.debug(resMsg);
// }
// }
// }
// }
//}
@@ -0,0 +1,94 @@
package com.eactive.eai.adapter.http;
//import org.apache.commons.httpclient.params.HttpClientParams;
public class HttpClientTest
{
// public static void main(String args[]) throws Exception {
// MultiThreadedHttpConnectionManager cm = new MultiThreadedHttpConnectionManager();
//
//
// cm.setConnectionStaleCheckingEnabled(false);
// cm.setMaxConnectionsPerHost(10);
// cm.setMaxTotalConnections(1);
//
// // 2.0
// HttpClient client = new HttpClient(cm);
//
// //---------------------------------------------
// // 3.1
// //---------------------------------------------
// /*
// HttpClientParams params = new HttpClientParams();
// params.setSoTimeout(10 * 1000);
// HttpClient client = new HttpClient(params, cm);
// */
// //---------------------------------------------
//
// // Client Timeout 2.0
// //client.setTimeout(1000);
// String url = "http://172.29.65.69:7001/servlets/knova/svc/servlet/KBServlet";
// //String url = "http://search.empas.com/error.html";
// //String url = "http://172.17.33.237:7001/servlets/knova/svc/servlet/KBServlet";
//
// PostMethod method = new PostMethod(url);
// DefaultMethodRetryHandler retryhandler = new DefaultMethodRetryHandler();
// retryhandler.setRequestSentRetryEnabled(false);
// retryhandler.setRetryCount(3);
// method.setMethodRetryHandler(retryhandler);
//
// method.getParams().setSoTimeout(5000);
//
// System.out.println("HttpClientAdapter] getContentCharset("+client.getParams().getContentCharset()+") ");
// //client.getParams().setContentCharset("KSC5601");
// System.out.println("HttpClientAdapter] getContentCharset("+client.getParams().getContentCharset()+") ");
//
// String encode = "ISO8859_1";
// byte[] data = "000924KCO.11YE#0803249920000026 0200NOV01500001 20080324175117 HOSTDOM NOVDOM BB2B YE#0803249920000026 4001 000306604151345551013205062155211 이기옥             EL08022500020000000000000000056020080324200902261 ? 00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000 "
// .getBytes();
// String sendData = null;
// if(encode != null && encode.length() > 0) {
// System.out.println("HttpClientAdapter] ENCODE("+encode+") ");
//
// try {
// sendData = new String(data,encode);
// } catch(Exception e) {
// System.out.println("HttpClientAdapter] ENCODE("+encode+") ERROR : "+ e.toString());
// System.out.println("HttpClientAdapter] ENCODE("+encode+") SKIP ");
// sendData = new String(data);
// }
// }
// else {
// sendData = java.net.URLEncoder.encode(new String(data));
// }
//
// method.addParameter("_ELD_", sendData);
//
// int status = -1;
// try {
// status = client.executeMethod(method);
// //String responseMessage = method.getResponseBodyAsString();
// byte[] responseBytes = method.getResponseBody();
// System.out.println("method.getRequestCharSet() [" + method.getRequestCharSet() +"]");
// System.out.println("method.getResponseCharSet() [" + method.getResponseCharSet() +"]");
// System.out.println("responseMessage [" +new String(responseBytes) +"]");
// System.out.println("ISO8859_1 [" + new String(responseBytes, "ISO8859_1") +"]");
// System.out.println("EUC-KR [" + new String(responseBytes, "EUC-KR") +"]");
// } catch(ConnectException ce) {
// System.out.println("Connection Exception : " + ce.toString() );
// } catch(HttpRecoverableException hre) { // HttpClient 2.0일 경우에 발생
// System.out.println("HttpRecoverableException : " + hre.toString() );
// } catch(SocketTimeoutException ste) { // HttpClient 3.1일 경우에 발생
// System.out.println("SocketTimeoutException : " + ste.toString() );
// } catch(Exception e) {
// e.printStackTrace();
// throw e;
// } finally {
// method.releaseConnection();
// if(status != HttpStatus.SC_OK) {
// System.out.println("HttpStatus ["+status+"]");
// }
// }
// }
}
@@ -0,0 +1,79 @@
package com.eactive.eai.adapter.http;
import com.eactive.eai.adapter.AdapterPropManager;
import com.eactive.eai.adapter.AdapterVO;
import com.eactive.eai.common.testcall.TestCallException;
import com.eactive.eai.common.testcall.TestCallSupport;
import com.eactive.eai.common.util.Logger;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Properties;
//HttpQuicsClientAdapter의 통신상태를 체크하는 클래스
public class HttpExtOrgClientAdapterTestCall extends TestCallSupport
{
static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
public boolean isAlive() throws TestCallException
{
logger.debug("HttpExtOrgClientAdapterTestCall started");
try {
AdapterVO vo = this.getAdapterInfo();
String pgoName = vo.getPropGroupName();
//PropManager manager = PropManager.getInstance();
AdapterPropManager manager = AdapterPropManager.getInstance();
Properties prop = manager.getProperties(pgoName);
String url = prop.getProperty("URL");
//String url = "101.88.50.120:8285";
logger.debug("HttpExtOrgClientAdapterTestCall URL]["+url+"s]");
URL u = null;
try {
logger.debug("HttpExtOrgClientAdapterTestCall] url - ["+url+"]");
u = new URL(url);
} catch (MalformedURLException e) {
logger.warn("HttpExtOrgClientAdapterTestCall] Error at new URL - "+e.getClass().getName()+" : "+e.getMessage());
return false;
}
HttpURLConnection conn = null;
try {
conn = (HttpURLConnection) u.openConnection();
} catch (Exception e) {
logger.warn("HttpExtOrgClientAdapterTestCall] Error at openConnection - "+e.getClass().getName()+" : "+e.getMessage());
return false;
}
if(conn == null){
logger.warn("HttpExtOrgClientAdapterTestCall] Error at HttpURLConnection is null ");
return false;
}
logger.debug("HttpExtOrgClientAdapterTestCall ] try HttpURLConnection connect");
conn.connect();
logger.debug("HttpExtOrgClientAdapterTestCall end");
return true;
} catch(Exception e) {
//e.printStackTrace();
logger.warn("HttpExtOrgClientAdapterTestCall] Error - "+e.getClass().getName()+" : "+e.getMessage());
return false;
}
}
// public static void main(String args[]) throws Exception {
// test();
//}
// private static void test() throws Exception {
// HttpExtOrgClientAdapterTestCall test = new HttpExtOrgClientAdapterTestCall();
// System.out.println("HttpExtOrgClientAdapterTestCall ] isAlive - ["+test.isAlive()+"]");
// }
}
@@ -0,0 +1,127 @@
package com.eactive.eai.adapter.http;
import com.eactive.eai.transformer.util.CircularQueue;
import com.eactive.eai.transformer.util.ExceptionStackTrace;
import java.util.LinkedHashMap;
public class HttpMemoryLogger {
final static int MAX_LOG_MESSAGE_SIZE = 500000;
static LinkedHashMap<String,CircularQueue> txQueues = new LinkedHashMap<String,CircularQueue>();
static LinkedHashMap<String,CircularQueue> errorQueues = new LinkedHashMap<String,CircularQueue>();
static LinkedHashMap<String,Long> errorCounts = new LinkedHashMap<String,Long>();
static LinkedHashMap<String,Long> txCounts = new LinkedHashMap<String,Long>();
static private void checkTxQueue(String adapterGroupName){
if (txQueues.get(adapterGroupName) == null){
txQueues.put(adapterGroupName,new CircularQueue(20));
}
}
static private void checkErrorQueue(String adapterGroupName){
if (errorQueues.get(adapterGroupName) == null){
errorQueues.put(adapterGroupName,new CircularQueue(20));
}
}
static private void checkErrorCount(String adapterGroupName){
if (errorCounts.get(adapterGroupName) == null){
errorCounts.put(adapterGroupName,new Long(0));
}
}
static private void checkTxCount(String adapterGroupName){
if (txCounts.get(adapterGroupName) == null){
txCounts.put(adapterGroupName,new Long(0));
}
}
static public long getTransactionCount(String adapterGroupName) {
checkTxCount(adapterGroupName);
if (txCounts.get(adapterGroupName) == null)
return 0;
return txCounts.get(adapterGroupName);
}
static public String[] getTransactions(String adapterGroupName) {
checkTxQueue(adapterGroupName);
return txQueues.get(adapterGroupName).getRecords();
}
// static public void txlog(String adapterGroupName, String message) {
// if (message == null)
// return;
// if (message.length() > MAX_LOG_MESSAGE_SIZE)
// message = message.substring(0, MAX_LOG_MESSAGE_SIZE);
// checkTxQueue(adapterGroupName);
// txQueues.get(adapterGroupName).addRecord(message);
// }
static public void txlog(String adapterGroupName, String message) {
if (message == null)
return;
if (message.length() > MAX_LOG_MESSAGE_SIZE)
message = message.substring(0, MAX_LOG_MESSAGE_SIZE);
synchronized(HttpMemoryLogger.class) {
checkTxCount(adapterGroupName);
checkTxQueue(adapterGroupName);
Long l = txCounts.get(adapterGroupName);
txCounts.put(adapterGroupName,++l);
}
txQueues.get(adapterGroupName).addRecord(message);
}
static public long getErrorCount(String adapterGroupName) {
checkErrorCount(adapterGroupName);
if (errorCounts.get(adapterGroupName) == null)
return 0;
return errorCounts.get(adapterGroupName);
}
static public String[] getErrors(String adapterGroupName) {
checkErrorQueue(adapterGroupName);
return errorQueues.get(adapterGroupName).getRecords();
}
static public void error(String adapterGroupName, String message) {
if (message == null)
return;
if (message.length() > MAX_LOG_MESSAGE_SIZE)
message = message.substring(0, MAX_LOG_MESSAGE_SIZE);
synchronized(HttpMemoryLogger.class) {
checkErrorCount(adapterGroupName);
checkErrorQueue(adapterGroupName);
Long l = errorCounts.get(adapterGroupName);
errorCounts.put(adapterGroupName,++l);
}
errorQueues.get(adapterGroupName).addRecord(message);
//txQueues.get(adapterGroupName).addRecord("<font color='blue'>" + message + "</font>");
}
static public void error(String adapterGroupName,String message, Throwable t) {
if (message == null)
return;
if (message.length() > MAX_LOG_MESSAGE_SIZE)
message = message.substring(0, MAX_LOG_MESSAGE_SIZE);
synchronized(HttpMemoryLogger.class) {
checkErrorCount(adapterGroupName);
checkErrorQueue(adapterGroupName);
Long l = errorCounts.get(adapterGroupName);
errorCounts.put(adapterGroupName,++l);
}
errorQueues.get(adapterGroupName).addRecord(message + " | " + ExceptionStackTrace.dump(t));
//txQueues.get(adapterGroupName).addRecord("<font color='blue'>" + message + "\n" + ExceptionStackTrace.dump(t) + "</font>");
}
static public boolean isMemoryLogEnabled(String adapterGroupName) {
return true;
// PropGroupVO propGroupVO = PropManager.getInstance().getPropGroupVO("Transformer");
// if (propGroupVO == null)
// return false;
// String value = propGroupVO.getProperty("memory.log");
// if ("1".equals(value))
// return true;
// return false;
}
}
@@ -0,0 +1,26 @@
package com.eactive.eai.adapter.http;
public enum HttpMethodType {
POST,
PUT,
DELETE,
GET,
UNKNOWN;
public static HttpMethodType getValue(String value) {
try {
return valueOf(value.toUpperCase());
} catch (Exception e) {
return UNKNOWN;
}
}
// public static void main(String[] args) throws Exception {
//
// if ("DELETE".equals(HttpMethodType.DELETE.toString())){
// System.out.println("delete");
// }else{
//
// System.out.println("not delete");
// }
// }
}
@@ -0,0 +1,63 @@
package com.eactive.eai.adapter.http;
import org.apache.commons.lang3.StringUtils;
public class HttpStatusException extends Exception {
/**
*
*/
private static final long serialVersionUID = 1L;
private int status = 200;
private String code;
/**
* 1. 기능 : Default Constructor
* 2. 처리 개요 : Default Constructor
* 3. 주의사항
*
**/
public HttpStatusException() {
super("HttpStatusException is occured.");
}
/**
* 1. 기능 : Exception message를 초기화하는 Constructor
* 2. 처리 개요 : Exception message를 초기화하는 Constructor
* -
* 3. 주의사항
*
* @param msg Exception message
**/
public HttpStatusException(String msg) {
super(msg);
}
public HttpStatusException(String msg, int status) {
super(msg);
this.status = status;
}
public HttpStatusException(String msg, String code, int status) {
super(msg);
this.setCode(code);
this.status = status;
}
public int getStatus() {
return status;
}
public void setStatus(int status) {
this.status = status;
}
public String getCode() {
if (StringUtils.isBlank(code)) {
return String.format("Http Status: %d", status);
} else {
return code;
}
}
public void setCode(String code) {
this.code = code;
}
}
@@ -0,0 +1,39 @@
package com.eactive.eai.adapter.http.async;
import javax.servlet.AsyncEvent;
import javax.servlet.AsyncListener;
import javax.servlet.ServletResponse;
import java.io.IOException;
import java.io.PrintWriter;
//@WebListener
public class AppAsyncListener implements AsyncListener {
@Override
public void onComplete(AsyncEvent asyncEvent) throws IOException {
// System.out.println("AppAsyncListener onComplete");
// we can do resource cleanup activity here
}
@Override
public void onError(AsyncEvent asyncEvent) throws IOException {
// System.out.println("AppAsyncListener onError");
//we can return error response to client
}
@Override
public void onStartAsync(AsyncEvent asyncEvent) throws IOException {
// System.out.println("AppAsyncListener onStartAsync");
//we can log the event here
}
@Override
public void onTimeout(AsyncEvent asyncEvent) throws IOException {
// System.out.println("AppAsyncListener onTimeout");
//we can send appropriate response to client
ServletResponse response = asyncEvent.getAsyncContext().getResponse();
PrintWriter out = response.getWriter();
out.write("TimeOut Error in Processing");
}
}
@@ -0,0 +1,28 @@
package com.eactive.eai.adapter.http.async;
import javax.servlet.ServletContextEvent;
import javax.servlet.ServletContextListener;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
//@WebListener
public class AppContextListener implements ServletContextListener {
public void contextInitialized(ServletContextEvent servletContextEvent) {
// Default Timeout Setting 60sec
ThreadPoolExecutor executor = new ThreadPoolExecutor(100, 200, 60000L,
TimeUnit.MILLISECONDS, new ArrayBlockingQueue<Runnable>(100));
servletContextEvent.getServletContext().setAttribute("executor",
executor);
// System.out.println("AppContextListener contextInitialized::set ThreadPoolExecutor");
}
public void contextDestroyed(ServletContextEvent servletContextEvent) {
ThreadPoolExecutor executor = (ThreadPoolExecutor) servletContextEvent
.getServletContext().getAttribute("executor");
executor.shutdown();
// System.out.println("AppContextListener contextDestroyed::shutdown ThreadPoolExecutor");
}
}
@@ -0,0 +1,92 @@
package com.eactive.eai.adapter.http.async;
import com.eactive.eai.adapter.RequestDispatcher;
import com.eactive.eai.common.util.Logger;
import javax.servlet.AsyncContext;
import javax.servlet.ServletInputStream;
import javax.servlet.ServletRequest;
import java.io.IOException;
import java.io.PrintWriter;
import java.nio.ByteBuffer;
import java.util.Properties;
public class AsyncRequestProcessor implements Runnable {
private static Logger logger = Logger.getLogger(Logger.LOGGER_DEFAULT);
private AsyncContext asyncContext;
private String adapterGroupName;
private String adapterName;
private String encode = "euc-kr";
public AsyncRequestProcessor() {
}
public AsyncRequestProcessor(AsyncContext asyncCtx) {
this.asyncContext = asyncCtx;
// TODO : define adapter name rule
this.adapterGroupName = "_EAI_IN_HTT_SyS";
this.adapterName = "_EAI_IN_HTT_SyS{ALL}";
}
@Override
public void run() {
// System.out.println("Async Supported? "
// + asyncContext.getRequest().isAsyncSupported());
ServletRequest request = asyncContext.getRequest();
ServletInputStream sis;
byte[] requestBytes = null;
byte[] result = null;
try {
sis = request.getInputStream();
ByteBuffer bb = ByteBuffer.allocate(1024);
int i=0;
byte[] cbuf = new byte[1024];
while( ( i = sis.read(cbuf, 0, 1024) ) != -1 ) {
if (i==1024){
bb.put(cbuf);
}else{
byte[] tail = new byte[i];
System.arraycopy(cbuf, 0, tail, 0, i);
bb.put(tail);
}
}
requestBytes = new byte[bb.position()];
bb.position(0);
bb.get(requestBytes);
Properties prop = new Properties();
// call Inbound Proxy
result = service(requestBytes, prop);
PrintWriter out = asyncContext.getResponse().getWriter();
String encodedResponse = new String(result, encode);
out.write(encodedResponse);
} catch (IOException e1) {
logger.error("AsyncRequestProcessor IOException", e1);
} catch (Exception e) {
logger.error("AsyncRequestProcessor Exception", e);
}
finally {
if(asyncContext != null) {
asyncContext.complete();
}
}
}
protected byte[] service(byte[] message, Properties prop) throws Exception {
Object obj = RequestDispatcher.getRequestDispatcher(this.adapterGroupName).handle(adapterName, message, prop);
if(obj == null) return null;
if(obj instanceof byte[]) {
return (byte[])obj;
} else if(obj instanceof String) {
return ((String)obj).getBytes();
} else {
throw new Exception("RECEAIAHA001");
}
}
}
@@ -0,0 +1,54 @@
package com.eactive.eai.adapter.http.async;
import javax.servlet.AsyncContext;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.concurrent.ThreadPoolExecutor;
//@WebServlet(urlPatterns = "/AsyncServlet", asyncSupported = true)
public class AsyncServlet extends HttpServlet {
private static final long serialVersionUID = 1L;
@Override
protected void doPost(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
handle(request, response);
}
@Override
protected void doGet(HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException {
handle(request, response);
}
private void handle(HttpServletRequest request,
HttpServletResponse response) {
// long startTime = System.currentTimeMillis();
// System.out.println("AsyncServlet Start::Name="
// + Thread.currentThread().getName() + "::ID="
// + Thread.currentThread().getId());
request.setAttribute("org.apache.catalina.ASYNC_SUPPORTED", true);
AsyncContext asyncCtx = request.startAsync();
AppAsyncListener asyncListener = new AppAsyncListener();
asyncCtx.addListener(asyncListener);
asyncCtx.setTimeout(30000); // Async Timeout 30 secs
// ThreadPoolExecutor executor = (ThreadPoolExecutor) request
// .getServletContext().getAttribute("executor");
// executor.execute(new AsyncRequestProcessor(asyncCtx));
asyncCtx.start(new AsyncRequestProcessor(asyncCtx));
// long endTime = System.currentTimeMillis();
// System.out.println("AsyncServlet End::Name="
// + Thread.currentThread().getName() + "::ID="
// + Thread.currentThread().getId() + "::Time Taken="
// + (endTime - startTime) + " ms.");
}
}
@@ -0,0 +1,538 @@
package com.eactive.eai.adapter.http.client;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URISyntaxException;
import java.nio.charset.Charset;
import java.nio.charset.UnsupportedCharsetException;
import java.security.KeyManagementException;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
import java.security.UnrecoverableKeyException;
import java.security.cert.CertificateException;
import java.util.HashMap;
import java.util.Properties;
import java.util.concurrent.TimeUnit;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.net.ssl.SSLContext;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import org.apache.hc.client5.http.classic.HttpClient;
import org.apache.hc.client5.http.classic.methods.HttpUriRequestBase;
import org.apache.hc.client5.http.config.RequestConfig;
import org.apache.hc.client5.http.impl.classic.HttpClients;
import org.apache.hc.client5.http.impl.io.PoolingHttpClientConnectionManager;
import org.apache.hc.client5.http.impl.io.PoolingHttpClientConnectionManagerBuilder;
import org.apache.hc.client5.http.ssl.NoopHostnameVerifier;
import org.apache.hc.client5.http.ssl.SSLConnectionSocketFactory;
import org.apache.hc.client5.http.ssl.TrustAllStrategy;
import org.apache.hc.core5.http.HttpRequest;
import org.apache.hc.core5.http.HttpRequestInterceptor;
import org.apache.hc.core5.http.HttpResponseInterceptor;
import org.apache.hc.core5.ssl.SSLContextBuilder;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterManager;
import com.eactive.eai.adapter.Keys;
import com.eactive.eai.adapter.http.secure.HttpClient5SSLContextFactory;
import com.eactive.eai.common.TransactionContextKeys;
import com.eactive.eai.common.util.HttpAdapterExtraLogUtil;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoVO;
import com.eactive.eai.util.TestModeChecker;
public abstract class HttpClient5AdapterServiceSupport implements HttpClientAdapterService, HttpClientAdapterServiceKey {
protected static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
protected HttpClient client;
PoolingHttpClientConnectionManager connectionManager;
private static boolean testMode = TestModeChecker.isTestMode();
public synchronized void close() {
if(connectionManager != null) {
connectionManager.close();
}
}
protected HttpClientAdapterVO setting(Properties prop, Properties tempProp) {
String url = null;
String parameterName = null;
String method = null;
String contentType = null;
String encode = null;
String testCallYn = null;
String adapterGroupName = null;
String adapterName = null;
String responseType = null;
String urlEncodeYn = null;
String adapterHeader = null;
boolean useMtls = false;
String keyStorePath = null;
String keyStorePassword = null;
String trustStorePath = null;
String trustStorePassword = null;
int connectionTimeout = 0;
int timeout = -1;
int traceLevel = 0;
long slowTranTime = 2000L;
url = prop.getProperty(URL);
String url2grp = tempProp.getProperty(URL);
if (!StringUtils.isEmpty(url2grp)) {
url = url2grp;
}
method = prop.getProperty(METHOD);
parameterName = prop.getProperty(PARAMETER_NAME, PARAMETER_MESSAGE);
contentType = prop.getProperty(CONTENT_TYPE, "");
responseType = prop.getProperty(RESPONSE_TYPE, "SYNC");
urlEncodeYn = prop.getProperty(URL_ENCODE_YN, "N");
String connectionTimeoutTemp = prop.getProperty(CONNECTION_TIMEOUT, "0");
String httpVersion = prop.getProperty(HTTP_VERSION);
adapterHeader = prop.getProperty(ADAPTER_HEADER, "");
String traceLevelTemp = prop.getProperty(TRACE_LEVEL, "0");
String timeoutTemp = prop.getProperty(HTTP_TIME_OUT, "0");
useMtls = StringUtils.equalsIgnoreCase(prop.getProperty(HttpClientAdapterServiceKey.USE_MTLS),"Y");
keyStorePath = prop.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PATH);
keyStorePassword = prop.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PWD);
trustStorePath = prop.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PATH);
trustStorePassword = prop.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PWD);
encode = tempProp.getProperty(Keys.CHARSET_KEY_OUT, Charset.defaultCharset().name());
testCallYn = tempProp.getProperty(TESTCALL_YN, "N");
adapterGroupName = tempProp.getProperty(ADAPTER_GROUP_NAME);
adapterName = tempProp.getProperty(ADAPTER_NAME);
// 인터페이스 정보에 설정된 타임아웃
String interfaceTimeout = tempProp.getProperty("INTERFACE_TIME_OUT");
if (StringUtils.isNotBlank(interfaceTimeout) && NumberUtils.toInt(interfaceTimeout) > 0) {
timeoutTemp = interfaceTimeout;
}
url = StringUtils.trim(url);
parameterName = StringUtils.trim(parameterName);
method = StringUtils.trim(method);
encode = StringUtils.trim(encode);
contentType = StringUtils.trim(contentType);
try {
connectionTimeout = Integer.parseInt(connectionTimeoutTemp);
} catch (Exception e) {
logger.debug("HttpClientAdapterSupport] connectionTimeoutTemp not int");
}
try {
timeout = Integer.parseInt(timeoutTemp);
} catch (NumberFormatException e) {
logger.warn("HttpClientAdapterSupport] timeoutTemp not int", e);
}
try {
traceLevel = Integer.parseInt(traceLevelTemp);
} catch (Exception e) {
logger.warn("HttpClientAdapterSupport] traceLevelTemp not int", e);
}
// client 중 BODY,POST,GET,NexCore 방식만 적용
HashMap<String, String> adapterHeaders = new HashMap<>();
try {
Matcher matcher = Pattern
.compile("\\{[ ]*\"[ ]*([a-zA-Z0-9_-]+)[ ]*\"[ ]*,[ ]*\"[ ]*([a-zA-Z0-9/;,\\*=_ -]+)[ ]*\"[ ]*\\}[ ]*")
.matcher(adapterHeader.trim());
while (matcher.find()) {
String key = matcher.group(1).trim();
String value = matcher.group(2).trim();
adapterHeaders.put(key, value);
}
} catch (Exception e) {
if(logger.isDebug()) logger.debug("HttpClientAdapterSupport] adapter header parsing error " + adapterHeader);
}
// GW 전달 로직 추가
// tempProp로 넘겨서 하는 이유는 outboundProp가 clone 안하는 로직이라 outboundProp로 넘길시 문제의 소지가있음
String transactionId = tempProp.getProperty(HttpClientAdapterServiceKey.TRANSACTION_ID);
String instanceId = tempProp.getProperty(HttpClientAdapterServiceKey.INSTANCE_ID);
if (StringUtils.isNotBlank(transactionId) && StringUtils.isNotBlank(instanceId)) {
adapterHeaders.put(HttpClientAdapterServiceKey.TRANSACTION_ID, transactionId);
adapterHeaders.put(HttpClientAdapterServiceKey.INSTANCE_ID, instanceId);
}
HttpClientAdapterVO vo = new HttpClientAdapterVO();
vo.setUrl(url);
vo.setMethod(method);
vo.setParameterName(parameterName);
vo.setEncode(encode);
vo.setContentType(contentType);
vo.setTestCallYn(testCallYn);
vo.setResponseType(responseType);
vo.setUrlEncodeYn(urlEncodeYn);
vo.setAdapterGroupName(adapterGroupName);
vo.setAdapterName(adapterName);
vo.setMaxTotalConnections(getMaxTotalConnections());
vo.setMaxHostConnections(getMaxConnectionsPerHost());
vo.setConnectionTimeout(connectionTimeout);
vo.setTimeout(timeout);
vo.setTraceLevel(traceLevel);
vo.setSlowTranTime(slowTranTime);
vo.setAdapterHeaders(adapterHeaders);
if (StringUtils.equalsAny(httpVersion, HTTP_VERSION_FULL_1_1, HTTP_VERSION_1_1)) {
vo.setHttpVersion(HTTP_VERSION_1_1);
}
else if (StringUtils.equals(httpVersion, HTTP_VERSION_2_0)) {
vo.setHttpVersion(HTTP_VERSION_2_0);
}
else {
vo.setHttpVersion(HTTP_VERSION_1_0);
}
vo.setUseMtls(useMtls);
vo.setKeyStorePath(keyStorePath);
vo.setKeyStorePassword(keyStorePassword);
vo.setTrustStorePath(trustStorePath);
vo.setTrustStorePassword(trustStorePassword);
if (logger.isDebug()) {
logger.debug(vo.toString());
}
return vo;
}
protected HttpClient5AdapterServiceSupport() {
}
public synchronized void init(String adapterName,
boolean useMtls, HttpOutTlsInfoVO mtlsInfo,
int maxTotalConnections, int maxHostConnections) {
if(connectionManager != null) {
if( (connectionManager.getMaxTotal() == maxTotalConnections)
&& (connectionManager.getDefaultMaxPerRoute() == maxHostConnections) ) {
if(logger.isInfo()) {
logger.info("ConnectionManager REUSE : AdapterName=" + adapterName
+ " MaxTotalConnection (" + connectionManager.getMaxTotal()
+ ") MaxHostConnections (" + connectionManager.getDefaultMaxPerRoute()
+ ")"
);
}
return;
}
else {
if(logger.isWarn()) {
logger.warn("ConnectionManager RELOAD : AdapterName=" + adapterName
+ " MaxTotalConnection (" + connectionManager.getMaxTotal() + " -> " + maxTotalConnections
+ ") MaxHostConnections (" + connectionManager.getDefaultMaxPerRoute() + " -> " + maxHostConnections
+ ")"
);
}
connectionManager.close();
connectionManager = null;
this.client = null;
}
}
if(logger.isWarn()) {
logger.warn("ConnectionManager INIT : AdapterName=" + adapterName
+ " MaxTotalConnection (" + maxTotalConnections
+ ") MaxHostConnections (" + maxHostConnections
+ ")"
);
}
PoolingHttpClientConnectionManagerBuilder cmBuilder = PoolingHttpClientConnectionManagerBuilder.create();
try {
if(logger.isWarn()) {
logger.warn("mTLS Config : AdapterName=" + adapterName
+ " useMtls (" + useMtls + ") mtlsInfo - " + mtlsInfo);
}
SSLContext sslContext = null;
if (useMtls && mtlsInfo != null) {
String storeType = mtlsInfo.getStoreType();
String keyStoreInfo = mtlsInfo.getKeystoreInfo();
String keyStorePassword = mtlsInfo.getKeystorePassword();
String trustStoreInfo = mtlsInfo.getTruststoreInfo();
String trustStorePassword = mtlsInfo.getTruststorePassword();
String[] tlsVersions = null;
// {
// "TLSv1.0"
// , "TLSv1.1"
// , "TLSv1.2"
// , "TLSv1.3"
// };
String[] cipherSuites = null;
// {
// "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384",
// "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384",
// "TLS_RSA_WITH_AES_256_CBC_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384",
// "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384",
// "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256",
// "TLS_DHE_DSS_WITH_AES_256_CBC_SHA256",
// "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
// "TLS_RSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA",
// "TLS_DHE_RSA_WITH_AES_256_CBC_SHA",
// "TLS_DHE_DSS_WITH_AES_256_CBC_SHA",
// "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_DHE_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_DHE_DSS_WITH_AES_128_CBC_SHA256",
// "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
// "TLS_RSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA",
// "TLS_DHE_RSA_WITH_AES_128_CBC_SHA",
// "TLS_DHE_DSS_WITH_AES_128_CBC_SHA",
// "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_DHE_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_DHE_DSS_WITH_AES_256_GCM_SHA384",
// "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_DHE_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_DHE_DSS_WITH_AES_128_GCM_SHA256",
// "TLS_EMPTY_RENEGOTIATION_INFO_SCSV"
// };
if( StringUtils.isAnyEmpty(keyStoreInfo, keyStorePassword) ) {
throw new Exception("mTLS keyStore config error");
}
boolean skipTrust = false;
// kbank에서는 trustStore를 사용하지 않음
if( StringUtils.isAnyEmpty(trustStoreInfo, trustStorePassword) ) {
// throw new Exception("mTLS trustStore config error");
if(logger.isWarn()) logger.warn("Skip trustStore validation adapterName : " + adapterName);
skipTrust = true;
}
sslContext = HttpClient5SSLContextFactory.createMTLSContextFromContent(
storeType,
keyStoreInfo, keyStorePassword,
trustStoreInfo, trustStorePassword, skipTrust
,tlsVersions, cipherSuites);
// SSLConnectionSocketFactory 생성
// Exception in thread "main" javax.net.ssl.SSLPeerUnverifiedException: Certificate for <localhost> doesn't match common name of the certificate subject: elink
// at org.apache.hc.client5.http.ssl.DefaultHostnameVerifier.matchCN(DefaultHostnameVerifier.java:180)
// at org.apache.hc.client5.http.ssl.DefaultHostnameVerifier.verify(DefaultHostnameVerifier.java:118)
// at org.apache.hc.client5.http.ssl.TlsSessionValidator.verifySession(TlsSessionValidator.java:112)
// => NoopHostnameVerifier.INSTANCE
SSLConnectionSocketFactory sslSocketFactory = null;
if(testMode) {
// Hostname verifier 비활성화 (테스트용)
sslSocketFactory = new SSLConnectionSocketFactory(
sslContext
, NoopHostnameVerifier.INSTANCE
);
}
else {
sslSocketFactory = new SSLConnectionSocketFactory(
sslContext
);
}
cmBuilder.setSSLSocketFactory(sslSocketFactory);
}
else {
sslContext = SSLContextBuilder.create().loadTrustMaterial(new TrustAllStrategy()).build();
SSLConnectionSocketFactory csf = new SSLConnectionSocketFactory(sslContext);
cmBuilder.setSSLSocketFactory(csf);
}
} catch (KeyManagementException | NoSuchAlgorithmException | KeyStoreException
| CertificateException | IOException | UnrecoverableKeyException e) {
throw new RuntimeException(e);
}
catch (Exception e) {
throw new RuntimeException(e);
}
this.connectionManager = cmBuilder.build();
connectionManager.setMaxTotal(maxTotalConnections);
connectionManager.setDefaultMaxPerRoute(maxHostConnections);
HttpRequestInterceptor requestLogInterceptor = (request, entity, context) -> {
try {
String uuid = (String) context.getAttribute(TransactionContextKeys.TRANSACTION_UUID);
String contextAdapterGroupName = (String) context.getAttribute(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME);
String contextAdapterName = (String) context.getAttribute(HttpClientAdapterServiceKey.ADAPTER_NAME);
String url = request.getUri().toString();
Integer logProcessNo = (Integer) context.getAttribute(HttpClientAdapterServiceKey.LOG_PROCESS_NO);
if (logProcessNo == null || logProcessNo <= 0) {
logProcessNo = 200;
}
HttpAdapterExtraLogUtil.insertHttpAdapterExtraLog(uuid, logProcessNo,
contextAdapterGroupName, contextAdapterName, request.getHeaders(), url, request.getMethod());
} catch (URISyntaxException e) {
throw new RuntimeException(e);
}
};
HttpResponseInterceptor responseLogInterceptor = (response, entity, context) -> {
try{
HttpRequest request = (HttpRequest)context.getAttribute("http.request");
String url = request.getUri().toString();
String uuid = (String) context.getAttribute(TransactionContextKeys.TRANSACTION_UUID);
String contextAdapterGroupName = (String) context.getAttribute(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME);
String contextAdapterName = (String) context.getAttribute(HttpClientAdapterServiceKey.ADAPTER_NAME);
Integer logProcessNo = (Integer) context.getAttribute(HttpClientAdapterServiceKey.LOG_PROCESS_NO);
if (logProcessNo == null || logProcessNo <= 0) {
logProcessNo = 300;
}else if(logProcessNo == 400){
return;
}else{
logProcessNo += 100;
}
HttpAdapterExtraLogUtil.insertHttpAdapterExtraLog(uuid, logProcessNo,
contextAdapterGroupName, contextAdapterName, response.getHeaders(), url, request.getMethod(), response.getCode());
} catch (URISyntaxException e) {
throw new RuntimeException(e);
}
};
this.client = HttpClients.custom()
.addRequestInterceptorLast(requestLogInterceptor)
.addResponseInterceptorFirst(responseLogInterceptor)
.setConnectionManager(connectionManager)
.build();
}
public int getConnectionsInPool() {
if (this.client == null || this.connectionManager == null)
return 0;
return this.connectionManager.getTotalStats().getAvailable() + this.connectionManager.getTotalStats().getLeased();
}
public int getMaxTotalConnections() {
if (this.client == null || this.connectionManager == null)
return 0;
return this.connectionManager.getMaxTotal();
}
public int getMaxConnectionsPerHost() {
if (this.client == null || this.connectionManager == null)
return 0;
return this.connectionManager.getDefaultMaxPerRoute();
}
public String getResponseCharSet(String httpResponseCharset, String adapterGroupName) {
if (StringUtils.isNotBlank(httpResponseCharset)) {
return httpResponseCharset;
} else {
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo = m.getAdapterGroupVO(adapterGroupName);
return agvo.getMessageEncode();
}
}
/**
* encoding에 대한 정의 필요 고려할 문제
* 1. 어댑터그룹이 UJN 타입일경우 return 은 UTF-8 로 getBytes 된
* 데이터여야됨.
* 2. http response에 받은 encoding 타입은 고려대상임. 결론 : response Encoding 과
* 어댑터의 MESSAGE_TYPE 다르면 변환, 나머지면 return 어댑터의 ENCODE은 요청전문 encoding에서만 사용
*
* 예) 어댑터의 ENCODE, 어댑터의 MESSAGE TYPE, RESPNSE ENCODING TYPE, 처리내용
* 예) ,ECU-KR ,JSN , EUC-KR , 응답받은 메시지를 return 예) ,ECU-KR , JSN , UTF-8 , 응답받은 메시지를 new
* String(xxx,"UTF-8") => getBytes("EUC-KR") 예) ,ECU-KR , UJN , EUC-KR , 응답받은
* 메시지를 new String(xxx,"EUC-KR") => getBytes("UTF-8") 예) ,ECU-KR , UJN , UTF-8 ,
* 응답받은 메시지를 return 예) ,UTF-8 , JSN , EUC-KR , 응답받은 메시지를 return
* 예) ,UTF-8 , JSN , UTF-8 , 응답받은 메시지를 new String(xxx,"UTF-8") => getBytes(EUC-KR") 예) ,UTF-8 ,
* UJN , EUC-KR , 응답받은 메시지를 new String(xxx,"EUC-KR") => getBytes("UTF-8") 예)
* ,UTF-8 , UJN , UTF-8 , 응답받은 메시지를 return
*
*
*/
public byte[] getEncodingConvert(String httpResponseCharset, String adapterGroupName, byte[] message) {
byte[] responseMessage = null;
if (StringUtils.isNotBlank(httpResponseCharset)) {
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo = m.getAdapterGroupVO(adapterGroupName);
String adapterTypeEncoding = StringUtils.defaultIfBlank(agvo.getMessageEncode(),
Charset.defaultCharset().name());
Charset responseCharset = null;
Charset adapterCharset = null;
try {
responseCharset = Charset.forName(httpResponseCharset);
adapterCharset = Charset.forName(adapterTypeEncoding);
if (responseCharset.compareTo(adapterCharset) == 0) {
responseMessage = message;
} else {// http 응답 charset 과 어댑터의 charset 이 다를경우 charset 변환 필요
String encodingString = new String(message, httpResponseCharset);
responseMessage = encodingString.getBytes(adapterTypeEncoding);
}
} catch (UnsupportedCharsetException | UnsupportedEncodingException e) {
responseMessage = message;
}
} else {
responseMessage = message;
}
return responseMessage;
}
public void configureHttpClient(RequestConfig.Builder requestConfigBuilder, HttpClientAdapterVO vo, HttpUriRequestBase method) {
if (vo.getConnectionTimeout() != 0) {
requestConfigBuilder.setConnectTimeout(vo.getConnectionTimeout(), TimeUnit.MILLISECONDS);
}
if (vo.getTimeout() > -1) {
requestConfigBuilder.setResponseTimeout(vo.getTimeout(), TimeUnit.MILLISECONDS);
}
/*
if (HTTP_VERSION_1_1.equals(vo.getHttpVersion())) {
method.addHeader("Connection", "close");
}
*/
org.apache.hc.core5.http.HttpVersion httpVersion ;
if (HTTP_VERSION_1_0.equals(vo.getHttpVersion())) {
httpVersion = org.apache.hc.core5.http.HttpVersion.HTTP_1_0;
}
else if (HTTP_VERSION_2_0.equals(vo.getHttpVersion())) {
httpVersion = org.apache.hc.core5.http.HttpVersion.HTTP_2_0;
}
else {
httpVersion = org.apache.hc.core5.http.HttpVersion.HTTP_1_1;
method.addHeader("Connection", "close");
}
method.setVersion(httpVersion);
RequestConfig requestConfig = requestConfigBuilder
.setConnectTimeout(vo.getConnectionTimeout(), TimeUnit.MILLISECONDS) // 연결 시간 초과를 5초로 설정
.setResponseTimeout(vo.getTimeout(), TimeUnit.MILLISECONDS) // 응답 시간 초과를 5초로 설정
.build();
method.setConfig(requestConfig);
}
public abstract Object execute(Properties prop, Object message, Properties tempProp) throws Exception;
}
@@ -0,0 +1,55 @@
package com.eactive.eai.adapter.http.client;
import java.util.Properties;
import com.eactive.eai.adapter.AdapterPropManager;
import com.eactive.eai.adapter.http.dynamic.HttpLoggerManager;
import com.eactive.eai.adapter.listener.AdapterException;
import com.eactive.eai.adapter.listener.AdapterListenerSupport;
import com.eactive.eai.common.util.Logger;
public class HttpClientAdapterListener extends AdapterListenerSupport {
final static Logger logger2 = HttpLoggerManager.getInstance().getLogger();
final static Logger errLogger = HttpLoggerManager.getInstance().getErrLogger();
public void start() throws AdapterException {
try {
if (info == null) {
throw new Exception("HttpClientAdapterListener | AdapterVO가 NULL입니다.");
}
AdapterPropManager manager = AdapterPropManager.getInstance();
Properties outboundProp = manager.getProperties(info.getPropGroupName());
String adapterGroupName = info.getAdapterGroupName();
String adapterName = info.getName();
String httpType = outboundProp.getProperty(HttpClientAdapterServiceKey.HTTP_TYPE);
HttpClientAdapterServiceFactory.createFactory(httpType, adapterGroupName, adapterName);
if(logger2.isInfo()) {
logger2.info("[HttpClientAdapterListener] AdapterName [" + info.getAdapterGroupName() + "." + info.getName()
+ "] httpType [" + httpType + "] start");
}
info.setStatus(true);
} catch (Exception e) {
logger.error(info.getName() + " | HttpClientAdapterListener | cannot start : " + e.getMessage(), e);
throw new AdapterException(info.getName() + " | HttpClientAdapterListener | cannot start - " + e.getMessage());
}
}
public void stop() throws AdapterException {
try {
if (info == null) {
throw new Exception("HttpClientAdapterListener | AdapterVO가 NULL입니다.");
}
String adapterName = info.getName();
HttpClientAdapterServiceFactory.removeFactory(adapterName);
if(logger2.isInfo()) {
logger2.info("[HttpClientAdapterListener] AdapterName [" + info.getAdapterGroupName() + "." + info.getName()
+ "] adapter info [" + info + "] stop");
}
info.setStatus(false);
} catch (Exception e) {
logger.error(info.getName() + " | HttpClientAdapterListener | cannot stop : " + e.getMessage(), e);
throw new AdapterException(info.getName() + " | HttpClientAdapterListener | cannot stop - " + e.getMessage());
}
}
}
@@ -0,0 +1,22 @@
package com.eactive.eai.adapter.http.client;
import java.util.Properties;
import com.eactive.eai.adapter.ElinkDefaultAdapter;
import com.eactive.eai.common.util.Logger;
public class HttpClientAdapterMain extends ElinkDefaultAdapter {
private static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception {
String httpType = prop.getProperty(HttpClientAdapterServiceKey.HTTP_TYPE); // Http Type에 대한 class name
String adapterGroupName = tempProp.getProperty(com.eactive.eai.adapter.Keys.OUT_ADAPTER_GROUP_NAME);
String adapterName = tempProp.getProperty(com.eactive.eai.adapter.Keys.OUT_ADAPTER_NAME);
HttpClientAdapterService service = HttpClientAdapterServiceFactory.createFactory(httpType, adapterGroupName, adapterName);
if (service == null) {
throw new Exception("Can not create HttpClientAdapterService httpType=" + httpType +" adapterName="+adapterName);
}
return service.execute(prop, message, tempProp);
}
}
@@ -0,0 +1,14 @@
package com.eactive.eai.adapter.http.client;
import java.util.Properties;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoVO;
public interface HttpClientAdapterService {
public Object execute(Properties prop, Object message, Properties tempProp) throws Exception;
public void close();
public void init(String adapterName,
boolean useMtls, HttpOutTlsInfoVO mtlsInfo,
int maxTotalConnections, int maxHostConnections);
}
@@ -0,0 +1,119 @@
package com.eactive.eai.adapter.http.client;
import java.util.Properties;
import java.util.concurrent.ConcurrentHashMap;
import org.apache.commons.lang.StringUtils;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterManager;
import com.eactive.eai.adapter.AdapterPropManager;
import com.eactive.eai.adapter.AdapterVO;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoManager;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoVO;
public class HttpClientAdapterServiceFactory {
private static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
private static ConcurrentHashMap<String, HttpClientAdapterService> adapters = new ConcurrentHashMap<>();
private static ConcurrentHashMap<String, String> adapterClass = new ConcurrentHashMap<>();
private HttpClientAdapterServiceFactory() {
super();
}
public static HttpClientAdapterService createFactory(String className, String adapterGroupName, String adapterName) throws Exception {
HttpClientAdapterService service = null;
if (adapters.containsKey(adapterName)) {
service = adapters.get(adapterName);
if (className.equals(adapterClass.get(adapterName))) {
return service;
}
else {
service.close();
service = null;
}
}
try {
Class cl = Class.forName(className);
service = (HttpClientAdapterService) cl.newInstance();
boolean useMtls = false;
int maxTotalConnections = HttpClientAdapterServiceKey.DEFAULT_MAX_TOTAL_CONNECTIONS;
int maxHostConnections = HttpClientAdapterServiceKey.DEFAULT_MAX_CONNECTION_PER_HOST;
AdapterVO adapterVo = AdapterManager.getInstance().getAdapterVO(adapterGroupName, adapterName);
AdapterPropManager manager = AdapterPropManager.getInstance();
Properties outboundProp = manager.getProperties(adapterVo.getPropGroupName());
try {
maxTotalConnections = Integer.parseInt(outboundProp.getProperty(HttpClientAdapterServiceKey.MAX_TOTAL_CONNECTIONS));
}
catch(NumberFormatException ex) {
maxTotalConnections = HttpClientAdapterServiceKey.DEFAULT_MAX_TOTAL_CONNECTIONS;
if(logger.isWarn()) {
logger.warn("HttpClientAdapterService. : {}, adatperName : {} UseDefault {}={}, {}"
, className, adapterName,HttpClientAdapterServiceKey.MAX_TOTAL_CONNECTIONS, maxTotalConnections, ex.toString());
}
}
try {
maxHostConnections = Integer.parseInt(outboundProp.getProperty(HttpClientAdapterServiceKey.MAX_CONNECTION_PER_HOST));
}
catch(NumberFormatException ex) {
maxHostConnections = HttpClientAdapterServiceKey.DEFAULT_MAX_CONNECTION_PER_HOST;
if(logger.isWarn()) {
logger.warn("HttpClientAdapterService. : {}, adatperName : {} UseDefault {}={}, {}"
, className, adapterName,HttpClientAdapterServiceKey.MAX_CONNECTION_PER_HOST, maxHostConnections, ex.toString());
}
}
// clientID -> mTLS 인증정보 획득
useMtls = StringUtils.equalsIgnoreCase(outboundProp.getProperty(HttpClientAdapterServiceKey.USE_MTLS),"Y");
AdapterGroupVO adapterGroup = AdapterManager.getInstance().getAdapterGroup(adapterGroupName);
// outboundProp.getProperty(HttpClientAdapterServiceKey.CLIENT_ID);
String clientId = adapterGroup.getClientId();
if(logger.isInfo()) {
logger.info("MTLS adapterName. : {}, useMtls. : {}, clientId : {}", adapterName, useMtls, clientId);
}
HttpOutTlsInfoVO mtlsInfo = null;
if(useMtls) {
HttpOutTlsInfoManager tlsManager = HttpOutTlsInfoManager.getInstance();
if(StringUtils.isNotEmpty(clientId)) {
mtlsInfo = tlsManager.getHttpOutTlsInfo(clientId);
}
}
// keyStorePath = outboundProp.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PATH);
// keyStorePassword = outboundProp.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PWD);
// trustStorePath = outboundProp.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PATH);
// trustStorePassword = outboundProp.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PWD);
service.init(adapterName,
useMtls, mtlsInfo,
maxTotalConnections, maxHostConnections);
if (service != null) {
adapters.put(adapterName, service);
adapterClass.put(adapterName, className);
}
} catch (Exception e) {
logger.error("Cannot create a HttpClientAdapterService. : {}, adatperName : {}", className, adapterName, e);
throw e;
}
return service;
}
public static void removeFactory(String adapterName) {
String className = null;
if (adapters.containsKey(adapterName)) {
adapters.remove(adapterName);
className = adapterClass.remove(adapterName);
if(logger.isWarn()) {
logger.warn("Remove HttpClientAdapterService. : {}, adatperName : {}", className, adapterName);
}
}
}
}
@@ -0,0 +1,90 @@
package com.eactive.eai.adapter.http.client;
public interface HttpClientAdapterServiceKey {
public static final String ADAPTER_GROUP_NAME = "ADAPTER_GROUP_NAME";
public static final String ADAPTER_NAME = "ADAPTER_NAME";
public static final String HTTP_TYPE = "HTTP_TYPE";
public static final String URL = "URL";
public static final String URL_2GRP = "URL_2GRP";
public static final String METHOD = "METHOD";
public static final String PARAMETER_NAME = "PARAMETER_NAME";
public static final String TRAN_CODE = "TRAN_CODE";
public static final String LOCAL_CALL = "LOCAL_CALL";
public static final String LOCAL_CALL_Y = "Y";
public static final String LOG_PROCESS_NO = "LOG_PROCESS_NO";
public static final String LOCAL_IP = "LOCAL_IP";
public static final String ENCODE = "ENCODE";
public static final String CONTENT_TYPE = "CONTENT_TYPE";
public static final String CONTENT_TYPE_KEY = "Content-Type";
public static final String METHOD_GET = "GET";
public static final String METHOD_POST = "POST";
public static final String RESPONSE_TYPE = "RESPONSE_TYPE";
public static final String RESPONSE_TYPE_SYNC = "SYNC";
public static final String RESPONSE_TYPE_ASYNC = "ASYN";
public static final String METHOD_SOAP = "SOAP";
public static final String METHOD_SOAP_ACTION = "SOAPAction";
public static final String REST_OPTION = "REST_OPTION";
public static final String TOUTVAL = "TOUTVAL";
public static final String CONNECTION_STALE_CHECKING_ENABLED = "CONNECTION_STALE_CHECKING_ENABLED";
// 호스트 마다 최대 연결 수
public static final int DEFAULT_MAX_CONNECTION_PER_HOST = 10;
public static final String MAX_CONNECTION_PER_HOST = "MAX_CONNECTION_PER_HOST";
// 최대 HTTP 연결 수
public static final int DEFAULT_MAX_TOTAL_CONNECTIONS = 100;
public static final String MAX_TOTAL_CONNECTIONS = "MAX_TOTAL_CONNECTIONS";
static final String PARAMETER_MESSAGE = "_message_";
static final String URL_ENCODE_YN = "URL_ENCODE_YN";
static final String CONNECTION_TIMEOUT = "CONNECTION_TIMEOUT";
static final String ADAPTER_HEADER = "ADAPTER_HEADER";
public static final String HTTP_TIME_OUT = "HTTP_TIME_OUT";
public static final int DEFAULT_TIME_OUT = 30 * 1000;
public static final String TESTCALL_URL = "TESTCALL_URL";
public static final String TESTCALL_YN = "TESTCALL_YN";
public static final String TRACE_LEVEL = "TRACE_LEVEL";
public static final String HEALTHCHECK_URL = "HEALTHCHECK_URL";
public static final String HEALTHCHECK_TIMEOUTMS = "HEALTHCHECK_TIMEOUTMS";
public static final String INBOUND_METHOD = "INBOUND_METHOD";
public static final String INBOUND_URI = "INBOUND_URI";
public static final String INBOUND_EXTURI = "INBOUND_EXTURI";
public static final String INBOUND_HEADER = "INBOUND_HEADER";
public static final String HTTP_VERSION = "HTTP_VERSION";
public static final String HTTP_VERSION_1_0 = "1.0";
public static final String HTTP_VERSION_1_1 = "1.1";
public static final String HTTP_VERSION_2_0 = "2.0";
public static final String HTTP_VERSION_FULL_1_1 = "HTTP_1_1";
public static final String HTTP_VERSION_FULL_1_0 = "HTTP_1_0";
public static final String USE_MTLS = "USE_MTLS";
public static final String CLIENT_ID = "CLIENT_ID";
public static final String KEYSTORE_PATH = "KEYSTORE_PATH";
public static final String KEYSTORE_PWD = "KEYSTORE_PWD";
public static final String TRUSTSTORE_PATH = "TRUSTSTORE_PATH";
public static final String TRUSTSTORE_PWD = "TRUSTSTORE_PWD";
public static final String TRANSACTION_ID = "transactionId";
public static final String INSTANCE_ID = "instanceId";
public static final String TRANSACTION_SVC_PATTERN ="TRANSACTION_SVC_PATTERN";//(SYNC/ASYN)-(SYNC/ASYN)
}
@@ -0,0 +1,439 @@
package com.eactive.eai.adapter.http.client;
import java.io.UnsupportedEncodingException;
import java.nio.charset.Charset;
import java.nio.charset.UnsupportedCharsetException;
import java.util.HashMap;
import java.util.Properties;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import javax.net.ssl.SSLContext;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpMethodBase;
import org.apache.commons.httpclient.HttpVersion;
import org.apache.commons.httpclient.MultiThreadedHttpConnectionManager;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.httpclient.protocol.ProtocolSocketFactory;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.math.NumberUtils;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterManager;
import com.eactive.eai.adapter.Keys;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.CustomSSLProtocolSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.adapter.http.secure.SSLContextFactory;
import com.eactive.eai.common.util.Logger;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoManager;
import com.eactive.eai.httpouttlsinfo.HttpOutTlsInfoVO;
public abstract class HttpClientAdapterServiceSupport implements HttpClientAdapterService, HttpClientAdapterServiceKey {
protected static Logger logger = Logger.getLogger(Logger.LOGGER_ADAPTER);
protected HttpClient client;
private MultiThreadedHttpConnectionManager connectionManager;
public synchronized void close() {
if (connectionManager != null) {
connectionManager.shutdown();
}
}
protected HttpClientAdapterVO setting(Properties prop, Properties tempProp) {
String url = null;
String parameterName = null;
String method = null;
String contentType = null;
String encode = null;
String testCallYn = null;
String adapterGroupName = null;
String adapterName = null;
String responseType = null;
String urlEncodeYn = null;
String adapterHeader = null;
boolean useMtls = false;
String keyStorePath = null;
String keyStorePassword = null;
String trustStorePath = null;
String trustStorePassword = null;
int connectionTimeout = 0;
int timeout = -1;
int traceLevel = 0;
long slowTranTime = 2000L;
url = prop.getProperty(URL);
String url2grp = tempProp.getProperty(URL);
if (!StringUtils.isEmpty(url2grp)) {
url = url2grp;
}
method = prop.getProperty(METHOD);
parameterName = prop.getProperty(PARAMETER_NAME, PARAMETER_MESSAGE);
contentType = prop.getProperty(CONTENT_TYPE, "");
responseType = prop.getProperty(RESPONSE_TYPE, "SYNC");
urlEncodeYn = prop.getProperty(URL_ENCODE_YN, "N");
String connectionTimeoutTemp = prop.getProperty(CONNECTION_TIMEOUT, "0");
String httpVersion = prop.getProperty(HTTP_VERSION);
adapterHeader = prop.getProperty(ADAPTER_HEADER, "");
String traceLevelTemp = prop.getProperty(TRACE_LEVEL, "0");
String timeoutTemp = prop.getProperty(HTTP_TIME_OUT);
useMtls = StringUtils.equalsIgnoreCase(prop.getProperty(HttpClientAdapterServiceKey.USE_MTLS), "Y");
keyStorePath = prop.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PATH);
keyStorePassword = prop.getProperty(HttpClientAdapterServiceKey.KEYSTORE_PWD);
trustStorePath = prop.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PATH);
trustStorePassword = prop.getProperty(HttpClientAdapterServiceKey.TRUSTSTORE_PWD);
encode = tempProp.getProperty(Keys.CHARSET_KEY_OUT, Charset.defaultCharset().name());
testCallYn = tempProp.getProperty(TESTCALL_YN, "N");
adapterGroupName = tempProp.getProperty(ADAPTER_GROUP_NAME);
adapterName = tempProp.getProperty(ADAPTER_NAME);
// 인터페이스 정보에 설정된 타임아웃
String interfaceTimeout = tempProp.getProperty("INTERFACE_TIME_OUT");
if (StringUtils.isNotBlank(interfaceTimeout) && NumberUtils.toInt(interfaceTimeout) > 0) {
timeoutTemp = interfaceTimeout;
}
url = StringUtils.trim(url);
parameterName = StringUtils.trim(parameterName);
method = StringUtils.trim(method);
encode = StringUtils.trim(encode);
contentType = StringUtils.trim(contentType);
if (timeoutTemp == null) {
timeoutTemp = "0";
} else {
timeoutTemp = timeoutTemp.trim();
}
try {
connectionTimeout = Integer.parseInt(connectionTimeoutTemp);
} catch (Exception e) {
logger.debug("HttpClientAdapterSupport] connectionTimeoutTemp not int");
}
try {
timeout = Integer.parseInt(timeoutTemp);
} catch (NumberFormatException e) {
logger.warn("HttpClientAdapterSupport] timeoutTemp not int", e);
}
try {
traceLevel = Integer.parseInt(traceLevelTemp);
} catch (Exception e) {
logger.warn("HttpClientAdapterSupport] traceLevelTemp not int", e);
}
// client 중 BODY,POST,GET,NexCore 방식만 적용
HashMap<String, String> adapterHeaders = new HashMap<>();
try {
Matcher matcher = Pattern.compile(
"\\{[ ]*\"[ ]*([a-zA-Z0-9_-]+)[ ]*\"[ ]*,[ ]*\"[ ]*([a-zA-Z0-9/;,\\*=_ -]+)[ ]*\"[ ]*\\}[ ]*")
.matcher(adapterHeader.trim());
while (matcher.find()) {
String key = matcher.group(1).trim();
String value = matcher.group(2).trim();
adapterHeaders.put(key, value);
}
} catch (Exception e) {
if (logger.isDebug())
logger.debug("HttpClientAdapterSupport] adapter header parsing error " + adapterHeader);
}
// GW 전달 로직 추가
// tempProp로 넘겨서 하는 이유는 outboundProp가 clone 안하는 로직이라 outboundProp로 넘길시 문제의 소지가있음
String transactionId = tempProp.getProperty(HttpClientAdapterServiceKey.TRANSACTION_ID);
String instanceId = tempProp.getProperty(HttpClientAdapterServiceKey.INSTANCE_ID);
if (StringUtils.isNotBlank(transactionId) && StringUtils.isNotBlank(instanceId)) {
adapterHeaders.put(HttpClientAdapterServiceKey.TRANSACTION_ID, transactionId);
adapterHeaders.put(HttpClientAdapterServiceKey.INSTANCE_ID, instanceId);
}
HttpClientAdapterVO vo = new HttpClientAdapterVO();
vo.setUrl(url);
vo.setMethod(method);
vo.setParameterName(parameterName);
vo.setEncode(encode);
vo.setContentType(contentType);
vo.setTestCallYn(testCallYn);
vo.setResponseType(responseType);
vo.setUrlEncodeYn(urlEncodeYn);
vo.setAdapterGroupName(adapterGroupName);
vo.setAdapterName(adapterName);
vo.setMaxTotalConnections(getMaxTotalConnections());
vo.setMaxHostConnections(getMaxConnectionsPerHost());
vo.setConnectionTimeout(connectionTimeout);
vo.setTimeout(timeout);
vo.setTraceLevel(traceLevel);
vo.setSlowTranTime(slowTranTime);
vo.setAdapterHeaders(adapterHeaders);
if (StringUtils.equalsAny(httpVersion, HTTP_VERSION_FULL_1_1, HTTP_VERSION_1_1)) {
vo.setHttpVersion(HTTP_VERSION_1_1);
} else {
vo.setHttpVersion(HTTP_VERSION_1_0);
}
vo.setUseMtls(useMtls);
vo.setKeyStorePath(keyStorePath);
vo.setKeyStorePassword(keyStorePassword);
vo.setTrustStorePath(trustStorePath);
vo.setTrustStorePassword(trustStorePassword);
if (logger.isDebug()) {
logger.debug(vo.toString());
}
return vo;
}
protected HttpClientAdapterServiceSupport() {
}
public synchronized void init(String adapterName, boolean useMtls, HttpOutTlsInfoVO mtlsInfo,
int maxTotalConnections, int maxHostConnections) {
if (connectionManager != null) {
if ((connectionManager.getParams().getMaxTotalConnections() == maxTotalConnections)
&& (connectionManager.getParams().getDefaultMaxConnectionsPerHost() == maxHostConnections)) {
if (logger.isInfo()) {
logger.info("ConnectionManager REUSE : AdapterName=" + adapterName + " MaxTotalConnection ("
+ connectionManager.getParams().getMaxTotalConnections() + ") MaxHostConnections ("
+ connectionManager.getParams().getDefaultMaxConnectionsPerHost() + ")");
}
return;
} else {
if (logger.isWarn()) {
logger.warn("ConnectionManager RELOAD : AdapterName=" + adapterName + " MaxTotalConnection ("
+ connectionManager.getParams().getMaxTotalConnections() + " -> " + maxTotalConnections
+ ") MaxHostConnections (" + connectionManager.getParams().getDefaultMaxConnectionsPerHost()
+ " -> " + maxHostConnections + ")");
}
connectionManager.shutdown();
connectionManager = null;
this.client = null;
}
}
if (logger.isWarn()) {
logger.warn("ConnectionManager INIT : AdapterName=" + adapterName + " MaxTotalConnection ("
+ maxTotalConnections + ") MaxHostConnections (" + maxHostConnections + ")");
}
connectionManager = new MultiThreadedHttpConnectionManager();
connectionManager.getParams().setStaleCheckingEnabled(true);
connectionManager.getParams().setMaxTotalConnections(maxTotalConnections);
connectionManager.getParams().setDefaultMaxConnectionsPerHost(maxHostConnections);
this.client = new HttpClient(connectionManager);
}
public int getConnectionsInPool() {
if (this.client == null)
return 0;
MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager) this.client
.getHttpConnectionManager();
return mgr.getConnectionsInPool();
}
public int getMaxTotalConnections() {
if (this.client == null)
return 0;
MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager) this.client
.getHttpConnectionManager();
return mgr.getParams().getMaxTotalConnections();
}
public int getMaxConnectionsPerHost() {
if (this.client == null)
return 0;
MultiThreadedHttpConnectionManager mgr = (MultiThreadedHttpConnectionManager) this.client
.getHttpConnectionManager();
return mgr.getParams().getDefaultMaxConnectionsPerHost();
}
public String getResponseCharSet(String httpResponseCharset, String adapterGroupName) {
if (StringUtils.isNotBlank(httpResponseCharset)) {
return httpResponseCharset;
} else {
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo = m.getAdapterGroupVO(adapterGroupName);
return agvo.getMessageEncode();
}
}
/**
* encoding에 대한 정의 필요 고려할 문제 1. 어댑터그룹이 UJN 타입일경우 return 은 UTF-8 로 getBytes 된
* 데이터여야됨. 2. http response에 받은 encoding 타입은 고려대상임. 결론 : response Encoding 과
* 어댑터의 MESSAGE_TYPE 다르면 변환, 나머지면 return 어댑터의 ENCODE은 요청전문 encoding에서만 사용
*
* 예) 어댑터의 ENCODE, 어댑터의 MESSAGE TYPE, RESPNSE ENCODING TYPE, 처리내용 예) ,ECU-KR
* ,JSN , EUC-KR , 응답받은 메시지를 return 예) ,ECU-KR , JSN , UTF-8 , 응답받은 메시지를 new
* String(xxx,"UTF-8") => getBytes("EUC-KR") 예) ,ECU-KR , UJN , EUC-KR , 응답받은
* 메시지를 new String(xxx,"EUC-KR") => getBytes("UTF-8") 예) ,ECU-KR , UJN , UTF-8 ,
* 응답받은 메시지를 return 예) ,UTF-8 , JSN , EUC-KR , 응답받은 메시지를 return 예) ,UTF-8 , JSN
* , UTF-8 , 응답받은 메시지를 new String(xxx,"UTF-8") => getBytes(EUC-KR") 예) ,UTF-8 ,
* UJN , EUC-KR , 응답받은 메시지를 new String(xxx,"EUC-KR") => getBytes("UTF-8") 예)
* ,UTF-8 , UJN , UTF-8 , 응답받은 메시지를 return
*
*
*/
public byte[] getEncodingConvert(String httpResponseCharset, String adapterGroupName, byte[] message) {
byte[] responseMessage = null;
if (StringUtils.isNotBlank(httpResponseCharset)) {
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo = m.getAdapterGroupVO(adapterGroupName);
String adapterTypeEncoding = StringUtils.defaultIfBlank(agvo.getMessageEncode(),
Charset.defaultCharset().name());
Charset responseCharset = null;
Charset adapterCharset = null;
try {
responseCharset = Charset.forName(httpResponseCharset);
adapterCharset = Charset.forName(adapterTypeEncoding);
if (responseCharset.compareTo(adapterCharset) == 0) {
responseMessage = message;
} else {// http 응답 charset 과 어댑터의 charset 이 다를경우 charset 변환 필요
String encodingString = new String(message, httpResponseCharset);
responseMessage = encodingString.getBytes(adapterTypeEncoding);
}
} catch (UnsupportedCharsetException | UnsupportedEncodingException e) {
responseMessage = message;
}
} else {
responseMessage = message;
}
return responseMessage;
}
@SuppressWarnings("deprecation")
public void configureHttpClient(HttpClient mclient, HttpMethodBase method, HttpClientAdapterVO vo, String url,
String contentType) throws Exception {
if (StringUtils.isNotBlank(vo.getEncode())) {
mclient.getParams().setContentCharset(vo.getEncode());
}
if (vo.getConnectionTimeout() != 0) {
mclient.getHttpConnectionManager().getParams().setConnectionTimeout(vo.getConnectionTimeout());
}
if (vo.getTimeout() > -1) {
mclient.getHttpConnectionManager().getParams().setSoTimeout(vo.getTimeout());
}
if (HTTP_VERSION_1_1.equals(vo.getHttpVersion())) {
method.setRequestHeader("Connection", "close");
method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_1);
} else {
method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_0);
}
method.setFollowRedirects(false);
if (StringUtils.startsWith(url, "https")) {
if (vo.isUseMtls()) {
HttpOutTlsInfoManager tlsManager = HttpOutTlsInfoManager.getInstance();
String clientId = vo.getClientId();
HttpOutTlsInfoVO mtlsInfo = tlsManager.getHttpOutTlsInfo(clientId);
String storeType = mtlsInfo.getStoreType();
String keyStoreInfo = mtlsInfo.getKeystoreInfo();
String keyStorePassword = mtlsInfo.getKeystorePassword();
String trustStoreInfo = mtlsInfo.getTruststoreInfo();
String trustStorePassword = mtlsInfo.getTruststorePassword();
// Server negotiation 에 의해 변경될 수 있음
String[] tlsVersions = null;
// {
// "TLSv1.0"
// , "TLSv1.1"
// , "TLSv1.2"
// , "TLSv1.3"
// };
String[] cipherSuites = null;
// {
// "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA384",
// "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA384",
// "TLS_RSA_WITH_AES_256_CBC_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA384",
// "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA384",
// "TLS_DHE_RSA_WITH_AES_256_CBC_SHA256",
// "TLS_DHE_DSS_WITH_AES_256_CBC_SHA256",
// "TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA",
// "TLS_RSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDH_ECDSA_WITH_AES_256_CBC_SHA",
// "TLS_ECDH_RSA_WITH_AES_256_CBC_SHA",
// "TLS_DHE_RSA_WITH_AES_256_CBC_SHA",
// "TLS_DHE_DSS_WITH_AES_256_CBC_SHA",
// "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA256",
// "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_DHE_RSA_WITH_AES_128_CBC_SHA256",
// "TLS_DHE_DSS_WITH_AES_128_CBC_SHA256",
// "TLS_ECDHE_ECDSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDHE_RSA_WITH_AES_128_CBC_SHA",
// "TLS_RSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDH_ECDSA_WITH_AES_128_CBC_SHA",
// "TLS_ECDH_RSA_WITH_AES_128_CBC_SHA",
// "TLS_DHE_RSA_WITH_AES_128_CBC_SHA",
// "TLS_DHE_DSS_WITH_AES_128_CBC_SHA",
// "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDH_ECDSA_WITH_AES_256_GCM_SHA384",
// "TLS_ECDH_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_DHE_RSA_WITH_AES_256_GCM_SHA384",
// "TLS_DHE_DSS_WITH_AES_256_GCM_SHA384",
// "TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDH_ECDSA_WITH_AES_128_GCM_SHA256",
// "TLS_ECDH_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_DHE_RSA_WITH_AES_128_GCM_SHA256",
// "TLS_DHE_DSS_WITH_AES_128_GCM_SHA256",
// "TLS_EMPTY_RENEGOTIATION_INFO_SCSV"
// };
if (StringUtils.isAnyEmpty(keyStoreInfo, keyStorePassword)) {
throw new Exception("mTLS keyStore config error");
}
boolean skipTrust = false;
// kbank에서는 trustStore를 사용하지 않음
if (StringUtils.isAnyEmpty(trustStoreInfo, trustStorePassword)) {
// throw new Exception("mTLS trustStore config error");
if (logger.isWarn())
logger.warn("Skip trustStore validation adapterName : " + vo.getAdapterName());
skipTrust = true;
}
SSLContext sslContext = SSLContextFactory.createMTLSContextFromContent(storeType, keyStoreInfo,
keyStorePassword, trustStoreInfo, trustStorePassword, skipTrust, tlsVersions, cipherSuites);
// SSLProtocolSocketFactory 생성
ProtocolSocketFactory socketFactory = new CustomSSLProtocolSocketFactory(sslContext);
Protocol.registerProtocol("https", new Protocol("https", socketFactory, 443));
} else {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
}
if (StringUtils.equalsIgnoreCase(method.getName(), "POST")
|| StringUtils.equalsIgnoreCase(method.getName(), "PUT")) {
if (StringUtils.isNotBlank(contentType)) {
if (StringUtils.isBlank(vo.getEncode())) {
method.setRequestHeader("Content-Type", contentType);
} else {
method.setRequestHeader("Content-Type",
String.format("%s; charset=%s", contentType, vo.getEncode()));
}
}
}
}
public abstract Object execute(Properties prop, Object message, Properties tempProp) throws Exception;
}
@@ -0,0 +1,16 @@
package com.eactive.eai.adapter.http.client;
public enum HttpClientAdapterServiceType {
STANDARD,
EXTORG,
QUICS,
REST,
UNKNOWN;
public static HttpClientAdapterServiceType getValue(String value) {
try {
return valueOf(value.toUpperCase());
} catch (Exception e) {
return UNKNOWN;
}
}
}
@@ -0,0 +1,268 @@
package com.eactive.eai.adapter.http.client;
import java.util.HashMap;
public class HttpClientAdapterVO {
protected String url = null;
protected String parameterName = null;
protected String method = null;
protected String contentType = null;
protected String encode = null;
protected String testCallYn = null;
protected String adapterGroupName = null;
protected String adapterName = null;
protected String responseType = null;
protected String urlEncodeYn = null;
protected int connectionTimeout = 0;
protected int maxTotalConnections = 50;
protected int maxHostConnections = 10;
protected int timeout = -1;
protected int traceLevel = 0;
protected long slowTranTime = 2000L;
protected String httpVersion = null;
// client header 값 추가
protected HashMap<String, String> adapterHeaders = null;
// mTLS
boolean useMtls = false;
String clientId = null;
String keyStorePath = null;
String keyStorePassword = null;
String trustStorePath = null;
String trustStorePassword = null;
public int getMaxTotalConnections() {
return maxTotalConnections;
}
public void setMaxTotalConnections(int maxTotalConnections) {
this.maxTotalConnections = maxTotalConnections;
}
public int getMaxHostConnections() {
return maxHostConnections;
}
public void setMaxHostConnections(int maxHostConnections) {
this.maxHostConnections = maxHostConnections;
}
public String getHttpVersion() {
return httpVersion;
}
public void setHttpVersion(String httpVersion) {
this.httpVersion = httpVersion;
}
public String getUrl() {
return url;
}
public void setUrl(String url) {
this.url = url;
}
public String getParameterName() {
return parameterName;
}
public void setParameterName(String parameterName) {
this.parameterName = parameterName;
}
public String getMethod() {
return method;
}
public void setMethod(String method) {
this.method = method;
}
public String getContentType() {
return contentType;
}
public void setContentType(String contentType) {
this.contentType = contentType;
}
public String getEncode() {
return encode;
}
public void setEncode(String encode) {
this.encode = encode;
}
public String getTestCallYn() {
return testCallYn;
}
public void setTestCallYn(String testCallYn) {
this.testCallYn = testCallYn;
}
public String getAdapterGroupName() {
return adapterGroupName;
}
public void setAdapterGroupName(String adapterGroupName) {
this.adapterGroupName = adapterGroupName;
}
public String getAdapterName() {
return adapterName;
}
public void setAdapterName(String adapterName) {
this.adapterName = adapterName;
}
public String getResponseType() {
return responseType;
}
public void setResponseType(String responseType) {
this.responseType = responseType;
}
public String getUrlEncodeYn() {
return urlEncodeYn;
}
public void setUrlEncodeYn(String urlEncodeYn) {
this.urlEncodeYn = urlEncodeYn;
}
public int getConnectionTimeout() {
return connectionTimeout;
}
public void setConnectionTimeout(int connectionTimeout) {
this.connectionTimeout = connectionTimeout;
}
public int getTimeout() {
return timeout;
}
public void setTimeout(int timeout) {
this.timeout = timeout;
}
public int getTraceLevel() {
return traceLevel;
}
public void setTraceLevel(int traceLevel) {
this.traceLevel = traceLevel;
}
public long getSlowTranTime() {
return slowTranTime;
}
public void setSlowTranTime(long slowTranTime) {
this.slowTranTime = slowTranTime;
}
public HashMap<String, String> getAdapterHeaders() {
return adapterHeaders;
}
public void setAdapterHeaders(HashMap<String, String> adapterHeaders) {
this.adapterHeaders = adapterHeaders;
}
public boolean isUseMtls() {
return useMtls;
}
public void setUseMtls(boolean useMtls) {
this.useMtls = useMtls;
}
public String getClientId() {
return clientId;
}
public void setClientId(String clientId) {
this.clientId = clientId;
}
public String getKeyStorePath() {
return keyStorePath;
}
public void setKeyStorePath(String keyStorePath) {
this.keyStorePath = keyStorePath;
}
public String getKeyStorePassword() {
return keyStorePassword;
}
public void setKeyStorePassword(String keyStorePassword) {
this.keyStorePassword = keyStorePassword;
}
public String getTrustStorePath() {
return trustStorePath;
}
public void setTrustStorePath(String trustStorePath) {
this.trustStorePath = trustStorePath;
}
public String getTrustStorePassword() {
return trustStorePassword;
}
public void setTrustStorePassword(String trustStorePassword) {
this.trustStorePassword = trustStorePassword;
}
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
sb.append("HttpClientAdapterVO [adapterGroupName=" + adapterGroupName + ", adapterGroupName=" + adapterGroupName + ", responseType=" + responseType );
sb.append("\n");
sb.append("url=" + url + ", parameterName=" + parameterName + ", method=" + method );
sb.append("\n");
sb.append(", contentType=" + contentType + ", encode=" + encode + ", testCallYn=" + testCallYn );
sb.append("\n");
sb.append(", urlEncodeYn=" + urlEncodeYn + ", connectionTimeout=" + connectionTimeout );
sb.append("\n");
sb.append(", maxTotalConnections=" + maxTotalConnections + ", maxHostConnections=" + maxHostConnections );
sb.append("\n");
sb.append(", timeout=" + timeout + ", traceLevel=" + traceLevel + ", slowTranTime=" + slowTranTime );
sb.append("\n");
sb.append(", httpVersion=" + httpVersion + "]" );
if(adapterHeaders != null) {
sb.append("\nadapter header [\n");
for (String key : adapterHeaders.keySet()) {
sb.append(key).append("=").append(adapterHeaders.get(key));
sb.append("\n");
}
sb.append("\n]");
}
sb.append("\n");
sb.append(", useMtls=" + useMtls + ", clientId=" + clientId);
sb.append(", keyStorePath=" + keyStorePath + ", keyStorePassword=" + keyStorePassword );
sb.append(", trustStorePath=" + trustStorePath + ", trustStorePassword=" + trustStorePassword );
return sb.toString();
}
}
@@ -0,0 +1,206 @@
package com.eactive.eai.adapter.http.client.impl;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.client.HttpClient5AdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.common.TransactionContextKeys;
import com.eactive.eai.common.util.CommonLib;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import org.apache.hc.client5.http.classic.methods.HttpPost;
import org.apache.hc.client5.http.config.RequestConfig;
import org.apache.hc.client5.http.impl.classic.CloseableHttpResponse;
import org.apache.hc.core5.http.ContentType;
import org.apache.hc.core5.http.HttpHost;
import org.apache.hc.core5.http.io.entity.EntityUtils;
import org.apache.hc.core5.http.io.entity.StringEntity;
import org.apache.hc.core5.http.protocol.BasicHttpContext;
import org.apache.hc.core5.http.protocol.HttpContext;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.node.ObjectNode;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.Properties;
public class HttpClient5AdapterServiceBody extends HttpClient5AdapterServiceSupport {
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
boolean isAsync = false;
if (RESPONSE_TYPE_ASYNC.equals(vo.getResponseType())) {
isAsync = true;
}
RequestConfig.Builder requestConfigBuilder = RequestConfig.custom();
boolean useForwardProxy = StringUtils.equalsIgnoreCase(prop.getProperty("FORWARD_PROXY_USE_YN", "N"), "Y");
String forwardProxyUrl = prop.getProperty("FORWARD_PROXY_URL");
if(useForwardProxy) {
java.net.URL url = new java.net.URL(forwardProxyUrl);
// 프로토콜, 호스트, 포트 추출
String protocol = url.getProtocol();
String host = url.getHost();
int port = url.getPort();
HttpHost proxy = new HttpHost(protocol,host, port);
requestConfigBuilder.setProxy(proxy);
}
String sendData = "";
if (data instanceof String) {
sendData = (String) data;
} else if (data instanceof byte[]) {
sendData = new String((byte[]) data, vo.getEncode());
}
ObjectMapper mapper = new ObjectMapper();
ObjectNode jsonNode = (ObjectNode) mapper.readTree(sendData);
ObjectNode headerPart = (ObjectNode) jsonNode.get("header_part");
if( headerPart.get("mciIntfId") != null && headerPart.get("mciIntfId").asText().trim().length() > 0 ) {
headerPart.put("eaiIntfId", "");
sendData = mapper.writerWithDefaultPrettyPrinter().writeValueAsString(jsonNode);
}
if ("Y".equals(vo.getUrlEncodeYn())) {
sendData = java.net.URLEncoder.encode(sendData);
}
ContentType contentTypeObj ;
if (StringUtils.isNotEmpty(vo.getContentType())) {
//주석이유 : ContentType.create에서 "application/json;charset=UTF-8" 이런 형태면 오류발생
// String contentTypeValue ;
// if (StringUtils.isNotEmpty(vo.getEncode())) {
// contentTypeValue = vo.getContentType() + "; charset=" + vo.getEncode();
// } else {
// contentTypeValue = vo.getContentType();
// }
contentTypeObj = ContentType.create(vo.getContentType(), vo.getEncode());
}else{
contentTypeObj = ContentType.APPLICATION_JSON;
}
HttpPost method = new HttpPost(vo.getUrl());
// POST 요청 본문 설정
if (sendData != null) {
method.setEntity(new StringEntity(sendData, contentTypeObj));
}
if (vo.getAdapterHeaders() != null) {
for (String key : vo.getAdapterHeaders().keySet()) {
method.setHeader(key, vo.getAdapterHeaders().get(key));
}
}
if (logger.isInfoEnabled()) {
logger.info("" + CONTENT_TYPE_KEY + "(" + contentTypeObj + ")");
}
configureHttpClient(requestConfigBuilder, vo, method);
int status = -1;
try {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug(
"SEND (" + vo.getAdapterGroupName() + ") = [" + sendData + "]");
logger.debug("SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(sendData));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + sendData + "]" + CommonLib.getDumpMessage(sendData));
}
String uuid = tempProp.getProperty(TransactionContextKeys.TRANSACTION_UUID);
HttpContext context = new BasicHttpContext();
context.setAttribute(TransactionContextKeys.TRANSACTION_UUID, uuid);
context.setAttribute(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME, vo.getAdapterGroupName());
context.setAttribute(HttpClientAdapterServiceKey.ADAPTER_NAME, vo.getAdapterName());
Integer logProcessNo = (Integer) tempProp.get(HttpClientAdapterServiceKey.LOG_PROCESS_NO);
if (logProcessNo != null && logProcessNo > 0) {
context.setAttribute(HttpClientAdapterServiceKey.LOG_PROCESS_NO, logProcessNo);
}
byte[] responseMessage = null;
String responseString = "";
try (CloseableHttpResponse response = (CloseableHttpResponse) this.client.execute(method, context)) {
status = response.getCode();
responseMessage = EntityUtils.toByteArray(response.getEntity());
responseString = new String(responseMessage, vo.getEncode());
if (logger.isDebug()) {
logger.debug("[received status]" + status);
logger.debug("HttpClientAdapterServiceBody] RECV (" + vo.getAdapterGroupName() + ") = [" + responseString + "]");
}
} catch (ConnectException e) {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceBody] responseType =" + vo.getResponseType());
}
throw new Exception("excuteMethod java.net.ConnectException = " + e.getMessage());
}
stopWatch.stop();
if (status >= 400 && status < 500) {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), vo.getUrl(), "post", responseString);
throw new Exception(errMsg);
} else if(status != HttpStatus.SC_OK) {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), vo.getUrl(), "post", responseString);
throw new Exception(errMsg);
}
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime() && (logger.isWarn())) {
logger.warn("URL[" + vo.getUrl() + "] lazy async response time = "
+ stopWatch.toString() + " responseMessage=" + responseString);
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + responseString + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
return responseMessage;
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"SocketTimeoutException : " + ste.toString(), ste);
}
if (logger.isError()) {
logger.error("SocketTimeoutException : " + ste.toString(), ste);
}
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"Connection Exception : " + ce.toString(), ce);
}
if (logger.isError()) {
logger.error("Connection Exception : " + ce.toString(), ce);
}
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"Exception : " + e.toString(), e);
}
if (logger.isError()) {
logger.error("Exception : " + e.toString(), e);
}
throw e;
}
}
}
@@ -0,0 +1,895 @@
package com.eactive.eai.adapter.http.client.impl;
import java.io.IOException;
import java.io.StringReader;
import java.math.BigDecimal;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.net.URI;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Properties;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import com.eactive.eai.common.property.PropManager;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import org.apache.hc.client5.http.classic.HttpClient;
import org.apache.hc.client5.http.classic.methods.HttpDelete;
import org.apache.hc.client5.http.classic.methods.HttpGet;
import org.apache.hc.client5.http.classic.methods.HttpPost;
import org.apache.hc.client5.http.classic.methods.HttpPut;
import org.apache.hc.client5.http.classic.methods.HttpUriRequestBase;
import org.apache.hc.client5.http.config.RequestConfig;
import org.apache.hc.client5.http.entity.UrlEncodedFormEntity;
import org.apache.hc.client5.http.impl.classic.CloseableHttpResponse;
import org.apache.hc.core5.http.ContentType;
import org.apache.hc.core5.http.Header;
import org.apache.hc.core5.http.HttpHost;
import org.apache.hc.core5.http.HttpStatus;
import org.apache.hc.core5.http.NameValuePair;
import org.apache.hc.core5.http.io.entity.EntityUtils;
import org.apache.hc.core5.http.io.entity.StringEntity;
import org.apache.hc.core5.http.message.BasicNameValuePair;
import org.apache.hc.core5.http.protocol.BasicHttpContext;
import org.apache.hc.core5.http.protocol.HttpContext;
import org.apache.hc.core5.net.URIBuilder;
import org.dom4j.Document;
import org.dom4j.Element;
import org.dom4j.io.SAXReader;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import org.json.simple.parser.JSONParser;
import org.json.simple.parser.ParseException;
import org.springframework.web.util.UriComponents;
import org.springframework.web.util.UriComponentsBuilder;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpMethodType;
import com.eactive.eai.adapter.http.client.HttpClient5AdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.dynamic.HttpAdapterServiceKey;
import com.eactive.eai.common.TransactionContextKeys;
import com.eactive.eai.common.authoutbound.AccessTokenManagerByDB;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.message.MessageType;
import com.eactive.eai.common.util.CommonLib;
import com.jayway.jsonpath.DocumentContext;
import com.jayway.jsonpath.JsonPath;
import com.openbanking.eai.common.token.AccessTokenManager;
import com.openbanking.eai.common.token.AccessTokenVO;
import com.openbanking.eai.common.token.OAuth2AccessTokenVO;
/**
* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를 GET/POST 방식으로 호출할 수 있는
* 기능을 제공한다.<br>
* 2. 처리 개요 : <br>
* * - 2020-09-25: Http Header 받아서 처리할 수 있게 기능 추가<br>
* 3. 주의사항 <br>
*
* @author :
* @version : v 1.0.0
* @see : HttpClientAdapterServiceFactory.java,
* HttpClientAdapterServiceSupport.java
* @since :
*
*/
public class HttpClient5AdapterServiceRest extends HttpClient5AdapterServiceSupport
implements HttpClientAdapterServiceKey {
public static final String TYPE_VARIABLE_URL_REQUEST = "variableUrlRequest";
public static final String TYPE_SIMPLE_REQUEST = "simpleRequest";
public static final String REST_OPTION = "REST_OPTION";
//public static final String HEADER_CONTENT_TYPE = "Content-Type";
public static final String HEADER_GROUP = "HEADER_GROUP";
public static final String HTTP_STATUS = "HTTP_STATUS";
public static final String HEADER_KEYS = "HEADER_KEYS";
public static final String AUTH_TOKEN = "AUTH_TOKEN";
/**
* 1. 기능 : REST API 통신에 사용 <br>
* 2. 처리 개요 : - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다. <br>
* 3. 주의사항 <br>
*
* @param prop Http Adapter 속성 정보
* @return 반환 된 Object
* @exception Exception 수동 시스템 간 통신 중 발생
**/
@SuppressWarnings({ "unchecked" })
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
// 2025.04.09 Authorization 헤더값을 프로퍼티(AUTH_TOKEN)에서 지정하여 설정할 수 있도록 수정
// 2025.05.29 프로퍼티 그룹 AUTH_TOKEN이 없을때 Null Point Exception 발생하여 수정
String bizCode = "";
String authToken = "";
try {
Properties authProp = PropManager.getInstance().getProperties(AUTH_TOKEN); //Authorization
bizCode = vo.getAdapterGroupName().substring(1, 4);
authToken = authProp.getProperty(bizCode, "");
} catch (Exception e) {
logger.debug("Property Group AUTH_TOKEN is not Exist !!");
}
logger.debug("authToken :::::::::::::::::::::::::::::::::::" + authToken);
String headerGroupName = prop.getProperty(HEADER_GROUP);
String relayResponseHeaderKeys = prop.getProperty(HEADER_KEYS, "");
boolean useAdapterToken = StringUtils.equalsIgnoreCase(prop.getProperty("ADAPTER_TOKEN_USE_YN", "N"), "Y");
boolean useForwardProxy = StringUtils.equalsIgnoreCase(prop.getProperty("FORWARD_PROXY_USE_YN", "N"), "Y");
String forwardProxyUrl = prop.getProperty("FORWARD_PROXY_URL");
// ex) $.dataHeader.GW_RSLT_CD
String tokenErrorCodeKey = prop.getProperty("ADAPTER_TOKEN_ERROR_CODE_KEY");
String tokenErrorCodeValues = prop.getProperty("ADAPTER_TOKEN_ERROR_CODE_VALUES");
String tokenErrorHttpStatusCode = prop.getProperty("ADAPTER_TOKEN_ERROR_HTTP_STATUS_CODE"); // 200 or 400번대
// 레이아웃 메시지 타입 REST URL 추출 시 활용. Default JSON
String messageType = prop.getProperty("MESSAGE_TYPE", MessageType.JSON);
String inboundMethod = tempProp.getProperty(HttpAdapterServiceKey.INBOUND_METHOD, "POST");
/**
* @formatter:off
* TSEAIHE02.RESTOPTION 정보 => JSON 형태로 구성
* - type : simpleRequest, variableUrlRequest
* - extraPath : 어댑터 프로퍼티 URL에 추가될 HTTP REST URL
* - method : get, delete, post, put
* - contentType: application/json(default), application/x-www-form-urlencoded
* - adapterTokenUseYn: Y, N(default)
* ex)
* {"type":"simpleRequest","extraPath":"v2.0/accout/balance","method":"post"}
* @formatter:on
*/
String restOptionData = tempProp.getProperty(REST_OPTION);
JSONObject restOptionObject = parseJson(restOptionData);
if (restOptionObject == null) {
throw new Exception("OptionData parsing result is NULL");
}
String rmethod = (String) restOptionObject.getOrDefault("method", inboundMethod);
String contentType = (String) restOptionObject.getOrDefault("contentType", "application/json");
String adapterTokenUseYn = (String) restOptionObject.get("adapterTokenUseYn");
if (StringUtils.isNotBlank(adapterTokenUseYn)) { // interface 에 설정된게 우선한다.
useAdapterToken = StringUtils.equalsIgnoreCase(adapterTokenUseYn, "Y");
}
HttpClient mclient = this.client;
String sendData = "";
if (data instanceof String) {
sendData = (String) data;
} else if (data instanceof byte[]) {
sendData = new String((byte[]) data, vo.getEncode());
}
////mclient.getParams().setContentCharset(vo.getEncode());
JSONObject dataObject = null;
Object httpHeader = null;
Object dataContent = null;
if (MessageType.JSON.equals(messageType)) {
Object parsed = parseJsonGeneric(sendData);
if(parsed instanceof JSONObject) {
dataObject = parseJson(sendData);
if (dataObject != null && StringUtils.isNotBlank(headerGroupName)) {
httpHeader = dataObject.get(headerGroupName);
dataObject.remove(headerGroupName);
}
dataContent = dataObject;
if (dataObject.containsKey("innerList")) {
JSONArray innerList = (JSONArray) dataObject.get("innerList");
dataContent = innerList;
}
}
}
// if (MessageType.JSON.equals(messageType)) {
// dataObject = parseJson(sendData);
// if (dataObject != null && StringUtils.isNotBlank(headerGroupName)) {
// httpHeader = dataObject.get(headerGroupName);
// dataObject.remove(headerGroupName);
// }
// }
logger.debug("HttpClientAdapterServiceRest] dataObject1 = [" + dataObject + "]");
// interface 에 설정된게 우선한다.
String uri = null;
if (dataObject == null) {
uri = changeUrl(messageType, vo.getUrl(), restOptionData, sendData);
} else {
uri = changeUrl(messageType, vo.getUrl(), restOptionData, dataObject);
}
logger.debug("HttpClientAdapterServiceRest] dataObject2 = [" + dataObject + "]");
// ////if (vo.getConnectionTimeout() != 0) {
// mclient.getHttpConnectionManager().getParams().setConnectionTimeout(vo.getConnectionTimeout());
// }
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") URL=[" + vo.getUrl() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") PARAMETER_NAME=[" + vo.getParameterName() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") ENCODE=[" + vo.getEncode() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") RESPONSE_TYPE=[" + vo.getResponseType() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") URL_ENCODE_YN=[" + vo.getUrlEncodeYn() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") CONNECTION_TIMEOUT=[" + vo.getConnectionTimeout() + "] ");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") REST_OPTION=[" + restOptionData + "] ");
}
HttpUriRequestBase method = null;
// 메소드 타입에 따라 HttpRequestBase 인스턴스 생성
switch (HttpMethodType.getValue(rmethod)) {
case GET:
method = new HttpGet(uri);
break;
case DELETE:
method = new HttpDelete(uri);
break;
case POST:
method = new HttpPost(uri);
break;
case PUT:
method = new HttpPut(uri);
break;
default:
method = new HttpGet(uri);
break;
}
RequestConfig.Builder requestConfigBuilder = RequestConfig.custom();
if(useForwardProxy) {
java.net.URL url = new java.net.URL(forwardProxyUrl);
// 프로토콜, 호스트, 포트 추출
String protocol = url.getProtocol();
String host = url.getHost();
int port = url.getPort();
HttpHost proxy = new HttpHost(protocol,host, port);
requestConfigBuilder.setProxy(proxy);
}
configureHttpClient(requestConfigBuilder, vo, method);
switch (HttpMethodType.getValue(rmethod)) {
case GET:
case DELETE:
HashMap<String, String> h = getParameters(dataObject);
URIBuilder uriBuilder = new URIBuilder(uri);
for (Map.Entry<String, String> entry : h.entrySet()) {
uriBuilder.addParameter(entry.getKey(), entry.getValue());
}
URI fullUri = uriBuilder.build();
if (method instanceof HttpGet) {
((HttpGet) method).setUri(fullUri);
} else if (method instanceof HttpDelete) {
((HttpDelete) method).setUri(fullUri);
}
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceRest] (get Method) QueryString = [" + fullUri.getQuery() + "]");
}
break;
case PUT:
case POST:
// assignPostBody(dataObject, contentType, vo.getEncode(), method);
assignPostBody(dataContent, contentType, vo.getEncode(), method);
break;
default:
break;
}
if (logger.isDebugEnabled()) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") method.getParams()=["
+ method.getEntity() + "] ");
}
OAuth2AccessTokenVO accessToken = null;
if (useAdapterToken) {
AccessTokenManagerByDB tokenManager = AccessTokenManagerByDB.getInstance();
accessToken = (OAuth2AccessTokenVO) tokenManager.getAccessTokenVO(vo.getAdapterGroupName());
// 토큰이 없거나 만료 됐으면 재발급
if (accessToken == null || accessToken.isExpired()) {
String oldToken = accessToken == null ? null : accessToken.getAccessToken();
accessToken = (OAuth2AccessTokenVO) tokenManager.retryAccessTokenVO(vo.getAdapterGroupName(), prop,
oldToken);
}
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") TOKEN = ["
+ accessToken + "]");
}
setAuthHeaders(method, accessToken);
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName()
+ ") RequestHeader [Authorization=" + method.getHeader("Authorization") + "]");
}
}
if(!StringUtils.isBlank(authToken)) {
setAuthHeaders(method, authToken);
}
// 전달 header 셋팅
// Adapter 레벨 header 보다 data로 넘어온 httpHeader를 우선 적용(header명이 같다면 덮어씀)
assignRequestHeaders(method, httpHeader);
int status = -1;
try {
byte[] responseMessage = null;
Header[] responseHeaders;
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
if (dataObject != null) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") = ["
+ dataObject.toJSONString() + "]");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(dataObject.toJSONString()));
} else {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") = [" + sendData
+ "]");
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(sendData));
}
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + sendData + "]" + CommonLib.getDumpMessage(sendData));
}
String uuid = tempProp.getProperty(TransactionContextKeys.TRANSACTION_UUID);
HttpContext context = new BasicHttpContext();
context.setAttribute(TransactionContextKeys.TRANSACTION_UUID, uuid);
context.setAttribute(HttpClientAdapterServiceKey.ADAPTER_GROUP_NAME, vo.getAdapterGroupName());
context.setAttribute(HttpClientAdapterServiceKey.ADAPTER_NAME, vo.getAdapterName());
Integer logProcessNo = (Integer) tempProp.get(HttpClientAdapterServiceKey.LOG_PROCESS_NO);
if (logProcessNo != null && logProcessNo > 0) {
context.setAttribute(HttpClientAdapterServiceKey.LOG_PROCESS_NO, logProcessNo);
}
try {
if (logger.isDebug()) {
logger.debug("[method getName]" + method.getMethod());
logger.debug("[method getEntity]" + method.getEntity());
logger.debug("[method getRequestHeaders]" + method.getHeaders().toString());
logger.debug("[method getURI]" + method.getPath());
}
try (CloseableHttpResponse response = (CloseableHttpResponse) mclient.execute(method, context)) {
status = response.getCode();
responseMessage = EntityUtils.toByteArray(response.getEntity());
responseHeaders = response.getHeaders();
if (logger.isDebug()) {
logger.debug("[received status]" + status);
logger.debug("HttpClientAdapterServiceRest] RECV (" + vo.getAdapterGroupName() + ") = [" + responseMessage + "]");
}
}
} catch (ConnectException e) {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] responseType =" + vo.getResponseType());
}
throw new Exception("excuteMethod java.net.ConnectException = " + e.getMessage());
}
stopWatch.stop();
/**
* @formatter:off
* OAuth 토큰 응답 체크(Adapter properties로 설정)
* 응답코드에 따라 유효한 토큰 확인(토큰 재발급 여부 확인)
* API 서비스 마다 정책이 다름(보통 400대에서 체크하나 200에서도 체크할 수 있음)
*
* TOKEN_ERROR_CODE_KEY: 응답 json error code key
* __ex) $.dataHeader.resultCode
* TOKEN_ERROR_CODE_VALUES: 토큰 재발급이 필요한 응답 error codes(ex: O0001,O0002,O0003)
* TOKEN_ERROR_HTTP_STATUS_CODE: 보통 400대에서 체크하나 API 제공자에 따라 200에서도 체클할수 있음
* ex) TOKEN_ERROR_HTTP_STATUS_CODE = 200
* @formatter:on
*/
boolean needReissue = false;
Properties responseHeaderProp = assignRelayDataToInbound(tempProp, responseHeaders);
String responseString = new String(responseMessage, vo.getEncode());
Map<String, Object> map = new HashMap<String, Object>();
tempProp.put(HttpAdapterServiceKey.OUTBOUND_PROPERTY_MAP, map);
map.put(HttpAdapterServiceKey.OUTBOUND_RESPONSE_HEADERS, responseHeaderProp);
map.put(HttpAdapterServiceKey.OUTBOUND_RESPONSE_MESSAGE, responseString);
map.put(HttpAdapterServiceKey.OUTBOUND_RESPONSE_STATUS, status);
if (status >= 200 && status <= 207) {
if (useAdapterToken && StringUtils.equals(tokenErrorHttpStatusCode, "200")) {
needReissue = checkTokenRetry(responseMessage, tokenErrorCodeKey, tokenErrorCodeValues,
vo.getEncode());
}
} else if (status == 302) {
if (!StringUtils.contains(relayResponseHeaderKeys, "Location")) {
relayResponseHeaderKeys += ",Location";
}
} else {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), uri, rmethod, responseString);
// logger.error(errMsg);
if (status >= 400 && status < 500) {
if (useAdapterToken) {
needReissue = checkTokenRetry(responseMessage, tokenErrorCodeKey, tokenErrorCodeValues,
vo.getEncode());
}
if (!needReissue) {
throw new Exception(errMsg);
}
} else {
throw new Exception(errMsg);
}
}
// ----------------------------------------------------------
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] responseType =" + vo.getResponseType());
logger.debug("HttpClientAdapterServiceRest] RECV " + vo.getEncode() + "(" + vo.getAdapterGroupName() + ") = [" + new String(responseMessage, vo.getEncode()) + "]");
// logger.debug("HttpClientAdapterServiceRest] RECV MS949 (" + vo.getAdapterGroupName() + ") = [" + new String(responseMessage, "MS949") + "]");
// logger.debug("HttpClientAdapterServiceRest] RECV euc-kr (" + vo.getAdapterGroupName() + ") = [" + new String(responseMessage, "euc-kr") + "]");
logger.debug("HttpClientAdapterServiceRest] RECV (" + vo.getAdapterGroupName() + ") = " + CommonLib.getDumpMessage(responseMessage));
}
if (useAdapterToken) {
if (responseMessage == null) {
throw new Exception("responseMessage is NULL, HttpStatus=" + status);
}
// OAuth 토큰 재요청 코드 확인
if (needReissue) {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] retry access token response code = ["
+ vo.getResponseType() + "] message = [" + new String(responseMessage, vo.getEncode())
+ "]");
}
// 토큰 재발급
AccessTokenManager tokenManager = AccessTokenManager.getInstance();
String oldToken = accessToken == null ? null : accessToken.getAccessToken();
OAuth2AccessTokenVO newaccessToken = (OAuth2AccessTokenVO) tokenManager
.retryAccessTokenVO(vo.getAdapterGroupName(), prop, oldToken);
method.setHeader("Authorization", newaccessToken.getAuthorization());
setAuthHeaders(method, newaccessToken);
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] SEND (" + vo.getAdapterGroupName()
+ ") RETRY TOKEN = [" + newaccessToken + "]");
}
try (CloseableHttpResponse response = (CloseableHttpResponse) mclient.execute(method)) {
status = response.getCode();
responseMessage = EntityUtils.toByteArray(response.getEntity());
if (logger.isDebug()) {
logger.debug("[received status]" + status);
logger.debug("HttpClientAdapterServiceRest] RECV (" + vo.getAdapterGroupName() + ") = [" + new String(responseMessage, vo.getEncode()) + "]");
}
}catch (IOException e){
throw new Exception("retry excuteMethod Exceptioin = " + e.getMessage());
}
if (status == 302) {
if (!StringUtils.contains(relayResponseHeaderKeys, "Location")) {
relayResponseHeaderKeys += ",Location";
}
} else {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), uri, rmethod, responseMessage);
throw new Exception(errMsg);
}
// ----------------------------------------------------------
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceRest] RETRY responseType =" + vo.getResponseType());
logger.debug("HttpClientAdapterServiceRest] RETRY RECV " + vo.getEncode() + "("
+ vo.getAdapterGroupName() + ") = [" + new String(responseMessage, vo.getEncode())
+ "]");
logger.debug("HttpClientAdapterServiceRest] RETRY RECV (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(responseMessage));
}
// ----------------------------------------------------------
}
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + new String(responseMessage, vo.getEncode()) + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
return assignResponseHeaders(method, responseMessage, headerGroupName, vo.getEncode(), messageType,
relayResponseHeaderKeys, status, responseHeaderProp);
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceRest] SocketTimeoutException (" + vo.getAdapterGroupName() + ") : "
+ ste.toString(),
ste);
}
logger.error("HttpClientAdapterServiceRest] SocketTimeoutException (" + vo.getAdapterGroupName() + ") : "
+ ste.toString(), ste);
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceRest] Connection Exception (" + vo.getAdapterGroupName() + ") : "
+ ce.toString(),
ce);
}
logger.error("HttpClientAdapterServiceRest] Connection Exception (" + vo.getAdapterGroupName() + ") : "
+ ce.toString(), ce);
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(), e.toString(), e);
}
logger.error("HttpClientAdapterServiceRest] Exception (" + vo.getAdapterGroupName() + ") : " + e.toString(),
e);
throw e;
} finally {
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
private Properties assignRelayDataToInbound(Properties prop, Header[] responseHeaders) {
Properties headerProp = new Properties();
if (responseHeaders == null || responseHeaders.length == 0) {
return headerProp;
}
for (Header header : responseHeaders) {
headerProp.put(header.getName(), header.getValue());
}
return headerProp;
}
/**
* 현재 1단계 레이아웃에만 적용되도록 구현됨.
*
* @param method
* @param responseMessage
* @param headerGroupName
* @param encode
* @param messageType
* @param relayHeaderKeys
* @return
* @throws Exception
*/
@SuppressWarnings("unchecked")
private String assignResponseHeaders(HttpUriRequestBase method, byte[] responseMessage, String headerGroupName,
String encode, String messageType, String relayHeaderKeys, int status, Properties responseHeaderProp) throws Exception {
if (!MessageType.JSON.equals(messageType) || StringUtils.isBlank(headerGroupName)
|| StringUtils.isBlank(relayHeaderKeys)) {
return new String(responseMessage, encode);
}
String[] relayKeyArr = org.springframework.util.StringUtils.tokenizeToStringArray(relayHeaderKeys, ",");
JSONObject headerJson = new JSONObject();
for (String key : relayKeyArr) {
String value = responseHeaderProp.getProperty(key);
if (StringUtils.isNotBlank(value)) {
headerJson.put(key, value);
}
}
headerJson.put(HTTP_STATUS, String.valueOf(status));
if (headerJson.size() <= 0) {
return new String(responseMessage, encode);
}
JSONObject message = null;
if (responseMessage == null || responseMessage.length == 0) {
message = new JSONObject();
} else {
message = parseJson(new String(responseMessage, encode));
if (message == null) {
message = new JSONObject();
message.put("Malformed_Response_Message", new String(responseMessage, encode));
}
}
if (StringUtils.isNotBlank(headerGroupName) && message != null)
message.put(headerGroupName, headerJson);
return message.toJSONString();
}
private void setAuthHeaders(HttpUriRequestBase method, String authorization) throws Exception {
method.setHeader("Authorization",
String.format("%s", authorization));
}
private void setAuthHeaders(HttpUriRequestBase method, OAuth2AccessTokenVO accessToken) throws Exception {
method.setHeader("Authorization",
String.format("%s %s", AccessTokenVO.BEARER_TYPE, accessToken.getAccessToken()));
}
private boolean checkTokenRetry(byte[] responseMessage, String tokenErrorCodeKey, String tokenErrorCodeValues,
String encode) {
if (responseMessage == null) {
return false;
}
if (StringUtils.isBlank(tokenErrorCodeKey)) {
return false;
}
if (StringUtils.isBlank(tokenErrorCodeValues)) {
return false;
}
try {
DocumentContext jsonContext = JsonPath.parse(new String(responseMessage, encode));
String responseCode = jsonContext.read(tokenErrorCodeKey);
if (StringUtils.isBlank(responseCode)) {
return false;
}
String[] arr = org.springframework.util.StringUtils.tokenizeToStringArray(tokenErrorCodeValues, ",");
return ArrayUtils.contains(arr, responseCode);
} catch (Exception e) {
logger.error("HttpClientAdapterServiceRest] checkTokenRetry error=" + e.getMessage());
}
return false;
}
private void assignRequestHeaders(HttpUriRequestBase method, Object httpHeader) {
if (httpHeader == null) {
return;
}
if (httpHeader instanceof JSONObject) {
JSONObject jsonObject = (JSONObject) httpHeader;
for (Object key : jsonObject.keySet()) {
Object obj = jsonObject.get(key);
if ((obj instanceof JSONObject) || (obj instanceof JSONArray)) {
continue;
}
method.setHeader((String) key, (String) obj);
if (logger.isDebugEnabled()) {
logger.debug("Request Header :" + (String) key + "=[" + (String) obj + "]");
}
}
}
}
@SuppressWarnings("deprecation")
private void assignPostBody(Object eaiBody, String contentType, String charset, HttpUriRequestBase method) {
if (eaiBody == null) {
return;
}
if (StringUtils.contains(contentType, "application/x-www-form-urlencoded")) {
if (eaiBody instanceof JSONObject) {
List<NameValuePair> params = new ArrayList<>();
JSONObject jsonObject = (JSONObject) eaiBody;
for (Object key : jsonObject.keySet()) {
params.add(new BasicNameValuePair((String) key, (String) jsonObject.get(key)));
}
UrlEncodedFormEntity entity = new UrlEncodedFormEntity(params, StandardCharsets.UTF_8);
method.setEntity(entity);
}
} else {
ContentType contentTypeObj = ContentType.create(contentType, charset);
// 요청 본문을 StringEntity 객체로 생성
StringEntity entity = new StringEntity(eaiBody.toString(), contentTypeObj);
// 요청에 본문 추가
method.setEntity(entity);
}
}
private HashMap<String, String> getParameters(Object message) throws Exception {
HashMap<String, String> result = new HashMap<String, String>();
if (message != null) {
if (message instanceof JSONObject) {
JSONObject jsonObject = (JSONObject) message;
for (Object key : jsonObject.keySet()) {
Object obj = jsonObject.get(key);
if ((obj instanceof JSONObject) || (obj instanceof JSONArray)) {
continue;
}
result.put((String) key, getStringValue(obj));
}
} else {
String[] messages = ((String) message).split("&");
String[] data = null;
for (int i = 0; i < messages.length; i++) {
data = messages[i].split("=", 2);
if (data.length == 2) {
result.put(data[0], data[1]);
}
}
}
}
return result;
}
public String getStringValue(Object obj) {
if (obj == null) {
return null;
}
if (obj instanceof String) {
return (String) obj;
} else if (obj instanceof Long) {
return Long.toString((Long) obj);
} else if (obj instanceof BigDecimal) {
return ((BigDecimal) obj).toPlainString();
} else {
return (String) obj;
}
}
public static Object parseJsonGeneric(String jsonData) {
if (StringUtils.isBlank(jsonData)) {
return null;
}
try {
JSONParser parser = new JSONParser();
Object parsedObj = parser.parse(jsonData);
return parsedObj;
} catch (ParseException e) {
e.printStackTrace();
return null;
}
}
@SuppressWarnings("deprecation")
private JSONObject parseJson(String message) throws Exception {
if (message == null) {
return null;
}
return (JSONObject) JSONValue.parse(message);
}
private Document convertXmlDocument(String message) throws Exception {
SAXReader builder = new SAXReader();
Document document = builder.read(new StringReader(message));
return document;
}
@SuppressWarnings("deprecation")
private String changeUrl(String messageType, String url, String restOption, Object sendData) {
if ((MessageType.JSON.equals(messageType) || MessageType.XML.equals(messageType))) {
try {
if (StringUtils.isBlank(restOption)) {
return url;
}
List<String> urlVariableList = new ArrayList<String>();
JSONObject restOptionObject = parseJson(restOption);
if (restOptionObject == null)
throw new Exception("restOption is NULL");
String type = (String) restOptionObject.get("type");
String requestExtraPath = (String) restOptionObject.get("extraPath");
url = getUrl(url, requestExtraPath);
if (TYPE_VARIABLE_URL_REQUEST.equals(type)) {
Pattern p = Pattern.compile("\\{(.*?)\\}");
Matcher m = p.matcher(requestExtraPath);
List<String> uriVariables = new ArrayList<>();
while(m.find()) {
String fieldName = m.group(1);
uriVariables.add(fieldName);
}
if (MessageType.JSON.equals(messageType)) {
JSONObject jsonObject;
if (sendData instanceof JSONObject) {
jsonObject = (JSONObject) sendData;
} else {
jsonObject = (JSONObject) JSONValue.parse((String) sendData);
}
for (Object tempObject : uriVariables) {
String urlVaribleId = (String) tempObject;
String uriVariable = (String) jsonObject.get(urlVaribleId);
urlVariableList.add(uriVariable);
jsonObject.remove(urlVaribleId);
}
} else if (MessageType.XML.equals(messageType)) {
Document doc;
if (sendData instanceof Document) {
doc = (Document) sendData;
} else {
doc = convertXmlDocument((String) sendData);
}
for (Object tempObject : uriVariables) {
String urlVaribleId = (String) tempObject;
Element element = (Element) doc.selectSingleNode("//" + urlVaribleId);
urlVariableList.add(element.getText());
if (doc.getRootElement() == element) {
doc = null;
} else {
element.getParent().remove(element);
}
}
}
if (urlVariableList.size() > 0) {
UriComponents uriComponents = UriComponentsBuilder.fromUriString(url).build();
Object[] urls = urlVariableList.toArray();
url = uriComponents.expand(urls).toUriString();
logger.debug("HttpClientAdapterServiceRest] after extand url=[" + url + "] ");
}
}
} catch (Exception e) {
logger.error("Failed to change url", e);
}
}
return url;
}
private String getUrl(String baseUrl, String extraPath) {
if (StringUtils.isBlank(extraPath)) {
return baseUrl;
}
if (StringUtils.contains(extraPath, "http://") || StringUtils.contains(extraPath, "https://")) {
return extraPath;
}
String targetUrl = baseUrl;
if (!targetUrl.endsWith("/")) {
targetUrl += "/";
}
if (extraPath.startsWith("/")) {
targetUrl += extraPath.substring(1);
} else {
targetUrl += extraPath;
}
logger.debug("HttpClientAdapterServiceRest] after concatenate url=[" + targetUrl + "] ");
return targetUrl;
}
}
@@ -0,0 +1,183 @@
//
//package com.eactive.eai.adapter.http.client.impl;
//
//import com.eactive.eai.adapter.http.HttpMemoryLogger;
//import com.eactive.eai.adapter.http.HttpStatusException;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.util.CommonLib;
//import org.apache.commons.httpclient.HttpClient;
//import org.apache.commons.httpclient.HttpStatus;
//import org.apache.commons.httpclient.HttpVersion;
//import org.apache.commons.httpclient.methods.PostMethod;
//
//import java.net.ConnectException;
//import java.net.SocketTimeoutException;
//import java.util.Properties;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapterServiceAnnounce extends HttpClientAdapterServiceSupport{
//
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, byte[] data, Properties tempProp) throws Exception {
//
// HttpClientAdapterVO vo = super.setting(prop, tempProp);
//
// if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
// logger.debug("HttpClientAdapterServiceAnnounce] SEND (" + vo.getMethod() + ") ");
// }
// PostMethod method = new PostMethod(vo.getUrl());
// if (vo.getTimeout() > -1) {
// method.getParams().setSoTimeout(vo.getTimeout());
// }
// HttpClient mclient = this.client;
// if ( vo.getConnectionTimeout() != 0){
// mclient.getParams().setParameter("http.connection.timeout", vo.getConnectionTimeout());
// }
// method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_0);
//
// // Announce Data Size : 113 Bytes
// int annMinSize = 113;
//
// String srvCode = "";
// String recipient = "";
// String body = "";
// String inurl = "";
//
// if (data.length >= annMinSize) {
// if (vo.getEncode() != null && vo.getEncode().length() > 0) {
// if (logger.isDebug()) {
// logger.debug("HttpClientAdapterServiceAnnounce] ENCODE(" + vo.getEncode() + ") ");
// }
// srvCode = new String(data, 0, 6, vo.getEncode());
// recipient = new String(data, 6, 7, vo.getEncode());
// body = new String(data, 13, 100, vo.getEncode());
// if (data.length > 153) {
// inurl = new String(data, 113, data.length - annMinSize, vo.getEncode());
// }
// } else {
// srvCode = new String(data, 0, 6);
// recipient = new String(data, 6, 7);
// body = new String(data, 13, 100);
// if (data.length > 153) {
// inurl = new String(data, 113, data.length - annMinSize);
// }
// }
// method.addParameter("SRV_CODE", srvCode);
// method.addParameter("RECIPIENT", recipient);
// method.addParameter("BODY", body);
// if (data.length > 153) {
// method.addParameter("URL", inurl);
// }
//
// } else {
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceAnnounce] Invalid Data Length (" + data.length + ") < " + annMinSize);
// }
// throw new Exception("HttpClientAdapterServiceAnnounce Error : MessageSize(" + (data.length) + " Bytes) too small < " + annMinSize);
// }
//
// int status = -1;
//
// try {
// if (vo.getTraceLevel() >= 3){
// if (data.length > 153){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[URL]"+ inurl + "\n"
// + "[SRV_CODE]" + srvCode + "\n"
// + "[RECIPIENT]" + recipient + "\n"
// + "[BODY]" + body + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) +"\n"
// );
// }else{
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[SRV_CODE]" + srvCode + "\n"
// + "[RECIPIENT]" + recipient + "\n"
// + "[BODY]" + body + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) +"\n"
// );
//
// }
// }
// //mclient.getHttpConnectionManager().getParams().setConnectionTimeout(connectionTimeout);
// //mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
//
// //status 200(정상) 이외에는 error 처리
// if (status !=200){
// try{
// logger.error("HttpClientAdapterServiceAnnounce] receive status["+status+"] data[" + new String(method.getResponseBody()) +"]");
// }catch(Exception e){
// logger.error(e);
// }
// throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="+vo.getAdapterGroupName()+"."+vo.getAdapterName(),status);
// }
// byte[] responseMessage = method.getResponseBody();
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "RECV ["+new String(responseMessage)+"]"+CommonLib.getDumpMessage(responseMessage) );
// }
// return responseMessage;
//
// } catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceAnnounce] SocketTimeoutException : " + ste.toString() ,ste);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceAnnounce] SocketTimeoutException : " + ste.toString() ,ste);
// }
// throw ste;
// } catch(ConnectException ce) {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceAnnounce] Connection Exception : " + ce.toString() ,ce);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceAnnounce] Connection Exception : " + ce.toString() ,ce);
// }
// throw ce;
// } catch(Exception e) {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceAnnounce] Exception : " + e.toString() ,e);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceAnnounce] Exception : " + e.toString() ,e);
// }
// throw e;
// } finally {
// method.releaseConnection();
// if (status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if (logger.isDebug()) {
// logger.debug(resMsg);
// }
// }
// }
//
// }
//
//}
@@ -0,0 +1,160 @@
package com.eactive.eai.adapter.http.client.impl;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.Properties;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.HttpVersion;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpConnectionParams;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import com.eactive.eai.adapter.Keys;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.CommonLib;
public class HttpClientAdapterServiceBody extends HttpClientAdapterServiceSupport {
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
boolean isAsync = false;
if (RESPONSE_TYPE_ASYNC.equals(vo.getResponseType())) {
isAsync = true;
}
PostMethod method = new PostMethod(vo.getUrl());
HttpClient mclient = this.client;
configureHttpClient(mclient, method, vo, vo.getUrl(), vo.getContentType());
String sendData = "";
if (data instanceof String) {
sendData = (String) data;
} else if (data instanceof byte[]) {
sendData = new String((byte[]) data, vo.getEncode());
}
mclient.getParams().setContentCharset(vo.getEncode());
String contentTypeValue = null;
if (StringUtils.isNotEmpty(vo.getContentType())) {
if (StringUtils.isNotEmpty(vo.getEncode())) {
contentTypeValue = vo.getContentType() + "; charset=" + vo.getEncode();
} else {
contentTypeValue = vo.getContentType();
}
method.setRequestHeader(CONTENT_TYPE_KEY, contentTypeValue);
}
if (vo.getAdapterHeaders() != null) {
for (String key : vo.getAdapterHeaders().keySet()) {
method.addRequestHeader(key, vo.getAdapterHeaders().get(key));
}
}
if (logger.isInfoEnabled()) {
logger.info("HttpClientAdapterServiceBody] " + CONTENT_TYPE_KEY + "(" + contentTypeValue + ")");
}
if ("Y".equals(vo.getUrlEncodeYn())) {
sendData = java.net.URLEncoder.encode(sendData);
}
method.setRequestBody(sendData);
int status = -1;
try {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug(
"HttpClientAdapterServiceBody] SEND (" + vo.getAdapterGroupName() + ") = [" + sendData + "]");
logger.debug("HttpClientAdapterServiceBody] SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(sendData));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + sendData + "]" + CommonLib.getDumpMessage(sendData));
}
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
stopWatch.stop();
String responseCharSet = getResponseCharSet(method.getResponseCharSet(), vo.getAdapterGroupName());
byte[] responseMessage = method.getResponseBody();
// status 200(정상) 이외에는 error 처리
if (status != 200) {
logger.error("HttpClientAdapterServiceBody] receive status[" + status + "] data["
+ new String(responseMessage) + "]");
throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="
+ vo.getAdapterGroupName() + "." + vo.getAdapterName(), status);
}
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime() && (logger.isWarn())) {
logger.warn("HttpClientAdapterServiceBody] URL[" + vo.getUrl() + "] lazy async response time = "
+ stopWatch.toString() + " responseMessage=" + new String(responseMessage, responseCharSet));
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + new String(responseMessage, vo.getEncode()) + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
return responseMessage;
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceBody] SocketTimeoutException : " + ste.toString(), ste);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceBody] SocketTimeoutException : " + ste.toString(), ste);
}
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceBody] Connection Exception : " + ce.toString(), ce);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceBody] Connection Exception : " + ce.toString(), ce);
}
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceBody] Exception : " + e.toString(), e);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceBody] Exception : " + e.toString(), e);
}
throw e;
} finally {
method.releaseConnection();
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
}
@@ -0,0 +1,667 @@
package com.eactive.eai.adapter.http.client.impl;
import java.io.ByteArrayInputStream;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.ArrayList;
import java.util.BitSet;
import java.util.Formatter;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.Map.Entry;
import java.util.Properties;
import org.apache.commons.httpclient.Header;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpMethodBase;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.methods.EntityEnclosingMethod;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.methods.PutMethod;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import org.json.simple.JSONArray;
import org.json.simple.JSONObject;
import org.json.simple.JSONValue;
import org.springframework.http.HttpHeaders;
import org.springframework.web.util.UriComponents;
import org.springframework.web.util.UriComponentsBuilder;
import com.eactive.eai.adapter.http.EntityEnclosingDeleteMethod;
import com.eactive.eai.adapter.http.EntityEnclosingGetMethod;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpMethodType;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceKey;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.dynamic.HttpAdapterServiceKey;
import com.eactive.eai.adapter.http.dynamic.impl.HttpAdapterServiceBypass;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.CommonLib;
import com.jayway.jsonpath.DocumentContext;
import com.jayway.jsonpath.JsonPath;
import com.openbanking.eai.common.token.AccessTokenManager;
import com.openbanking.eai.common.token.AccessTokenVO;
import com.openbanking.eai.common.token.OAuth2AccessTokenVO;
public class HttpClientAdapterServiceBypass extends HttpClientAdapterServiceSupport
implements HttpClientAdapterServiceKey {
public static final String TYPE_BYPASS_REQUEST = "bypassRequest";
public static final String REST_OPTION = "REST_OPTION";
protected boolean doSendUrlFragment = true;
protected boolean doHandleCompression = false;
protected boolean doForwardIP = true;
@SuppressWarnings({ "deprecation", "unchecked" })
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
boolean useAdapterToken = StringUtils.equalsIgnoreCase(prop.getProperty("ADAPTER_TOKEN_USE_YN", "N"), "Y");
// ex) $.dataHeader.GW_RSLT_CD
String tokenErrorCodeKey = prop.getProperty("ADAPTER_TOKEN_ERROR_CODE_KEY");
String tokenErrorCodeValues = prop.getProperty("ADAPTER_TOKEN_ERROR_CODE_VALUES");
String tokenErrorHttpStatusCode = prop.getProperty("ADAPTER_TOKEN_ERROR_HTTP_STATUS_CODE"); // 200 or 400번대
/**
* @formatter:off
* TSEAIHE02.RESTOPTION 정보 => JSON 형태로 구성
* - type : simpleRequest, variableUrlRequest
* - extraPath : 어댑터 프로퍼티 URL에 추가될 HTTP REST URL
* - method : get, delete, post, put
* - contentType : application/json, application/x-www-form-urlencoded
* - adapterTokenUseYn: Y, N(default)
* ex)
* {"type":"variableUrlRequest","extraPath":"/aaa/{userId}","uriVariables":["userId"]}
* @formatter:on
*/
String restOptionData = tempProp.getProperty(REST_OPTION, "{}");
JSONObject restOptionObject = parseJson(restOptionData);
String adapterTokenUseYn = (String) restOptionObject.get("adapterTokenUseYn");
if (StringUtils.isNotBlank(adapterTokenUseYn)) { // interface 에 설정된게 우선한다.
useAdapterToken = StringUtils.equalsIgnoreCase(adapterTokenUseYn, "Y");
}
String inboundMethod = tempProp.getProperty(HttpAdapterServiceKey.INBOUND_METHOD, "POST");
String inboundRewritePath = tempProp.getProperty(HttpAdapterServiceKey.INBOUND_REWRITE_PATH, "");
String inboundQueryString = tempProp.getProperty(HttpAdapterServiceKey.INBOUND_QUERY_STRING, "");
Properties inboundHeaders = (Properties) tempProp.get(HttpAdapterServiceKey.INBOUND_HEADER);
Map<String, String> inboundPathVariables = (Map<String, String>) tempProp
.get(HttpAdapterServiceKey.INBOUND_PATH_VARIABLES);
String restMethod = (String) restOptionObject.get("method");
if (StringUtils.isBlank(restMethod)) {
restMethod = inboundMethod;
}
String url = getRewriteUrl(vo, inboundRewritePath, inboundQueryString, restOptionObject, inboundPathVariables);
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceBypass] url = [" + url + "]");
}
HttpClient mclient = this.client;
HttpMethodBase method = generateMethod(restMethod, url);
assignRequestHeaders(method, inboundHeaders, tempProp);
if (hasBody(data, inboundHeaders)) {
if (data instanceof byte[]) {
((EntityEnclosingMethod) method).setRequestBody(new ByteArrayInputStream((byte[]) data));
} else if (data instanceof String) {
((EntityEnclosingMethod) method).setRequestBody((String) data);
}
}
String contentType = (String) restOptionObject.get("contentType");
if (StringUtils.isBlank(contentType) && inboundHeaders != null) {
contentType = getIgnoreCaseProp(inboundHeaders, HttpHeaders.CONTENT_TYPE);
contentType = StringUtils.substringBefore(contentType, ";");
}
configureHttpClient(mclient, method, vo, url, contentType);
OAuth2AccessTokenVO accessToken = null;
if (useAdapterToken) {
AccessTokenManager tokenManager = AccessTokenManager.getInstance();
accessToken = (OAuth2AccessTokenVO) tokenManager.getAccessTokenVO(vo.getAdapterGroupName());
// 토큰이 없거나 만료 됐으면 재발급
if (accessToken == null || accessToken.isExpired()) {
String oldToken = accessToken == null ? null : accessToken.getAccessToken();
accessToken = (OAuth2AccessTokenVO) tokenManager.retryAccessTokenVO(vo.getAdapterGroupName(), prop,
oldToken);
}
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceBypass] SEND (" + vo.getAdapterGroupName() + ") TOKEN = ["
+ accessToken + "]");
}
setAuthHeaders(method, accessToken);
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceBypass] SEND (" + vo.getAdapterGroupName()
+ ") RequestHeader [Authorization=" + method.getRequestHeader("Authorization") + "]");
}
}
int status = -1;
try {
StopWatch stopWatch = new StopWatch();
stopWatch.start();
byte[] responseMessage = null;
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [Bypass Request..]" + CommonLib.getDumpMessage(data));
}
try {
if (logger.isDebug()) {
logger.debug("[method getName]" + method.getName());
logger.debug("[method getRequestCharSet]" + method.getRequestCharSet());
logger.debug("[method getRequestHeaders]" + method.getRequestHeaders().toString());
logger.debug("[method getQueryString]" + method.getQueryString());
logger.debug("[method getParams]" + method.getParams().toString());
logger.debug("[method getURI]" + method.getURI());
}
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
if (logger.isDebug()) {
logger.debug("[received status]" + status);
}
} catch (ConnectException e) {
responseMessage = method.getResponseBody();
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceBypass] responseType =" + vo.getResponseType());
logger.debug("HttpClientAdapterServiceBypass] RECV (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(responseMessage));
}
throw new Exception("excuteMethod java.net.ConnectException = " + e.getMessage());
}
stopWatch.stop();
/**
* @formatter:off
* OAuth 토큰 응답 체크(Adapter properties로 설정)
* 응답코드에 따라 유효한 토큰 확인(토큰 재발급 여부 확인)
* API 서비스 마다 정책이 다름(보통 400대에서 체크하나 200에서도 체크할 수 있음)
*
* TOKEN_ERROR_CODE_KEY: 응답 json error code key
* __ex) $.dataHeader.resultCode
* TOKEN_ERROR_CODE_VALUES: 토큰 재발급이 필요한 응답 error codes(ex: O0001,O0002,O0003)
* TOKEN_ERROR_HTTP_STATUS_CODE: 보통 400대에서 체크하나 API 제공자에 따라 200에서도 체클할수 있음
* ex) TOKEN_ERROR_HTTP_STATUS_CODE = 200
* @formatter:on
*/
boolean needReissue = false;
if (status == 200) {
responseMessage = method.getResponseBody();
if (useAdapterToken && StringUtils.equals(tokenErrorHttpStatusCode, "200")) {
needReissue = checkTokenRetry(responseMessage, tokenErrorCodeKey, tokenErrorCodeValues,
vo.getEncode());
}
} else if (status >= 400 && status < 500) {
responseMessage = method.getResponseBody();
if (useAdapterToken) {
needReissue = checkTokenRetry(responseMessage, tokenErrorCodeKey, tokenErrorCodeValues,
vo.getEncode());
}
if (!needReissue) {
// body 값이 없을때만 exception 처리하고, body가 있으면 bypass 한다.
if (responseMessage == null || responseMessage.length == 0) {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), url, method, responseMessage);
throw new Exception(errMsg);
}
}
} else {
responseMessage = method.getResponseBody();
// body 값이 없을때만 exception 처리하고, body가 있으면 bypass 한다.
if (responseMessage == null || responseMessage.length == 0) {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), url, method, responseMessage);
throw new Exception(errMsg);
}
}
if (useAdapterToken) {
if (responseMessage == null) {
throw new Exception("responseMessage is NULL, HttpStatus=" + status);
}
// OAuth 토큰 재요청 코드 확인
if (needReissue) {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceBypass] retry access token response code = ["
+ vo.getResponseType() + "] message = [" + new String(responseMessage, vo.getEncode())
+ "]");
}
// 토큰 재발급
AccessTokenManager tokenManager = AccessTokenManager.getInstance();
String oldToken = accessToken == null ? null : accessToken.getAccessToken();
OAuth2AccessTokenVO newAccessToken = (OAuth2AccessTokenVO) tokenManager
.retryAccessTokenVO(vo.getAdapterGroupName(), prop, oldToken);
method.setRequestHeader("Authorization", newAccessToken.getAuthorization());
setAuthHeaders(method, newAccessToken);
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceBypass] SEND (" + vo.getAdapterGroupName()
+ ") RETRY TOKEN = [" + newAccessToken + "]");
}
try {
status = mclient.executeMethod(method);
} catch (ConnectException e) {
throw new Exception("retry excuteMethod Exceptioin = " + e.getMessage());
}
if (status == 200) {
responseMessage = method.getResponseBody();
} else {
responseMessage = method.getResponseBody();
// body 값이 없을때만 exception 처리하고, body가 있으면 bypass 한다.
if (responseMessage == null || responseMessage.length == 0) {
String errMsg = String.format(
"http receive status fail value=%d adapterName=%s.%s uri=%s method=%s response Data=%s",
status, vo.getAdapterGroupName(), vo.getAdapterName(), url, method,
responseMessage);
throw new Exception(errMsg);
}
}
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceBypass] RETRY responseType =" + vo.getResponseType());
logger.debug("HttpClientAdapterServiceBypass] RETRY RECV (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(responseMessage));
}
}
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [Bypass Request..]" + CommonLib.getDumpMessage(responseMessage));
}
assignRelayDataToInbound(tempProp, method.getResponseHeaders(), status);
return responseMessage;
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceBypass] SocketTimeoutException (" + vo.getAdapterGroupName() + ") : "
+ ste.toString(),
ste);
}
logger.error("HttpClientAdapterServiceBypass] SocketTimeoutException (" + vo.getAdapterGroupName() + ") : "
+ ste.toString(), ste);
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceBypass] Connection Exception (" + vo.getAdapterGroupName() + ") : "
+ ce.toString(),
ce);
}
logger.error("HttpClientAdapterServiceBypass] Connection Exception (" + vo.getAdapterGroupName() + ") : "
+ ce.toString(), ce);
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(), e.toString(), e);
}
logger.error(
"HttpClientAdapterServiceBypass] Exception (" + vo.getAdapterGroupName() + ") : " + e.toString(),
e);
throw e;
} finally {
method.releaseConnection();
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
private boolean hasBody(Object data, Properties inboundHeaders) {
if (data == null) {
return false;
}
// // spec: RFC 2616, sec 4.3
// String contentLength = getIgnoreCaseProp(inboundHeaders, HttpHeaders.CONTENT_LENGTH);
// String transferEncoding = getIgnoreCaseProp(inboundHeaders, HttpHeaders.TRANSFER_ENCODING);
// if (StringUtils.isNotBlank(contentLength) || StringUtils.isNotBlank(transferEncoding)) {
// return true;
// }
// return false;
// client adapter 단독으로 사용 가능하게 수정
return true;
}
private HttpMethodBase generateMethod(String restMethod, String url) {
HttpMethodBase method = null;
switch (HttpMethodType.getValue(restMethod)) {
case GET:
method = new EntityEnclosingGetMethod(url);
break;
case DELETE:
method = new EntityEnclosingDeleteMethod(url);
break;
case POST:
method = new PostMethod(url);
break;
case PUT:
method = new PutMethod(url);
break;
default:
// set default method
method = new PostMethod(url);
break;
}
return method;
}
private String getRewriteUrl(HttpClientAdapterVO vo, String inboundRewritePath, String queryString,
JSONObject restOptionObject, Map<String, String> inboundPathVariables) {
String fragment = null;
if (StringUtils.isNotBlank(queryString)) {
int fragIdx = queryString.indexOf('#');
if (fragIdx >= 0) {
fragment = queryString.substring(fragIdx + 1);
queryString = queryString.substring(0, fragIdx);
}
}
String restExtraPath = (String) restOptionObject.get("extraPath");
if (StringUtils.isBlank(restExtraPath)) {
StringBuilder uri = new StringBuilder(500);
uri.append(vo.getUrl()).append(inboundRewritePath);
if (StringUtils.isNotBlank(queryString)) {
uri.append('?');
uri.append(encodeUriQuery(queryString, false));
}
if (doSendUrlFragment && fragment != null) {
uri.append('#');
uri.append(encodeUriQuery(fragment, false));
}
return uri.toString();
} else {
String type = (String) restOptionObject.get("type");
String url = getUrl(vo.getUrl(), restExtraPath);
if (StringUtils.equalsIgnoreCase(type, HttpClientAdapterServiceRest.TYPE_VARIABLE_URL_REQUEST)) {
inboundPathVariables = mergeInboundPathVariables(inboundPathVariables, queryString);
List<String> urlVariableValueList = new ArrayList<>();
JSONArray uriVariables = (JSONArray) restOptionObject.get("uriVariables");
if (uriVariables != null && !uriVariables.isEmpty() && inboundPathVariables != null
&& !inboundPathVariables.isEmpty()) {
for (Object tempObject : uriVariables) {
String urlVaribleId = (String) tempObject;
String uriVariableValue = inboundPathVariables.get(urlVaribleId);
urlVariableValueList.add(uriVariableValue);
}
if (!urlVariableValueList.isEmpty()) {
UriComponents uriComponents = UriComponentsBuilder.fromUriString(url).build();
Object[] urls = urlVariableValueList.toArray();
url = uriComponents.expand(urls).toUriString();
}
}
} else {
if (StringUtils.isNotBlank(queryString)) {
url += "?" + encodeUriQuery(queryString, false);
}
if (doSendUrlFragment && fragment != null) {
url += "#" + encodeUriQuery(fragment, false);
}
}
return url;
}
}
private Map<String, String> mergeInboundPathVariables(Map<String, String> inboundPathVariables,
String queryString) {
if (StringUtils.isBlank(queryString)) {
return inboundPathVariables;
}
if (inboundPathVariables == null) {
inboundPathVariables = new LinkedHashMap<>();
}
String[] pairs = queryString.split("&");
for (String pair : pairs) {
int idx = pair.indexOf("=");
// URLDecoder.decode 필요??
inboundPathVariables.put(pair.substring(0, idx), pair.substring(idx + 1));
}
return inboundPathVariables;
}
private String getUrl(String baseUrl, String extraPath) {
if (StringUtils.isBlank(extraPath)) {
return baseUrl;
}
if (StringUtils.contains(extraPath, "http://") || StringUtils.contains(extraPath, "https://")) {
return extraPath;
}
String targetUrl = baseUrl;
if (!targetUrl.endsWith("/")) {
targetUrl += "/";
}
if (extraPath.startsWith("/")) {
targetUrl += extraPath.substring(1);
} else {
targetUrl += extraPath;
}
return targetUrl;
}
protected CharSequence encodeUriQuery(CharSequence in, boolean encodePercent) {
// Note that I can't simply use URI.java to encode because it will escape
// pre-existing escaped things.
StringBuilder outBuf = null;
Formatter formatter = null;
for (int i = 0; i < in.length(); i++) {
char c = in.charAt(i);
boolean escape = true;
if (c < 128) {
if (asciiQueryChars.get(c) && !(encodePercent && c == '%')) {
escape = false;
}
} else if (!Character.isISOControl(c) && !Character.isSpaceChar(c)) {// not-ascii
escape = false;
}
if (!escape) {
if (outBuf != null)
outBuf.append(c);
} else {
// escape
if (outBuf == null) {
outBuf = new StringBuilder(in.length() + 5 * 3);
outBuf.append(in, 0, i);
formatter = new Formatter(outBuf);
}
// leading %, 0 padded, width 2, capital hex
formatter.format("%%%02X", (int) c);// TODO
}
}
return outBuf != null ? outBuf : in;
}
protected static final BitSet asciiQueryChars;
static {
char[] c_unreserved = "_-!.~'()*".toCharArray();// plus alphanum
char[] c_punct = ",;:$&+=".toCharArray();
char[] c_reserved = "/@".toCharArray();// plus punct. Exclude '?'; RFC-2616 3.2.2. Exclude '[', ']';
// https://www.ietf.org/rfc/rfc1738.txt, unsafe characters
asciiQueryChars = new BitSet(128);
for (char c = 'a'; c <= 'z'; c++)
asciiQueryChars.set(c);
for (char c = 'A'; c <= 'Z'; c++)
asciiQueryChars.set(c);
for (char c = '0'; c <= '9'; c++)
asciiQueryChars.set(c);
for (char c : c_unreserved)
asciiQueryChars.set(c);
for (char c : c_punct)
asciiQueryChars.set(c);
for (char c : c_reserved)
asciiQueryChars.set(c);
asciiQueryChars.set('%');// leave existing percent escapes in place
}
private void assignRelayDataToInbound(Properties prop, Header[] responseHeaders, int status) {
if (responseHeaders == null || responseHeaders.length == 0) {
return;
}
Properties headerProp = new Properties();
for (Header header : responseHeaders) {
headerProp.put(header.getName(), header.getValue());
}
headerProp.put(HttpAdapterServiceBypass.HTTP_STATUS, String.valueOf(status));
Map<String, Object> map = new HashMap<String, Object>();
map.put(HttpAdapterServiceKey.OUTBOUND_RESPONSE_HEADERS, headerProp);
prop.put(HttpAdapterServiceKey.OUTBOUND_PROPERTY_MAP, map);
}
private void setAuthHeaders(HttpMethodBase method, OAuth2AccessTokenVO accessToken) throws Exception {
method.setRequestHeader("Authorization",
String.format("%s %s", AccessTokenVO.BEARER_TYPE, accessToken.getAccessToken()));
}
private boolean checkTokenRetry(byte[] responseMessage, String tokenErrorCodeKey, String tokenErrorCodeValues,
String encode) {
if (responseMessage == null) {
return false;
}
if (StringUtils.isBlank(tokenErrorCodeKey)) {
return false;
}
if (StringUtils.isBlank(tokenErrorCodeValues)) {
return false;
}
try {
DocumentContext jsonContext = JsonPath.parse(new String(responseMessage, encode));
String responseCode = jsonContext.read(tokenErrorCodeKey);
if (StringUtils.isBlank(responseCode)) {
return false;
}
String[] arr = org.springframework.util.StringUtils.tokenizeToStringArray(tokenErrorCodeValues, ",");
return ArrayUtils.contains(arr, responseCode);
} catch (Exception e) {
logger.error("HttpClientAdapterServiceBypass] checkTokenRetry error=" + e.getMessage());
}
return false;
}
private void assignRequestHeaders(HttpMethodBase method, Properties headerProp, Properties inProp) {
if (headerProp == null) {
return;
}
for (Entry<Object, Object> e : headerProp.entrySet()) {
String key = (String) e.getKey();
String value = (String) e.getValue();
if (StringUtils.equalsAnyIgnoreCase(key, HttpAdapterServiceBypass.HOP_BY_HOP_HEADERS)
|| StringUtils.equalsIgnoreCase(key, HttpHeaders.CONTENT_LENGTH)) {
continue;
}
if (doHandleCompression && StringUtils.equalsIgnoreCase(key, HttpHeaders.ACCEPT_ENCODING)) {
continue;
}
method.setRequestHeader(key, value);
if (logger.isDebugEnabled()) {
logger.debug("Request Header :" + key + "=[" + value + "]");
}
}
if (doForwardIP) {
String forHeaderName = "X-Forwarded-For";
String forHeader = inProp.getProperty(HttpAdapterServiceKey.INBOUND_REMOTE_ADDR);
if (StringUtils.isNotBlank(forHeader)) {
String existingForHeader = headerProp.getProperty(forHeaderName);
if (existingForHeader != null) {
forHeader = existingForHeader + ", " + forHeader;
}
method.setRequestHeader(forHeaderName, forHeader);
}
String protoHeaderName = "X-Forwarded-Proto";
String protoHeader = inProp.getProperty(HttpAdapterServiceKey.INBOUND_SCHEME);
if (StringUtils.isNotBlank(protoHeader)) {
method.setRequestHeader(protoHeaderName, protoHeader);
}
}
}
@SuppressWarnings("deprecation")
private JSONObject parseJson(String message) throws Exception {
if (message == null) {
return null;
}
return (JSONObject) JSONValue.parse(message);
}
public static final String getIgnoreCaseProp(Properties prop, String key) {
if (prop == null) {
return null;
}
for (Entry<Object, Object> e : prop.entrySet()) {
if (StringUtils.equalsIgnoreCase(key, (String) e.getKey())) {
return (String) e.getValue();
}
}
return null;
}
}
@@ -0,0 +1,157 @@
//
//package com.eactive.eai.adapter.http.client.impl;
//
//import com.eactive.eai.adapter.http.HttpMemoryLogger;
//import com.eactive.eai.adapter.http.HttpStatusException;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.util.CommonLib;
//import org.apache.commons.httpclient.HttpClient;
//import org.apache.commons.httpclient.HttpStatus;
//import org.apache.commons.httpclient.HttpVersion;
//import org.apache.commons.httpclient.methods.PostMethod;
//
//import java.net.ConnectException;
//import java.net.SocketTimeoutException;
//import java.util.Properties;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapterServiceChangedate extends HttpClientAdapterServiceSupport{
//
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, byte[] data, Properties tempProp) throws Exception {
//
// HttpClientAdapterVO vo = super.setting(prop, tempProp);
//
// if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
// logger.debug("HttpClientAdapterServiceChangedate] SEND (" + vo.getMethod() + ") ");
// }
// PostMethod method = new PostMethod(vo.getUrl());
// if (vo.getTimeout() > -1) {
// method.getParams().setSoTimeout(vo.getTimeout());
// }
// HttpClient mclient = this.client;
// if ( vo.getConnectionTimeout() != 0){
// mclient.getParams().setParameter("http.connection.timeout", vo.getConnectionTimeout());
// }
// method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_0);
//
// // Data Size : 15 Bytes
// int popupMinSize = 15;
//
// String req = "";
// String date = "";
//
// if (data.length >= popupMinSize) {
// if (vo.getEncode() != null && vo.getEncode().length() > 0) {
// if (logger.isDebug()) {
// logger.debug("HttpClientAdapterServiceChangedate] ENCODE(" + vo.getEncode() + ") ");
// }
// req = new String(data, 0, 7, vo.getEncode()).trim();
// date = new String(data, 7, 8, vo.getEncode());
// } else {
// req = new String(data, 0, 7 ).trim();
// date = new String(data, 7, 8 );
// }
// method.addParameter("req", req);
// method.addParameter("date", date);
//
// } else {
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceChangedate] Invalid Data Length (" + data.length + ") < "
// + popupMinSize);
// }
// throw new Exception("HttpClientAdapterServiceChangedate Error : MessageSize(" + (data.length)
// + " Bytes) too small < " + popupMinSize);
// }
//
// int status = -1;
//
// try {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[req]"+ req + "\n"
// + "[date]" + date + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) +"\n"
// );
// }
// //mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// //mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// //status 200(정상) 이외에는 error 처리
// if (status !=200){
// try{
// logger.error("HttpClientAdapterServiceChangedate] receive status["+status+"] data[" + new String(method.getResponseBody()) +"]");
// }catch(Exception e){
// logger.error(e);
// }
// throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="+vo.getAdapterGroupName()+"."+vo.getAdapterName(),status);
// }
// byte[] responseMessage = method.getResponseBody();
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "RECV ["+new String(responseMessage)+"]"+CommonLib.getDumpMessage(responseMessage) );
// }
// return responseMessage;
//
// } catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient// 3.1일 경우
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceChangedate] SocketTimeoutException : " + ste.toString() ,ste);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceChangedate] SocketTimeoutException : " + ste.toString() ,ste);
// }
// throw ste;
// } catch(ConnectException ce) {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceChangedate] Connection Exception : " + ce.toString() ,ce);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceChangedate] Connection Exception : " + ce.toString() ,ce);
// }
// throw ce;
// } catch(Exception e) {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServiceChangedate] Exception : " + e.toString() ,e);
// }
// if (logger.isError()){
// logger.error("HttpClientAdapterServiceChangedate] Exception : " + e.toString() ,e);
// }
// throw e;
// } finally {
// method.releaseConnection();
// if (status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if (logger.isDebug()) {
// logger.debug(resMsg);
// }
// }
// }
// }
//
//}
@@ -0,0 +1,152 @@
//
//package com.eactive.eai.adapter.http.client.impl;
//
//import com.eactive.eai.adapter.http.HttpMemoryLogger;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
//import com.eactive.eai.common.util.CommonLib;
//
//import java.util.Hashtable;
//import java.util.Map;
//import java.util.Properties;
//
////import k4m.eCross.client.Context;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapterServiceExtorg extends HttpClientAdapterServiceSupport{
//
// @Override
// protected void init(){
// ;
// }
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, byte[] data, Properties tempProp) throws Exception
// {
// HttpClientAdapterVO vo = super.setting(prop, tempProp);
// String msgNumber = "";
// String ReceiverID = "";
//
// if (logger.isDebug()){
// logger.debug("HttpClientAdapterServiceExtorg: Body Size] ["+data.length+"]");
// }
//
// if(data.length > 23){
// msgNumber = new String(data, 19, 4);
// if (logger.isDebug()){
// logger.debug("HttpClientAdapterServiceExtorg: msgNumber] ["+msgNumber+"]");
// }
// //String ReceiverID = "770000";
//
// /* 20081124 add MP at KIBO start------------------------------------*/
// /* ReceiverID extract Message */
// ReceiverID = new String(data, 12, 7).trim();
// /* 20081124 add MP at KIBO start------------------------------------*/
//
// if (logger.isDebug()){
// logger.debug("HttpClientAdapterServiceExtorg: ReceiverID] ["+ReceiverID+"]");
// }
// }else{
// logger.warn("Invalid message length - Length["+data.length+"]");
// }
//
//
// String url = prop.getProperty(URL);
//
// //flat데이타
// String inputLine = " "+new String(data);
// String outputString = "";
//
//
// try
// {
// Map inputStream = new Hashtable();
// Map outStream = new Hashtable();
// String serviceName = "MPS.Send.FlatSender";
// inputStream.put("MessageNumber",msgNumber);
// inputStream.put("ReceiverID",ReceiverID);
// // 트랜젝션 ID 15바이트를 처리
// inputStream.put("FlatStream",inputLine);
//
//
// if(logger.isDebug()){
// logger.debug( "[serviceName]"+ serviceName + "\n"
// + "[MessageNumber]" + msgNumber + "\n"
// + "[ReceiverID]" + ReceiverID + "\n"
// + "[FlatStream]" + inputLine + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) +"\n");
// }
//
// try{
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[serviceName]"+ serviceName + "\n"
// + "[MessageNumber]" + msgNumber + "\n"
// + "[ReceiverID]" + ReceiverID + "\n"
// + "[FlatStream]" + inputLine + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) +"\n"
// );
// }
// //eCross Partner 주소
//// Context ctx = new Context(url,"demo","demo");
//// outStream = ctx.CallService(serviceName,inputStream);
// //결과전문
// outputString = (String)outStream.get("ReplyStream");
//
// // 트렌젝션 ID 15바이트를 처리
// try {
// outputString = outputString.substring(15);
// }catch(Exception ex){
// logger.warn("substring error", ex);
// }
//
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "RECV ["+outputString+"]"+CommonLib.getDumpMessage(outputString.getBytes()) +"\n"
// );
// }
// }catch(Exception ee){
// if(logger.isError()){
// logger.error("HttpClientAdapterServiceExtorg] Exception"+ ee.getMessage(),ee);
// }
// }
// } catch (Exception e) {
// if(logger.isError()){
// logger.error("HttpClientAdapterServiceExtorg] Exception"+ e.getMessage(),e);
// }
// }
//
// if(logger.isDebug()){
// logger.debug("RECV ["+outputString+"]"+CommonLib.getDumpMessage(outputString.getBytes()) +"\n");
// }
//
// if (outputString == null){
// throw new Exception("HttpClientAdapterServiceExtorg ] execute - input message parse fail");
// }
//
// return outputString.getBytes();
// }
//
//}
@@ -0,0 +1,167 @@
package com.eactive.eai.adapter.http.client.impl;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterManager;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.CommonLib;
import com.eactive.eai.common.util.MessageUtil;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.HttpVersion;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.params.HttpConnectionParams;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.net.URLEncoder;
import java.util.Properties;
public class HttpClientAdapterServiceGet extends HttpClientAdapterServiceSupport {
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
boolean isAsync = false;
GetMethod method = new GetMethod(vo.getUrl());
HttpClient mclient = this.client;
configureHttpClient(mclient, method, vo, vo.getUrl(), vo.getContentType());
String sendData = "";
if (data instanceof String) {
sendData = URLEncoder.encode((String) data, vo.getEncode());
} else if (data instanceof byte[]) {
sendData = URLEncoder.encode(new String((byte[]) data, vo.getEncode()), vo.getEncode());
}
StringBuilder querySb = new StringBuilder();
if (logger.isDebug()) {
logger.debug("HttpClientAdapterServiceGet] GET Method URLEncoder");
}
if (RESPONSE_TYPE_ASYNC.equals(vo.getResponseType())) {
isAsync = true;
querySb.append("type=async&");
}
querySb.append(vo.getParameterName()).append("=");
querySb.append(sendData);
method.setQueryString(querySb.toString());
String contentTypeValue = null;
if (StringUtils.isNotEmpty(vo.getContentType())) {
if (StringUtils.isNotEmpty(vo.getEncode())) {
contentTypeValue = vo.getContentType() + "; charset=" + vo.getEncode();
} else {
contentTypeValue = vo.getContentType();
}
method.setRequestHeader(CONTENT_TYPE_KEY, contentTypeValue);
}
if (vo.getAdapterHeaders() != null) {
for (String key : vo.getAdapterHeaders().keySet()) {
method.addRequestHeader(key, vo.getAdapterHeaders().get(key));
}
}
if (logger.isInfoEnabled()) {
logger.info("HttpClientAdapterServiceGet] " + CONTENT_TYPE_KEY + "(" + contentTypeValue + ")");
}
int status = -1;
try {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + sendData + "]" + CommonLib.getDumpMessage(sendData));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
stopWatch.stop();
String responseCharSet = getResponseCharSet(method.getResponseCharSet(), vo.getAdapterGroupName());
// status 200(정상) 이외에는 error 처리
if (status != 200) {
try {
logger.error("HttpClientAdapterServiceGet] receive status[" + status + "] data["
+ new String(method.getResponseBody()) + "]");
} catch (Exception e) {
logger.error(e);
}
throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="
+ vo.getAdapterGroupName() + "." + vo.getAdapterName(), status);
}
byte[] responseMessage = method.getResponseBody();
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime() && logger.isWarn()) {
logger.warn("HttpClientAdapterServiceGet] URL[" + vo.getUrl() + "] lazy async response time = "
+ stopWatch.toString() + " responseMessage=" + new String(responseMessage, responseCharSet));
}
responseMessage = getEncodingConvert(responseCharSet, vo.getAdapterGroupName(), responseMessage);
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + new String(responseMessage, responseCharSet) + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo = m.getAdapterGroupVO(vo.getAdapterGroupName());
if (MessageUtil.isBytesMessage(agvo.getMessageType())) {
return responseMessage;
} else {
return new String(responseMessage, vo.getEncode());
}
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceGet] SocketTimeoutException : " + ste.toString(), ste);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceGet] SocketTimeoutException : " + ste.toString(), ste);
}
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceGet] Connection Exception : " + ce.toString(), ce);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceGet] Connection Exception : " + ce.toString(), ce);
}
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceGet] Exception : " + e.toString(), e);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceGet] Exception : " + e.toString(), e);
}
throw e;
} finally {
method.releaseConnection();
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA014", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
}
@@ -0,0 +1,203 @@
//
//package com.eactive.eai.adapter.http.client.impl;
//
//import com.eactive.eai.adapter.http.HttpMemoryLogger;
//import com.eactive.eai.adapter.http.HttpStatusException;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.util.CommonLib;
//import org.apache.commons.httpclient.HttpClient;
//import org.apache.commons.httpclient.HttpStatus;
//import org.apache.commons.httpclient.HttpVersion;
//import org.apache.commons.httpclient.methods.PostMethod;
//
//import java.net.ConnectException;
//import java.net.SocketTimeoutException;
//import java.util.Properties;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapterServiceMemo extends HttpClientAdapterServiceSupport{
//
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, byte[] data, Properties tempProp) throws Exception {
//
// HttpClientAdapterVO vo = super.setting(prop, tempProp);
//
// if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
// logger.debug("HttpClientAdapterServiceMemo] SEND (" + vo.getMethod() + ") ");
// }
// PostMethod method = new PostMethod(vo.getUrl());
// if (vo.getTimeout() > -1) {
// method.getParams().setSoTimeout(vo.getTimeout());
// }
// HttpClient mclient = this.client;
// if ( vo.getConnectionTimeout() != 0){
// mclient.getParams().setParameter("http.connection.timeout", vo.getConnectionTimeout());
// }
// method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_0);
// int memoMinSize = 587;
//
// String srvCode = "";
// String serType = "";
// String recipient = "";
// String send = "";
// String title = "";
// String body = "";
// String urgent = "";
// String saveOption = "";
// String rcvIp = "";
//
// if (data.length >= memoMinSize) {
// if (vo.getEncode() != null && vo.getEncode().length() > 0) {
// if (logger.isDebug()) {
// logger.debug("HttpClientAdapterServiceMemo] ENCODE(" + vo.getEncode() + ") ");
// }
// srvCode = new String(data, 0, 6, vo.getEncode());
// serType = new String(data, 6, 1, vo.getEncode());
// recipient = new String(data, 7, 7, vo.getEncode());
// send = new String(data, 14, 7, vo.getEncode());
// title = new String(data, 21, 40, vo.getEncode());
// body = new String(data, 61, 500, vo.getEncode());
// urgent = new String(data, 561, 1, vo.getEncode());
// saveOption = new String(data, 562, 1, vo.getEncode());
// rcvIp = new String(data, 563, 24, vo.getEncode());
//
// } else {
// srvCode = new String(data, 0, 6);
// serType = new String(data, 6, 1);
// recipient = new String(data, 7, 7);
// send = new String(data, 14, 7);
// title = new String(data, 21, 40);
// body = new String(data, 61, 500);
// urgent = new String(data, 561, 1);
// saveOption = new String(data, 562, 1);
// rcvIp = new String(data, 563, 24);
// }
// method.addParameter("SRV_CODE", srvCode );
// method.addParameter("SER_TYPE", serType );
// method.addParameter("RECIPIENT", recipient );
// method.addParameter("SEND", send );
// method.addParameter("TITLE", title );
// method.addParameter("BODY", body );
// method.addParameter("URGENT", urgent );
// method.addParameter("SAVEOPTION", saveOption);
// method.addParameter("RCV_IP", rcvIp );
//
// } else {
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceMemo] Invalid Data Length (" + data.length + ") < "
// + memoMinSize);
// }
// throw new Exception("HttpClientAdapterServiceMemo Error : MessageSize(" + (data.length)
// + " Bytes) too small < " + memoMinSize);
// }
//
// int status = -1;
//
// try {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[SRV_CODE] "+ srvCode + "\n"
// + "[SER_TYPE] "+ serType + "\n"
// + "[RECIPIENT] "+ recipient + "\n"
// + "[SEND] "+ send + "\n"
// + "[TITLE] "+ title + "\n"
// + "[BODY] "+ body + "\n"
// + "[URGENT] "+ urgent + "\n"
// + "[SAVEOPTION] "+ saveOption + "\n"
// + "[RCV_IP] "+ rcvIp + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) );
// }
// //mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// if (vo.getEncode() != null && vo.getEncode().length() > 0) {
// mclient.getParams().setContentCharset(vo.getEncode());
// }
// else {
// // ASIS 에서 DEFAULT로 EUC_KR로 설정했음
// mclient.getParams().setContentCharset("EUC_KR");
// }
//
// status = mclient.executeMethod(method);
// //status 200(정상) 이외에는 error 처리
// if (status !=200){
// try{
// logger.error("HttpClientAdapterServiceMemo] receive status["+status+"] data[" + new String(method.getResponseBody()) +"]");
// }catch(Exception e){
// logger.error(e);
// }
// throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="+vo.getAdapterGroupName()+"."+vo.getAdapterName(),status);
// }
// byte[] responseMessage = method.getResponseBody();
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "RECV ["+new String(responseMessage)+"]"+CommonLib.getDumpMessage(responseMessage) );
// }
// return responseMessage;
//
// } catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient
// // 3.1일 경우
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServiceMemo] SocketTimeoutException : " + ste.toString(), ste);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceMemo] SocketTimeoutException : " + ste.toString(), ste);
// }
// throw ste;
// } catch (ConnectException ce) {
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServiceMemo] Connection Exception : " + ce.toString(), ce);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceMemo] Connection Exception : " + ce.toString(), ce);
// }
// throw ce;
// } catch (Exception e) {
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServiceMemo] Exception : " + e.toString(), e);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServiceMemo] Exception : " + e.toString(), e);
// }
// throw e;
// } finally {
// method.releaseConnection();
// if (status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if (logger.isDebug()) {
// logger.debug(resMsg);
// }
// }
// }
//
// }
//
//
//}
@@ -0,0 +1,227 @@
package com.eactive.eai.adapter.http.client.impl;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.property.PropManager;
import com.eactive.eai.common.util.CommonLib;
import com.eactive.eai.util.UrlUtil;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.HttpVersion;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpConnectionParams;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.Properties;
// Msa 는 LG Micro Service Architecture F/W과 통신하기 위한 Adapter로 관련 Site 전용
public class HttpClientAdapterServiceMsa extends HttpClientAdapterServiceSupport {
public static String DEFAULT_ENCODE = "UTF-8";
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
String svcName = tempProp.getProperty(TRAN_CODE, "");
if (StringUtils.isEmpty(svcName)) {
throw new Exception("service name is empty");
}
boolean isAsync = false;
if (vo.getUrl() == null) {
throw new Exception("URL is NULL");
}
if (vo.getUrl().endsWith(".ajmd") || vo.getUrl().endsWith(".axmd")) {
isAsync = true;
}
String msaUrl = vo.getUrl().replace("%" + TRAN_CODE + "%", svcName);
// ENVR_INFO_DVSN_CD = L
// FRST_DMND_SYS_IP_VAL 로 라우팅하도록 함
boolean localCall = LOCAL_CALL_Y.equals(tempProp.getProperty(LOCAL_CALL, "N"));
if (localCall) {
String newIp = tempProp.getProperty(LOCAL_IP);
if (newIp == null) {
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceMsa] LOCAL_CALL FRST_DMND_SYS_IP_VAL is empty, SKIP : "
+ msaUrl);
}
} else {
String newPort = PropManager.getInstance().getProperty("LOCAL", "port", "7001");
msaUrl = UrlUtil.replaceIpAddress(msaUrl, newIp, newPort);
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceMsa] LOCAL_CALL REPLACED_URL : " + msaUrl);
}
}
}
PostMethod method = new PostMethod(msaUrl);
HttpClient mclient = this.client;
configureHttpClient(mclient, method, vo, vo.getUrl(), vo.getContentType());
logger.debug("HttpClientAdapterServiceMsa] ENCODE(" + vo.getEncode() + ")");
try {
mclient.getParams().setContentCharset(vo.getEncode());
} catch (Exception e) {
if (logger.isError()) {
logger.error("HttpClientAdapterServiceMsa] ENCODE(" + vo.getEncode() + ") ERROR : " + e.toString());
logger.error("HttpClientAdapterServiceMsa] ENCODE(" + vo.getEncode() + ") SKIP ");
}
}
String contentTypeValue = null;
if (StringUtils.isNotEmpty(vo.getContentType())) {
if (StringUtils.isNotEmpty(vo.getEncode())) {
contentTypeValue = vo.getContentType() + "; charset=" + vo.getEncode();
} else {
contentTypeValue = vo.getContentType();
}
method.setRequestHeader(CONTENT_TYPE_KEY, contentTypeValue);
}
if (vo.getAdapterHeaders() != null) {
for (String key : vo.getAdapterHeaders().keySet()) {
method.addRequestHeader(key, vo.getAdapterHeaders().get(key));
}
}
if (logger.isInfoEnabled()) {
logger.info("HttpClientAdapterServiceMsa] " + CONTENT_TYPE_KEY + "(" + contentTypeValue + ")");
}
byte[] sendBytes = null;
if (data instanceof String) {
sendBytes = ((String) data).getBytes(vo.getEncode());
} else if (data instanceof byte[]) {
sendBytes = (byte[]) data;
}
InputStream in = new ByteArrayInputStream(sendBytes); // "utf-8"
method.setRequestBody(in);
int status = -1;
try {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceMsa] SEND (" + vo.getAdapterGroupName() + ") = ["
+ new String(sendBytes, vo.getEncode()) + "]");
logger.debug("HttpClientAdapterServiceMsa] SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(sendBytes));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + new String(sendBytes, vo.getEncode()) + "]" + CommonLib.getDumpMessage(sendBytes));
}
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
stopWatch.stop();
String responseCharSet = getResponseCharSet(method.getResponseCharSet(), vo.getAdapterGroupName());
if (status != 200) {
try {
logger.error("HttpClientAdapterServiceMsa] receive status[" + status + "] data["
+ new String(method.getResponseBody()) + "]");
} catch (Exception e) {
logger.error(e);
}
throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="
+ vo.getAdapterGroupName() + "." + vo.getAdapterName(), status);
}
// 응답으로 온 byte[]를 그대로 전달한다.
byte[] responseMessage = method.getResponseBody();
;
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime()) {
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceMsa] URL[" + msaUrl + "] lazy async response time = "
+ stopWatch.toString() + " responseMessage="
+ new String(responseMessage, responseCharSet));
}
}
responseMessage = getEncodingConvert(responseCharSet, vo.getAdapterGroupName(), responseMessage);
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceMsa] responseType =" + vo.getResponseType()
+ ", responseCharSet=" + responseCharSet);
logger.debug("HttpClientAdapterServiceMsa] RECV (" + vo.getAdapterGroupName() + ") = ["
+ new String(responseMessage, responseCharSet) + "]");
logger.debug("HttpClientAdapterServiceMsa] RECV (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(responseMessage));
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + new String(responseMessage, responseCharSet) + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
return responseMessage;
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceMsa] SocketTimeoutException : " + ste.toString() + " url="
+ msaUrl,
ste);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceMsa] SocketTimeoutException : " + ste.toString() + " url="
+ msaUrl, ste);
}
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceMsa] Connection Exception : " + ce.toString() + " url=" + msaUrl,
ce);
}
if (logger.isError()) {
logger.error(
"HttpClientAdapterServiceMsa] Connection Exception : " + ce.toString() + " url=" + msaUrl,
ce);
}
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceMsa] Exception : " + e.toString() + " url=" + msaUrl, e);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceMsa] Exception : " + e.toString() + " url=" + msaUrl, e);
}
throw e;
} finally {
method.releaseConnection();
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
}
@@ -0,0 +1,227 @@
package com.eactive.eai.adapter.http.client.impl;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.property.PropManager;
import com.eactive.eai.common.util.CommonLib;
import com.eactive.eai.util.UrlUtil;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.HttpVersion;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpConnectionParams;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.Properties;
// NexCore F/W과 통신하기 위한 Adapter로 관련 Site 전용
public class HttpClientAdapterServiceNexCore extends HttpClientAdapterServiceSupport {
public static String DEFAULT_ENCODE = "UTF-8";
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception {
HttpClientAdapterVO vo = super.setting(prop, tempProp);
String svcName = tempProp.getProperty(TRAN_CODE, "");
if (StringUtils.isEmpty(svcName)) {
throw new Exception("service name is empty");
}
boolean isAsync = false;
if (vo.getUrl() == null) {
throw new Exception("URL is NULL");
}
if (vo.getUrl().endsWith(".ajmd") || vo.getUrl().endsWith(".axmd")) {
isAsync = true;
}
String nKesaUrl = vo.getUrl().replace("%" + TRAN_CODE + "%", svcName);
// ENVR_INFO_DVSN_CD = L
// FRST_DMND_SYS_IP_VAL 로 라우팅하도록 함
boolean localCall = LOCAL_CALL_Y.equals(tempProp.getProperty(LOCAL_CALL, "N"));
if (localCall) {
String newIp = tempProp.getProperty(LOCAL_IP);
if (newIp == null) {
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceNexCore] LOCAL_CALL FRST_DMND_SYS_IP_VAL is empty, SKIP : "
+ nKesaUrl);
}
} else {
String newPort = PropManager.getInstance().getProperty("LOCAL", "port", "7001");
nKesaUrl = UrlUtil.replaceIpAddress(nKesaUrl, newIp, newPort);
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceNexCore] LOCAL_CALL REPLACED_URL : " + nKesaUrl);
}
}
}
PostMethod method = new PostMethod(nKesaUrl);
HttpClient mclient = this.client;
configureHttpClient(mclient, method, vo, vo.getUrl(), vo.getContentType());
logger.debug("HttpClientAdapterServiceNexCore] ENCODE(" + vo.getEncode() + ")");
try {
mclient.getParams().setContentCharset(vo.getEncode());
} catch (Exception e) {
if (logger.isError()) {
logger.error("HttpClientAdapterServiceNexCore] ENCODE(" + vo.getEncode() + ") ERROR : " + e.toString());
logger.error("HttpClientAdapterServiceNexCore] ENCODE(" + vo.getEncode() + ") SKIP ");
}
}
String contentTypeValue = null;
if (StringUtils.isNotEmpty(vo.getContentType())) {
if (StringUtils.isNotEmpty(vo.getEncode())) {
contentTypeValue = vo.getContentType() + "; charset=" + vo.getEncode();
} else {
contentTypeValue = vo.getContentType();
}
method.setRequestHeader(CONTENT_TYPE_KEY, contentTypeValue);
}
if (vo.getAdapterHeaders() != null) {
for (String key : vo.getAdapterHeaders().keySet()) {
method.addRequestHeader(key, vo.getAdapterHeaders().get(key));
}
}
if (logger.isInfoEnabled()) {
logger.info("HttpClientAdapterServiceNexCore] " + CONTENT_TYPE_KEY + "(" + contentTypeValue + ")");
}
byte[] sendBytes = null;
if (data instanceof String) {
sendBytes = ((String) data).getBytes(vo.getEncode());
} else if (data instanceof byte[]) {
sendBytes = (byte[]) data;
}
InputStream in = new ByteArrayInputStream(sendBytes); // "utf-8"
method.setRequestBody(in);
int status = -1;
try {
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceNexCore] SEND (" + vo.getAdapterGroupName() + ") = ["
+ new String(sendBytes, vo.getEncode()) + "]");
logger.debug("HttpClientAdapterServiceNexCore] SEND (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(sendBytes));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"SEND [" + new String(sendBytes, vo.getEncode()) + "]" + CommonLib.getDumpMessage(sendBytes));
}
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
stopWatch.stop();
String responseCharSet = getResponseCharSet(method.getResponseCharSet(), vo.getAdapterGroupName());
if (status != 200) {
try {
logger.error("HttpClientAdapterServiceNexCore] receive status[" + status + "] data["
+ new String(method.getResponseBody()) + "]");
} catch (Exception e) {
logger.error(e);
}
throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="
+ vo.getAdapterGroupName() + "." + vo.getAdapterName(), status);
}
// 응답으로 온 byte[]를 그대로 전달한다.
byte[] responseMessage = method.getResponseBody();
;
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime()) {
if (logger.isWarn()) {
logger.warn("HttpClientAdapterServiceNexCore] URL[" + nKesaUrl + "] lazy async response time = "
+ stopWatch.toString() + " responseMessage="
+ new String(responseMessage, responseCharSet));
}
}
responseMessage = getEncodingConvert(responseCharSet, vo.getAdapterGroupName(), responseMessage);
if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
logger.debug("HttpClientAdapterServiceNexCore] responseType =" + vo.getResponseType()
+ ", responseCharSet=" + responseCharSet);
logger.debug("HttpClientAdapterServiceNexCore] RECV (" + vo.getAdapterGroupName() + ") = ["
+ new String(responseMessage, responseCharSet) + "]");
logger.debug("HttpClientAdapterServiceNexCore] RECV (" + vo.getAdapterGroupName() + ") = "
+ CommonLib.getDumpMessage(responseMessage));
}
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.txlog(vo.getAdapterGroupName() + vo.getAdapterName(),
"RECV [" + new String(responseMessage, responseCharSet) + "]"
+ CommonLib.getDumpMessage(responseMessage));
}
return responseMessage;
} catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceNexCore] SocketTimeoutException : " + ste.toString() + " url="
+ nKesaUrl,
ste);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceNexCore] SocketTimeoutException : " + ste.toString() + " url="
+ nKesaUrl, ste);
}
throw ste;
} catch (ConnectException ce) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceNexCore] Connection Exception : " + ce.toString() + " url=" + nKesaUrl,
ce);
}
if (logger.isError()) {
logger.error(
"HttpClientAdapterServiceNexCore] Connection Exception : " + ce.toString() + " url=" + nKesaUrl,
ce);
}
throw ce;
} catch (Exception e) {
if (vo.getTraceLevel() >= 3) {
HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
"HttpClientAdapterServiceNexCore] Exception : " + e.toString() + " url=" + nKesaUrl, e);
}
if (logger.isError()) {
logger.error("HttpClientAdapterServiceNexCore] Exception : " + e.toString() + " url=" + nKesaUrl, e);
}
throw e;
} finally {
method.releaseConnection();
if (status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if (logger.isDebug()) {
logger.debug(resMsg);
}
}
}
}
}
@@ -0,0 +1,169 @@
//
//package com.eactive.eai.adapter.http.client.impl;
//
//import com.eactive.eai.adapter.http.HttpMemoryLogger;
//import com.eactive.eai.adapter.http.HttpStatusException;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
//import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
//import com.eactive.eai.common.exception.ExceptionUtil;
//import com.eactive.eai.common.util.CommonLib;
//import org.apache.commons.httpclient.HttpClient;
//import org.apache.commons.httpclient.HttpStatus;
//import org.apache.commons.httpclient.HttpVersion;
//import org.apache.commons.httpclient.methods.PostMethod;
//
//import java.net.ConnectException;
//import java.net.SocketTimeoutException;
//import java.util.Properties;
//
//
///**
//* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
//* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
//* 2. 처리 개요 :
//* * - 2009.11.24 retry 로직 제거 : 요청
//* 3. 주의사항
//*
//* @author :
//* @version : v 1.0.0
//* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
//* @since :
//
//*/
//public class HttpClientAdapterServicePopup extends HttpClientAdapterServiceSupport{
//
// /**
// * 1. 기능 : 전문과 같은 Raw Data 통신에 사용
// * 2. 처리 개요 :
// * - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
// * 3. 주의사항
// *
// * @param prop Http Adapter 속성 정보
// * @param message 송신 전문
// * @return 반환 된 byte[] Object
// * @exception Exception 수동 시스템 간 통신 중 발생
// **/
// public Object execute(Properties prop, byte[] data, Properties tempProp) throws Exception {
//
// HttpClientAdapterVO vo = super.setting(prop, tempProp);
//
// if (logger.isDebug() && "N".equals(vo.getTestCallYn())) {
// logger.debug("HttpClientAdapter] SEND (" + vo.getMethod() + ") ");
// }
// PostMethod method = new PostMethod(vo.getUrl());
// if (vo.getTimeout() > -1) {
// method.getParams().setSoTimeout(vo.getTimeout());
// }
// HttpClient mclient = this.client;
// if ( vo.getConnectionTimeout() != 0){
// mclient.getParams().setParameter("http.connection.timeout", vo.getConnectionTimeout());
// }
// method.getParams().setParameter("http.protocol.version", HttpVersion.HTTP_1_0);
//
// // Popup Data Size : 153 Bytes
// int popupMinSize = 153;
// String srvCode = "";
// String recipient = "";
// String title = "";
// String body = "";
//
//
// if (data.length >= popupMinSize) {
// if (vo.getEncode() != null && vo.getEncode().length() > 0) {
// if (logger.isDebug()) {
// logger.debug("HttpClientAdapterServicePopup] ENCODE(" + vo.getEncode() + ") ");
// }
// srvCode = new String(data, 0, 6, vo.getEncode());
// recipient = new String(data, 6, 7, vo.getEncode());
// title = new String(data, 13, 40, vo.getEncode());
// body = new String(data, 53, 100, vo.getEncode());
// } else {
// srvCode = new String(data, 0, 6);
// recipient = new String(data, 6, 7);
// title = new String(data, 13, 40);
// body = new String(data, 53, 100);
// }
// method.addParameter("SRV_CODE", srvCode);
// method.addParameter("RECIPIENT", recipient);
// method.addParameter("TITLE", title);
// method.addParameter("BODY", body);
// } else {
// if (logger.isError()) {
// logger.error("HttpClientAdapterServicePopup] Invalid Data Length (" + data.length + ") < "
// + popupMinSize);
// }
// throw new Exception("HttpClientAdapterServicePopup Error : MessageSize(" + (data.length)
// + " Bytes) too small < " + popupMinSize);
// }
//
// int status = -1;
//
// try {
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(),
// "[SRV_CODE] "+ srvCode + "\n"
// + "[RECIPIENT] "+ recipient + "\n"
// + "[TITLE] "+ title + "\n"
// + "[BODY] "+ body + "\n"
// + "SEND ["+new String(data)+"]"+CommonLib.getDumpMessage(data) );
// }
// //mclient.getHttpConnectionManager().getParams().setConnectionTimeout(30000);
// //mclient.getParams().setContentCharset("EUC_KR");
// status = mclient.executeMethod(method);
// //status 200(정상) 이외에는 error 처리
// if (status !=200){
// try{
// logger.error("HttpClientAdapterServicePopup] receive status["+status+"] data[" + new String(method.getResponseBody()) +"]");
// }catch(Exception e){
// logger.error(e);
// }
// throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="+vo.getAdapterGroupName()+"."+vo.getAdapterName(),status);
// }
// byte[] responseMessage = method.getResponseBody();
// if (vo.getTraceLevel() >= 3){
// HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "RECV ["+new String(responseMessage)+"]"+CommonLib.getDumpMessage(responseMessage) );
// }
// return responseMessage;
//
// } catch (SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServicePopup] SocketTimeoutException : " + ste.toString(), ste);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServicePopup] SocketTimeoutException : " + ste.toString(), ste);
// }
// throw ste;
// } catch (ConnectException ce) {
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServicePopup] Connection Exception : " + ce.toString(), ce);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServicePopup] Connection Exception : " + ce.toString(), ce);
// }
// throw ce;
// } catch (Exception e) {
// if (vo.getTraceLevel() >= 3) {
// HttpMemoryLogger.error(vo.getAdapterGroupName() + vo.getAdapterName(),
// "HttpClientAdapterServicePopup] Exception : " + e.toString(), e);
// }
// if (logger.isError()) {
// logger.error("HttpClientAdapterServicePopup] Exception : " + e.toString(), e);
// }
// throw e;
// } finally {
// method.releaseConnection();
// if (status != HttpStatus.SC_OK) {
// String[] msgArgs = new String[1];
// msgArgs[0] = String.valueOf(status);
// String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
// if (logger.isDebug()) {
// logger.debug(resMsg);
// }
// }
// }
// }
//
//
//}
@@ -0,0 +1,224 @@
package com.eactive.eai.adapter.http.client.impl;
import java.net.ConnectException;
import java.net.SocketTimeoutException;
import java.util.Properties;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.protocol.Protocol;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.StopWatch;
import com.eactive.eai.adapter.AdapterGroupVO;
import com.eactive.eai.adapter.AdapterManager;
import com.eactive.eai.adapter.http.HttpMemoryLogger;
import com.eactive.eai.adapter.http.HttpStatusException;
import com.eactive.eai.adapter.http.client.HttpClientAdapterServiceSupport;
import com.eactive.eai.adapter.http.client.HttpClientAdapterVO;
import com.eactive.eai.adapter.http.secure.CustomHttpsSocketFactory;
import com.eactive.eai.adapter.http.secure.EasySSLProtocolSocketFactory;
import com.eactive.eai.common.exception.ExceptionUtil;
import com.eactive.eai.common.util.CommonLib;
import com.eactive.eai.common.util.MessageUtil;
/**
* 1. 기능 : EAI HTTP OutBound 용 어댑터로 수동 시스템의 HTTP 웹 컴포넌트를
* GET/POST 방식으로 호출할 수 있는 기능을 제공한다.
* 2. 처리 개요 :
* * - 2009.11.24 retry 로직 제거 : 요청
* 3. 주의사항
*
* @author :
* @version : v 1.0.0
* @see : WLIAdapterFactory.java, WLIAdapter.java, WLIDefaultAdapter.java
* @since :
*/
public class HttpClientAdapterServicePost extends HttpClientAdapterServiceSupport{
/**
* 1. 기능 : 전문과 같은 Raw Data 통신에 사용
* 2. 처리 개요 :
* - 속성 정보를 설정 하고 수동 시스템 서비스를 호출 한다.
* 3. 주의사항
*
* @param prop Http Adapter 속성 정보
* @param message 송신 전문
* @return 반환 된 byte[] Object
* @exception Exception 수동 시스템 간 통신 중 발생
**/
public Object execute(Properties prop, Object data, Properties tempProp) throws Exception
{
HttpClientAdapterVO vo = super.setting(prop, tempProp);
boolean isAsync = false;
PostMethod method = new PostMethod(vo.getUrl());
HttpClient mclient = this.client;
configureHttpClient(mclient, method, vo, vo.getUrl(), vo.getContentType());
String sendData = "";
if (data instanceof String) {
sendData = (String) data;
} else if (data instanceof byte[]) {
sendData = new String((byte[]) data, vo.getEncode());
}
mclient.getParams().setContentCharset(vo.getEncode());
if ("Y".equals(vo.getUrlEncodeYn())){
sendData = java.net.URLEncoder.encode(sendData);
}
if(RESPONSE_TYPE_ASYNC.equals(vo.getResponseType())) {
isAsync = true;
method.addParameter("type", "async");
}
method.addParameter(vo.getParameterName(), sendData);
String contentTypeValue = null;
if(StringUtils.isNotEmpty(vo.getContentType())) {
if(StringUtils.isNotEmpty(vo.getEncode())) {
contentTypeValue = vo.getContentType() +"; charset=" + vo.getEncode();
}
else {
contentTypeValue = vo.getContentType();
}
method.setRequestHeader(CONTENT_TYPE_KEY, contentTypeValue);
}
if (vo.getAdapterHeaders() != null){
for(String key : vo.getAdapterHeaders().keySet()){
method.addRequestHeader(key, vo.getAdapterHeaders().get(key));
}
}
if(logger.isInfoEnabled()) {
logger.info("HttpClientAdapterServicePost] "+CONTENT_TYPE_KEY+"("+contentTypeValue+")");
}
int status = -1;
try {
if(logger.isDebug() && "N".equals(vo.getTestCallYn())){
logger.debug("HttpClientAdapterServicePost] SEND ("+vo.getAdapterGroupName()+") = ["+sendData+"]");
logger.debug("HttpClientAdapterServicePost] SEND ("+vo.getAdapterGroupName()+") = "+CommonLib.getDumpMessage(sendData));
}
StopWatch stopWatch = new StopWatch();
stopWatch.start();
if (vo.getTraceLevel() >= 3){
HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "SEND ["+sendData+"]"+CommonLib.getDumpMessage(sendData));
}
if (vo.getUrl() != null && vo.getUrl().startsWith("https")) {
Protocol.registerProtocol("https",
new Protocol("https", new CustomHttpsSocketFactory(new EasySSLProtocolSocketFactory()), 443));
}
status = mclient.executeMethod(method);
stopWatch.stop();
String responseCharSet = getResponseCharSet(method.getResponseCharSet(),vo.getAdapterGroupName());
//status 200(정상) 이외에는 error 처리
if (status !=200){
try{
logger.error("HttpClientAdapterServicePost] receive status["+status+"] data[" + new String(method.getResponseBody()) +"]");
}catch(Exception e){
logger.error(e);
}
throw new HttpStatusException("수신시스템을 확인하세요. HTTP 에러[ " + status + "] adapterName="+vo.getAdapterGroupName()+"."+vo.getAdapterName(),status);
}
byte[] responseMessage = method.getResponseBody();
if (isAsync && stopWatch.getTime() > vo.getSlowTranTime()) {
if (logger.isWarn()){
logger.warn("HttpClientAdapterServicePost] URL[" + vo.getUrl() + "] lazy response time = " + stopWatch.toString()+ " responseMessage=" + new String(responseMessage,responseCharSet));
}
}
responseMessage = getEncodingConvert(responseCharSet, vo.getAdapterGroupName(), responseMessage);
// if(vo.getEncode() != null && vo.getEncode().length() > 0) {
// Charset res = null;
// Charset adpt = null;
// byte[] orgResponse = method.getResponseBody();
// try{
// res = Charset.forName(responseCharSet);
// adpt = Charset.forName(vo.getEncode());
// if (res.compareTo(adpt)==0){
// responseMessage = orgResponse;
// }else{
// String encodingString = new String(orgResponse, responseCharSet);
// responseMessage = encodingString.getBytes(vo.getEncode());
// }
// }catch(UnsupportedCharsetException e){
// responseMessage = orgResponse;
// }
// }
// else {
// responseMessage = method.getResponseBody();
// }
//----------------------------------------------------------
if (logger.isDebug() && "N".equals(vo.getTestCallYn())){
logger.debug("HttpClientAdapterServicePost] responseType ="+ vo.getResponseType());
logger.debug("HttpClientAdapterServicePost] RECV ("+vo.getAdapterGroupName()+") = ["+new String(responseMessage,responseCharSet)+"]");
logger.debug("HttpClientAdapterServicePost] RECV ("+vo.getAdapterGroupName()+") = "+CommonLib.getDumpMessage(responseMessage));
}
if (vo.getTraceLevel() >= 3){
HttpMemoryLogger.txlog(vo.getAdapterGroupName()+vo.getAdapterName(), "RECV ["+new String(responseMessage,responseCharSet)+"]"+CommonLib.getDumpMessage(responseMessage));
}
AdapterManager m = AdapterManager.getInstance();
AdapterGroupVO agvo= m.getAdapterGroupVO(vo.getAdapterGroupName());
if (MessageUtil.isBytesMessage(agvo.getMessageType())) {
return responseMessage;
} else {
return new String(responseMessage, vo.getEncode());
}
} catch(SocketTimeoutException ste) { // Read Timeout :: HttpClient 3.1일 경우
if (vo.getTraceLevel() >= 3){
HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServicePost] SocketTimeoutException : " + ste.toString() ,ste);
}
if (logger.isError()){
logger.error("HttpClientAdapterServicePost] SocketTimeoutException : " + ste.toString() ,ste);
}
throw ste;
} catch(ConnectException ce) {
if (vo.getTraceLevel() >= 3){
HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServicePost] Connection Exception : " + ce.toString() ,ce);
}
if (logger.isError()){
logger.error("HttpClientAdapterServicePost] Connection Exception : " + ce.toString() ,ce);
}
throw ce;
} catch(Exception e) {
if (vo.getTraceLevel() >= 3){
HttpMemoryLogger.error(vo.getAdapterGroupName()+vo.getAdapterName(),"HttpClientAdapterServicePost] Exception : " + e.toString() ,e);
}
if (logger.isError()){
logger.error("HttpClientAdapterServicePost] Exception : " + e.toString() ,e);
}
throw e;
} finally {
method.releaseConnection();
if(status != HttpStatus.SC_OK) {
String[] msgArgs = new String[1];
msgArgs[0] = String.valueOf(status);
String resMsg = ExceptionUtil.make("RDCEAIAHA013", msgArgs);
if(logger.isDebug()){
logger.debug(resMsg);
}
}
}
}
}

Some files were not shown because too many files have changed in this diff Show More