Commit 2034b5b1bc414860c9b8e17ae36f243c9a40103a

Authored by 함상기
0 parents

Init Version 20240228

Showing 61 changed files with 8688 additions and 0 deletions   Show diff stats
mvnw 0 → 100644
  1 +++ a/mvnw
  1 +#!/bin/sh
  2 +# ----------------------------------------------------------------------------
  3 +# Licensed to the Apache Software Foundation (ASF) under one
  4 +# or more contributor license agreements. See the NOTICE file
  5 +# distributed with this work for additional information
  6 +# regarding copyright ownership. The ASF licenses this file
  7 +# to you under the Apache License, Version 2.0 (the
  8 +# "License"); you may not use this file except in compliance
  9 +# with the License. You may obtain a copy of the License at
  10 +#
  11 +# https://www.apache.org/licenses/LICENSE-2.0
  12 +#
  13 +# Unless required by applicable law or agreed to in writing,
  14 +# software distributed under the License is distributed on an
  15 +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  16 +# KIND, either express or implied. See the License for the
  17 +# specific language governing permissions and limitations
  18 +# under the License.
  19 +# ----------------------------------------------------------------------------
  20 +
  21 +# ----------------------------------------------------------------------------
  22 +# Apache Maven Wrapper startup batch script, version 3.2.0
  23 +#
  24 +# Required ENV vars:
  25 +# ------------------
  26 +# JAVA_HOME - location of a JDK home dir
  27 +#
  28 +# Optional ENV vars
  29 +# -----------------
  30 +# MAVEN_OPTS - parameters passed to the Java VM when running Maven
  31 +# e.g. to debug Maven itself, use
  32 +# set MAVEN_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000
  33 +# MAVEN_SKIP_RC - flag to disable loading of mavenrc files
  34 +# ----------------------------------------------------------------------------
  35 +
  36 +if [ -z "$MAVEN_SKIP_RC" ] ; then
  37 +
  38 + if [ -f /usr/local/etc/mavenrc ] ; then
  39 + . /usr/local/etc/mavenrc
  40 + fi
  41 +
  42 + if [ -f /etc/mavenrc ] ; then
  43 + . /etc/mavenrc
  44 + fi
  45 +
  46 + if [ -f "$HOME/.mavenrc" ] ; then
  47 + . "$HOME/.mavenrc"
  48 + fi
  49 +
  50 +fi
  51 +
  52 +# OS specific support. $var _must_ be set to either true or false.
  53 +cygwin=false;
  54 +darwin=false;
  55 +mingw=false
  56 +case "$(uname)" in
  57 + CYGWIN*) cygwin=true ;;
  58 + MINGW*) mingw=true;;
  59 + Darwin*) darwin=true
  60 + # Use /usr/libexec/java_home if available, otherwise fall back to /Library/Java/Home
  61 + # See https://developer.apple.com/library/mac/qa/qa1170/_index.html
  62 + if [ -z "$JAVA_HOME" ]; then
  63 + if [ -x "/usr/libexec/java_home" ]; then
  64 + JAVA_HOME="$(/usr/libexec/java_home)"; export JAVA_HOME
  65 + else
  66 + JAVA_HOME="/Library/Java/Home"; export JAVA_HOME
  67 + fi
  68 + fi
  69 + ;;
  70 +esac
  71 +
  72 +if [ -z "$JAVA_HOME" ] ; then
  73 + if [ -r /etc/gentoo-release ] ; then
  74 + JAVA_HOME=$(java-config --jre-home)
  75 + fi
  76 +fi
  77 +
  78 +# For Cygwin, ensure paths are in UNIX format before anything is touched
  79 +if $cygwin ; then
  80 + [ -n "$JAVA_HOME" ] &&
  81 + JAVA_HOME=$(cygpath --unix "$JAVA_HOME")
  82 + [ -n "$CLASSPATH" ] &&
  83 + CLASSPATH=$(cygpath --path --unix "$CLASSPATH")
  84 +fi
  85 +
  86 +# For Mingw, ensure paths are in UNIX format before anything is touched
  87 +if $mingw ; then
  88 + [ -n "$JAVA_HOME" ] && [ -d "$JAVA_HOME" ] &&
  89 + JAVA_HOME="$(cd "$JAVA_HOME" || (echo "cannot cd into $JAVA_HOME."; exit 1); pwd)"
  90 +fi
  91 +
  92 +if [ -z "$JAVA_HOME" ]; then
  93 + javaExecutable="$(which javac)"
  94 + if [ -n "$javaExecutable" ] && ! [ "$(expr "\"$javaExecutable\"" : '\([^ ]*\)')" = "no" ]; then
  95 + # readlink(1) is not available as standard on Solaris 10.
  96 + readLink=$(which readlink)
  97 + if [ ! "$(expr "$readLink" : '\([^ ]*\)')" = "no" ]; then
  98 + if $darwin ; then
  99 + javaHome="$(dirname "\"$javaExecutable\"")"
  100 + javaExecutable="$(cd "\"$javaHome\"" && pwd -P)/javac"
  101 + else
  102 + javaExecutable="$(readlink -f "\"$javaExecutable\"")"
  103 + fi
  104 + javaHome="$(dirname "\"$javaExecutable\"")"
  105 + javaHome=$(expr "$javaHome" : '\(.*\)/bin')
  106 + JAVA_HOME="$javaHome"
  107 + export JAVA_HOME
  108 + fi
  109 + fi
  110 +fi
  111 +
  112 +if [ -z "$JAVACMD" ] ; then
  113 + if [ -n "$JAVA_HOME" ] ; then
  114 + if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
  115 + # IBM's JDK on AIX uses strange locations for the executables
  116 + JAVACMD="$JAVA_HOME/jre/sh/java"
  117 + else
  118 + JAVACMD="$JAVA_HOME/bin/java"
  119 + fi
  120 + else
  121 + JAVACMD="$(\unset -f command 2>/dev/null; \command -v java)"
  122 + fi
  123 +fi
  124 +
  125 +if [ ! -x "$JAVACMD" ] ; then
  126 + echo "Error: JAVA_HOME is not defined correctly." >&2
  127 + echo " We cannot execute $JAVACMD" >&2
  128 + exit 1
  129 +fi
  130 +
  131 +if [ -z "$JAVA_HOME" ] ; then
  132 + echo "Warning: JAVA_HOME environment variable is not set."
  133 +fi
  134 +
  135 +# traverses directory structure from process work directory to filesystem root
  136 +# first directory with .mvn subdirectory is considered project base directory
  137 +find_maven_basedir() {
  138 + if [ -z "$1" ]
  139 + then
  140 + echo "Path not specified to find_maven_basedir"
  141 + return 1
  142 + fi
  143 +
  144 + basedir="$1"
  145 + wdir="$1"
  146 + while [ "$wdir" != '/' ] ; do
  147 + if [ -d "$wdir"/.mvn ] ; then
  148 + basedir=$wdir
  149 + break
  150 + fi
  151 + # workaround for JBEAP-8937 (on Solaris 10/Sparc)
  152 + if [ -d "${wdir}" ]; then
  153 + wdir=$(cd "$wdir/.." || exit 1; pwd)
  154 + fi
  155 + # end of workaround
  156 + done
  157 + printf '%s' "$(cd "$basedir" || exit 1; pwd)"
  158 +}
  159 +
  160 +# concatenates all lines of a file
  161 +concat_lines() {
  162 + if [ -f "$1" ]; then
  163 + # Remove \r in case we run on Windows within Git Bash
  164 + # and check out the repository with auto CRLF management
  165 + # enabled. Otherwise, we may read lines that are delimited with
  166 + # \r\n and produce $'-Xarg\r' rather than -Xarg due to word
  167 + # splitting rules.
  168 + tr -s '\r\n' ' ' < "$1"
  169 + fi
  170 +}
  171 +
  172 +log() {
  173 + if [ "$MVNW_VERBOSE" = true ]; then
  174 + printf '%s\n' "$1"
  175 + fi
  176 +}
  177 +
  178 +BASE_DIR=$(find_maven_basedir "$(dirname "$0")")
  179 +if [ -z "$BASE_DIR" ]; then
  180 + exit 1;
  181 +fi
  182 +
  183 +MAVEN_PROJECTBASEDIR=${MAVEN_BASEDIR:-"$BASE_DIR"}; export MAVEN_PROJECTBASEDIR
  184 +log "$MAVEN_PROJECTBASEDIR"
  185 +
  186 +##########################################################################################
  187 +# Extension to allow automatically downloading the maven-wrapper.jar from Maven-central
  188 +# This allows using the maven wrapper in projects that prohibit checking in binary data.
  189 +##########################################################################################
  190 +wrapperJarPath="$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.jar"
  191 +if [ -r "$wrapperJarPath" ]; then
  192 + log "Found $wrapperJarPath"
  193 +else
  194 + log "Couldn't find $wrapperJarPath, downloading it ..."
  195 +
  196 + if [ -n "$MVNW_REPOURL" ]; then
  197 + wrapperUrl="$MVNW_REPOURL/org/apache/maven/wrapper/maven-wrapper/3.2.0/maven-wrapper-3.2.0.jar"
  198 + else
  199 + wrapperUrl="https://repo.maven.apache.org/maven2/org/apache/maven/wrapper/maven-wrapper/3.2.0/maven-wrapper-3.2.0.jar"
  200 + fi
  201 + while IFS="=" read -r key value; do
  202 + # Remove '\r' from value to allow usage on windows as IFS does not consider '\r' as a separator ( considers space, tab, new line ('\n'), and custom '=' )
  203 + safeValue=$(echo "$value" | tr -d '\r')
  204 + case "$key" in (wrapperUrl) wrapperUrl="$safeValue"; break ;;
  205 + esac
  206 + done < "$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.properties"
  207 + log "Downloading from: $wrapperUrl"
  208 +
  209 + if $cygwin; then
  210 + wrapperJarPath=$(cygpath --path --windows "$wrapperJarPath")
  211 + fi
  212 +
  213 + if command -v wget > /dev/null; then
  214 + log "Found wget ... using wget"
  215 + [ "$MVNW_VERBOSE" = true ] && QUIET="" || QUIET="--quiet"
  216 + if [ -z "$MVNW_USERNAME" ] || [ -z "$MVNW_PASSWORD" ]; then
  217 + wget $QUIET "$wrapperUrl" -O "$wrapperJarPath" || rm -f "$wrapperJarPath"
  218 + else
  219 + wget $QUIET --http-user="$MVNW_USERNAME" --http-password="$MVNW_PASSWORD" "$wrapperUrl" -O "$wrapperJarPath" || rm -f "$wrapperJarPath"
  220 + fi
  221 + elif command -v curl > /dev/null; then
  222 + log "Found curl ... using curl"
  223 + [ "$MVNW_VERBOSE" = true ] && QUIET="" || QUIET="--silent"
  224 + if [ -z "$MVNW_USERNAME" ] || [ -z "$MVNW_PASSWORD" ]; then
  225 + curl $QUIET -o "$wrapperJarPath" "$wrapperUrl" -f -L || rm -f "$wrapperJarPath"
  226 + else
  227 + curl $QUIET --user "$MVNW_USERNAME:$MVNW_PASSWORD" -o "$wrapperJarPath" "$wrapperUrl" -f -L || rm -f "$wrapperJarPath"
  228 + fi
  229 + else
  230 + log "Falling back to using Java to download"
  231 + javaSource="$MAVEN_PROJECTBASEDIR/.mvn/wrapper/MavenWrapperDownloader.java"
  232 + javaClass="$MAVEN_PROJECTBASEDIR/.mvn/wrapper/MavenWrapperDownloader.class"
  233 + # For Cygwin, switch paths to Windows format before running javac
  234 + if $cygwin; then
  235 + javaSource=$(cygpath --path --windows "$javaSource")
  236 + javaClass=$(cygpath --path --windows "$javaClass")
  237 + fi
  238 + if [ -e "$javaSource" ]; then
  239 + if [ ! -e "$javaClass" ]; then
  240 + log " - Compiling MavenWrapperDownloader.java ..."
  241 + ("$JAVA_HOME/bin/javac" "$javaSource")
  242 + fi
  243 + if [ -e "$javaClass" ]; then
  244 + log " - Running MavenWrapperDownloader.java ..."
  245 + ("$JAVA_HOME/bin/java" -cp .mvn/wrapper MavenWrapperDownloader "$wrapperUrl" "$wrapperJarPath") || rm -f "$wrapperJarPath"
  246 + fi
  247 + fi
  248 + fi
  249 +fi
  250 +##########################################################################################
  251 +# End of extension
  252 +##########################################################################################
  253 +
  254 +# If specified, validate the SHA-256 sum of the Maven wrapper jar file
  255 +wrapperSha256Sum=""
  256 +while IFS="=" read -r key value; do
  257 + case "$key" in (wrapperSha256Sum) wrapperSha256Sum=$value; break ;;
  258 + esac
  259 +done < "$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.properties"
  260 +if [ -n "$wrapperSha256Sum" ]; then
  261 + wrapperSha256Result=false
  262 + if command -v sha256sum > /dev/null; then
  263 + if echo "$wrapperSha256Sum $wrapperJarPath" | sha256sum -c > /dev/null 2>&1; then
  264 + wrapperSha256Result=true
  265 + fi
  266 + elif command -v shasum > /dev/null; then
  267 + if echo "$wrapperSha256Sum $wrapperJarPath" | shasum -a 256 -c > /dev/null 2>&1; then
  268 + wrapperSha256Result=true
  269 + fi
  270 + else
  271 + echo "Checksum validation was requested but neither 'sha256sum' or 'shasum' are available."
  272 + echo "Please install either command, or disable validation by removing 'wrapperSha256Sum' from your maven-wrapper.properties."
  273 + exit 1
  274 + fi
  275 + if [ $wrapperSha256Result = false ]; then
  276 + echo "Error: Failed to validate Maven wrapper SHA-256, your Maven wrapper might be compromised." >&2
  277 + echo "Investigate or delete $wrapperJarPath to attempt a clean download." >&2
  278 + echo "If you updated your Maven version, you need to update the specified wrapperSha256Sum property." >&2
  279 + exit 1
  280 + fi
  281 +fi
  282 +
  283 +MAVEN_OPTS="$(concat_lines "$MAVEN_PROJECTBASEDIR/.mvn/jvm.config") $MAVEN_OPTS"
  284 +
  285 +# For Cygwin, switch paths to Windows format before running java
  286 +if $cygwin; then
  287 + [ -n "$JAVA_HOME" ] &&
  288 + JAVA_HOME=$(cygpath --path --windows "$JAVA_HOME")
  289 + [ -n "$CLASSPATH" ] &&
  290 + CLASSPATH=$(cygpath --path --windows "$CLASSPATH")
  291 + [ -n "$MAVEN_PROJECTBASEDIR" ] &&
  292 + MAVEN_PROJECTBASEDIR=$(cygpath --path --windows "$MAVEN_PROJECTBASEDIR")
  293 +fi
  294 +
  295 +# Provide a "standardized" way to retrieve the CLI args that will
  296 +# work with both Windows and non-Windows executions.
  297 +MAVEN_CMD_LINE_ARGS="$MAVEN_CONFIG $*"
  298 +export MAVEN_CMD_LINE_ARGS
  299 +
  300 +WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain
  301 +
  302 +# shellcheck disable=SC2086 # safe args
  303 +exec "$JAVACMD" \
  304 + $MAVEN_OPTS \
  305 + $MAVEN_DEBUG_OPTS \
  306 + -classpath "$MAVEN_PROJECTBASEDIR/.mvn/wrapper/maven-wrapper.jar" \
  307 + "-Dmaven.multiModuleProjectDirectory=${MAVEN_PROJECTBASEDIR}" \
  308 + ${WRAPPER_LAUNCHER} $MAVEN_CONFIG "$@"
... ...
mvnw.cmd 0 → 100644
  1 +++ a/mvnw.cmd
  1 +@REM ----------------------------------------------------------------------------
  2 +@REM Licensed to the Apache Software Foundation (ASF) under one
  3 +@REM or more contributor license agreements. See the NOTICE file
  4 +@REM distributed with this work for additional information
  5 +@REM regarding copyright ownership. The ASF licenses this file
  6 +@REM to you under the Apache License, Version 2.0 (the
  7 +@REM "License"); you may not use this file except in compliance
  8 +@REM with the License. You may obtain a copy of the License at
  9 +@REM
  10 +@REM https://www.apache.org/licenses/LICENSE-2.0
  11 +@REM
  12 +@REM Unless required by applicable law or agreed to in writing,
  13 +@REM software distributed under the License is distributed on an
  14 +@REM "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  15 +@REM KIND, either express or implied. See the License for the
  16 +@REM specific language governing permissions and limitations
  17 +@REM under the License.
  18 +@REM ----------------------------------------------------------------------------
  19 +
  20 +@REM ----------------------------------------------------------------------------
  21 +@REM Apache Maven Wrapper startup batch script, version 3.2.0
  22 +@REM
  23 +@REM Required ENV vars:
  24 +@REM JAVA_HOME - location of a JDK home dir
  25 +@REM
  26 +@REM Optional ENV vars
  27 +@REM MAVEN_BATCH_ECHO - set to 'on' to enable the echoing of the batch commands
  28 +@REM MAVEN_BATCH_PAUSE - set to 'on' to wait for a keystroke before ending
  29 +@REM MAVEN_OPTS - parameters passed to the Java VM when running Maven
  30 +@REM e.g. to debug Maven itself, use
  31 +@REM set MAVEN_OPTS=-Xdebug -Xrunjdwp:transport=dt_socket,server=y,suspend=y,address=8000
  32 +@REM MAVEN_SKIP_RC - flag to disable loading of mavenrc files
  33 +@REM ----------------------------------------------------------------------------
  34 +
  35 +@REM Begin all REM lines with '@' in case MAVEN_BATCH_ECHO is 'on'
  36 +@echo off
  37 +@REM set title of command window
  38 +title %0
  39 +@REM enable echoing by setting MAVEN_BATCH_ECHO to 'on'
  40 +@if "%MAVEN_BATCH_ECHO%" == "on" echo %MAVEN_BATCH_ECHO%
  41 +
  42 +@REM set %HOME% to equivalent of $HOME
  43 +if "%HOME%" == "" (set "HOME=%HOMEDRIVE%%HOMEPATH%")
  44 +
  45 +@REM Execute a user defined script before this one
  46 +if not "%MAVEN_SKIP_RC%" == "" goto skipRcPre
  47 +@REM check for pre script, once with legacy .bat ending and once with .cmd ending
  48 +if exist "%USERPROFILE%\mavenrc_pre.bat" call "%USERPROFILE%\mavenrc_pre.bat" %*
  49 +if exist "%USERPROFILE%\mavenrc_pre.cmd" call "%USERPROFILE%\mavenrc_pre.cmd" %*
  50 +:skipRcPre
  51 +
  52 +@setlocal
  53 +
  54 +set ERROR_CODE=0
  55 +
  56 +@REM To isolate internal variables from possible post scripts, we use another setlocal
  57 +@setlocal
  58 +
  59 +@REM ==== START VALIDATION ====
  60 +if not "%JAVA_HOME%" == "" goto OkJHome
  61 +
  62 +echo.
  63 +echo Error: JAVA_HOME not found in your environment. >&2
  64 +echo Please set the JAVA_HOME variable in your environment to match the >&2
  65 +echo location of your Java installation. >&2
  66 +echo.
  67 +goto error
  68 +
  69 +:OkJHome
  70 +if exist "%JAVA_HOME%\bin\java.exe" goto init
  71 +
  72 +echo.
  73 +echo Error: JAVA_HOME is set to an invalid directory. >&2
  74 +echo JAVA_HOME = "%JAVA_HOME%" >&2
  75 +echo Please set the JAVA_HOME variable in your environment to match the >&2
  76 +echo location of your Java installation. >&2
  77 +echo.
  78 +goto error
  79 +
  80 +@REM ==== END VALIDATION ====
  81 +
  82 +:init
  83 +
  84 +@REM Find the project base dir, i.e. the directory that contains the folder ".mvn".
  85 +@REM Fallback to current working directory if not found.
  86 +
  87 +set MAVEN_PROJECTBASEDIR=%MAVEN_BASEDIR%
  88 +IF NOT "%MAVEN_PROJECTBASEDIR%"=="" goto endDetectBaseDir
  89 +
  90 +set EXEC_DIR=%CD%
  91 +set WDIR=%EXEC_DIR%
  92 +:findBaseDir
  93 +IF EXIST "%WDIR%"\.mvn goto baseDirFound
  94 +cd ..
  95 +IF "%WDIR%"=="%CD%" goto baseDirNotFound
  96 +set WDIR=%CD%
  97 +goto findBaseDir
  98 +
  99 +:baseDirFound
  100 +set MAVEN_PROJECTBASEDIR=%WDIR%
  101 +cd "%EXEC_DIR%"
  102 +goto endDetectBaseDir
  103 +
  104 +:baseDirNotFound
  105 +set MAVEN_PROJECTBASEDIR=%EXEC_DIR%
  106 +cd "%EXEC_DIR%"
  107 +
  108 +:endDetectBaseDir
  109 +
  110 +IF NOT EXIST "%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config" goto endReadAdditionalConfig
  111 +
  112 +@setlocal EnableExtensions EnableDelayedExpansion
  113 +for /F "usebackq delims=" %%a in ("%MAVEN_PROJECTBASEDIR%\.mvn\jvm.config") do set JVM_CONFIG_MAVEN_PROPS=!JVM_CONFIG_MAVEN_PROPS! %%a
  114 +@endlocal & set JVM_CONFIG_MAVEN_PROPS=%JVM_CONFIG_MAVEN_PROPS%
  115 +
  116 +:endReadAdditionalConfig
  117 +
  118 +SET MAVEN_JAVA_EXE="%JAVA_HOME%\bin\java.exe"
  119 +set WRAPPER_JAR="%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.jar"
  120 +set WRAPPER_LAUNCHER=org.apache.maven.wrapper.MavenWrapperMain
  121 +
  122 +set WRAPPER_URL="https://repo.maven.apache.org/maven2/org/apache/maven/wrapper/maven-wrapper/3.2.0/maven-wrapper-3.2.0.jar"
  123 +
  124 +FOR /F "usebackq tokens=1,2 delims==" %%A IN ("%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.properties") DO (
  125 + IF "%%A"=="wrapperUrl" SET WRAPPER_URL=%%B
  126 +)
  127 +
  128 +@REM Extension to allow automatically downloading the maven-wrapper.jar from Maven-central
  129 +@REM This allows using the maven wrapper in projects that prohibit checking in binary data.
  130 +if exist %WRAPPER_JAR% (
  131 + if "%MVNW_VERBOSE%" == "true" (
  132 + echo Found %WRAPPER_JAR%
  133 + )
  134 +) else (
  135 + if not "%MVNW_REPOURL%" == "" (
  136 + SET WRAPPER_URL="%MVNW_REPOURL%/org/apache/maven/wrapper/maven-wrapper/3.2.0/maven-wrapper-3.2.0.jar"
  137 + )
  138 + if "%MVNW_VERBOSE%" == "true" (
  139 + echo Couldn't find %WRAPPER_JAR%, downloading it ...
  140 + echo Downloading from: %WRAPPER_URL%
  141 + )
  142 +
  143 + powershell -Command "&{"^
  144 + "$webclient = new-object System.Net.WebClient;"^
  145 + "if (-not ([string]::IsNullOrEmpty('%MVNW_USERNAME%') -and [string]::IsNullOrEmpty('%MVNW_PASSWORD%'))) {"^
  146 + "$webclient.Credentials = new-object System.Net.NetworkCredential('%MVNW_USERNAME%', '%MVNW_PASSWORD%');"^
  147 + "}"^
  148 + "[Net.ServicePointManager]::SecurityProtocol = [Net.SecurityProtocolType]::Tls12; $webclient.DownloadFile('%WRAPPER_URL%', '%WRAPPER_JAR%')"^
  149 + "}"
  150 + if "%MVNW_VERBOSE%" == "true" (
  151 + echo Finished downloading %WRAPPER_JAR%
  152 + )
  153 +)
  154 +@REM End of extension
  155 +
  156 +@REM If specified, validate the SHA-256 sum of the Maven wrapper jar file
  157 +SET WRAPPER_SHA_256_SUM=""
  158 +FOR /F "usebackq tokens=1,2 delims==" %%A IN ("%MAVEN_PROJECTBASEDIR%\.mvn\wrapper\maven-wrapper.properties") DO (
  159 + IF "%%A"=="wrapperSha256Sum" SET WRAPPER_SHA_256_SUM=%%B
  160 +)
  161 +IF NOT %WRAPPER_SHA_256_SUM%=="" (
  162 + powershell -Command "&{"^
  163 + "$hash = (Get-FileHash \"%WRAPPER_JAR%\" -Algorithm SHA256).Hash.ToLower();"^
  164 + "If('%WRAPPER_SHA_256_SUM%' -ne $hash){"^
  165 + " Write-Output 'Error: Failed to validate Maven wrapper SHA-256, your Maven wrapper might be compromised.';"^
  166 + " Write-Output 'Investigate or delete %WRAPPER_JAR% to attempt a clean download.';"^
  167 + " Write-Output 'If you updated your Maven version, you need to update the specified wrapperSha256Sum property.';"^
  168 + " exit 1;"^
  169 + "}"^
  170 + "}"
  171 + if ERRORLEVEL 1 goto error
  172 +)
  173 +
  174 +@REM Provide a "standardized" way to retrieve the CLI args that will
  175 +@REM work with both Windows and non-Windows executions.
  176 +set MAVEN_CMD_LINE_ARGS=%*
  177 +
  178 +%MAVEN_JAVA_EXE% ^
  179 + %JVM_CONFIG_MAVEN_PROPS% ^
  180 + %MAVEN_OPTS% ^
  181 + %MAVEN_DEBUG_OPTS% ^
  182 + -classpath %WRAPPER_JAR% ^
  183 + "-Dmaven.multiModuleProjectDirectory=%MAVEN_PROJECTBASEDIR%" ^
  184 + %WRAPPER_LAUNCHER% %MAVEN_CONFIG% %*
  185 +if ERRORLEVEL 1 goto error
  186 +goto end
  187 +
  188 +:error
  189 +set ERROR_CODE=1
  190 +
  191 +:end
  192 +@endlocal & set ERROR_CODE=%ERROR_CODE%
  193 +
  194 +if not "%MAVEN_SKIP_RC%"=="" goto skipRcPost
  195 +@REM check for post script, once with legacy .bat ending and once with .cmd ending
  196 +if exist "%USERPROFILE%\mavenrc_post.bat" call "%USERPROFILE%\mavenrc_post.bat"
  197 +if exist "%USERPROFILE%\mavenrc_post.cmd" call "%USERPROFILE%\mavenrc_post.cmd"
  198 +:skipRcPost
  199 +
  200 +@REM pause the script if MAVEN_BATCH_PAUSE is set to 'on'
  201 +if "%MAVEN_BATCH_PAUSE%"=="on" pause
  202 +
  203 +if "%MAVEN_TERMINATE_CMD%"=="on" exit %ERROR_CODE%
  204 +
  205 +cmd /C exit /B %ERROR_CODE%
... ...
pom.xml 0 → 100644
  1 +++ a/pom.xml
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  3 + xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd">
  4 + <modelVersion>4.0.0</modelVersion>
  5 + <parent>
  6 + <groupId>org.springframework.boot</groupId>
  7 + <artifactId>spring-boot-starter-parent</artifactId>
  8 + <version>3.2.2</version>
  9 + <relativePath/> <!-- lookup parent from repository -->
  10 + </parent>
  11 + <groupId>com.batch</groupId>
  12 + <artifactId>SpringBatch</artifactId>
  13 + <version>0.0.1-SNAPSHOT</version>
  14 + <name>spring_batch</name>
  15 + <description>Batch application</description>
  16 + <properties>
  17 + <java.version>17</java.version>
  18 + </properties>
  19 + <dependencies>
  20 + <dependency>
  21 + <groupId>org.springframework.boot</groupId>
  22 + <artifactId>spring-boot-starter-batch</artifactId>
  23 + </dependency>
  24 + <dependency>
  25 + <groupId>org.springframework.boot</groupId>
  26 + <artifactId>spring-boot-starter-web</artifactId>
  27 + </dependency>
  28 + <dependency>
  29 + <groupId>org.mybatis.spring.boot</groupId>
  30 + <artifactId>mybatis-spring-boot-starter</artifactId>
  31 + <version>3.0.3</version>
  32 + </dependency>
  33 +
  34 + <dependency>
  35 + <groupId>org.postgresql</groupId>
  36 + <artifactId>postgresql</artifactId>
  37 + <scope>runtime</scope>
  38 + </dependency>
  39 + <dependency>
  40 + <groupId>com.oracle.database.jdbc</groupId>
  41 + <artifactId>ojdbc11</artifactId>
  42 + <scope>runtime</scope>
  43 + </dependency>
  44 + <dependency>
  45 + <groupId>org.projectlombok</groupId>
  46 + <artifactId>lombok</artifactId>
  47 + <optional>true</optional>
  48 + </dependency>
  49 + <dependency>
  50 + <groupId>org.springframework.boot</groupId>
  51 + <artifactId>spring-boot-starter-test</artifactId>
  52 + <scope>test</scope>
  53 + </dependency>
  54 + <dependency>
  55 + <groupId>org.mybatis.spring.boot</groupId>
  56 + <artifactId>mybatis-spring-boot-starter-test</artifactId>
  57 + <version>3.0.3</version>
  58 + <scope>test</scope>
  59 + </dependency>
  60 + <dependency>
  61 + <groupId>org.springframework.batch</groupId>
  62 + <artifactId>spring-batch-test</artifactId>
  63 + <scope>test</scope>
  64 + </dependency>
  65 + <dependency>
  66 + <groupId>org.springframework.boot</groupId>
  67 + <artifactId>spring-boot-devtools</artifactId>
  68 + </dependency>
  69 + <!-- https://mvnrepository.com/artifact/com.github.gavlyukovskiy/p6spy-spring-boot-starter -->
  70 + <dependency>
  71 + <groupId>com.github.gavlyukovskiy</groupId>
  72 + <artifactId>p6spy-spring-boot-starter</artifactId>
  73 + <version>1.9.1</version>
  74 + </dependency>
  75 + <!-- https://mvnrepository.com/artifact/com.google.code.gson/gson -->
  76 + <dependency>
  77 + <groupId>com.google.code.gson</groupId>
  78 + <artifactId>gson</artifactId>
  79 + <version>2.10.1</version>
  80 + </dependency>
  81 + <!-- https://mvnrepository.com/artifact/org.springframework.batch/spring-batch-integration -->
  82 + <dependency>
  83 + <groupId>org.springframework.batch</groupId>
  84 + <artifactId>spring-batch-integration</artifactId>
  85 + <version>5.1.0</version>
  86 + </dependency>
  87 +
  88 + <!-- https://mvnrepository.com/artifact/org.zeroturnaround/zt-exec -->
  89 + <dependency>
  90 + <groupId>org.zeroturnaround</groupId>
  91 + <artifactId>zt-exec</artifactId>
  92 + <version>1.12</version>
  93 + </dependency>
  94 +
  95 + <!-- https://mvnrepository.com/artifact/org.springdoc/springdoc-openapi-starter-webmvc-ui -->
  96 + <dependency>
  97 + <groupId>org.springdoc</groupId>
  98 + <artifactId>springdoc-openapi-starter-webmvc-ui</artifactId>
  99 + <version>2.3.0</version>
  100 + </dependency>
  101 +
  102 +
  103 +
  104 + <!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-data-jpa -->
  105 + <dependency>
  106 + <groupId>org.springframework.boot</groupId>
  107 + <artifactId>spring-boot-starter-data-jpa</artifactId>
  108 + <version>3.2.3</version>
  109 + </dependency>
  110 + <!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-security -->
  111 + <dependency>
  112 + <groupId>org.springframework.boot</groupId>
  113 + <artifactId>spring-boot-starter-security</artifactId>
  114 + <version>3.2.3</version>
  115 + </dependency>
  116 + <!-- https://mvnrepository.com/artifact/org.springframework.boot/spring-boot-starter-validation -->
  117 + <dependency>
  118 + <groupId>org.springframework.boot</groupId>
  119 + <artifactId>spring-boot-starter-validation</artifactId>
  120 + <version>3.2.3</version>
  121 + </dependency>
  122 + <!-- https://mvnrepository.com/artifact/io.jsonwebtoken/jjwt-api -->
  123 + <dependency>
  124 + <groupId>io.jsonwebtoken</groupId>
  125 + <artifactId>jjwt-api</artifactId>
  126 + <version>0.12.5</version>
  127 + </dependency>
  128 + <!-- https://mvnrepository.com/artifact/io.jsonwebtoken/jjwt-impl -->
  129 + <dependency>
  130 + <groupId>io.jsonwebtoken</groupId>
  131 + <artifactId>jjwt-impl</artifactId>
  132 + <version>0.12.5</version>
  133 + <scope>runtime</scope>
  134 + </dependency>
  135 + <!-- https://mvnrepository.com/artifact/io.jsonwebtoken/jjwt-jackson -->
  136 + <dependency>
  137 + <groupId>io.jsonwebtoken</groupId>
  138 + <artifactId>jjwt-jackson</artifactId>
  139 + <version>0.12.5</version>
  140 + <scope>runtime</scope>
  141 + </dependency>
  142 + <!-- https://mvnrepository.com/artifact/org.springframework.security/spring-security-test -->
  143 + <dependency>
  144 + <groupId>org.springframework.security</groupId>
  145 + <artifactId>spring-security-test</artifactId>
  146 + <version>6.2.2</version>
  147 + <scope>test</scope>
  148 + </dependency>
  149 + <!-- https://mvnrepository.com/artifact/org.mybatis.spring.boot/mybatis-spring-boot-starter-test -->
  150 + <dependency>
  151 + <groupId>org.mybatis.spring.boot</groupId>
  152 + <artifactId>mybatis-spring-boot-starter-test</artifactId>
  153 + <version>3.0.3</version>
  154 + <scope>test</scope>
  155 + </dependency>
  156 +
  157 +
  158 + </dependencies>
  159 +
  160 + <build>
  161 + <plugins>
  162 + <plugin>
  163 + <groupId>org.springframework.boot</groupId>
  164 + <artifactId>spring-boot-maven-plugin</artifactId>
  165 + <configuration>
  166 + <excludes>
  167 + <exclude>
  168 + <groupId>org.projectlombok</groupId>
  169 + <artifactId>lombok</artifactId>
  170 + </exclude>
  171 + </excludes>
  172 + </configuration>
  173 + </plugin>
  174 +
  175 + </plugins>
  176 + </build>
  177 +
  178 +</project>
... ...
src/main/java/daeucna/MatchingAiApplication.java 0 → 100644
  1 +++ a/src/main/java/daeucna/MatchingAiApplication.java
  1 +package daeucna;
  2 +
  3 +import org.springframework.boot.SpringApplication;
  4 +import org.springframework.boot.autoconfigure.SpringBootApplication;
  5 +import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
  6 +import org.springframework.scheduling.annotation.EnableAsync;
  7 +
  8 +@EnableAsync
  9 +@SpringBootApplication(exclude = {DataSourceAutoConfiguration.class})
  10 +public class MatchingAiApplication {
  11 +
  12 + public static void main(String[] args) {
  13 + SpringApplication.run(MatchingAiApplication.class, args);
  14 +
  15 + }
  16 +
  17 +}
... ...
src/main/java/daeucna/batch/controller/JobController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/batch/controller/JobController.java
  1 +package daeucna.batch.controller;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.List;
  5 +import java.util.Map;
  6 +
  7 +import org.springframework.beans.factory.annotation.Autowired;
  8 +import org.springframework.web.bind.annotation.GetMapping;
  9 +import org.springframework.web.bind.annotation.PostMapping;
  10 +import org.springframework.web.bind.annotation.RequestBody;
  11 +import org.springframework.web.bind.annotation.RequestMapping;
  12 +import org.springframework.web.bind.annotation.RestController;
  13 +
  14 +import com.google.gson.JsonObject;
  15 +
  16 +import daeucna.batch.service.JobService;
  17 +import daeucna.batch.util.FileUtil;
  18 +import daeucna.config.batch.MatchingSetup;
  19 +import daeucna.config.batch.MatchingSetup.Matching;
  20 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  21 +import lombok.extern.slf4j.Slf4j;
  22 +
  23 +@RestController
  24 +@RequestMapping("/api/job")
  25 +@Slf4j
  26 +public class JobController {
  27 +
  28 + @Autowired
  29 + private JobService jobService;
  30 + @Autowired
  31 + private MatchingInnerDelingMapper matchingInnerDelingMapper;
  32 +
  33 +
  34 + @PostMapping("/create")
  35 + public String createJob( @RequestBody Map<String, String> params) throws Exception {
  36 +
  37 + /*
  38 + * {
  39 + * "sysSe": "LS_ALL",
  40 + * "accnutYm": "202306",
  41 + * }
  42 + */
  43 + log.debug("Start Create Job");
  44 + jobService.createData(params);
  45 + log.debug("End Create Job");
  46 +
  47 +
  48 + return "신규 작업데이타를 생성합니다. 작업이 끝난후 작업결과는 별도로 확인 바랍니다.";
  49 + }
  50 +
  51 +
  52 + @PostMapping("/matching")
  53 + public String matchingJob( @RequestBody Map<String, String> params) throws Exception {
  54 +
  55 + /*
  56 + * {
  57 + * "sysSe": "LS_ALL",
  58 + * "accnutYm": "202306",
  59 + * }
  60 + */
  61 + log.debug("Start Matching Job");
  62 + jobService.matchingJob(params);
  63 + log.debug("End Matching Job");
  64 +
  65 +
  66 + return "매칭작업을 시작합니다. 작업이 끝난후 작업결과는 별도로 확인 바랍니다.";
  67 + }
  68 +
  69 + @PostMapping("/extramatching")
  70 + public String extraMatchingJob( @RequestBody Map<String, String> params) throws Exception {
  71 +
  72 + /*
  73 + * {
  74 + * "sysSe": "LS_ALL",
  75 + * "accnutYm": "202306",
  76 + * }
  77 + */
  78 + log.debug("Start Extra Matching Job");
  79 + List<Map> retData = matchingInnerDelingMapper.getCustomItemReadData(params);
  80 +// List<Map> retData = new ArrayList<Map>();
  81 +// Map m = new HashMap();
  82 +// m.put("sys_se", "LS_ALL");
  83 +// m.put("accnut_ym", "202311");
  84 +// m.put("cpr_code", "A15300");
  85 +// m.put("partn_cpr", "A01100");
  86 +// retData.add(m);
  87 + for(Map curMap : retData) {
  88 + jobService.extraJobSub(curMap);
  89 + }
  90 + log.debug("End Extra Matching Job");
  91 +
  92 +
  93 + return "Extra 매칭작업을 시작합니다. 작업이 끝난후 작업결과는 별도로 확인 바랍니다.";
  94 + }
  95 +
  96 +
  97 + @PostMapping("/aimatching")
  98 + public String aiMatchingJob( @RequestBody Map<String, String> params) throws Exception {
  99 +
  100 + /*
  101 + * {
  102 + * "sysSe": "LS_ALL",
  103 + * "accnutYm": "202306",
  104 + * }
  105 + */
  106 + log.debug("Start AI Matching Job");
  107 + List<Map> retData = matchingInnerDelingMapper.getAiReadData(params);
  108 + for(Map curMap : retData) {
  109 + jobService.aiJobSub(curMap);
  110 + }
  111 + log.debug("End AI Matching Job");
  112 +
  113 +
  114 + return "AI 매칭작업을 시작합니다. 작업이 끝난후 작업결과는 별도로 확인 바랍니다.";
  115 + }
  116 +
  117 + @PostMapping("/return")
  118 + public String returnJob( @RequestBody Map<String, String> params) throws Exception {
  119 +
  120 + /*
  121 + * {
  122 + * "sysSe": "LS_ALL",
  123 + * "accnutYm": "202306",
  124 + * }
  125 + */
  126 + log.debug("Start Return Job");
  127 + jobService.returnRwsultData(params);
  128 + log.debug("End Return Job");
  129 +
  130 +
  131 + return "매칭결과 반영을 시작합니다. 작업이 끝난후 작업결과는 별도로 확인 바랍니다.";
  132 + }
  133 +
  134 +
  135 + @GetMapping("/configJobStr")
  136 + public String configJobStr() throws Exception {
  137 +
  138 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  139 +
  140 + return sb.toString();
  141 + }
  142 +
  143 + @GetMapping("/configJobJsonObj")
  144 + public JsonObject configJobJsonObj() throws Exception {
  145 +
  146 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  147 + JsonObject jobj = FileUtil.strToJsonObj(sb.toString());
  148 +
  149 + return jobj;
  150 + }
  151 +
  152 + @GetMapping("/configJobObj")
  153 + public Object configJobObj() throws Exception {
  154 +
  155 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  156 + MatchingSetup matchingSetup = (MatchingSetup) FileUtil.strToObj(sb.toString(), MatchingSetup.class);
  157 +
  158 + return matchingSetup;
  159 + }
  160 +
  161 + @GetMapping("/config")
  162 + public Object config() throws Exception {
  163 + return configJobObj();
  164 + }
  165 +
  166 + @GetMapping("/config/jobList")
  167 + public Object configJobList() throws Exception {
  168 +
  169 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  170 + MatchingSetup matchingSetup = (MatchingSetup) FileUtil.strToObj(sb.toString(), MatchingSetup.class);
  171 +
  172 + List<String> lJobList = new ArrayList<String>();
  173 + for (Matching curMatching : matchingSetup.getMatchingSetup()) {
  174 + lJobList.add(curMatching.getType() + ':' + curMatching.getTypeName());
  175 + }
  176 +
  177 + return lJobList;
  178 + }
  179 +
  180 +
  181 +}
... ...
src/main/java/daeucna/batch/request/JobParamsRequest.java 0 → 100644
  1 +++ a/src/main/java/daeucna/batch/request/JobParamsRequest.java
  1 +package daeucna.batch.request;
  2 +
  3 +import lombok.Getter;
  4 +import lombok.Setter;
  5 +
  6 +@Setter
  7 +@Getter
  8 +public class JobParamsRequest {
  9 + private String paramKey;
  10 + private String paramValue;
  11 +}
0 12 \ No newline at end of file
... ...
src/main/java/daeucna/batch/service/JobService.java 0 → 100644
  1 +++ a/src/main/java/daeucna/batch/service/JobService.java
  1 +package daeucna.batch.service;
  2 +
  3 +import java.text.SimpleDateFormat;
  4 +import java.util.ArrayList;
  5 +import java.util.Arrays;
  6 +import java.util.Date;
  7 +import java.util.HashMap;
  8 +import java.util.List;
  9 +import java.util.Map;
  10 +import java.util.UUID;
  11 +
  12 +import org.springframework.batch.core.BatchStatus;
  13 +import org.springframework.batch.core.Job;
  14 +import org.springframework.batch.core.JobExecution;
  15 +import org.springframework.batch.core.JobParameters;
  16 +import org.springframework.batch.core.JobParametersBuilder;
  17 +import org.springframework.batch.core.JobParametersInvalidException;
  18 +import org.springframework.batch.core.launch.JobLauncher;
  19 +import org.springframework.batch.core.repository.JobExecutionAlreadyRunningException;
  20 +import org.springframework.batch.core.repository.JobInstanceAlreadyCompleteException;
  21 +import org.springframework.batch.core.repository.JobRestartException;
  22 +import org.springframework.beans.factory.annotation.Autowired;
  23 +import org.springframework.beans.factory.annotation.Value;
  24 +import org.springframework.context.ApplicationContext;
  25 +import org.springframework.scheduling.annotation.Async;
  26 +import org.springframework.stereotype.Service;
  27 +import org.zeroturnaround.exec.ProcessExecutor;
  28 +import org.zeroturnaround.exec.stream.LogOutputStream;
  29 +
  30 +import daeucna.batch.util.FileUtil;
  31 +import daeucna.config.batch.MatchingExtraProcessorAuto;
  32 +import daeucna.config.batch.MatchingSetup;
  33 +import daeucna.config.batch.MatchingSetup.Matching;
  34 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  35 +import daeucna.mapper.secondary.batch.OracleMapper;
  36 +import lombok.extern.slf4j.Slf4j;
  37 +
  38 +@Slf4j
  39 +@Service
  40 +public class JobService {
  41 +
  42 + @Value("${pytyon.path}")
  43 + String sPythonPrg;
  44 +
  45 + @Value("${python.ai.target}")
  46 + String sPythonAiTarget;
  47 +
  48 + @Autowired
  49 + private JobLauncher jobLauncher;
  50 +
  51 + @Autowired
  52 + private ApplicationContext context;
  53 +
  54 + @Autowired
  55 + private MatchingInnerDelingMapper matchingInnerDelingMapper;
  56 +
  57 + @Autowired
  58 + private OracleMapper oracleMapper;
  59 +
  60 +
  61 + @SuppressWarnings("rawtypes")
  62 + @Async("commAsync")
  63 + public void matchingJob( Map<String, String> params) throws Exception {
  64 +
  65 + long startTime = System.currentTimeMillis();
  66 + log.info("Job Started : " + startTime);
  67 + log.debug("params=" + params.toString());
  68 +
  69 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  70 + MatchingSetup matchingSetup = (MatchingSetup) FileUtil.strToObj(sb.toString(), MatchingSetup.class);
  71 +
  72 + String sJobTypeList = params.get("jobType").toUpperCase();
  73 + List<String> lJobType = Arrays.asList(sJobTypeList != null?sJobTypeList.split(","):new String[0]);
  74 +
  75 + //파라미터가 ALL일 경우 ALL 대신 등록된 모든 Type를 넣어준다.
  76 + if (lJobType.size() > 0 && lJobType.indexOf("ALL") != -1) {
  77 + lJobType = new ArrayList();
  78 + for (Matching matching : matchingSetup.getMatchingSetup()) {
  79 + if (matching.getActive()) {
  80 + lJobType.add(matching.getType());
  81 + } else {
  82 + log.info("JobType(" + matching.getType() + ") is Disabled");
  83 + }
  84 + }
  85 + }
  86 +
  87 +
  88 + for (String sJobType : lJobType) {
  89 + log.info("Current running job type: " + sJobType);
  90 + JobExecution jobExe = invokeJob("matchingInnerDelng", sJobType, params);
  91 + if (!jobExe.getStatus().equals(BatchStatus.COMPLETED)) {
  92 + throw new Exception("Job execution error : Batchstatus(" + jobExe.getStatus() + "), ExitStatus(" + jobExe.getExitStatus() + ")" );
  93 + }
  94 + }
  95 +
  96 + long endTime = System.currentTimeMillis();
  97 + log.info("Job Type : " + lJobType.toString());
  98 + log.info("Job Ended: " + endTime);
  99 + log.info("Running Time : " + (endTime - startTime) + "ms");
  100 +
  101 + }
  102 +
  103 +
  104 + @SuppressWarnings("rawtypes")
  105 + @Async("aiAsync")
  106 + public void extraJobSub(Map paramRec) throws Exception {
  107 +
  108 + long startTime = System.currentTimeMillis();
  109 + log.info("Job Started : " + startTime);
  110 + log.debug("params=" + paramRec.toString());
  111 +
  112 + MatchingExtraProcessorAuto matchingExtraProcessorAuto = new MatchingExtraProcessorAuto(matchingInnerDelingMapper);
  113 +
  114 + //2건씩 합산 매칭일 경우 최대 20000건 까지
  115 + for (int i=0; i<20000;i=i+1000) {
  116 + matchingExtraProcessorAuto.process(paramRec, 1, 2, 0, i);
  117 + }
  118 + for (int i=0; i<20000;i=i+1000) {
  119 + matchingExtraProcessorAuto.process(paramRec, 2, 1, i, 0);
  120 + }
  121 + for (int i=0; i<20000;i=i+1000) {
  122 + matchingExtraProcessorAuto.process(paramRec, 2, 2, i, i);
  123 + }
  124 +
  125 + //3건씩 매칭일 경우 최대 5000건 까지
  126 + for (int i=0; i<2000;i=i+100) {
  127 + matchingExtraProcessorAuto.process(paramRec, 1, 3, 0, i);
  128 + }
  129 + for (int i=0; i<2000;i=i+100) {
  130 + matchingExtraProcessorAuto.process(paramRec, 3, 1, i, 0);
  131 + }
  132 +
  133 + long endTime = System.currentTimeMillis();
  134 + log.info("Job Ended: " + endTime);
  135 + log.info("Running Time : " + (endTime - startTime) + "ms");
  136 +
  137 + }
  138 +
  139 + @SuppressWarnings("rawtypes")
  140 + @Async("aiAsync")
  141 + public void aiJobSub(Map paramRec) throws Exception {
  142 +
  143 +
  144 + //Job Create Log
  145 + UUID uuid = UUID.randomUUID();
  146 + HashMap<String, String> mt = new HashMap<String, String>();
  147 + SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-hh-mm-ss");
  148 + String sDate = dateFormat.format(new Date()) + ":" + uuid.toString();
  149 +
  150 + Map<String, Object> paramLog = new HashMap<String, Object>();
  151 + paramLog.put("user_job_id", sDate);
  152 + paramLog.put("user_job_name", "AI매칭(" + paramRec.toString() + ")");
  153 + matchingInnerDelingMapper.createUserJob(paramLog);
  154 +
  155 +
  156 + long startTime = System.currentTimeMillis();
  157 + log.info("Job Started : " + startTime);
  158 + log.debug("params=" + paramRec.toString());
  159 +
  160 + String sSysSe = (String) paramRec.get("sys_se");
  161 + String sAccnutYm = (String) paramRec.get("accnut_ym");
  162 + String sCprCode = (String) paramRec.get("cpr_code");
  163 + String sPartCpr = (String) paramRec.get("partn_cpr");
  164 + String sDelngCrncy = (String) paramRec.get("delng_crncy");
  165 +
  166 + log.debug("call python");
  167 + new ProcessExecutor()
  168 + .command(sPythonPrg, sPythonAiTarget, sSysSe, sAccnutYm, sCprCode, sPartCpr, sDelngCrncy)
  169 + .redirectOutput(new LogOutputStream() {
  170 + @Override
  171 + protected void processLine(String line) {
  172 + log.info(line);
  173 + }
  174 + })
  175 + .execute();
  176 +
  177 + long endTime = System.currentTimeMillis();
  178 + log.info("Job Ended: " + endTime);
  179 + log.info("Running Time : " + (endTime - startTime) + "ms");
  180 +
  181 +
  182 + //작업종료에 대한 로그 업데이트
  183 + paramLog.put("exit_code", "0");
  184 + paramLog.put("exit_message", "");
  185 + matchingInnerDelingMapper.finishUserJob(paramLog);
  186 +
  187 + }
  188 +
  189 +
  190 +
  191 + public JobExecution invokeJob(String jobName, String jobType, Map<String, String> params) throws JobInstanceAlreadyCompleteException, JobExecutionAlreadyRunningException, JobParametersInvalidException, JobRestartException {
  192 +
  193 + UUID uuid = UUID.randomUUID();
  194 + HashMap<String, String> mt = new HashMap<String, String>();
  195 + SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-hh-mm-ss");
  196 + final String date = dateFormat.format(new Date()) + ":" + uuid.toString();
  197 + JobParameters jobParameters = new JobParametersBuilder()
  198 + .addString("syncDate", date)
  199 + .addString("jobType", jobType)
  200 + .addString("sysSe", params.get("sysSe"))
  201 + .addString("accnutYm", params.get("accnutYm"))
  202 + .addString("searchCond", params.get("searchCond"))
  203 + .toJobParameters();
  204 +
  205 + var jobToStart = context.getBean(jobName, Job.class);
  206 + JobExecution jobExe = jobLauncher.run(jobToStart, jobParameters);
  207 +
  208 + return jobExe;
  209 + }
  210 +
  211 +
  212 +
  213 + @SuppressWarnings("rawtypes")
  214 + @Async("commAsync")
  215 + public void createData( Map<String, String> params) throws Exception {
  216 +
  217 + //Job Create Log
  218 + UUID uuid = UUID.randomUUID();
  219 + HashMap<String, String> mt = new HashMap<String, String>();
  220 + SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-hh-mm-ss");
  221 + String sDate = dateFormat.format(new Date()) + ":" + uuid.toString();
  222 +
  223 + Map<String, Object> paramLog = new HashMap<String, Object>();
  224 + paramLog.put("user_job_id", sDate);
  225 + paramLog.put("user_job_name", "작업데이타생성(" + params.toString() + ")");
  226 + matchingInnerDelingMapper.createUserJob(paramLog);
  227 +
  228 +
  229 + long startTime = System.currentTimeMillis();
  230 + log.info("Create Data Started : " + startTime);
  231 + log.debug("params=" + params.toString());
  232 +
  233 + //기존데이타 삭제
  234 + int iDeleted = matchingInnerDelingMapper.deleteOriginalData(params);
  235 + log.debug("Deleted OrgData : " + iDeleted + "건");
  236 +
  237 + //신규데이타 생성
  238 + //매칭키에 대한 정보 (sql로 조인하여 조회하기에는 너무 느리고 데이타 중복도 발생함)
  239 + List<Map> lMatchingInfo = oracleMapper.getMatchingInfo(params);
  240 + Map<String, Map> mMatchingInfo = new HashMap<String, Map>();
  241 + for (Map curMap : lMatchingInfo) {
  242 + String sKey = String.valueOf(curMap.get("SEQ"));
  243 + mMatchingInfo.put(sKey, curMap);
  244 + }
  245 +
  246 + List<Map> lOrgData = oracleMapper.getOriginalData(params);
  247 + int iInserted = 0;
  248 + int limit = 1000; //1000건씩 batch
  249 + List<Map> lInserted = new ArrayList<Map>();
  250 + for (Map curRec : lOrgData) {
  251 + String sKey = String.valueOf(curRec.get("SEQ"));
  252 + Map curMatchingInfo = mMatchingInfo.get(sKey);
  253 + if (curMatchingInfo != null) {
  254 + curRec.put("MATCHING_CAUSE", curMatchingInfo.get("MATCHING_CAUSE"));
  255 + curRec.put("MATCH_KEY", curMatchingInfo.get("MATCH_KEY"));
  256 + }
  257 + lInserted.add(curRec);
  258 + if (lInserted.size() == limit) {
  259 + matchingInnerDelingMapper.insertOriginalData(Map.of("itemList", lInserted));
  260 + iInserted = iInserted + lInserted.size();
  261 + lInserted.clear();
  262 + }
  263 + }
  264 + if (lInserted.size() > 0) {
  265 + matchingInnerDelingMapper.insertOriginalData(Map.of("itemList", lInserted));
  266 + iInserted = iInserted + lInserted.size();
  267 + }
  268 + log.info("Inserted OrgData : " + iInserted + "건");
  269 +
  270 + iDeleted = matchingInnerDelingMapper.deleteData(params);
  271 + log.debug("Deleted Work Data : " + iDeleted + "건");
  272 + iInserted = matchingInnerDelingMapper.insertDataFromOriginal(params);
  273 + log.info("Inserted Work Data : " + iInserted + "건");
  274 +
  275 + iDeleted = matchingInnerDelingMapper.deleteDataAi(params);
  276 + log.debug("Deleted Work AI Data : " + iDeleted + "건");
  277 + iInserted = matchingInnerDelingMapper.insertDataAiFromOriginal(params);
  278 + log.info("Inserted Work AI Data : " + iInserted + "건");
  279 +
  280 + long endTime = System.currentTimeMillis();
  281 + log.info("Create Data Ended : " + endTime);
  282 + log.info("Running Time : " + (endTime - startTime) + "ms");
  283 +
  284 + //작업종료에 대한 로그 업데이트
  285 + paramLog.put("exit_code", "0");
  286 + paramLog.put("exit_message", "");
  287 + matchingInnerDelingMapper.finishUserJob(paramLog);
  288 +
  289 + }
  290 +
  291 +
  292 +
  293 + @SuppressWarnings("rawtypes")
  294 + @Async("commAsync")
  295 + public void returnRwsultData( Map<String, String> params) throws Exception {
  296 +
  297 + //Job Create Log
  298 + UUID uuid = UUID.randomUUID();
  299 + HashMap<String, String> mt = new HashMap<String, String>();
  300 + SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-hh-mm-ss");
  301 + String sDate = dateFormat.format(new Date()) + ":" + uuid.toString();
  302 +
  303 + Map<String, Object> paramLog = new HashMap<String, Object>();
  304 + paramLog.put("user_job_id", sDate);
  305 + paramLog.put("user_job_name", "결과데이타리턴(" + params.toString() + ")");
  306 + matchingInnerDelingMapper.createUserJob(paramLog);
  307 +
  308 + long startTime = System.currentTimeMillis();
  309 + log.info("Update Data Started : " + startTime);
  310 + log.debug("params=" + params.toString());
  311 +
  312 + //기존데이타 삭제
  313 + int iUpdated = matchingInnerDelingMapper.updateNewMatchKey(params);
  314 + log.debug("Updated OrgData : " + iUpdated + "건");
  315 +
  316 + long endTime = System.currentTimeMillis();
  317 + log.info("Update Data Ended : " + endTime);
  318 + log.info("Running Time : " + (endTime - startTime) + "ms");
  319 +
  320 +
  321 + //작업종료에 대한 로그 업데이트
  322 + paramLog.put("exit_code", "0");
  323 + paramLog.put("exit_message", "");
  324 + matchingInnerDelingMapper.finishUserJob(paramLog);
  325 +
  326 + }
  327 +}
... ...
src/main/java/daeucna/batch/util/FileUtil.java 0 → 100644
  1 +++ a/src/main/java/daeucna/batch/util/FileUtil.java
  1 +package daeucna.batch.util;
  2 +
  3 +import java.io.BufferedReader;
  4 +import java.io.InputStreamReader;
  5 +
  6 +import org.springframework.core.io.ClassPathResource;
  7 +
  8 +import com.google.gson.Gson;
  9 +import com.google.gson.JsonObject;
  10 +import com.google.gson.JsonParser;
  11 +
  12 +public class FileUtil {
  13 +
  14 + public static StringBuffer readFileToString(String resourceName) {
  15 + StringBuffer sb = new StringBuffer();
  16 + try {
  17 + ClassPathResource resource = new ClassPathResource(resourceName);
  18 + BufferedReader br = new BufferedReader(new InputStreamReader(resource.getInputStream()));
  19 +
  20 + // br.readLine() 이 null 인지 검사할 때 한번 사용되므로 String 에 먼저 저장해둬야한다.
  21 + String s = "";
  22 + while((s = br.readLine()) != null){
  23 + sb.append(s);
  24 + }
  25 + } catch (Exception e) {
  26 + sb.append(e.getStackTrace());
  27 + }
  28 + return sb;
  29 + }
  30 +
  31 + public static JsonObject strToJsonObj(String jsonString) {
  32 + JsonObject jsonObject = JsonParser.parseString(jsonString).getAsJsonObject();
  33 + return jsonObject;
  34 + }
  35 +
  36 + public static Object strToObj(String jsonString, Class<?> anyClass) {
  37 + Gson gson = new Gson();
  38 + Object convertedObject = gson.fromJson(jsonString, anyClass);
  39 + return convertedObject;
  40 + }
  41 +
  42 + public static String objToStr(Object obj) {
  43 + Gson gson = new Gson();
  44 + String stringObject = gson.toJson(obj);
  45 + return stringObject;
  46 + }
  47 +
  48 +}
... ...
src/main/java/daeucna/batch/util/StatisticsUtil.java 0 → 100644
  1 +++ a/src/main/java/daeucna/batch/util/StatisticsUtil.java
  1 +package daeucna.batch.util;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.List;
  5 +import java.util.Map;
  6 +
  7 +import lombok.extern.slf4j.Slf4j;
  8 +
  9 +@Slf4j
  10 +public class StatisticsUtil {
  11 +
  12 +// public static void main(String[] args) {
  13 +//
  14 +// List<Map> arr = new ArrayList<Map>();
  15 +// arr.add(Map.of("col", 100));
  16 +// arr.add(Map.of("col", 200));
  17 +// arr.add(Map.of("col", 300));
  18 +// arr.add(Map.of("col", 400));
  19 +// arr.add(Map.of("col", 500));
  20 +//
  21 +// List<Map> result = new ArrayList<Map>();
  22 +// List<List<Map>> resultAll = new ArrayList<List<Map>>();
  23 +// reculsion(arr, result, 3, arr.size(), 2, resultAll);
  24 +//
  25 +// log.info("resultAll=" + resultAll.toString());
  26 +// }
  27 +
  28 + /**
  29 + * 조합 구하기
  30 + *
  31 + * @param arr : 기준 리스트
  32 + * @param result : 결과를 담아줄 리스트
  33 + * @param index : 반복문 시작 인덱스
  34 + * @param n : 전체 갯수
  35 + * @param r : 뽑을 갯수
  36 + */
  37 + public static void reculsion(List<Map> arr, List<Map> result, int index, int n, int r, List<List<Map>> resultAll) {
  38 +
  39 + if (r == 0) {
  40 +
  41 + log.debug("Reuslt=" + result.toString());
  42 + List<Map> lmConfirmList = new ArrayList<Map>();
  43 + lmConfirmList.addAll(result);
  44 + resultAll.add(lmConfirmList);
  45 +
  46 + return;
  47 + }
  48 +
  49 + for (int i = index; i < n; i++) {
  50 +
  51 + result.add(arr.get(i));
  52 + reculsion(arr, result, i + 1, n, r - 1, resultAll);
  53 + result.remove(result.size() - 1);
  54 + }
  55 +
  56 + }
  57 +
  58 +}
... ...
src/main/java/daeucna/config/batch/AsyncConfig.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/AsyncConfig.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.util.concurrent.Executor;
  4 +
  5 +import org.springframework.context.annotation.Bean;
  6 +import org.springframework.context.annotation.Configuration;
  7 +import org.springframework.scheduling.annotation.EnableAsync;
  8 +import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
  9 +
  10 +@Configuration
  11 +@EnableAsync
  12 +public class AsyncConfig {
  13 +
  14 + @Bean(name = "commAsync")
  15 + public Executor commAsyncExecutor() {
  16 + ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
  17 + executor.setCorePoolSize(5);
  18 + executor.setMaxPoolSize(50);
  19 + executor.setKeepAliveSeconds(30);
  20 + executor.setAllowCoreThreadTimeOut(true);
  21 + executor.setWaitForTasksToCompleteOnShutdown(true);
  22 + executor.setThreadNamePrefix("commAsync-processor-");
  23 + executor.initialize();
  24 +
  25 + return executor;
  26 + }
  27 +
  28 + @Bean(name = "aiAsync")
  29 + public Executor aiAsyncExecutor() {
  30 + ThreadPoolTaskExecutor executor = new ThreadPoolTaskExecutor();
  31 + executor.setCorePoolSize(50);
  32 + executor.setMaxPoolSize(100);
  33 + executor.setQueueCapacity(1000);
  34 + executor.setKeepAliveSeconds(30);
  35 + executor.setAllowCoreThreadTimeOut(true);
  36 + executor.setWaitForTasksToCompleteOnShutdown(true);
  37 + executor.setThreadNamePrefix("aiAsync-processor-");
  38 + executor.initialize();
  39 +
  40 + return executor;
  41 + }
  42 +}
0 43 \ No newline at end of file
... ...
src/main/java/daeucna/config/batch/BatchMatchingConfig.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/BatchMatchingConfig.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.List;
  5 +import java.util.Map;
  6 +
  7 +import org.springframework.batch.core.Job;
  8 +import org.springframework.batch.core.Step;
  9 +import org.springframework.batch.core.configuration.annotation.JobScope;
  10 +import org.springframework.batch.core.job.builder.JobBuilder;
  11 +import org.springframework.batch.core.launch.support.RunIdIncrementer;
  12 +import org.springframework.batch.core.repository.JobRepository;
  13 +import org.springframework.batch.core.step.builder.StepBuilder;
  14 +import org.springframework.batch.item.ItemProcessor;
  15 +import org.springframework.batch.item.ItemReader;
  16 +import org.springframework.batch.item.ItemWriter;
  17 +import org.springframework.batch.item.adapter.ItemWriterAdapter;
  18 +import org.springframework.batch.item.support.CompositeItemProcessor;
  19 +import org.springframework.batch.item.support.ListItemReader;
  20 +import org.springframework.beans.factory.annotation.Autowired;
  21 +import org.springframework.context.annotation.Bean;
  22 +import org.springframework.context.annotation.Configuration;
  23 +import org.springframework.transaction.PlatformTransactionManager;
  24 +
  25 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  26 +import lombok.extern.slf4j.Slf4j;
  27 +
  28 +@Configuration
  29 +@Slf4j
  30 +public class BatchMatchingConfig {
  31 +
  32 + final JobRepository jobRepository;
  33 + final PlatformTransactionManager batchTransactionManager;
  34 + private static final int BATCH_SIZE = 50;
  35 +
  36 + @Autowired
  37 + MatchingInnerDelingMapper matchingInnerDelingMapper;
  38 + @Autowired
  39 + MatchingItemReader customItemReader;
  40 + @Autowired
  41 + MatchingItemWriter<Map<String, Object>> matchingItemWriter;
  42 +
  43 + public BatchMatchingConfig(JobRepository jobRepository, PlatformTransactionManager batchTransactionManager) {
  44 + this.jobRepository = jobRepository;
  45 + this.batchTransactionManager = batchTransactionManager;
  46 + }
  47 +
  48 + /**
  49 + * Job which contains multiple steps
  50 + */
  51 + @Bean
  52 + public Job matchingInnerDelng() {
  53 + return new JobBuilder("자료매칭 job", jobRepository)
  54 + .incrementer(new RunIdIncrementer())
  55 + .start(chunkStep())
  56 + .build();
  57 + }
  58 +
  59 + @SuppressWarnings({ "unchecked", "rawtypes" })
  60 + @Bean
  61 + @JobScope
  62 + public Step chunkStep() {
  63 + log.debug("chunkStep");
  64 + return new StepBuilder("자료매칭 step", jobRepository)
  65 + .<Map, Map>chunk(BATCH_SIZE, batchTransactionManager)
  66 + .reader(reader())
  67 + .processor(compositeProcessor())
  68 + .writer(writer())
  69 + .build();
  70 + }
  71 +
  72 + @SuppressWarnings({ "rawtypes", "unchecked" })
  73 + @Bean
  74 + public CompositeItemProcessor compositeProcessor() {
  75 + log.debug("CompositeItemProcessor");
  76 +
  77 + List<ItemProcessor> delegates = new ArrayList<>(2);
  78 + MatchingItemProcessorAuto customItemProcessorAuto = new MatchingItemProcessorAuto();
  79 + customItemProcessorAuto.setMapper(matchingInnerDelingMapper);
  80 + delegates.add(customItemProcessorAuto);
  81 +
  82 + CompositeItemProcessor processor = new CompositeItemProcessor();
  83 +
  84 + processor.setDelegates(delegates);
  85 +
  86 + return processor;
  87 + }
  88 +
  89 + @Bean
  90 + @JobScope
  91 + public ItemReader<Map> reader() {
  92 +
  93 + log.debug("run ItemReader");
  94 +
  95 + List<Map> lmData = customItemReader.customRead();
  96 + return new ListItemReader<>(lmData);
  97 + }
  98 +
  99 + @Bean
  100 + public ItemWriter<Map> writer() {
  101 +
  102 + ItemWriterAdapter<Map> writer = new ItemWriterAdapter<>();
  103 + writer.setTargetObject(matchingItemWriter); // 대상 클래스
  104 + writer.setTargetMethod("customWrite"); // 대상 메서드
  105 + return writer;
  106 + }
  107 +
  108 +
  109 +}
0 110 \ No newline at end of file
... ...
src/main/java/daeucna/config/batch/MatchingExtraProcessorAuto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/MatchingExtraProcessorAuto.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.math.BigDecimal;
  4 +import java.text.SimpleDateFormat;
  5 +import java.util.ArrayList;
  6 +import java.util.Date;
  7 +import java.util.HashMap;
  8 +import java.util.List;
  9 +import java.util.Map;
  10 +import java.util.UUID;
  11 +
  12 +import daeucna.batch.util.StatisticsUtil;
  13 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  14 +import lombok.RequiredArgsConstructor;
  15 +import lombok.extern.slf4j.Slf4j;
  16 +
  17 +@Slf4j
  18 +@RequiredArgsConstructor
  19 +public class MatchingExtraProcessorAuto {
  20 +
  21 + private final MatchingInnerDelingMapper matchingInnerDelingMapper;
  22 +
  23 + @SuppressWarnings("unchecked")
  24 + public void process(Map paramRec, int iCmbnOwnCnt, int iCmbnTranCnt, int iStartOwn, int iStartTran) throws Exception {
  25 +
  26 + //Job Create Log
  27 + UUID uuid = UUID.randomUUID();
  28 + HashMap<String, String> mt = new HashMap<String, String>();
  29 + SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd-hh-mm-ss");
  30 + String sDate = dateFormat.format(new Date()) + ":" + uuid.toString();
  31 +
  32 + Map<String, Object> paramLog = new HashMap<String, Object>();
  33 + paramLog.put("user_job_id", sDate);
  34 + paramLog.put("user_job_name", "자동조합매칭(" + paramRec.toString() + ",[" + iCmbnOwnCnt + "," + iStartOwn + "],[" + iCmbnTranCnt + "," + iStartTran + "])");
  35 + matchingInnerDelingMapper.createUserJob(paramLog);
  36 +
  37 +
  38 + int iUpdated = 0;
  39 +
  40 + String sSysSe = (String) paramRec.get("sys_se");
  41 + String sAccnutYm = (String) paramRec.get("accnut_ym");
  42 + String sCprCode = (String) paramRec.get("cpr_code");
  43 + String sPartCpr = (String) paramRec.get("partn_cpr");
  44 +
  45 + //작업시작
  46 + Map<String, Object> mParam = new HashMap<String, Object>();
  47 + mParam.put("sysSe", sSysSe);
  48 + mParam.put("accnutYm", sAccnutYm);
  49 +
  50 + //----------------------------------------------------------------------------
  51 + //자기법인 데이타 가져오기
  52 + mParam.put("cprCode", sCprCode);
  53 + mParam.put("partnCpr", sPartCpr);
  54 + List<Map> lMatchingDataOne = matchingInnerDelingMapper.getMatchingExtraDataOne(mParam);
  55 +
  56 + //상대법인 데이타 가져오기
  57 + mParam.put("cprCode", sPartCpr);
  58 + mParam.put("partnCpr", sCprCode);
  59 + List<Map> lMatchingDataTwo = matchingInnerDelingMapper.getMatchingExtraDataTwo(mParam);
  60 +
  61 + //Combination 데이타 만들기
  62 + List<Map> compResult = new ArrayList<Map>();
  63 + List<List<Map>> llMatchingDataOne = new ArrayList<List<Map>>();
  64 + List<List<Map>> llMatchingDataTwo = new ArrayList<List<Map>>();
  65 +
  66 + int iEndOwn = lMatchingDataOne.size();
  67 + if (iCmbnOwnCnt == 2) {
  68 + iEndOwn = iStartOwn + 1000;
  69 + if (iEndOwn > lMatchingDataOne.size()) iEndOwn = lMatchingDataOne.size();
  70 + }
  71 + if (iCmbnOwnCnt > 2) {
  72 + iEndOwn = iStartOwn + 100;
  73 + if (iEndOwn > lMatchingDataOne.size()) iEndOwn = lMatchingDataOne.size();
  74 + }
  75 + int iEndTran = lMatchingDataTwo.size();
  76 + if (iCmbnTranCnt == 2) {
  77 + iEndTran = iStartTran + 1000;
  78 + if (iEndTran > lMatchingDataTwo.size()) iEndTran = lMatchingDataTwo.size();
  79 + }
  80 + if (iCmbnTranCnt > 2) {
  81 + iEndTran = iStartTran + 100;
  82 + if (iEndTran > lMatchingDataTwo.size()) iEndTran = lMatchingDataTwo.size();
  83 + }
  84 +
  85 + StatisticsUtil.reculsion(lMatchingDataOne, compResult, iStartOwn, iEndOwn, iCmbnOwnCnt, llMatchingDataOne);
  86 + StatisticsUtil.reculsion(lMatchingDataTwo, compResult, iStartTran, iEndTran, iCmbnTranCnt, llMatchingDataTwo);
  87 +
  88 + //----------------------------------------------------------------------------
  89 + //자기법인 데이타를 맵으로 처리한다.
  90 + Map<BigDecimal, List<List<Map>>> mMatchingDataOne = new HashMap<BigDecimal, List<List<Map>>>();
  91 + for (List<Map> curlMap : llMatchingDataOne) {
  92 + BigDecimal bdKey = BigDecimal.ZERO;
  93 + for(Map curMap : curlMap) {
  94 + bdKey = bdKey.add((BigDecimal) curMap.get("delng_amt"));
  95 + }
  96 + List<List<Map>> curllMap = new ArrayList<List<Map>>();
  97 + if (mMatchingDataOne.containsKey(bdKey)) curllMap = mMatchingDataOne.get(bdKey);
  98 + curllMap.add(curlMap);
  99 + mMatchingDataOne.put(bdKey, curllMap);
  100 + }
  101 +
  102 + //상대법인 데이타를 맵으로 처리한다.
  103 + Map<BigDecimal, List<List<Map>>> mMatchingDataTwo = new HashMap<BigDecimal, List<List<Map>>>();
  104 + for (List<Map> curlMap : llMatchingDataTwo) {
  105 + BigDecimal bdKey = BigDecimal.ZERO;
  106 + for(Map curMap : curlMap) {
  107 + bdKey = bdKey.add((BigDecimal) curMap.get("delng_amt"));
  108 + }
  109 + List<List<Map>> curllMap = new ArrayList<List<Map>>();
  110 + if (mMatchingDataTwo.containsKey(bdKey)) curllMap = mMatchingDataTwo.get(bdKey);
  111 + curllMap.add(curlMap);
  112 + mMatchingDataTwo.put(bdKey, curllMap);
  113 + }
  114 +
  115 + //여기서 매칭 비교
  116 + //비교 lMatchingDataOne vs mMatchingDataTwo
  117 + List<Map> lMatchingResultUpdate = new ArrayList<Map>(); //업데이트할 대상
  118 +
  119 + int mtchNumber = 0;
  120 + String mtchSys = "AUTO";
  121 + String mtchType = "EX_" + iCmbnOwnCnt + "_" + iCmbnTranCnt;
  122 + String mtchTypeName = "자기(" + iCmbnOwnCnt + "건Sum), 상대(" + iCmbnTranCnt + "건Sum), 비교(금액)";
  123 + for (BigDecimal curKey : mMatchingDataOne.keySet()) {
  124 + if (mMatchingDataTwo.containsKey(curKey)) {
  125 + List<List<Map>> llMapOne = mMatchingDataOne.get(curKey);
  126 + List<List<Map>> llMapTwo = mMatchingDataTwo.get(curKey);
  127 +
  128 + //위와 관련된 동일 레코드가 있는 리스트 삭제
  129 + for (int i=llMapOne.size()-1; i>=0;i--) {
  130 + List<Map> curlMap = llMapOne.get(i);
  131 + for (Map curMap : lMatchingResultUpdate) {
  132 + int curIdx = curlMap.indexOf(curMap);
  133 + if (curIdx != -1) {
  134 + llMapOne.remove(i);
  135 + break;
  136 + }
  137 + }
  138 + }
  139 + for (int i=llMapTwo.size()-1; i>=0;i--) {
  140 + List<Map> curlMap = llMapTwo.get(i);
  141 + for (Map curMap : lMatchingResultUpdate) {
  142 + int curIdx = curlMap.indexOf(curMap);
  143 + if (curIdx != -1) {
  144 + llMapTwo.remove(i);
  145 + break;
  146 + }
  147 + }
  148 + }
  149 +
  150 +
  151 + int iMin = Math.min(llMapOne.size(), llMapTwo.size());
  152 + if (iMin > 0) mtchNumber++;
  153 + while (iMin > 0) {
  154 + List<Map> curlMapOne = llMapOne.get(0);
  155 + for (Map curMap : curlMapOne) {
  156 + curMap.put("mtch_sys", mtchSys);
  157 + curMap.put("mtch_ty", mtchType);
  158 + curMap.put("mtch_ty_nm", mtchTypeName);
  159 + curMap.put("mtch_ky", mtchNumber);
  160 + lMatchingResultUpdate.add(curMap);
  161 + }
  162 + llMapOne.remove(0);
  163 +
  164 + List<Map> curlMapTwo = llMapTwo.get(0);
  165 + for (Map curMap : curlMapTwo) {
  166 + curMap.put("mtch_sys", mtchSys);
  167 + curMap.put("mtch_ty", mtchType);
  168 + curMap.put("mtch_ty_nm", mtchTypeName);
  169 + curMap.put("mtch_ky", mtchNumber);
  170 + lMatchingResultUpdate.add(curMap);
  171 + }
  172 + llMapTwo.remove(0);
  173 +
  174 + //위와 관련된 동일 레코드가 있는 리스트 삭제(추가 업데이트 목록)
  175 + for (int i=llMapOne.size()-1; i>=0;i--) {
  176 + List<Map> curlMap = llMapOne.get(i);
  177 + for (Map curMap : curlMapOne) {
  178 + int curIdx = curlMap.indexOf(curMap);
  179 + if (curIdx != -1) {
  180 + llMapOne.remove(i);
  181 + break;
  182 + }
  183 + }
  184 + }
  185 + for (int i=llMapTwo.size()-1; i>=0;i--) {
  186 + List<Map> curlMap = llMapTwo.get(i);
  187 + for (Map curMap : curlMapTwo) {
  188 + int curIdx = curlMap.indexOf(curMap);
  189 + if (curIdx != -1) {
  190 + llMapTwo.remove(i);
  191 + break;
  192 + }
  193 + }
  194 + }
  195 + iMin = Math.min(llMapOne.size(), llMapTwo.size());
  196 + }
  197 + }
  198 + }
  199 +
  200 + //----------------------------------------------------------------------------
  201 + //여기서 결과 업데이트
  202 + iUpdated = 0;
  203 + int limit = 1000; //1000건씩 batch
  204 + List<Map> lUpdated = new ArrayList<Map>();
  205 + for (Map curMap : lMatchingResultUpdate) {
  206 + lUpdated.add(curMap);
  207 + if (lUpdated.size() == limit) {
  208 + matchingInnerDelingMapper.setExtraResult(Map.of("itemList", lUpdated));
  209 + iUpdated = iUpdated + lUpdated.size();
  210 + lUpdated.clear();
  211 + }
  212 + }
  213 + if (lUpdated.size() > 0) {
  214 + matchingInnerDelingMapper.setExtraResult(Map.of("itemList", lUpdated));
  215 + iUpdated = iUpdated + lUpdated.size();
  216 + }
  217 + log.debug("Updated OrgData : " + iUpdated + "건");
  218 +
  219 + //작업종료에 대한 로그 업데이트
  220 + paramLog.put("exit_code", "0");
  221 + paramLog.put("exit_message", "");
  222 + matchingInnerDelingMapper.finishUserJob(paramLog);
  223 +
  224 + }
  225 +
  226 +}
0 227 \ No newline at end of file
... ...
src/main/java/daeucna/config/batch/MatchingItemProcessorAuto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/MatchingItemProcessorAuto.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.HashMap;
  5 +import java.util.List;
  6 +import java.util.Map;
  7 +
  8 +import org.springframework.batch.core.configuration.annotation.StepScope;
  9 +import org.springframework.batch.item.ItemProcessor;
  10 +import org.springframework.stereotype.Component;
  11 +
  12 +import daeucna.config.batch.MatchingSetup.Cond;
  13 +import daeucna.config.batch.MatchingSetup.Matching;
  14 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  15 +import lombok.RequiredArgsConstructor;
  16 +import lombok.extern.slf4j.Slf4j;
  17 +
  18 +@Slf4j
  19 +@StepScope
  20 +@Component
  21 +@RequiredArgsConstructor
  22 +public class MatchingItemProcessorAuto implements ItemProcessor<Map, Map> {
  23 +
  24 + MatchingInnerDelingMapper matchingInnerDelingMapper;
  25 +
  26 + public void setMapper(MatchingInnerDelingMapper matchingInnerDelingMapper) {
  27 + this.matchingInnerDelingMapper = matchingInnerDelingMapper;
  28 + }
  29 +
  30 + @SuppressWarnings("unchecked")
  31 + public Map process(Map item) throws Exception {
  32 + Map<String, Object> params = new HashMap<String, Object>((Map<String, String>) item.get("jobParameters"));
  33 + Matching matching = (Matching) item.get("matchingType");
  34 + Cond condOne = matching.getCondOne();
  35 + Cond condTwo = matching.getCondTwo();
  36 + List<String> lCompareField = matching.getCompareField();
  37 + String mtchType = matching.getType();
  38 + String mtchTypeName = matching.getTypeName();
  39 + int mtchNumber = 0;
  40 + int iUpdated = 0;
  41 +
  42 + log.debug("CustomItemProcessorA.params : " + params.toString());
  43 + log.debug("CustomItemProcessorA.item : " + item.get("cpr_code") + "," + item.get("partn_cpr"));
  44 +
  45 + //----------------------------------------------------------------------------
  46 + //자기법인 업데이트
  47 + params.put("cprCode", item.get("cpr_code"));
  48 + params.put("partnCpr", item.get("partn_cpr"));
  49 +
  50 + params.put("cond", condOne.getCond() ); //조건리스트
  51 + params.put("compareKey", matching.getCompareKey() );
  52 + params.put("makeCompareKey", "'" + mtchType + ":' || " + condOne.getMakeCompareKey() );
  53 +
  54 + iUpdated = matchingInnerDelingMapper.setDataMakeCompareKy(params);
  55 + log.debug("matchingInnerDelingMapper.setDataMakeCompareKy ; " + iUpdated);
  56 +
  57 + //상대법인업데이트
  58 + params.put("cprCode", item.get("partn_cpr"));
  59 + params.put("partnCpr", item.get("cpr_code"));
  60 +
  61 + params.put("cond", condTwo.getCond() ); //조건리스트
  62 + params.put("compareKey", matching.getCompareKey() );
  63 + params.put("makeCompareKey", "'" + mtchType + ":' || " + condTwo.getMakeCompareKey() );
  64 +
  65 + iUpdated = matchingInnerDelingMapper.setDataMakeCompareKy(params);
  66 + log.debug("matchingInnerDelingMapper.setDataMakeCompareKy ; " + iUpdated);
  67 +
  68 + //----------------------------------------------------------------------------
  69 + //자기법인 데이타 가져오기
  70 + params.put("cprCode", item.get("cpr_code"));
  71 + params.put("partnCpr", item.get("partn_cpr"));
  72 + params.put("amtField", matching.getAmtField());
  73 + params.put("cond", condOne.getCond() ); //조건리스트
  74 + List<Map> lMatchingDataOne = matchingInnerDelingMapper.getMatchingData(params);
  75 +
  76 + //상대법인 데이타 가져오기
  77 + params.put("cprCode", item.get("partn_cpr"));
  78 + params.put("partnCpr", item.get("cpr_code"));
  79 + params.put("amtField", matching.getAmtField());
  80 + params.put("cond", condTwo.getCond() ); //조건리스트
  81 + List<Map> lMatchingDataTwo = matchingInnerDelingMapper.getMatchingData(params);
  82 +
  83 + //----------------------------------------------------------------------------
  84 + //자기법인 데이타를 맵으로 처리한다.
  85 + Map<String, List<Map>> mMatchingDataOne = new HashMap<String, List<Map>>();
  86 + for (Map curMap : lMatchingDataOne) {
  87 + StringBuffer sbKey = new StringBuffer();
  88 + for (String curField : lCompareField) {
  89 + if (sbKey.length() > 0) sbKey.append(":");
  90 + sbKey.append(curMap.get(curField).toString());
  91 + }
  92 +
  93 + List<Map> curlMap = new ArrayList<Map>();
  94 + String sKey = sbKey.toString();
  95 + if (mMatchingDataOne.containsKey(sKey)) curlMap = mMatchingDataOne.get(sKey);
  96 + curlMap.add(curMap);
  97 + mMatchingDataOne.put(sKey, curlMap);
  98 + }
  99 +
  100 + //상대법인 데이타를 맵으로 처리한다.
  101 + Map<String, List<Map>> mMatchingDataTwo = new HashMap<String, List<Map>>();
  102 + for (Map curMap : lMatchingDataTwo) {
  103 + StringBuffer sbKey = new StringBuffer();
  104 + for (String curField : lCompareField) {
  105 + if (sbKey.length() > 0) sbKey.append(":");
  106 + sbKey.append(curMap.get(curField).toString());
  107 + }
  108 +
  109 + List<Map> curlMap = new ArrayList<Map>();
  110 + String sKey = sbKey.toString();
  111 + if (mMatchingDataTwo.containsKey(sKey)) curlMap = mMatchingDataTwo.get(sKey);
  112 + curlMap.add(curMap);
  113 + mMatchingDataTwo.put(sKey, curlMap);
  114 + }
  115 +
  116 + //여기서 매칭 비교
  117 + //비교 lMatchingDataOne vs mMatchingDataTwo
  118 + for (String curKey : mMatchingDataOne.keySet()) {
  119 + if (mMatchingDataTwo.containsKey(curKey)) {
  120 + List<Map> lMapOne = mMatchingDataOne.get(curKey);
  121 + List<Map> lMapTwo = mMatchingDataTwo.get(curKey);
  122 +
  123 + int iMin = Math.min(lMapOne.size(), lMapTwo.size());
  124 + if (iMin > 0) mtchNumber++;
  125 + for (int i=0; i<iMin; i++) {
  126 + lMapOne.get(i).put("mtchType", mtchType);
  127 + lMapOne.get(i).put("mtchTypeName", mtchTypeName);
  128 + lMapOne.get(i).put("mtchNumber", mtchNumber);
  129 +
  130 + lMapTwo.get(i).put("mtchType", mtchType);
  131 + lMapTwo.get(i).put("mtchTypeName", mtchTypeName);
  132 + lMapTwo.get(i).put("mtchNumber", mtchNumber);
  133 + }
  134 + }
  135 + }
  136 +
  137 + //----------------------------------------------------------------------------
  138 + //여기서 결과 업데이트
  139 + List<Map> lMatchingResultUpdate = new ArrayList<Map>(); //업데이트할 대상
  140 + String sCompareKey = matching.getCompareKey();
  141 +
  142 + //자기법인 데이타 가져오기
  143 + params.put("cprCode", item.get("cpr_code"));
  144 + params.put("partnCpr", item.get("partn_cpr"));
  145 + params.put("cond", condOne.getCond() ); //조건리스트
  146 + List<Map> lMatchingResultOne = matchingInnerDelingMapper.getMatchingResult(params);
  147 +
  148 + Map<String, Map> mMatchingResultOne = new HashMap<String, Map>();
  149 + for (Map curMap : lMatchingDataOne) {
  150 + String curComapreKeyVal = (String)curMap.get(sCompareKey);
  151 + boolean curBlnMatching = curMap.get("mtchType")!=null && curMap.get("mtchNumber")!=null;
  152 + if (curBlnMatching) mMatchingResultOne.put(curComapreKeyVal, curMap);
  153 + }
  154 + for (Map curMap : lMatchingResultOne) {
  155 + String curComapreKeyVal = (String)curMap.get(sCompareKey);
  156 + if ( mMatchingResultOne.containsKey(curComapreKeyVal) ) {
  157 + Map mResult = mMatchingResultOne.get(curComapreKeyVal);
  158 + curMap.put(matching.getMatchingType() , mResult.get("mtchType"));
  159 + curMap.put(matching.getMatchingTypeName(), mResult.get("mtchTypeName"));
  160 + curMap.put(matching.getMatchingNumber(), mResult.get("mtchNumber"));
  161 + lMatchingResultUpdate.add(curMap);
  162 + }
  163 + }
  164 +
  165 + //상대법인 데이타 가져오기
  166 + params.put("cprCode", item.get("partn_cpr"));
  167 + params.put("partnCpr", item.get("cpr_code"));
  168 + params.put("cond", condTwo.getCond() ); //조건리스트
  169 + List<Map> lMatchingResultTwo = matchingInnerDelingMapper.getMatchingResult(params);
  170 +
  171 + Map<String, Map> mMatchingResultTwo = new HashMap<String, Map>();
  172 + for (Map curMap : lMatchingDataTwo) {
  173 + String curComapreKeyVal = (String)curMap.get(sCompareKey);
  174 + boolean curBlnMatching = curMap.get("mtchType")!=null && curMap.get("mtchNumber")!=null;
  175 + if (curBlnMatching) mMatchingResultTwo.put(curComapreKeyVal, curMap);
  176 + }
  177 + for (Map curMap : lMatchingResultTwo) {
  178 + String curComapreKeyVal = (String)curMap.get(sCompareKey);
  179 + if ( mMatchingResultTwo.containsKey(curComapreKeyVal) ) {
  180 + Map mResult = mMatchingResultTwo.get(curComapreKeyVal);
  181 + curMap.put(matching.getMatchingType() , mResult.get("mtchType"));
  182 + curMap.put(matching.getMatchingTypeName(), mResult.get("mtchTypeName"));
  183 + curMap.put(matching.getMatchingNumber(), mResult.get("mtchNumber"));
  184 + lMatchingResultUpdate.add(curMap);
  185 + }
  186 + }
  187 +
  188 + iUpdated = 0;
  189 + int limit = 1000; //1000건씩 batch
  190 + List<Map> lUpdated = new ArrayList<Map>();
  191 + for (Map curMap : lMatchingResultUpdate) {
  192 + curMap.put("matchingType", matching.getMatchingType());
  193 + curMap.put("matchingTypeVal", curMap.get(matching.getMatchingType()));
  194 + curMap.put("matchingTypeName", matching.getMatchingTypeName());
  195 + curMap.put("matchingTypeNameVal", curMap.get(matching.getMatchingTypeName()));
  196 + curMap.put("matchingNumber", matching.getMatchingNumber());
  197 + curMap.put("matchingNumberVal", curMap.get(matching.getMatchingNumber()));
  198 + lUpdated.add(curMap);
  199 + if (lUpdated.size() == limit) {
  200 + matchingInnerDelingMapper.setResult(Map.of("itemList", lUpdated));
  201 + iUpdated = iUpdated + lUpdated.size();
  202 + lUpdated.clear();
  203 + }
  204 + }
  205 + if (lUpdated.size() > 0) {
  206 + matchingInnerDelingMapper.setResult(Map.of("itemList", lUpdated));
  207 + iUpdated = iUpdated + lUpdated.size();
  208 + }
  209 + log.debug("Updated OrgData : " + iUpdated + "건");
  210 +
  211 + //작업이 정상적으로 작동 되었을 경우 현재 처리하고 있는 데이타 그대로 넘겨준다.
  212 + return item;
  213 + }
  214 +}
0 215 \ No newline at end of file
... ...
src/main/java/daeucna/config/batch/MatchingItemReader.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/MatchingItemReader.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.util.List;
  4 +import java.util.Map;
  5 +
  6 +import org.springframework.batch.core.configuration.annotation.StepScope;
  7 +import org.springframework.beans.factory.annotation.Autowired;
  8 +import org.springframework.beans.factory.annotation.Value;
  9 +import org.springframework.stereotype.Component;
  10 +
  11 +import daeucna.batch.util.FileUtil;
  12 +import daeucna.config.batch.MatchingSetup.Matching;
  13 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  14 +import lombok.RequiredArgsConstructor;
  15 +import lombok.extern.slf4j.Slf4j;
  16 +
  17 +@Slf4j
  18 +@Component
  19 +@StepScope
  20 +@RequiredArgsConstructor
  21 +public class MatchingItemReader {
  22 +
  23 + @Value("#{jobParameters}")
  24 + private final Map<String, String> params;
  25 +
  26 + @Autowired
  27 + MatchingInnerDelingMapper matchingInnerDelingMapper;
  28 +
  29 + /*
  30 + * 자기 상대 법인단위로 작업할 단위를 읽는다.
  31 + */
  32 + public List<Map> customRead(){
  33 + log.debug("customRead.params : " + this.params.toString());
  34 + // customRead.params : {sysSe=KUMKANG, searchCond=mtch_ky is null, run.id=1, syncDate=2024-02-02-03-52-27:50deede8-ce3d-4841-ba65-f733bdd38533, jobType=F, accnutYm=202112}
  35 + String sMatchType = this.params.get("jobType");
  36 + StringBuffer sb = FileUtil.readFileToString("matchingSetup.json");
  37 + MatchingSetup matchingSetup = (MatchingSetup) FileUtil.strToObj(sb.toString(), MatchingSetup.class);
  38 + Matching matcning = matchingSetup.getMatching(sMatchType);
  39 +
  40 + List<Map> retData = matchingInnerDelingMapper.getCustomItemReadData(this.params);
  41 +
  42 + //레코드에 jobParameters 정보 추가
  43 + for (Map rec : retData) {
  44 + rec.put("jobParameters", this.params);
  45 + rec.put("matchingType", matcning);
  46 + }
  47 +
  48 + log.debug(">> customRead >> " + FileUtil.objToStr(retData));
  49 + return retData;
  50 + }
  51 +
  52 +}
... ...
src/main/java/daeucna/config/batch/MatchingItemWriter.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/MatchingItemWriter.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.util.HashMap;
  4 +import java.util.List;
  5 +import java.util.Map;
  6 +
  7 +import org.springframework.batch.core.configuration.annotation.JobScope;
  8 +import org.springframework.batch.item.ItemProcessor;
  9 +import org.springframework.beans.factory.annotation.Autowired;
  10 +import org.springframework.beans.factory.annotation.Value;
  11 +import org.springframework.stereotype.Component;
  12 +
  13 +import daeucna.mapper.primary.batch.MatchingInnerDelingMapper;
  14 +import lombok.RequiredArgsConstructor;
  15 +import lombok.extern.slf4j.Slf4j;
  16 +
  17 +@Slf4j
  18 +@Component
  19 +@RequiredArgsConstructor
  20 +public class MatchingItemWriter<T> {
  21 +
  22 + @Autowired
  23 + MatchingInnerDelingMapper matchingInnerDelingMapper;
  24 +
  25 + @SuppressWarnings("unchecked")
  26 + public void customWrite(T item){
  27 + Map<String, String> params = (Map<String, String>) ((Map) item).get("jobParameters");
  28 +
  29 + log.debug("customWrite.params : " + params.toString());
  30 +
  31 +// matchingInnerDelingMapper.setTest((Map) item);
  32 + log.debug("item test = " + item);
  33 + }
  34 +
  35 +}
... ...
src/main/java/daeucna/config/batch/MatchingSetup.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/batch/MatchingSetup.java
  1 +package daeucna.config.batch;
  2 +
  3 +import java.math.BigDecimal;
  4 +import java.util.ArrayList;
  5 +import java.util.List;
  6 +
  7 +import lombok.Data;
  8 +
  9 +@Data
  10 +public class MatchingSetup {
  11 +
  12 + List<Matching> matchingSetup;
  13 +
  14 + @Data
  15 + public class Matching {
  16 + String type;
  17 + String typeName;
  18 + Cond condOne;
  19 + Cond condTwo;
  20 + List<String> uniqueKey;
  21 + String compareKey;
  22 + List<String> compareField;
  23 + String amtField;
  24 + String matchingType;
  25 + String matchingTypeName;
  26 + String matchingNumber;
  27 + Boolean active;
  28 +
  29 + public Matching() {
  30 + this.uniqueKey = new ArrayList<String>();
  31 + this.condOne = new Cond();
  32 + this.condTwo = new Cond();
  33 + this.compareField = new ArrayList<String>();
  34 + }
  35 +
  36 + };
  37 +
  38 + @Data
  39 + public class Cond {
  40 + List<String> cond;
  41 + List<String> makeCompareKey;
  42 +
  43 + public Cond() {
  44 + this.cond = new ArrayList<String>();
  45 + this.makeCompareKey = new ArrayList<String>();
  46 + }
  47 +
  48 + public String getMakeCompareKey() {
  49 + StringBuffer sbMakeCompareKey = new StringBuffer();
  50 +
  51 + for (String curStr : this.makeCompareKey) {
  52 + if (sbMakeCompareKey.length() > 0) sbMakeCompareKey.append(" || ':' || ");
  53 + sbMakeCompareKey.append(curStr);
  54 + }
  55 + String sRtnVal = sbMakeCompareKey.toString();
  56 + if (sRtnVal.length() < this.makeCompareKey.size()) sRtnVal = "NULL";
  57 + return sbMakeCompareKey.toString();
  58 + }
  59 + }
  60 +
  61 + public Matching getMatching(String sName) {
  62 + Matching matching = null;
  63 +
  64 + for (Matching curObj : this.matchingSetup) {
  65 + if (curObj.getType().equalsIgnoreCase(sName)) {
  66 + matching = curObj;
  67 + break;
  68 + }
  69 + }
  70 +
  71 + return matching;
  72 + }
  73 +
  74 +}
  75 +
  76 +/*
  77 + * 예시 데이타
  78 + */
  79 +/*
  80 +{
  81 + "matchingSetup": [
  82 + {
  83 + "type": "A1",
  84 + "typeName": "A type",
  85 +
  86 + "condOne": {
  87 + "cond": [
  88 + "dta_ty in ('11', '12')"
  89 + ],
  90 + "makeCompareKey": [
  91 + "cmpnsp_ky"
  92 + ]
  93 + },
  94 + "condTwo": {
  95 + "cond": [
  96 + "dta_ty in ('21', '22')"
  97 + ],
  98 + "makeCompareKey": [
  99 + "cmpnsp_ky"
  100 + ]
  101 + },
  102 + "uniqueKey": [
  103 + "sys_se",
  104 + "accnut_ym",
  105 + "sn"
  106 + ],
  107 + "compareKey": "compare_ky",
  108 + "amtField": "delng_amt",
  109 + "compareField": [
  110 + "accnut_ym",
  111 + "compare_ky"
  112 + ]
  113 + },
  114 + ]
  115 +}
  116 +*/
0 117 \ No newline at end of file
... ...
src/main/java/daeucna/config/datasource/MultipleDataSourceConfiguration.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/datasource/MultipleDataSourceConfiguration.java
  1 +package daeucna.config.datasource;
  2 +
  3 +import javax.sql.DataSource;
  4 +
  5 +import org.springframework.beans.factory.annotation.Qualifier;
  6 +import org.springframework.boot.context.properties.ConfigurationProperties;
  7 +import org.springframework.context.annotation.Bean;
  8 +import org.springframework.context.annotation.Configuration;
  9 +import org.springframework.context.annotation.Primary;
  10 +
  11 +import com.zaxxer.hikari.HikariConfig;
  12 +import com.zaxxer.hikari.HikariDataSource;
  13 +
  14 +@Configuration
  15 +public class MultipleDataSourceConfiguration {
  16 +
  17 +
  18 + @Bean
  19 + @Primary
  20 + @Qualifier("primaryHikariConfig")
  21 + @ConfigurationProperties(prefix="spring.datasource.hikari.primary")
  22 + public HikariConfig primaryHikariConfig() {
  23 + return new HikariConfig();
  24 + }
  25 +
  26 + @Bean
  27 + @Primary
  28 + @Qualifier("primaryDataSource")
  29 + public DataSource primaryDataSource() throws Exception {
  30 + return new HikariDataSource(primaryHikariConfig());
  31 + }
  32 +
  33 + @Bean
  34 + @Qualifier("secondaryHikariConfig")
  35 + @ConfigurationProperties(prefix="spring.datasource.hikari.secondary")
  36 + public HikariConfig secondaryHikariConfig() {
  37 + return new HikariConfig();
  38 + }
  39 +
  40 + @Bean
  41 + @Qualifier("secondaryDataSource")
  42 + public DataSource secondaryDataSource() throws Exception {
  43 + return new HikariDataSource(secondaryHikariConfig());
  44 + }
  45 +
  46 +}
... ...
src/main/java/daeucna/config/datasource/PrimaryMybatisConfiguration.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/datasource/PrimaryMybatisConfiguration.java
  1 +package daeucna.config.datasource;
  2 +
  3 +import javax.sql.DataSource;
  4 +
  5 +import org.apache.ibatis.session.SqlSessionFactory;
  6 +import org.mybatis.spring.SqlSessionFactoryBean;
  7 +import org.mybatis.spring.SqlSessionTemplate;
  8 +import org.mybatis.spring.annotation.MapperScan;
  9 +import org.springframework.beans.factory.annotation.Qualifier;
  10 +import org.springframework.context.ApplicationContext;
  11 +import org.springframework.context.annotation.Bean;
  12 +import org.springframework.context.annotation.Configuration;
  13 +import org.springframework.context.annotation.Primary;
  14 +import org.springframework.transaction.annotation.EnableTransactionManagement;
  15 +
  16 +@Configuration
  17 +@MapperScan(value = "daeucna.mapper.primary", sqlSessionFactoryRef="primarySqlSessionFactory")
  18 +public class PrimaryMybatisConfiguration {
  19 +
  20 + @Primary
  21 + @Bean(name = "primarySqlSessionFactory")
  22 + public SqlSessionFactory sqlSessionFactory(
  23 + @Qualifier("primaryDataSource") DataSource dataSource, ApplicationContext applicationContext) throws Exception {
  24 + SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
  25 + sqlSessionFactoryBean.setDataSource(dataSource);
  26 + sqlSessionFactoryBean.setConfigLocation(applicationContext.getResource("classpath:mybatis/mybatis-config.xml"));
  27 + sqlSessionFactoryBean.setMapperLocations(applicationContext.getResources("classpath:mybatis/primary/**/*.xml"));
  28 +
  29 + return sqlSessionFactoryBean.getObject();
  30 + }
  31 +
  32 + @Primary
  33 + @Bean(name = "primarySqlSessionTemplate")
  34 + public SqlSessionTemplate sqlSessionTemplate(
  35 + @Qualifier("primarySqlSessionFactory") SqlSessionFactory sqlSessionFactory) {
  36 + return new SqlSessionTemplate(sqlSessionFactory);
  37 + }
  38 +
  39 +}
... ...
src/main/java/daeucna/config/datasource/SecondaryMyBatisConfiguration.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/datasource/SecondaryMyBatisConfiguration.java
  1 +package daeucna.config.datasource;
  2 +
  3 +import javax.sql.DataSource;
  4 +
  5 +import org.apache.ibatis.session.SqlSessionFactory;
  6 +import org.mybatis.spring.SqlSessionFactoryBean;
  7 +import org.mybatis.spring.SqlSessionTemplate;
  8 +import org.mybatis.spring.annotation.MapperScan;
  9 +import org.springframework.beans.factory.annotation.Qualifier;
  10 +import org.springframework.context.ApplicationContext;
  11 +import org.springframework.context.annotation.Bean;
  12 +import org.springframework.context.annotation.Configuration;
  13 +import org.springframework.transaction.annotation.EnableTransactionManagement;
  14 +
  15 +@Configuration
  16 +@MapperScan(value = "daeucna.mapper.secondary", sqlSessionFactoryRef="secondarySqlSessionFactory")
  17 +public class SecondaryMyBatisConfiguration {
  18 +
  19 + @Bean(name = "secondarySqlSessionFactory")
  20 + public SqlSessionFactory sqlSessionFactory(
  21 + @Qualifier("secondaryDataSource") DataSource dataSource, ApplicationContext applicationContext) throws Exception {
  22 + SqlSessionFactoryBean sqlSessionFactoryBean = new SqlSessionFactoryBean();
  23 + sqlSessionFactoryBean.setDataSource(dataSource);
  24 + sqlSessionFactoryBean.setConfigLocation(applicationContext.getResource("classpath:mybatis/mybatis-config.xml"));
  25 + sqlSessionFactoryBean.setMapperLocations(applicationContext.getResources("classpath:mybatis/secondary/**/*.xml"));
  26 +
  27 + return sqlSessionFactoryBean.getObject();
  28 + }
  29 +
  30 + @Bean(name = "secondarySqlSessionTemplate")
  31 + public SqlSessionTemplate sqlSessionTemplate(
  32 + @Qualifier("secondarySqlSessionFactory") SqlSessionFactory sqlSessionFactory) {
  33 + return new SqlSessionTemplate(sqlSessionFactory);
  34 + }
  35 +
  36 +}
... ...
src/main/java/daeucna/config/handler/RootController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/handler/RootController.java
  1 +package daeucna.config.handler;
  2 +
  3 +import org.springframework.boot.web.servlet.error.ErrorController;
  4 +import org.springframework.stereotype.Controller;
  5 +import org.springframework.web.bind.annotation.GetMapping;
  6 +
  7 +@Controller
  8 +public class RootController implements ErrorController {
  9 + // url 직접 접근할 경우 대체 경로 추가
  10 + private final String ERROR_PATH = "/error";
  11 +
  12 + @GetMapping(ERROR_PATH)
  13 + public String redirectRoot(){
  14 + return "forward:/index.html";
  15 + }
  16 +
  17 + public String getErrorPath(){
  18 + return null;
  19 + }
  20 +}
0 21 \ No newline at end of file
... ...
src/main/java/daeucna/config/p6spy/P6SpyFomatter.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/p6spy/P6SpyFomatter.java
  1 +package daeucna.config.p6spy;
  2 +
  3 +import java.util.Locale;
  4 +
  5 +import org.hibernate.engine.jdbc.internal.FormatStyle;
  6 +import org.springframework.context.annotation.Configuration;
  7 +
  8 +import com.p6spy.engine.logging.Category;
  9 +import com.p6spy.engine.spy.P6SpyOptions;
  10 +import com.p6spy.engine.spy.appender.MessageFormattingStrategy;
  11 +
  12 +import jakarta.annotation.PostConstruct;
  13 +
  14 +@Configuration
  15 +public class P6SpyFomatter implements MessageFormattingStrategy {
  16 +
  17 + @PostConstruct
  18 + public void setLogMessageFormat() {
  19 + P6SpyOptions.getActiveInstance().setLogMessageFormat(this.getClass().getName());
  20 + }
  21 +
  22 + @Override
  23 + public String formatMessage(int connectionId, String now, long elapsed, String category, String prepared, String sql, String url) {
  24 + sql = formatSql(category, sql);
  25 + return String.format("[%s] | %d ms | %s", category, elapsed, formatSql(category, sql));
  26 + }
  27 +
  28 + private String formatSql(String category, String sql) {
  29 + if (sql != null && !sql.trim().isEmpty() && Category.STATEMENT.getName().equals(category)) {
  30 + String trimmedSQL = sql.trim().toLowerCase(Locale.ROOT);
  31 + if (trimmedSQL.startsWith("create") || trimmedSQL.startsWith("alter") || trimmedSQL.startsWith("comment")) {
  32 + sql = FormatStyle.DDL.getFormatter().format(sql);
  33 + } else {
  34 + sql = FormatStyle.BASIC.getFormatter().format(sql);
  35 + }
  36 + return sql;
  37 + }
  38 + return sql;
  39 + }
  40 +}
0 41 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/JwtSecurityConfig.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/JwtSecurityConfig.java
  1 +package daeucna.config.security;
  2 +
  3 +import org.springframework.security.config.annotation.SecurityConfigurerAdapter;
  4 +import org.springframework.security.config.annotation.web.builders.HttpSecurity;
  5 +import org.springframework.security.web.DefaultSecurityFilterChain;
  6 +import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter;
  7 +
  8 +import daeucna.config.security.jwt.JwtFilter;
  9 +import daeucna.config.security.jwt.JwtTokenProvider;
  10 +import lombok.RequiredArgsConstructor;
  11 +
  12 +@RequiredArgsConstructor
  13 +public class JwtSecurityConfig extends SecurityConfigurerAdapter<DefaultSecurityFilterChain, HttpSecurity> {
  14 + private final JwtTokenProvider tokenProvider;
  15 +
  16 + @Override
  17 + public void configure(HttpSecurity http) {
  18 +
  19 + // security 로직에 JwtFilter 등록
  20 + http.addFilterBefore(
  21 + new JwtFilter(tokenProvider),
  22 + UsernamePasswordAuthenticationFilter.class
  23 + );
  24 + }
  25 +}
0 26 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/SecurityConfig.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/SecurityConfig.java
  1 +package daeucna.config.security;
  2 +
  3 +import org.springframework.context.annotation.Bean;
  4 +import org.springframework.context.annotation.Configuration;
  5 +import org.springframework.security.config.Customizer;
  6 +import org.springframework.security.config.annotation.web.builders.HttpSecurity;
  7 +import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
  8 +import org.springframework.security.config.annotation.web.configurers.AbstractHttpConfigurer;
  9 +import org.springframework.security.config.http.SessionCreationPolicy;
  10 +import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
  11 +import org.springframework.security.crypto.password.PasswordEncoder;
  12 +import org.springframework.security.web.SecurityFilterChain;
  13 +
  14 +import daeucna.config.security.jwt.JwtAuthenticationEntryPoint;
  15 +import daeucna.config.security.jwt.JwtTokenProvider;
  16 +import lombok.RequiredArgsConstructor;
  17 +
  18 +@Configuration
  19 +@EnableWebSecurity
  20 +@RequiredArgsConstructor
  21 +public class SecurityConfig {
  22 +
  23 + private final JwtTokenProvider tokenProvider;
  24 + private final JwtAuthenticationEntryPoint jwtAuthenticationEntryPoint;
  25 +
  26 + // PasswordEncoder는 BCryptPasswordEncoder를 사용
  27 + @Bean
  28 + public PasswordEncoder passwordEncoder() {
  29 + return new BCryptPasswordEncoder();
  30 + }
  31 +
  32 + @Bean
  33 + public SecurityFilterChain filterChain(HttpSecurity httpSecurity) throws Exception {
  34 + httpSecurity
  35 + // token을 사용하는 방식이기 때문에 csrf를 disable합니다.
  36 + .csrf(AbstractHttpConfigurer::disable)
  37 + .securityMatcher("/api/**")
  38 + .authorizeHttpRequests((authorizeHttpRequests) ->
  39 + authorizeHttpRequests
  40 + .requestMatchers("/api/admin/**").hasRole("ADMIN")
  41 + .requestMatchers("/api/authenticate").permitAll() // 로그인 api
  42 + .requestMatchers("/api/refreshtoken").permitAll() // Refresh Token api
  43 + .requestMatchers("/api/signup").permitAll() // 회원가입 api
  44 + .requestMatchers("/api/exceptionDenied").permitAll() // Exception Denied
  45 +// .anyRequest().permitAll()
  46 + .anyRequest().authenticated() // 그 외 인증 없이 접근X
  47 + )
  48 + .formLogin(Customizer.withDefaults())
  49 + .headers((headers) ->
  50 + headers
  51 + .frameOptions(frameOptions -> frameOptions
  52 + .sameOrigin()
  53 + )
  54 + )
  55 + .exceptionHandling(exceptionHandling -> exceptionHandling
  56 + .authenticationEntryPoint(jwtAuthenticationEntryPoint)
  57 + .accessDeniedPage("/api/exceptionDenied")
  58 + )
  59 + // 세션을 사용하지 않기 때문에 STATELESS로 설정
  60 + .sessionManagement((sessionManagement) ->
  61 + sessionManagement
  62 + .sessionCreationPolicy(SessionCreationPolicy.STATELESS)
  63 + )
  64 + .apply(new JwtSecurityConfig(tokenProvider)); // JwtFilter를 addFilterBefore로 등록했던 JwtSecurityConfig class 적용
  65 +
  66 + return httpSecurity.build();
  67 + }
  68 +
  69 +}
0 70 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/UserInitializer.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/UserInitializer.java
  1 +package daeucna.config.security;
  2 +import java.util.Arrays;
  3 +import java.util.HashSet;
  4 +
  5 +import org.springframework.beans.factory.annotation.Autowired;
  6 +import org.springframework.boot.ApplicationArguments;
  7 +import org.springframework.boot.ApplicationRunner;
  8 +import org.springframework.core.env.Environment;
  9 +import org.springframework.stereotype.Component;
  10 +
  11 +import daeucna.config.security.dto.AuthorityDto;
  12 +import daeucna.config.security.dto.UserDto;
  13 +import daeucna.config.security.service.UserService;
  14 +
  15 +@Component
  16 +public class UserInitializer implements ApplicationRunner {
  17 +
  18 + private final UserService userService;
  19 + private final Environment env;
  20 +
  21 + @Autowired
  22 + public UserInitializer(Environment env, UserService userService) {
  23 + this.userService = userService;
  24 + this.env = env;
  25 + }
  26 +
  27 + @Override
  28 + public void run(ApplicationArguments args) {
  29 + //초기 Admin User 넣어주기
  30 + AuthorityDto authorityDto = AuthorityDto.builder().authorityName("ROLE_ADMIN").build();
  31 + UserDto userDto = UserDto.builder()
  32 + .username("sangkiham")
  33 + .password("sangkiham")
  34 + .nickname("sangkiham")
  35 + .authorityDtoSet(new HashSet<AuthorityDto>( Arrays.asList(authorityDto) ))
  36 + .build();
  37 +
  38 + //사용자 정보가 없으면 Insert한다.
  39 + boolean blnAdminInit = Boolean.parseBoolean(env.getProperty("admin.init"));
  40 + if (blnAdminInit && userService.getUserWithAuthorities(userDto.getUsername()) == null) {
  41 + userService.signup(userDto);
  42 + }
  43 + }
  44 +}
0 45 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/controller/AuthController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/controller/AuthController.java
  1 +package daeucna.config.security.controller;
  2 +
  3 +import java.util.HashMap;
  4 +
  5 +import org.springframework.beans.factory.annotation.Value;
  6 +import org.springframework.http.HttpHeaders;
  7 +import org.springframework.http.HttpStatus;
  8 +import org.springframework.http.ResponseEntity;
  9 +import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
  10 +import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
  11 +import org.springframework.security.core.Authentication;
  12 +import org.springframework.security.core.context.SecurityContextHolder;
  13 +import org.springframework.web.bind.annotation.PostMapping;
  14 +import org.springframework.web.bind.annotation.RequestBody;
  15 +import org.springframework.web.bind.annotation.RequestHeader;
  16 +import org.springframework.web.bind.annotation.RequestMapping;
  17 +import org.springframework.web.bind.annotation.RestController;
  18 +
  19 +import daeucna.config.security.dto.LoginDto;
  20 +import daeucna.config.security.dto.TokenDto;
  21 +import daeucna.config.security.jwt.JwtFilter;
  22 +import daeucna.config.security.jwt.JwtTokenProvider;
  23 +import daeucna.config.security.utils.CommonJson;
  24 +import io.jsonwebtoken.Claims;
  25 +import io.jsonwebtoken.Jws;
  26 +import jakarta.validation.Valid;
  27 +import lombok.RequiredArgsConstructor;
  28 +import lombok.extern.slf4j.Slf4j;
  29 +
  30 +@RestController
  31 +@RequestMapping("/api")
  32 +@RequiredArgsConstructor
  33 +@Slf4j
  34 +public class AuthController {
  35 + private final JwtTokenProvider tokenProvider;
  36 + private final AuthenticationManagerBuilder authenticationManagerBuilder;
  37 +
  38 + @PostMapping("/authenticate")
  39 + public ResponseEntity<TokenDto> authorize(
  40 + @Valid @RequestBody LoginDto loginDto,
  41 + @Value("${jwt.token-validity-in-seconds}") long tokenValidityInSeconds,
  42 + @Value("${jwt.refresh-token-validity-in-seconds}") long refreshTokenValidityInSeconds
  43 + ) {
  44 +
  45 + return fnAuthorize(loginDto, tokenValidityInSeconds, refreshTokenValidityInSeconds, false);
  46 + }
  47 +
  48 + public ResponseEntity<TokenDto> fnAuthorize(LoginDto loginDto, long tokenValidityInSeconds, long refreshTokenValidityInSeconds, boolean blnRefresh) {
  49 +
  50 + UsernamePasswordAuthenticationToken authenticationToken =
  51 + new UsernamePasswordAuthenticationToken(loginDto.getUsername(), loginDto.getPassword());
  52 +
  53 + // authenticate 메소드가 실행이 될 때 CustomUserDetailsService class의 loadUserByUsername 메소드가 실행
  54 + Authentication authentication = authenticationManagerBuilder.getObject().authenticate(authenticationToken);
  55 + // 해당 객체를 SecurityContextHolder에 저장하고
  56 + SecurityContextHolder.getContext().setAuthentication(authentication);
  57 + // authentication 객체를 createToken 메소드를 통해서 JWT Token을 생성
  58 + String jwt = tokenProvider.createToken(authentication, tokenValidityInSeconds, loginDto);
  59 + String jwtRefresh = tokenProvider.createToken(authentication, refreshTokenValidityInSeconds, loginDto);
  60 + //요청이 RefreshToken 아닐 경우만 생성
  61 + if (blnRefresh) jwtRefresh = null;
  62 +
  63 + HttpHeaders httpHeaders = new HttpHeaders();
  64 + // response header에 jwt token에 넣어줌
  65 + httpHeaders.add(JwtFilter.AUTHORIZATION_HEADER, "Bearer " + jwt);
  66 +
  67 + // tokenDto를 이용해 response body에도 넣어서 리턴
  68 + log.debug("jwt = " + jwt);
  69 + log.debug("jwtRefresh = " + jwtRefresh);
  70 + return new ResponseEntity<>(new TokenDto(jwt, jwtRefresh), httpHeaders, HttpStatus.OK);
  71 + }
  72 + @PostMapping("/refreshtoken")
  73 + public ResponseEntity<TokenDto> refreshToken(
  74 + @RequestHeader HttpHeaders header,
  75 + @Value("${jwt.token-validity-in-seconds}") long tokenValidityInSeconds,
  76 + @Value("${jwt.refresh-token-validity-in-seconds}") long refreshTokenValidityInSeconds
  77 + ) {
  78 +
  79 + String sRefreshToken = header.getFirst(JwtFilter.AUTHORIZATION_REFRESH_HEADER);
  80 + LoginDto loginDto = null;
  81 + if (tokenProvider.validateToken(sRefreshToken)) {
  82 + Jws<Claims> claims = tokenProvider.getClaims(sRefreshToken);
  83 +
  84 + log.debug("parseJwt = " + CommonJson.objectToString(claims));
  85 + log.debug("parseJwt(getSubject) = " + claims.getBody().getSubject());
  86 + log.debug("parseJwt(auth) = " + (String) claims.getBody().get("auth"));
  87 +
  88 + HashMap<String, String> hmLoginDto = claims.getBody().get("loginDto", HashMap.class);
  89 + loginDto = LoginDto.builder()
  90 + .username(hmLoginDto.get("username"))
  91 + .password(hmLoginDto.get("password"))
  92 + .build();
  93 + log.debug("parseJwt(LoginDto) = " + CommonJson.objectToString(loginDto));
  94 + }
  95 +
  96 + return fnAuthorize(loginDto, tokenValidityInSeconds, refreshTokenValidityInSeconds, true);
  97 + }
  98 +}
0 99 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/controller/ExceptionController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/controller/ExceptionController.java
  1 +package daeucna.config.security.controller;
  2 +
  3 +import org.springframework.security.access.AccessDeniedException;
  4 +import org.springframework.web.bind.annotation.RequestMapping;
  5 +import org.springframework.web.bind.annotation.RequestMethod;
  6 +import org.springframework.web.bind.annotation.RestController;
  7 +
  8 +import io.swagger.v3.oas.annotations.Operation;
  9 +import lombok.extern.slf4j.Slf4j;
  10 +
  11 +@Slf4j
  12 +@RestController
  13 +@RequestMapping("/api")
  14 +public class ExceptionController {
  15 +
  16 + @Operation(summary = "인가 거부", description = "인가에 따른 예외가 발생했습니다.")
  17 + @RequestMapping(value = "/exceptionDenied", method = {RequestMethod.GET, RequestMethod.POST})
  18 + public void AccessDeniedException() {
  19 + throw new AccessDeniedException("");
  20 + }
  21 +
  22 +}
... ...
src/main/java/daeucna/config/security/controller/UserController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/controller/UserController.java
  1 +package daeucna.config.security.controller;
  2 +
  3 +import java.io.IOException;
  4 +
  5 +import org.springframework.http.ResponseEntity;
  6 +import org.springframework.security.access.prepost.PreAuthorize;
  7 +import org.springframework.web.bind.annotation.GetMapping;
  8 +import org.springframework.web.bind.annotation.PathVariable;
  9 +import org.springframework.web.bind.annotation.PostMapping;
  10 +import org.springframework.web.bind.annotation.RequestBody;
  11 +import org.springframework.web.bind.annotation.RequestMapping;
  12 +import org.springframework.web.bind.annotation.RestController;
  13 +
  14 +import daeucna.config.security.dto.UserDto;
  15 +import daeucna.config.security.service.UserService;
  16 +import jakarta.servlet.http.HttpServletRequest;
  17 +import jakarta.servlet.http.HttpServletResponse;
  18 +import jakarta.validation.Valid;
  19 +import lombok.RequiredArgsConstructor;
  20 +
  21 +@RestController
  22 +@RequiredArgsConstructor
  23 +@RequestMapping("/api")
  24 +public class UserController {
  25 + private final UserService userService;
  26 +
  27 + @GetMapping("/hello")
  28 + public ResponseEntity<String> hello() {
  29 + return ResponseEntity.ok("hello");
  30 + }
  31 +
  32 + @PostMapping("/test-redirect")
  33 + public void testRedirect(HttpServletResponse response) throws IOException {
  34 + response.sendRedirect("/api/user");
  35 + }
  36 +
  37 + @PostMapping("/signup")
  38 + public ResponseEntity<UserDto> signup(
  39 + @Valid @RequestBody UserDto userDto
  40 + ) {
  41 + return ResponseEntity.ok(userService.signup(userDto));
  42 + }
  43 +
  44 + @GetMapping("/user")
  45 + @PreAuthorize("hasAnyRole('USER','ADMIN')")
  46 + public ResponseEntity<UserDto> getMyUserInfo(HttpServletRequest request) {
  47 + return ResponseEntity.ok(userService.getMyUserWithAuthorities());
  48 + }
  49 +
  50 + @GetMapping("/user/{username}")
  51 + @PreAuthorize("hasAnyRole('ADMIN')")
  52 + public ResponseEntity<UserDto> getUserInfo(@PathVariable String username) {
  53 + return ResponseEntity.ok(userService.getUserWithAuthorities(username));
  54 + }
  55 +}
0 56 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/dto/AuthorityDto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/dto/AuthorityDto.java
  1 +package daeucna.config.security.dto;
  2 +
  3 +import daeucna.config.security.entity.Authority;
  4 +import jakarta.validation.constraints.NotNull;
  5 +import jakarta.validation.constraints.Size;
  6 +import lombok.AllArgsConstructor;
  7 +import lombok.Builder;
  8 +import lombok.Getter;
  9 +import lombok.NoArgsConstructor;
  10 +import lombok.Setter;
  11 +
  12 +@Getter @Setter @Builder
  13 +@AllArgsConstructor
  14 +@NoArgsConstructor
  15 +public class AuthorityDto {
  16 +
  17 + @NotNull
  18 + @Size(min = 3, max = 50)
  19 + private String authorityName;
  20 +
  21 + public static AuthorityDto from(Authority authority) {
  22 + if(authority == null) return null;
  23 +
  24 + return AuthorityDto.builder()
  25 + .authorityName(authority.getAuthorityName())
  26 + .build();
  27 + }
  28 +}
0 29 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/dto/LoginDto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/dto/LoginDto.java
  1 +package daeucna.config.security.dto;
  2 +
  3 +import jakarta.validation.constraints.NotNull;
  4 +import jakarta.validation.constraints.Size;
  5 +import lombok.AllArgsConstructor;
  6 +import lombok.Builder;
  7 +import lombok.Getter;
  8 +import lombok.NoArgsConstructor;
  9 +import lombok.Setter;
  10 +
  11 +@Getter
  12 +@Setter
  13 +@Builder
  14 +@AllArgsConstructor
  15 +@NoArgsConstructor
  16 +public class LoginDto {
  17 +
  18 + @NotNull
  19 + @Size(min = 3, max = 50)
  20 + private String username;
  21 +
  22 + @NotNull
  23 + @Size(min = 3, max = 100)
  24 + private String password;
  25 +}
0 26 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/dto/TokenDto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/dto/TokenDto.java
  1 +package daeucna.config.security.dto;
  2 +
  3 +import lombok.AllArgsConstructor;
  4 +import lombok.Builder;
  5 +import lombok.Getter;
  6 +import lombok.NoArgsConstructor;
  7 +import lombok.Setter;
  8 +
  9 +@Getter
  10 +@Setter
  11 +@Builder
  12 +@AllArgsConstructor
  13 +@NoArgsConstructor
  14 +public class TokenDto {
  15 +
  16 + private String token;
  17 + private String refreshToken;
  18 +
  19 +}
0 20 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/dto/UserDto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/dto/UserDto.java
  1 +package daeucna.config.security.dto;
  2 +
  3 +import java.util.Set;
  4 +import java.util.stream.Collectors;
  5 +
  6 +import com.fasterxml.jackson.annotation.JsonProperty;
  7 +
  8 +import daeucna.config.security.entity.User;
  9 +import jakarta.validation.constraints.NotNull;
  10 +import jakarta.validation.constraints.Size;
  11 +import lombok.AllArgsConstructor;
  12 +import lombok.Builder;
  13 +import lombok.Getter;
  14 +import lombok.NoArgsConstructor;
  15 +import lombok.Setter;
  16 +
  17 +@Getter @Setter @Builder
  18 +@AllArgsConstructor
  19 +@NoArgsConstructor
  20 +public class UserDto {
  21 +
  22 + @NotNull
  23 + @Size(min = 3, max = 50)
  24 + private String username;
  25 +
  26 +// @JsonProperty(access = JsonProperty.Access.WRITE_ONLY)
  27 + @NotNull
  28 + @Size(min = 3, max = 100)
  29 + private String password;
  30 +
  31 + @NotNull
  32 + @Size(min = 3, max = 50)
  33 + private String nickname;
  34 +
  35 + private Set<AuthorityDto> authorityDtoSet;
  36 +
  37 + public static UserDto from(User user) {
  38 + if(user == null) return null;
  39 +
  40 + return UserDto.builder()
  41 + .username(user.getUsername())
  42 + .password(user.getPassword())
  43 + .nickname(user.getNickname())
  44 + .authorityDtoSet(user.getAuthorities().stream()
  45 + .map(authority -> AuthorityDto.builder().authorityName(authority.getAuthorityName()).build())
  46 + .collect(Collectors.toSet()))
  47 + .build();
  48 + }
  49 +}
0 50 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/entity/Authority.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/entity/Authority.java
  1 +package daeucna.config.security.entity;
  2 +
  3 +import jakarta.persistence.Column;
  4 +import jakarta.persistence.Entity;
  5 +import jakarta.persistence.Id;
  6 +import jakarta.persistence.Table;
  7 +import lombok.AllArgsConstructor;
  8 +import lombok.Builder;
  9 +import lombok.Getter;
  10 +import lombok.NoArgsConstructor;
  11 +import lombok.Setter;
  12 +
  13 +@Entity
  14 +@Table(name = "authority")
  15 +@Getter
  16 +@Setter
  17 +@Builder
  18 +@AllArgsConstructor
  19 +@NoArgsConstructor
  20 +public class Authority {
  21 +
  22 + @Id
  23 + @Column(name = "authority_name", length = 50)
  24 + private String authorityName;
  25 +}
0 26 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/entity/User.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/entity/User.java
  1 +package daeucna.config.security.entity;
  2 +
  3 +import java.util.Set;
  4 +
  5 +import com.fasterxml.jackson.annotation.JsonIgnore;
  6 +
  7 +import jakarta.persistence.Column;
  8 +import jakarta.persistence.Entity;
  9 +import jakarta.persistence.GeneratedValue;
  10 +import jakarta.persistence.GenerationType;
  11 +import jakarta.persistence.Id;
  12 +import jakarta.persistence.JoinColumn;
  13 +import jakarta.persistence.JoinTable;
  14 +import jakarta.persistence.ManyToMany;
  15 +import jakarta.persistence.Table;
  16 +import lombok.AllArgsConstructor;
  17 +import lombok.Builder;
  18 +import lombok.Getter;
  19 +import lombok.NoArgsConstructor;
  20 +import lombok.Setter;
  21 +
  22 +@Entity // DB의 테이블과 1:1 매핑되는 객체
  23 +@Table(name = "users")
  24 +@Getter
  25 +@Setter
  26 +@Builder
  27 +@AllArgsConstructor
  28 +@NoArgsConstructor
  29 +public class User {
  30 +
  31 + @JsonIgnore
  32 + @Id // primary key
  33 + @Column(name = "user_id")
  34 + // 자동 증가 되는
  35 + @GeneratedValue(strategy = GenerationType.IDENTITY)
  36 + private Long userId;
  37 +
  38 + @Column(name = "username", length = 50, unique = true)
  39 + private String username;
  40 +
  41 + @JsonIgnore
  42 + @Column(name = "password", length = 100)
  43 + private String password;
  44 +
  45 + @Column(name = "nickname", length = 50)
  46 + private String nickname;
  47 +
  48 + @JsonIgnore
  49 + @Column(name = "activated")
  50 + private boolean activated;
  51 +
  52 + @ManyToMany
  53 + @JoinTable(
  54 + name = "user_authority",
  55 + joinColumns = {@JoinColumn(name = "user_id", referencedColumnName = "user_id")},
  56 + inverseJoinColumns = {@JoinColumn(name = "authority_name", referencedColumnName = "authority_name")})
  57 + private Set<Authority> authorities;
  58 +}
0 59 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/jwt/JwtAuthenticationEntryPoint.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/jwt/JwtAuthenticationEntryPoint.java
  1 +package daeucna.config.security.jwt;
  2 +
  3 +import java.io.IOException;
  4 +
  5 +import org.springframework.security.core.AuthenticationException;
  6 +import org.springframework.security.web.AuthenticationEntryPoint;
  7 +import org.springframework.stereotype.Component;
  8 +
  9 +import jakarta.servlet.http.HttpServletRequest;
  10 +import jakarta.servlet.http.HttpServletResponse;
  11 +import lombok.extern.slf4j.Slf4j;
  12 +
  13 +@Slf4j
  14 +@Component
  15 +public class JwtAuthenticationEntryPoint implements AuthenticationEntryPoint {
  16 + @Override
  17 + public void commence(HttpServletRequest request,
  18 + HttpServletResponse response,
  19 + AuthenticationException authException) throws IOException {
  20 + // 유효한 자격증명을 제공하지 않고 접근하려 할때 401
  21 + response.sendError(HttpServletResponse.SC_UNAUTHORIZED);
  22 + }
  23 +}
0 24 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/jwt/JwtFilter.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/jwt/JwtFilter.java
  1 +package daeucna.config.security.jwt;
  2 +
  3 +import java.io.IOException;
  4 +
  5 +import org.springframework.security.core.Authentication;
  6 +import org.springframework.security.core.context.SecurityContextHolder;
  7 +import org.springframework.util.StringUtils;
  8 +import org.springframework.web.filter.GenericFilterBean;
  9 +
  10 +import jakarta.servlet.FilterChain;
  11 +import jakarta.servlet.ServletException;
  12 +import jakarta.servlet.ServletRequest;
  13 +import jakarta.servlet.ServletResponse;
  14 +import jakarta.servlet.http.HttpServletRequest;
  15 +import lombok.RequiredArgsConstructor;
  16 +import lombok.extern.slf4j.Slf4j;
  17 +
  18 +@RequiredArgsConstructor
  19 +@Slf4j
  20 +public class JwtFilter extends GenericFilterBean {
  21 +
  22 + public static final String AUTHORIZATION_HEADER = "Authorization";
  23 + public static final String AUTHORIZATION_REFRESH_HEADER = "REFRESH_TOKEN";
  24 + private final JwtTokenProvider tokenProvider;
  25 +
  26 + // 실제 필터릴 로직
  27 + // 토큰의 인증정보를 SecurityContext에 저장하는 역할 수행
  28 + @Override
  29 + public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
  30 + HttpServletRequest httpServletRequest = (HttpServletRequest) servletRequest;
  31 + String jwt = resolveToken(httpServletRequest);
  32 + String requestURI = httpServletRequest.getRequestURI();
  33 +
  34 + if (StringUtils.hasText(jwt) && tokenProvider.validateToken(jwt)) {
  35 + Authentication authentication = tokenProvider.getAuthentication(jwt);
  36 + SecurityContextHolder.getContext().setAuthentication(authentication);
  37 + log.debug("Security Context에 '{}' 인증 정보를 저장했습니다, uri: {}", authentication.getName(), requestURI);
  38 + } else {
  39 + log.debug("유효한 JWT 토큰이 없습니다, uri: {}", requestURI);
  40 + }
  41 +
  42 + filterChain.doFilter(servletRequest, servletResponse);
  43 + }
  44 +
  45 + // Request Header 에서 토큰 정보를 꺼내오기 위한 메소드
  46 + private String resolveToken(HttpServletRequest request) {
  47 + String bearerToken = request.getHeader(AUTHORIZATION_HEADER);
  48 +
  49 + if (StringUtils.hasText(bearerToken) && bearerToken.startsWith("Bearer ")) {
  50 + return bearerToken.substring(7);
  51 + }
  52 +
  53 + return null;
  54 + }
  55 +}
0 56 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/jwt/JwtTokenProvider.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/jwt/JwtTokenProvider.java
  1 +package daeucna.config.security.jwt;
  2 +
  3 +import java.security.Key;
  4 +import java.util.Arrays;
  5 +import java.util.Collection;
  6 +import java.util.Date;
  7 +import java.util.Map;
  8 +import java.util.stream.Collectors;
  9 +
  10 +import javax.crypto.SecretKey;
  11 +
  12 +import org.springframework.beans.factory.InitializingBean;
  13 +import org.springframework.beans.factory.annotation.Value;
  14 +import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
  15 +import org.springframework.security.core.Authentication;
  16 +import org.springframework.security.core.GrantedAuthority;
  17 +import org.springframework.security.core.authority.SimpleGrantedAuthority;
  18 +import org.springframework.security.core.userdetails.User;
  19 +import org.springframework.stereotype.Component;
  20 +
  21 +import daeucna.config.security.dto.LoginDto;
  22 +import io.jsonwebtoken.Claims;
  23 +import io.jsonwebtoken.ExpiredJwtException;
  24 +import io.jsonwebtoken.Jws;
  25 +import io.jsonwebtoken.Jwts;
  26 +import io.jsonwebtoken.MalformedJwtException;
  27 +import io.jsonwebtoken.SignatureAlgorithm;
  28 +import io.jsonwebtoken.UnsupportedJwtException;
  29 +import io.jsonwebtoken.io.Decoders;
  30 +import io.jsonwebtoken.security.Keys;
  31 +import lombok.extern.slf4j.Slf4j;
  32 +
  33 +@Component
  34 +@Slf4j
  35 +public class JwtTokenProvider implements InitializingBean {
  36 +
  37 + private static final String AUTHORITIES_KEY = "auth";
  38 + private final String secret;
  39 + private final long tokenValidityInMilliseconds;
  40 + private final long freshTokenValidityInMilliseconds;
  41 + private SecretKey key;
  42 +
  43 + public JwtTokenProvider(
  44 + @Value("${jwt.secret}") String secret,
  45 + @Value("${jwt.token-validity-in-seconds}") long tokenValidityInSeconds,
  46 + @Value("${jwt.refresh-token-validity-in-seconds}") long refreshTokenValidityInSeconds) {
  47 + this.secret = secret;
  48 + this.tokenValidityInMilliseconds = tokenValidityInSeconds * 1000;
  49 + this.freshTokenValidityInMilliseconds = refreshTokenValidityInSeconds * 1000;
  50 + }
  51 +
  52 + // 빈이 생성되고 주입을 받은 후에 secret값을 Base64 Decode해서 key 변수에 할당하기 위해
  53 + @Override
  54 + public void afterPropertiesSet() {
  55 + byte[] keyBytes = Decoders.BASE64URL.decode(secret);
  56 + this.key = Keys.hmacShaKeyFor(keyBytes);
  57 + }
  58 +
  59 + public SecretKey getSecretKey() {
  60 + return this.key;
  61 + }
  62 +
  63 + public String createToken(Authentication authentication, long tokenValidityInMilliseconds, LoginDto loginDto) {
  64 + String authorities = authentication.getAuthorities().stream()
  65 + .map(GrantedAuthority::getAuthority)
  66 + .collect(Collectors.joining(","));
  67 +
  68 + // 토큰의 expire 시간을 설정
  69 + long now = (new Date()).getTime();
  70 + Date validity = new Date(now + (tokenValidityInMilliseconds * 1000) ); //1000분의 1초
  71 +
  72 + return Jwts.builder()
  73 + .subject(authentication.getName())
  74 + .claim(AUTHORITIES_KEY, authorities) // 정보 저장
  75 + .claims()
  76 + .add(Map.of("loginDto", loginDto))
  77 + .and()
  78 + .signWith(key, Jwts.SIG.HS512) // 사용할 암호화 알고리즘과 , signature 에 들어갈 secret값 세팅
  79 + .expiration(validity) // set Expire Time 해당 옵션 안넣으면 expire안함
  80 + .compact();
  81 + }
  82 +
  83 + // 토큰으로 클레임을 만들고 이를 이용해 유저 객체를 만들어서 최종적으로 authentication 객체를 리턴
  84 + public Authentication getAuthentication(String token) {
  85 + Claims claims = Jwts
  86 + .parser()
  87 + .verifyWith(key)
  88 + .build()
  89 + .parseSignedClaims(token)
  90 + .getPayload();
  91 +
  92 + Collection<? extends GrantedAuthority> authorities =
  93 + Arrays.stream(claims.get(AUTHORITIES_KEY).toString().split(","))
  94 + .map(SimpleGrantedAuthority::new)
  95 + .collect(Collectors.toList());
  96 +
  97 + User principal = new User(claims.getSubject(), "", authorities);
  98 +
  99 + return new UsernamePasswordAuthenticationToken(principal, token, authorities);
  100 + }
  101 +
  102 + public Jws<Claims> getClaims(String sToken) {
  103 + return Jwts.parser()
  104 + .verifyWith(this.getSecretKey())
  105 + .build()
  106 + .parseSignedClaims(sToken);
  107 + }
  108 +
  109 + // 토큰의 유효성 검증을 수행
  110 + public boolean validateToken(String token) {
  111 + try {
  112 + Jwts.parser().verifyWith(key).build().parseSignedClaims(token);
  113 + return true;
  114 + } catch (io.jsonwebtoken.security.SecurityException | MalformedJwtException e) {
  115 +
  116 + log.info("잘못된 JWT 서명입니다.");
  117 + } catch (ExpiredJwtException e) {
  118 +
  119 + log.info("만료된 JWT 토큰입니다.");
  120 + } catch (UnsupportedJwtException e) {
  121 +
  122 + log.info("지원되지 않는 JWT 토큰입니다.");
  123 + } catch (IllegalArgumentException e) {
  124 +
  125 + log.info("JWT 토큰이 잘못되었습니다.");
  126 + }
  127 + return false;
  128 + }
  129 +}
0 130 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/repository/UserRepository.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/repository/UserRepository.java
  1 +package daeucna.config.security.repository;
  2 +
  3 +import java.util.Optional;
  4 +
  5 +import org.springframework.data.jpa.repository.EntityGraph;
  6 +import org.springframework.data.jpa.repository.JpaRepository;
  7 +
  8 +import daeucna.config.security.entity.User;
  9 +
  10 +public interface UserRepository extends JpaRepository<User, Long> {
  11 + @EntityGraph(attributePaths = "authorities")
  12 + Optional<User> findOneWithAuthoritiesByUsername(String username);
  13 +}
... ...
src/main/java/daeucna/config/security/service/CustomUserDetailsService.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/service/CustomUserDetailsService.java
  1 +package daeucna.config.security.service;
  2 +
  3 +import java.util.List;
  4 +import java.util.stream.Collectors;
  5 +
  6 +import org.springframework.security.core.GrantedAuthority;
  7 +import org.springframework.security.core.authority.SimpleGrantedAuthority;
  8 +import org.springframework.security.core.userdetails.UserDetails;
  9 +import org.springframework.security.core.userdetails.UserDetailsService;
  10 +import org.springframework.security.core.userdetails.UsernameNotFoundException;
  11 +import org.springframework.stereotype.Component;
  12 +import org.springframework.transaction.annotation.Transactional;
  13 +
  14 +import daeucna.config.security.entity.User;
  15 +import daeucna.config.security.repository.UserRepository;
  16 +import lombok.RequiredArgsConstructor;
  17 +
  18 +@Component("userDetailsService")
  19 +@RequiredArgsConstructor
  20 +public class CustomUserDetailsService implements UserDetailsService {
  21 + private final UserRepository userRepository;
  22 +
  23 + @Override
  24 + @Transactional
  25 + // 로그인시에 DB에서 유저정보와 권한정보를 가져와서 해당 정보를 기반으로 userdetails.User 객체를 생성해 리턴
  26 + public UserDetails loadUserByUsername(final String username) {
  27 +
  28 + return userRepository.findOneWithAuthoritiesByUsername(username)
  29 + .map(user -> createUser(username, user))
  30 + .orElseThrow(() -> new UsernameNotFoundException(username + " -> 데이터베이스에서 찾을 수 없습니다."));
  31 + }
  32 +
  33 + private org.springframework.security.core.userdetails.User createUser(String username, User user) {
  34 + if (!user.isActivated()) {
  35 + throw new RuntimeException(username + " -> 활성화되어 있지 않습니다.");
  36 + }
  37 +
  38 + List<GrantedAuthority> grantedAuthorities = user.getAuthorities().stream()
  39 + .map(authority -> new SimpleGrantedAuthority(authority.getAuthorityName()))
  40 + .collect(Collectors.toList());
  41 +
  42 + return new org.springframework.security.core.userdetails.User(user.getUsername(),
  43 + user.getPassword(),
  44 + grantedAuthorities);
  45 + }
  46 +}
0 47 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/service/UserService.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/service/UserService.java
  1 +package daeucna.config.security.service;
  2 +
  3 +import java.util.HashSet;
  4 +import java.util.Iterator;
  5 +import java.util.Set;
  6 +
  7 +import org.springframework.security.crypto.password.PasswordEncoder;
  8 +import org.springframework.stereotype.Service;
  9 +import org.springframework.transaction.annotation.Transactional;
  10 +
  11 +import daeucna.config.security.dto.AuthorityDto;
  12 +import daeucna.config.security.dto.UserDto;
  13 +import daeucna.config.security.entity.Authority;
  14 +import daeucna.config.security.entity.User;
  15 +import daeucna.config.security.repository.UserRepository;
  16 +import daeucna.config.security.utils.CommonJson;
  17 +import daeucna.config.security.utils.DuplicateMemberException;
  18 +import daeucna.config.security.utils.SecurityUtil;
  19 +import lombok.RequiredArgsConstructor;
  20 +import lombok.extern.slf4j.Slf4j;
  21 +
  22 +@Service
  23 +@RequiredArgsConstructor
  24 +@Slf4j
  25 +public class UserService {
  26 + private final UserRepository userRepository;
  27 + private final PasswordEncoder passwordEncoder;
  28 +
  29 + @Transactional
  30 + public UserDto signup(UserDto userDto) {
  31 + if (userRepository.findOneWithAuthoritiesByUsername(userDto.getUsername()).orElse(null) != null) {
  32 + throw new DuplicateMemberException("이미 가입되어 있는 유저입니다.");
  33 + }
  34 +
  35 + Set<Authority> setAuthority = new HashSet<Authority>();
  36 + Set<AuthorityDto> setAuthorityDto = userDto.getAuthorityDtoSet();
  37 + Iterator<AuthorityDto> itAuthorityDto = setAuthorityDto.iterator();
  38 + while(itAuthorityDto.hasNext()) {
  39 + AuthorityDto curAuthorityDto = itAuthorityDto.next();
  40 + setAuthority.add(
  41 + Authority.builder()
  42 + .authorityName(curAuthorityDto.getAuthorityName())
  43 + .build()
  44 + );
  45 +
  46 + log.debug("setAuthority = " + CommonJson.objectToString(setAuthority));
  47 + }
  48 +
  49 +
  50 +
  51 + User user = User.builder()
  52 + .username(userDto.getUsername())
  53 + .password(passwordEncoder.encode(userDto.getPassword()))
  54 + .nickname(userDto.getNickname())
  55 + .authorities(setAuthority)
  56 + .activated(true)
  57 + .build();
  58 +
  59 + return UserDto.from(userRepository.save(user));
  60 + }
  61 +
  62 + @Transactional(readOnly = true)
  63 + public UserDto getUserWithAuthorities(String username) {
  64 + return UserDto.from(userRepository.findOneWithAuthoritiesByUsername(username).orElse(null));
  65 + }
  66 +
  67 + @Transactional(readOnly = true)
  68 + public UserDto getMyUserWithAuthorities() {
  69 + return UserDto.from(SecurityUtil.getCurrentUsername().flatMap(userRepository::findOneWithAuthoritiesByUsername).orElse(null));
  70 + }
  71 +}
0 72 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/utils/CommonJson.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/utils/CommonJson.java
  1 +package daeucna.config.security.utils;
  2 +
  3 +import org.springframework.stereotype.Component;
  4 +
  5 +import com.fasterxml.jackson.databind.ObjectMapper;
  6 +
  7 +@Component
  8 +public class CommonJson {
  9 +
  10 + public static String objectToString(Object object) {
  11 + String rtnVal = "";
  12 + try {
  13 + ObjectMapper objectMapper = new ObjectMapper();
  14 + rtnVal = objectMapper.writeValueAsString(object);
  15 + } catch (Exception e) {
  16 + e.printStackTrace();
  17 + rtnVal = "Error";
  18 + }
  19 + return rtnVal;
  20 + }
  21 +
  22 + public static Object stringToObject(String sJson, Class<?> objClass) {
  23 + Object rtnVal;
  24 + try {
  25 + ObjectMapper objectMapper = new ObjectMapper();
  26 + rtnVal = objectMapper.readValue(sJson, objClass);
  27 + } catch (Exception e) {
  28 + e.printStackTrace();
  29 + rtnVal = "Error";
  30 + }
  31 + return rtnVal;
  32 + }
  33 +
  34 +}
0 35 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/utils/DuplicateMemberException.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/utils/DuplicateMemberException.java
  1 +package daeucna.config.security.utils;
  2 +
  3 +public class DuplicateMemberException extends RuntimeException {
  4 + public DuplicateMemberException() {
  5 + super();
  6 + }
  7 + public DuplicateMemberException(String message, Throwable cause) {
  8 + super(message, cause);
  9 + }
  10 + public DuplicateMemberException(String message) {
  11 + super(message);
  12 + }
  13 + public DuplicateMemberException(Throwable cause) {
  14 + super(cause);
  15 + }
  16 +}
0 17 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/utils/NotFoundMemberException.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/utils/NotFoundMemberException.java
  1 +package daeucna.config.security.utils;
  2 +
  3 +public class NotFoundMemberException extends RuntimeException {
  4 + public NotFoundMemberException() {
  5 + super();
  6 + }
  7 + public NotFoundMemberException(String message, Throwable cause) {
  8 + super(message, cause);
  9 + }
  10 + public NotFoundMemberException(String message) {
  11 + super(message);
  12 + }
  13 + public NotFoundMemberException(Throwable cause) {
  14 + super(cause);
  15 + }
  16 +}
0 17 \ No newline at end of file
... ...
src/main/java/daeucna/config/security/utils/SecurityUtil.java 0 → 100644
  1 +++ a/src/main/java/daeucna/config/security/utils/SecurityUtil.java
  1 +package daeucna.config.security.utils;
  2 +
  3 +import java.util.Optional;
  4 +
  5 +import org.springframework.security.core.Authentication;
  6 +import org.springframework.security.core.context.SecurityContextHolder;
  7 +import org.springframework.security.core.userdetails.UserDetails;
  8 +
  9 +import lombok.extern.slf4j.Slf4j;
  10 +
  11 +@Slf4j
  12 +public class SecurityUtil {
  13 +
  14 + private SecurityUtil() {}
  15 +
  16 + // getCurrentUsername 메소드의 역할은 Security Cont
  17 + public static Optional<String> getCurrentUsername() {
  18 +
  19 + // authentication객체가 저장되는 시점은 JwtFilter의 doFilter 메소드에서
  20 + // Request가 들어올 때 SecurityContext에 Authentication 객체를 저장해서 사용
  21 + final Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
  22 +
  23 + if (authentication == null) {
  24 + log.debug("Security Context에 인증 정보가 없습니다.");
  25 + return Optional.empty();
  26 + }
  27 +
  28 + String username = null;
  29 + if (authentication.getPrincipal() instanceof UserDetails springSecurityUser) {
  30 + username = springSecurityUser.getUsername();
  31 + } else if (authentication.getPrincipal() instanceof String) {
  32 + username = (String) authentication.getPrincipal();
  33 + }
  34 +
  35 + return Optional.ofNullable(username);
  36 + }
  37 +}
0 38 \ No newline at end of file
... ...
src/main/java/daeucna/mapper/primary/batch/MatchingInnerDelingMapper.java 0 → 100644
  1 +++ a/src/main/java/daeucna/mapper/primary/batch/MatchingInnerDelingMapper.java
  1 +package daeucna.mapper.primary.batch;
  2 +
  3 +import java.util.List;
  4 +import java.util.Map;
  5 +
  6 +import org.apache.ibatis.annotations.Mapper;
  7 +
  8 +@Mapper
  9 +public interface MatchingInnerDelingMapper {
  10 +
  11 + /*
  12 + * 작업리스트
  13 + */
  14 + @SuppressWarnings("rawtypes")
  15 + List<Map> getCustomItemReadData(Map param);
  16 +
  17 +
  18 + /**
  19 + * 작업키 업데이트 (파라미터 : 자기데이타/상대데이타)
  20 + * @param param
  21 + * @return
  22 + */
  23 + @SuppressWarnings("rawtypes")
  24 + int setDataMakeCompareKy(Map param);
  25 +
  26 +
  27 + /**
  28 + * 매칭작업할 데이타 가져오기(파라미터 : 자기데이타/상대데이타)
  29 + * @param param
  30 + * @return
  31 + */
  32 + @SuppressWarnings("rawtypes")
  33 + List<Map> getMatchingData(Map param);
  34 +
  35 + /**
  36 + * 업데이트할 데이타 가져오기(파라미터 : 자기데이타/상대데이타)
  37 + * @param param
  38 + * @return
  39 + */
  40 + @SuppressWarnings("rawtypes")
  41 + List<Map> getMatchingResult(Map param);
  42 +
  43 + /**
  44 + * 결과 업데이트
  45 + * @param param
  46 + * @return
  47 + */
  48 + @SuppressWarnings("rawtypes")
  49 + int setResult(Map param);
  50 +
  51 +
  52 +
  53 +
  54 + /**
  55 + * Original Data 삭제
  56 + * @param param
  57 + * @return
  58 + */
  59 + @SuppressWarnings("rawtypes")
  60 + int deleteOriginalData(Map param);
  61 +
  62 +
  63 + /**
  64 + * Original Data 생성
  65 + * @param param
  66 + * @return
  67 + */
  68 + @SuppressWarnings("rawtypes")
  69 + int insertOriginalData(Map param);
  70 +
  71 +
  72 + /**
  73 + * 작업영역 데이타 삭제
  74 + * @param param
  75 + * @return
  76 + */
  77 + @SuppressWarnings("rawtypes")
  78 + int deleteData(Map param);
  79 +
  80 + /**
  81 + * 작업영역 데이타 생성(From Original Data)
  82 + * @param param
  83 + * @return
  84 + */
  85 + @SuppressWarnings("rawtypes")
  86 + int insertDataFromOriginal(Map param);
  87 +
  88 + /**
  89 + * 작업영역 ai데이타 삭제
  90 + * @param param
  91 + * @return
  92 + */
  93 + @SuppressWarnings("rawtypes")
  94 + int deleteDataAi(Map param);
  95 +
  96 + /**
  97 + * 작업영역 데이타 생성(From Original Data)
  98 + * @param param
  99 + * @return
  100 + */
  101 + @SuppressWarnings("rawtypes")
  102 + int insertDataAiFromOriginal(Map param);
  103 +
  104 + /**
  105 + * 값을 돌려주기전 월별 새로운 일치키 생성
  106 + * @param param
  107 + * @return
  108 + */
  109 + @SuppressWarnings("rawtypes")
  110 + int updateNewMatchKey(Map param);
  111 +
  112 + /**
  113 + * Extra matching을 위한 자료 조회
  114 + * @param param
  115 + * @return
  116 + */
  117 + @SuppressWarnings("rawtypes")
  118 + List<Map> getMatchingExtraDataOne(Map param);
  119 +
  120 + /**
  121 + * Extra matching을 위한 자료 조회
  122 + * @param param
  123 + * @return
  124 + */
  125 + @SuppressWarnings("rawtypes")
  126 + List<Map> getMatchingExtraDataTwo(Map param);
  127 +
  128 + /**
  129 + * Extra matching 데이타 적용
  130 + * @param param
  131 + * @return
  132 + */
  133 + @SuppressWarnings("rawtypes")
  134 + int setExtraResult(Map param);
  135 +
  136 + /**
  137 + * User Job Start
  138 + * @param param
  139 + * @return
  140 + */
  141 + @SuppressWarnings("rawtypes")
  142 + int createUserJob(Map param);
  143 +
  144 + /**
  145 + * User Job End
  146 + * @param param
  147 + * @return
  148 + */
  149 + @SuppressWarnings("rawtypes")
  150 + int finishUserJob(Map param);
  151 +
  152 + /*
  153 + * ai 작업리스트
  154 + */
  155 + @SuppressWarnings("rawtypes")
  156 + List<Map> getAiReadData(Map param);
  157 +
  158 +}
0 159 \ No newline at end of file
... ...
src/main/java/daeucna/mapper/primary/system/CodeMapper.java 0 → 100644
  1 +++ a/src/main/java/daeucna/mapper/primary/system/CodeMapper.java
  1 +package daeucna.mapper.primary.system;
  2 +
  3 +import java.util.List;
  4 +
  5 +import org.apache.ibatis.annotations.Mapper;
  6 +
  7 +import daeucna.system.code.CodeDto;
  8 +
  9 +@Mapper
  10 +public interface CodeMapper {
  11 + List<CodeDto> getCmmnCode(CodeDto param);
  12 +}
0 13 \ No newline at end of file
... ...
src/main/java/daeucna/mapper/secondary/batch/OracleMapper.java 0 → 100644
  1 +++ a/src/main/java/daeucna/mapper/secondary/batch/OracleMapper.java
  1 +package daeucna.mapper.secondary.batch;
  2 +
  3 +import java.util.List;
  4 +import java.util.Map;
  5 +
  6 +import org.apache.ibatis.annotations.Mapper;
  7 +
  8 +@Mapper
  9 +public interface OracleMapper {
  10 +
  11 + /*
  12 + * Original Data 조회
  13 + */
  14 + @SuppressWarnings("rawtypes")
  15 + List<Map> getOriginalData(Map param);
  16 +
  17 + /*
  18 + * Original Data 조회
  19 + */
  20 + @SuppressWarnings("rawtypes")
  21 + List<Map> getMatchingInfo(Map param);
  22 +
  23 + /**
  24 + * 원 테이블에 결과값 업데이트
  25 + * @param param
  26 + * @return
  27 + */
  28 + @SuppressWarnings("rawtypes")
  29 + int updateMatchingResult(Map param);
  30 +
  31 +
  32 +}
0 33 \ No newline at end of file
... ...
src/main/java/daeucna/system/code/CodeController.java 0 → 100644
  1 +++ a/src/main/java/daeucna/system/code/CodeController.java
  1 +package daeucna.system.code;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.List;
  5 +
  6 +import org.springframework.beans.factory.annotation.Autowired;
  7 +import org.springframework.http.ResponseEntity;
  8 +import org.springframework.web.bind.annotation.GetMapping;
  9 +import org.springframework.web.bind.annotation.PostMapping;
  10 +import org.springframework.web.bind.annotation.RequestBody;
  11 +import org.springframework.web.bind.annotation.RequestMapping;
  12 +import org.springframework.web.bind.annotation.RestController;
  13 +
  14 +import daeucna.system.code.CodeDto;
  15 +import lombok.RequiredArgsConstructor;
  16 +
  17 +@RestController
  18 +@RequiredArgsConstructor
  19 +@RequestMapping("/api/code")
  20 +public class CodeController {
  21 + @Autowired
  22 + private final CodeService codeService;
  23 +
  24 + @PostMapping("/cmmncode")
  25 + public ResponseEntity<List<CodeDto>> getCmmnCode(@RequestBody CodeDto param) {
  26 + List<CodeDto> rtnVal = new ArrayList<CodeDto>();
  27 +
  28 + rtnVal = codeService.getCmmnCode(param);
  29 +
  30 + return ResponseEntity.ok(rtnVal);
  31 + }
  32 +
  33 +}
0 34 \ No newline at end of file
... ...
src/main/java/daeucna/system/code/CodeDto.java 0 → 100644
  1 +++ a/src/main/java/daeucna/system/code/CodeDto.java
  1 +package daeucna.system.code;
  2 +
  3 +import java.math.BigDecimal;
  4 +
  5 +import lombok.Data;
  6 +
  7 +@Data
  8 +public class CodeDto {
  9 +
  10 + private String codeTy;
  11 + private String cmmnCode;
  12 +
  13 + private String mngIem1;
  14 + private String mngIem2;
  15 + private String mngIem3;
  16 + private String mngIem4;
  17 + private BigDecimal ordr;
  18 + private String useAt;
  19 +
  20 + private String lcal;
  21 + private String cmmnCodeNm;
  22 +
  23 + private String register;
  24 + private String inputDe;
  25 + private String updusr;
  26 + private String updtDe;
  27 +
  28 +}
0 29 \ No newline at end of file
... ...
src/main/java/daeucna/system/code/CodeService.java 0 → 100644
  1 +++ a/src/main/java/daeucna/system/code/CodeService.java
  1 +package daeucna.system.code;
  2 +
  3 +import java.util.List;
  4 +
  5 +public interface CodeService {
  6 +
  7 + @SuppressWarnings("rawtypes")
  8 + public List<CodeDto> getCmmnCode(CodeDto param);
  9 +
  10 +}
0 11 \ No newline at end of file
... ...
src/main/java/daeucna/system/code/CodeServiceImpl.java 0 → 100644
  1 +++ a/src/main/java/daeucna/system/code/CodeServiceImpl.java
  1 +package daeucna.system.code;
  2 +
  3 +import java.util.ArrayList;
  4 +import java.util.List;
  5 +
  6 +import org.springframework.beans.factory.annotation.Autowired;
  7 +import org.springframework.stereotype.Repository;
  8 +import org.springframework.stereotype.Service;
  9 +import org.springframework.transaction.annotation.Propagation;
  10 +import org.springframework.transaction.annotation.Transactional;
  11 +
  12 +import daeucna.mapper.primary.system.CodeMapper;
  13 +import lombok.RequiredArgsConstructor;
  14 +import lombok.extern.slf4j.Slf4j;
  15 +
  16 +@Service
  17 +@RequiredArgsConstructor
  18 +@Slf4j
  19 +@Repository
  20 +@Transactional(propagation = Propagation.REQUIRED, rollbackFor={Exception.class})
  21 +public class CodeServiceImpl implements CodeService {
  22 + @Autowired
  23 + private CodeMapper codeMapper;
  24 +
  25 +
  26 + @Override
  27 + public List<CodeDto> getCmmnCode(CodeDto param) {
  28 + List<CodeDto> lCodeDto = new ArrayList<CodeDto>();
  29 +
  30 + lCodeDto = codeMapper.getCmmnCode(param);
  31 +
  32 + log.info("CodeServiceImpl");
  33 + return lCodeDto;
  34 + }
  35 +
  36 +}
0 37 \ No newline at end of file
... ...
src/main/resources/application.properties 0 → 100644
  1 +++ a/src/main/resources/application.properties
  1 +server.port=8080
  2 +
  3 +spring.mvc.converters.preferred-json-mapper=gson
  4 +
  5 +spring.mvc.view.prefix=/
  6 +spring.mvc.view.suffix: .html
  7 +spring.mvc.hiddenmethod.filter.enabled=true
  8 +
  9 +spring.main.allow-bean-definition-overriding=true
  10 +
  11 +## JPA
  12 +spring.jpa.database-platform=org.hibernate.dialect.PostgreSQLDialect
  13 +spring.jpa.generate-ddl=true
  14 +spring.jpa.hibernate.ddl-auto=update
  15 +spring.jpa.defer-datasource-initialization=true
  16 +
  17 +## Datasource
  18 +# primary
  19 +spring.datasource.hikari.primary.driver-class-name=org.postgresql.Driver
  20 +spring.datasource.hikari.primary.jdbc-url=jdbc:postgresql://daeuserver.iptime.org:20430/account
  21 +spring.datasource.hikari.primary.username=account
  22 +spring.datasource.hikari.primary.password=daeucna10!
  23 +
  24 +# secondary
  25 +#spring.datasource.hikari.secondary.driver-class-name=oracle.jdbc.driver.OracleDriver
  26 +#spring.datasource.hikari.secondary.jdbc-url=jdbc:oracle:thin:@vanguardlab.kr:63522/CONFINAS19C
  27 +#spring.datasource.hikari.secondary.username=ai
  28 +#spring.datasource.hikari.secondary.password=ai
  29 +spring.datasource.hikari.secondary.driver-class-name=oracle.jdbc.driver.OracleDriver
  30 +spring.datasource.hikari.secondary.jdbc-url=jdbc:oracle:thin:@daeuserver2.iptime.org:1521/orcl
  31 +spring.datasource.hikari.secondary.username=CONFINAS3
  32 +spring.datasource.hikari.secondary.password=CONFINAS3
  33 +
  34 +
  35 +spring.sql.encoding=UTF-8
  36 +spring.sql.init.mode=always
  37 +
  38 +spring.batch.jdbc.initialize-schema=always
  39 +#스프링잡 자동시작 옵션
  40 +spring.batch.job.enabled=false
  41 +
  42 +spring.devtools.livereload.enabled=true
  43 +spring.devtools.restart.enabled=true
  44 +
  45 +#p6spy query logging
  46 +decorator.datasource.p6spy.enable-logging=true
  47 +
  48 +logging.level.root=info
  49 +logging.level.daeucna=debug
  50 +logging.level.p6spy=debug
  51 +
  52 +## Python 프로퍼티 설정
  53 +pytyon.path=D:\\Programs\\devp\\python-3.12.2\\python.exe
  54 +python.ai.target=D:\\Working\\Python\\Test1.py
  55 +
  56 +## JWT
  57 +jwt.header=Authorization
  58 +# HS512 알고리즘을 사용할 것이기 때문에 512bit, 즉 64byte 이상의 secret key를 사용
  59 +# echo 'jsh-springboot-and-jwt-tutorial-this-is-for-generating-jwt-secretkey-base64'|base64
  60 +jwt.secret=4oCYc2lsdmVybmluZS10ZWNoLXNwcmluZy1ib290LWp3dC10dXRvcmlhbC1zZWNyZXQtc2lsdmVybmluZS10ZWNoLXNwcmluZy1ib290LWp3dC10dXRvcmlhbC1zZWNyZXTigJkK
  61 +jwt.token-validity-in-seconds=60
  62 +jwt.refresh-token-validity-in-seconds=86400
... ...
src/main/resources/data.sql 0 → 100644
  1 +++ a/src/main/resources/data.sql
  1 +MERGE INTO authority m
  2 +USING (
  3 + SELECT
  4 + 'ROLE_ADMIN' as authority_name
  5 + ) s
  6 +ON
  7 + m.authority_name = s.authority_name
  8 +WHEN NOT MATCHED THEN
  9 + INSERT (authority_name) VALUES (s.authority_name);
  10 +
  11 +MERGE INTO authority m
  12 +USING (
  13 + SELECT
  14 + 'ROLE_USER' as authority_name
  15 + ) s
  16 +ON
  17 + m.authority_name = s.authority_name
  18 +WHEN NOT MATCHED THEN
  19 + INSERT (authority_name) VALUES (s.authority_name);
  20 +
  21 +MERGE INTO users m
  22 +USING (
  23 + SELECT
  24 + 1 as user_id,
  25 + true as activated,
  26 + 'sangkiham' as nickname,
  27 + '$2a$10$nyHQj.Nj2tID4UzIkd1/SuMeYwlKaaHT8Gi3Wgg2x/h9K9qLQciLO' as password,
  28 + 'sangkiham' as username
  29 + ) s
  30 +ON
  31 + m.user_id = s.user_id
  32 +WHEN NOT MATCHED THEN
  33 + INSERT (user_id, activated, nickname, password, username) VALUES (s.user_id, s.activated, s.nickname, s.password, s.username);
  34 +
  35 +MERGE INTO user_authority m
  36 +USING (
  37 + SELECT
  38 + 1 as user_id,
  39 + 'ROLE_ADMIN' as authority_name
  40 + ) s
  41 +ON
  42 + m.user_id = s.user_id
  43 + and m.authority_name = s.authority_name
  44 +WHEN NOT MATCHED THEN
  45 + INSERT (user_id, authority_name) VALUES (s.user_id, s.authority_name);
... ...
src/main/resources/matchingSetup.json 0 → 100644
  1 +++ a/src/main/resources/matchingSetup.json
  1 +{
  2 + "matchingSetup": [
  3 + {
  4 + "active": true,
  5 + "type": "A-A",
  6 + "typeName": "자기수익(대사키),상대비용(대사키),비교(년월,비교키,거래금액)",
  7 +
  8 + "condOne": {
  9 + "cond": [
  10 + "dta_ty in ('11','21')",
  11 + "mtch_ty is null",
  12 + "cmpnsp_ky is not null",
  13 + "cmpnsp_ky != ''"
  14 + ],
  15 + "makeCompareKey": [
  16 + "cmpnsp_ky"
  17 + ]
  18 + },
  19 + "condTwo": {
  20 + "cond": [
  21 + "dta_ty in ('12','22')",
  22 + "mtch_ty is null",
  23 + "cmpnsp_ky is not null",
  24 + "cmpnsp_ky != ''"
  25 + ],
  26 + "makeCompareKey": [
  27 + "cmpnsp_ky"
  28 + ]
  29 + },
  30 + "uniqueKey": [
  31 + "sys_se",
  32 + "accnut_ym",
  33 + "sn"
  34 + ],
  35 + "compareKey": "compare_ky",
  36 + "amtField": "sum(delng_amt) as delng_amt",
  37 + "compareField": [
  38 + "accnut_ym",
  39 + "compare_ky",
  40 + "delng_amt"
  41 + ],
  42 + "matchingType": "mtch_ty",
  43 + "matchingTypeName": "mtch_ty_nm",
  44 + "matchingNumber": "mtch_ky"
  45 + },
  46 + {
  47 + "active": true,
  48 + "type": "A-B",
  49 + "typeName": "자기채권(대사키),상대채무(대사키),비교(년월,비교키,거래금액)",
  50 +
  51 + "condOne": {
  52 + "cond": [
  53 + "dta_ty in ('31','33','35','37','41')",
  54 + "mtch_ty is null",
  55 + "cmpnsp_ky is not null",
  56 + "cmpnsp_ky != ''"
  57 + ],
  58 + "makeCompareKey": [
  59 + "cmpnsp_ky"
  60 + ]
  61 + },
  62 + "condTwo": {
  63 + "cond": [
  64 + "dta_ty in ('32','34','36','38','42')",
  65 + "mtch_ty is null",
  66 + "cmpnsp_ky is not null",
  67 + "cmpnsp_ky != ''"
  68 + ],
  69 + "makeCompareKey": [
  70 + "cmpnsp_ky"
  71 + ]
  72 + },
  73 + "uniqueKey": [
  74 + "sys_se",
  75 + "accnut_ym",
  76 + "sn"
  77 + ],
  78 + "compareKey": "compare_ky",
  79 + "amtField": "sum(delng_amt) as delng_amt",
  80 + "compareField": [
  81 + "accnut_ym",
  82 + "compare_ky",
  83 + "delng_amt"
  84 + ],
  85 + "matchingType": "mtch_ty",
  86 + "matchingTypeName": "mtch_ty_nm",
  87 + "matchingNumber": "mtch_ky"
  88 + },
  89 +
  90 +
  91 +
  92 +
  93 + {
  94 + "active": true,
  95 + "type": "B-A",
  96 + "typeName": "자기수익(합산키),상대비용(합산키),비교(년월,거래금액)",
  97 +
  98 + "condOne": {
  99 + "cond": [
  100 + "dta_ty in ('11','21')",
  101 + "mtch_ty is null",
  102 + "ext_key1 is not null",
  103 + "ext_key1 != ''"
  104 + ],
  105 + "makeCompareKey": [
  106 + "ext_key1"
  107 + ]
  108 + },
  109 + "condTwo": {
  110 + "cond": [
  111 + "dta_ty in ('12','22')",
  112 + "mtch_ty is null",
  113 + "ext_key1 is not null",
  114 + "ext_key1 != ''"
  115 + ],
  116 + "makeCompareKey": [
  117 + "ext_key1"
  118 + ]
  119 + },
  120 + "uniqueKey": [
  121 + "sys_se",
  122 + "accnut_ym",
  123 + "sn"
  124 + ],
  125 + "compareKey": "compare_ky",
  126 + "amtField": "sum(delng_amt) as delng_amt",
  127 + "compareField": [
  128 + "accnut_ym",
  129 + "delng_amt"
  130 + ],
  131 + "matchingType": "mtch_ty",
  132 + "matchingTypeName": "mtch_ty_nm",
  133 + "matchingNumber": "mtch_ky"
  134 + },
  135 + {
  136 + "active": true,
  137 + "type": "B-B",
  138 + "typeName": "자기채권(합산키),상대채무(합산키),비교(년월,거래금액)",
  139 +
  140 + "condOne": {
  141 + "cond": [
  142 + "dta_ty in ('31','33','35','37','41')",
  143 + "mtch_ty is null",
  144 + "ext_key1 is not null",
  145 + "ext_key1 != ''"
  146 + ],
  147 + "makeCompareKey": [
  148 + "ext_key1"
  149 + ]
  150 + },
  151 + "condTwo": {
  152 + "cond": [
  153 + "dta_ty in ('32','34','36','38','42')",
  154 + "mtch_ty is null",
  155 + "ext_key1 is not null",
  156 + "ext_key1 != ''"
  157 + ],
  158 + "makeCompareKey": [
  159 + "ext_key1"
  160 + ]
  161 + },
  162 + "uniqueKey": [
  163 + "sys_se",
  164 + "accnut_ym",
  165 + "sn"
  166 + ],
  167 + "compareKey": "compare_ky",
  168 + "amtField": "sum(delng_amt) as delng_amt",
  169 + "compareField": [
  170 + "accnut_ym",
  171 + "delng_amt"
  172 + ],
  173 + "matchingType": "mtch_ty",
  174 + "matchingTypeName": "mtch_ty_nm",
  175 + "matchingNumber": "mtch_ky"
  176 + },
  177 +
  178 +
  179 +
  180 +
  181 +
  182 +
  183 + {
  184 + "active": true,
  185 + "type": "C-A",
  186 + "typeName": "자기수익(전표번호),상대비용(전표번호),비교(년월,거래금액)",
  187 +
  188 + "condOne": {
  189 + "cond": [
  190 + "dta_ty in ('11','21')",
  191 + "mtch_ty is null",
  192 + "chit_no is not null",
  193 + "chit_no != ''"
  194 + ],
  195 + "makeCompareKey": [
  196 + "chit_no"
  197 + ]
  198 + },
  199 + "condTwo": {
  200 + "cond": [
  201 + "dta_ty in ('12','22')",
  202 + "mtch_ty is null",
  203 + "chit_no is not null",
  204 + "chit_no != ''"
  205 + ],
  206 + "makeCompareKey": [
  207 + "chit_no"
  208 + ]
  209 + },
  210 + "uniqueKey": [
  211 + "sys_se",
  212 + "accnut_ym",
  213 + "sn"
  214 + ],
  215 + "compareKey": "compare_ky",
  216 + "amtField": "sum(delng_amt) as delng_amt",
  217 + "compareField": [
  218 + "accnut_ym",
  219 + "delng_amt"
  220 + ],
  221 + "matchingType": "mtch_ty",
  222 + "matchingTypeName": "mtch_ty_nm",
  223 + "matchingNumber": "mtch_ky"
  224 + },
  225 + {
  226 + "active": true,
  227 + "type": "C-B",
  228 + "typeName": "자기채권(전표번호),상대채무(전표번호),비교(년월,거래금액)",
  229 +
  230 + "condOne": {
  231 + "cond": [
  232 + "dta_ty in ('31','33','35','37','41')",
  233 + "mtch_ty is null",
  234 + "chit_no is not null",
  235 + "chit_no != ''"
  236 + ],
  237 + "makeCompareKey": [
  238 + "chit_no"
  239 + ]
  240 + },
  241 + "condTwo": {
  242 + "cond": [
  243 + "dta_ty in ('32','34','36','38','42')",
  244 + "mtch_ty is null",
  245 + "chit_no is not null"
  246 + ],
  247 + "makeCompareKey": [
  248 + "chit_no"
  249 + ]
  250 + },
  251 + "uniqueKey": [
  252 + "sys_se",
  253 + "accnut_ym",
  254 + "sn"
  255 + ],
  256 + "compareKey": "compare_ky",
  257 + "amtField": "sum(delng_amt) as delng_amt",
  258 + "compareField": [
  259 + "accnut_ym",
  260 + "delng_amt"
  261 + ],
  262 + "matchingType": "mtch_ty",
  263 + "matchingTypeName": "mtch_ty_nm",
  264 + "matchingNumber": "mtch_ky"
  265 + },
  266 +
  267 +
  268 +
  269 +
  270 +
  271 +
  272 + {
  273 + "active": true,
  274 + "type": "D-A",
  275 + "typeName": "자기수익(거래일자),상대비용(거래일자),비교(년월,거래금액)",
  276 +
  277 + "condOne": {
  278 + "cond": [
  279 + "dta_ty in ('11','21')",
  280 + "mtch_ty is null"
  281 + ],
  282 + "makeCompareKey": [
  283 + "delng_de"
  284 + ]
  285 + },
  286 + "condTwo": {
  287 + "cond": [
  288 + "dta_ty in ('12','22')",
  289 + "mtch_ty is null"
  290 + ],
  291 + "makeCompareKey": [
  292 + "delng_de"
  293 + ]
  294 + },
  295 + "uniqueKey": [
  296 + "sys_se",
  297 + "accnut_ym",
  298 + "sn"
  299 + ],
  300 + "compareKey": "compare_ky",
  301 + "amtField": "sum(delng_amt) as delng_amt",
  302 + "compareField": [
  303 + "accnut_ym",
  304 + "delng_amt"
  305 + ],
  306 + "matchingType": "mtch_ty",
  307 + "matchingTypeName": "mtch_ty_nm",
  308 + "matchingNumber": "mtch_ky"
  309 + },
  310 + {
  311 + "active": true,
  312 + "type": "D-B",
  313 + "typeName": "자기채권(거래일자),상대채무(거래일자),비교(년월,거래금액)",
  314 +
  315 + "condOne": {
  316 + "cond": [
  317 + "dta_ty in ('31','33','35','37','41')",
  318 + "mtch_ty is null"
  319 + ],
  320 + "makeCompareKey": [
  321 + "delng_de"
  322 + ]
  323 + },
  324 + "condTwo": {
  325 + "cond": [
  326 + "dta_ty in ('32','34','36','38','42')",
  327 + "mtch_ty is null"
  328 + ],
  329 + "makeCompareKey": [
  330 + "delng_de"
  331 + ]
  332 + },
  333 + "uniqueKey": [
  334 + "sys_se",
  335 + "accnut_ym",
  336 + "sn"
  337 + ],
  338 + "compareKey": "compare_ky",
  339 + "amtField": "sum(delng_amt) as delng_amt",
  340 + "compareField": [
  341 + "accnut_ym",
  342 + "delng_amt"
  343 + ],
  344 + "matchingType": "mtch_ty",
  345 + "matchingTypeName": "mtch_ty_nm",
  346 + "matchingNumber": "mtch_ky"
  347 + },
  348 +
  349 +
  350 +
  351 +
  352 +
  353 + {
  354 + "active": true,
  355 + "type": "E-A",
  356 + "typeName": "자기수익(거래월),상대비용(거래월),비교(년월,거래금액)",
  357 +
  358 + "condOne": {
  359 + "cond": [
  360 + "dta_ty in ('11','21')",
  361 + "mtch_ty is null"
  362 + ],
  363 + "makeCompareKey": [
  364 + "substring(delng_de,1,6)"
  365 + ]
  366 + },
  367 + "condTwo": {
  368 + "cond": [
  369 + "dta_ty in ('12','22')",
  370 + "mtch_ty is null"
  371 + ],
  372 + "makeCompareKey": [
  373 + "substring(delng_de,1,6)"
  374 + ]
  375 + },
  376 + "uniqueKey": [
  377 + "sys_se",
  378 + "accnut_ym",
  379 + "sn"
  380 + ],
  381 + "compareKey": "compare_ky",
  382 + "amtField": "sum(delng_amt) as delng_amt",
  383 + "compareField": [
  384 + "accnut_ym",
  385 + "delng_amt"
  386 + ],
  387 + "matchingType": "mtch_ty",
  388 + "matchingTypeName": "mtch_ty_nm",
  389 + "matchingNumber": "mtch_ky"
  390 + },
  391 + {
  392 + "active": true,
  393 + "type": "E-B",
  394 + "typeName": "자기채권(거래월),상대채무(거래월),비교(년월,거래금액)",
  395 +
  396 + "condOne": {
  397 + "cond": [
  398 + "dta_ty in ('31','33','35','37','41')",
  399 + "mtch_ty is null"
  400 + ],
  401 + "makeCompareKey": [
  402 + "substring(delng_de,1,6)"
  403 + ]
  404 + },
  405 + "condTwo": {
  406 + "cond": [
  407 + "dta_ty in ('32','34','36','38','42')",
  408 + "mtch_ty is null"
  409 + ],
  410 + "makeCompareKey": [
  411 + "substring(delng_de,1,6)"
  412 + ]
  413 + },
  414 + "uniqueKey": [
  415 + "sys_se",
  416 + "accnut_ym",
  417 + "sn"
  418 + ],
  419 + "compareKey": "compare_ky",
  420 + "amtField": "sum(delng_amt) as delng_amt",
  421 + "compareField": [
  422 + "accnut_ym",
  423 + "delng_amt"
  424 + ],
  425 + "matchingType": "mtch_ty",
  426 + "matchingTypeName": "mtch_ty_nm",
  427 + "matchingNumber": "mtch_ky"
  428 + },
  429 +
  430 +
  431 +
  432 +
  433 +
  434 +
  435 +
  436 +
  437 + {
  438 + "active": true,
  439 + "type": "F-A",
  440 + "typeName": "자기수익(전체),상대비용(전체),비교(년월,거래금액)",
  441 +
  442 + "condOne": {
  443 + "cond": [
  444 + "dta_ty in ('11','21')",
  445 + "mtch_ty is null"
  446 + ],
  447 + "makeCompareKey": [
  448 + "sys_se",
  449 + "accnut_ym"
  450 + ]
  451 + },
  452 + "condTwo": {
  453 + "cond": [
  454 + "dta_ty in ('12','22')",
  455 + "mtch_ty is null"
  456 + ],
  457 + "makeCompareKey": [
  458 + "sys_se",
  459 + "accnut_ym"
  460 + ]
  461 + },
  462 + "uniqueKey": [
  463 + "sys_se",
  464 + "accnut_ym",
  465 + "sn"
  466 + ],
  467 + "compareKey": "compare_ky",
  468 + "amtField": "sum(delng_amt) as delng_amt",
  469 + "compareField": [
  470 + "accnut_ym",
  471 + "delng_amt"
  472 + ],
  473 + "matchingType": "mtch_ty",
  474 + "matchingTypeName": "mtch_ty_nm",
  475 + "matchingNumber": "mtch_ky"
  476 + },
  477 + {
  478 + "active": true,
  479 + "type": "F-B",
  480 + "typeName": "자기채권(전체),상대채무(전체),비교(년월,거래금액)",
  481 +
  482 + "condOne": {
  483 + "cond": [
  484 + "dta_ty in ('31','33','35','37','41')",
  485 + "mtch_ty is null"
  486 + ],
  487 + "makeCompareKey": [
  488 + "sys_se",
  489 + "accnut_ym"
  490 + ]
  491 + },
  492 + "condTwo": {
  493 + "cond": [
  494 + "dta_ty in ('32','34','36','38','42')",
  495 + "mtch_ty is null"
  496 + ],
  497 + "makeCompareKey": [
  498 + "sys_se",
  499 + "accnut_ym"
  500 + ]
  501 + },
  502 + "uniqueKey": [
  503 + "sys_se",
  504 + "accnut_ym",
  505 + "sn"
  506 + ],
  507 + "compareKey": "compare_ky",
  508 + "amtField": "sum(delng_amt) as delng_amt",
  509 + "compareField": [
  510 + "accnut_ym",
  511 + "delng_amt"
  512 + ],
  513 + "matchingType": "mtch_ty",
  514 + "matchingTypeName": "mtch_ty_nm",
  515 + "matchingNumber": "mtch_ky"
  516 + },
  517 +
  518 +
  519 +
  520 +
  521 +
  522 + {
  523 + "active": true,
  524 + "type": "G-A",
  525 + "typeName": "개별자기수익,상대개별비용,비교(년월,거래금액)",
  526 +
  527 + "condOne": {
  528 + "cond": [
  529 + "dta_ty in ('11','21')",
  530 + "mtch_ty is null"
  531 + ],
  532 + "makeCompareKey": [
  533 + "sys_se",
  534 + "accnut_ym",
  535 + "cast(sn as text)"
  536 + ]
  537 + },
  538 + "condTwo": {
  539 + "cond": [
  540 + "dta_ty in ('12','22')",
  541 + "mtch_ty is null"
  542 + ],
  543 + "makeCompareKey": [
  544 + "sys_se",
  545 + "accnut_ym",
  546 + "cast(sn as text)"
  547 + ]
  548 + },
  549 + "uniqueKey": [
  550 + "sys_se",
  551 + "accnut_ym",
  552 + "sn"
  553 + ],
  554 + "compareKey": "compare_ky",
  555 + "amtField": "sum(delng_amt) as delng_amt",
  556 + "compareField": [
  557 + "accnut_ym",
  558 + "delng_amt"
  559 + ],
  560 + "matchingType": "mtch_ty",
  561 + "matchingTypeName": "mtch_ty_nm",
  562 + "matchingNumber": "mtch_ky"
  563 + },
  564 + {
  565 + "active": true,
  566 + "type": "G-B",
  567 + "typeName": "개별자기채권,상대개별채무,비교(년월,거래금액)",
  568 +
  569 + "condOne": {
  570 + "cond": [
  571 + "dta_ty in ('31','33','35','37','41')",
  572 + "mtch_ty is null"
  573 + ],
  574 + "makeCompareKey": [
  575 + "sys_se",
  576 + "accnut_ym",
  577 + "cast(sn as text)"
  578 + ]
  579 + },
  580 + "condTwo": {
  581 + "cond": [
  582 + "dta_ty in ('32','34','36','38','42')",
  583 + "mtch_ty is null"
  584 + ],
  585 + "makeCompareKey": [
  586 + "sys_se",
  587 + "accnut_ym",
  588 + "cast(sn as text)"
  589 + ]
  590 + },
  591 + "uniqueKey": [
  592 + "sys_se",
  593 + "accnut_ym",
  594 + "sn"
  595 + ],
  596 + "compareKey": "compare_ky",
  597 + "amtField": "sum(delng_amt) as delng_amt",
  598 + "compareField": [
  599 + "accnut_ym",
  600 + "delng_amt"
  601 + ],
  602 + "matchingType": "mtch_ty",
  603 + "matchingTypeName": "mtch_ty_nm",
  604 + "matchingNumber": "mtch_ky"
  605 + },
  606 +
  607 +
  608 +
  609 +
  610 +
  611 +
  612 +
  613 +
  614 + {
  615 + "active": true,
  616 + "type": "H-AA",
  617 + "typeName": "자기수익(거래일자),개별상대비용,비교(년월,거래금액)",
  618 +
  619 + "condOne": {
  620 + "cond": [
  621 + "dta_ty in ('11','21')",
  622 + "mtch_ty is null"
  623 + ],
  624 + "makeCompareKey": [
  625 + "sys_se",
  626 + "accnut_ym",
  627 + "delng_de"
  628 + ]
  629 + },
  630 + "condTwo": {
  631 + "cond": [
  632 + "dta_ty in ('12','22')",
  633 + "mtch_ty is null"
  634 + ],
  635 + "makeCompareKey": [
  636 + "sys_se",
  637 + "accnut_ym",
  638 + "cast(sn as text)"
  639 + ]
  640 + },
  641 + "uniqueKey": [
  642 + "sys_se",
  643 + "accnut_ym",
  644 + "sn"
  645 + ],
  646 + "compareKey": "compare_ky",
  647 + "amtField": "sum(delng_amt) as delng_amt",
  648 + "compareField": [
  649 + "accnut_ym",
  650 + "delng_amt"
  651 + ],
  652 + "matchingType": "mtch_ty",
  653 + "matchingTypeName": "mtch_ty_nm",
  654 + "matchingNumber": "mtch_ky"
  655 + },
  656 + {
  657 + "active": true,
  658 + "type": "H-AB",
  659 + "typeName": "자기수익(거래월),개별상대비용,비교(년월,거래금액)",
  660 +
  661 + "condOne": {
  662 + "cond": [
  663 + "dta_ty in ('11','21')",
  664 + "mtch_ty is null"
  665 + ],
  666 + "makeCompareKey": [
  667 + "sys_se",
  668 + "accnut_ym",
  669 + "substring(delng_de,1,6)" ]
  670 + },
  671 + "condTwo": {
  672 + "cond": [
  673 + "dta_ty in ('12','22')",
  674 + "mtch_ty is null"
  675 + ],
  676 + "makeCompareKey": [
  677 + "sys_se",
  678 + "accnut_ym",
  679 + "cast(sn as text)"
  680 + ]
  681 + },
  682 + "uniqueKey": [
  683 + "sys_se",
  684 + "accnut_ym",
  685 + "sn"
  686 + ],
  687 + "compareKey": "compare_ky",
  688 + "amtField": "sum(delng_amt) as delng_amt",
  689 + "compareField": [
  690 + "accnut_ym",
  691 + "delng_amt"
  692 + ],
  693 + "matchingType": "mtch_ty",
  694 + "matchingTypeName": "mtch_ty_nm",
  695 + "matchingNumber": "mtch_ky"
  696 + },
  697 + {
  698 + "active": true,
  699 + "type": "H-AC",
  700 + "typeName": "자기수익(전표번호),개별상대비용,비교(년월,거래금액)",
  701 +
  702 + "condOne": {
  703 + "cond": [
  704 + "dta_ty in ('11','21')",
  705 + "mtch_ty is null",
  706 + "chit_no is not null",
  707 + "chit_no != ''"
  708 + ],
  709 + "makeCompareKey": [
  710 + "sys_se",
  711 + "accnut_ym",
  712 + "chit_no" ]
  713 + },
  714 + "condTwo": {
  715 + "cond": [
  716 + "dta_ty in ('12','22')",
  717 + "mtch_ty is null"
  718 + ],
  719 + "makeCompareKey": [
  720 + "sys_se",
  721 + "accnut_ym",
  722 + "cast(sn as text)"
  723 + ]
  724 + },
  725 + "uniqueKey": [
  726 + "sys_se",
  727 + "accnut_ym",
  728 + "sn"
  729 + ],
  730 + "compareKey": "compare_ky",
  731 + "amtField": "sum(delng_amt) as delng_amt",
  732 + "compareField": [
  733 + "accnut_ym",
  734 + "delng_amt"
  735 + ],
  736 + "matchingType": "mtch_ty",
  737 + "matchingTypeName": "mtch_ty_nm",
  738 + "matchingNumber": "mtch_ky"
  739 + },
  740 + {
  741 + "active": true,
  742 + "type": "H-AD",
  743 + "typeName": "자기수익(합산키),개별상대비용,비교(년월,거래금액)",
  744 +
  745 + "condOne": {
  746 + "cond": [
  747 + "dta_ty in ('11','21')",
  748 + "mtch_ty is null",
  749 + "ext_key1 is not null",
  750 + "ext_key1 != ''"
  751 + ],
  752 + "makeCompareKey": [
  753 + "sys_se",
  754 + "accnut_ym",
  755 + "ext_key1" ]
  756 + },
  757 + "condTwo": {
  758 + "cond": [
  759 + "dta_ty in ('12','22')",
  760 + "mtch_ty is null"
  761 + ],
  762 + "makeCompareKey": [
  763 + "sys_se",
  764 + "accnut_ym",
  765 + "cast(sn as text)"
  766 + ]
  767 + },
  768 + "uniqueKey": [
  769 + "sys_se",
  770 + "accnut_ym",
  771 + "sn"
  772 + ],
  773 + "compareKey": "compare_ky",
  774 + "amtField": "sum(delng_amt) as delng_amt",
  775 + "compareField": [
  776 + "accnut_ym",
  777 + "delng_amt"
  778 + ],
  779 + "matchingType": "mtch_ty",
  780 + "matchingTypeName": "mtch_ty_nm",
  781 + "matchingNumber": "mtch_ky"
  782 + },
  783 + {
  784 + "active": true,
  785 + "type": "H-AE",
  786 + "typeName": "자기비용(거래일자),개별상대수익,비교(년월,거래금액)",
  787 +
  788 + "condOne": {
  789 + "cond": [
  790 + "dta_ty in ('12','22')",
  791 + "mtch_ty is null"
  792 + ],
  793 + "makeCompareKey": [
  794 + "sys_se",
  795 + "accnut_ym",
  796 + "delng_de"
  797 + ]
  798 + },
  799 + "condTwo": {
  800 + "cond": [
  801 + "dta_ty in ('11','21')",
  802 + "mtch_ty is null"
  803 + ],
  804 + "makeCompareKey": [
  805 + "sys_se",
  806 + "accnut_ym",
  807 + "cast(sn as text)"
  808 + ]
  809 + },
  810 + "uniqueKey": [
  811 + "sys_se",
  812 + "accnut_ym",
  813 + "sn"
  814 + ],
  815 + "compareKey": "compare_ky",
  816 + "amtField": "sum(delng_amt) as delng_amt",
  817 + "compareField": [
  818 + "accnut_ym",
  819 + "delng_amt"
  820 + ],
  821 + "matchingType": "mtch_ty",
  822 + "matchingTypeName": "mtch_ty_nm",
  823 + "matchingNumber": "mtch_ky"
  824 + },
  825 + {
  826 + "active": true,
  827 + "type": "H-AF",
  828 + "typeName": "자기비용(거래월),개별상대수익,비교(년월,거래금액)",
  829 +
  830 + "condOne": {
  831 + "cond": [
  832 + "dta_ty in ('12','22')",
  833 + "mtch_ty is null"
  834 + ],
  835 + "makeCompareKey": [
  836 + "sys_se",
  837 + "accnut_ym",
  838 + "substring(delng_de,1,6)" ]
  839 + },
  840 + "condTwo": {
  841 + "cond": [
  842 + "dta_ty in ('11','21')",
  843 + "mtch_ty is null"
  844 + ],
  845 + "makeCompareKey": [
  846 + "sys_se",
  847 + "accnut_ym",
  848 + "cast(sn as text)"
  849 + ]
  850 + },
  851 + "uniqueKey": [
  852 + "sys_se",
  853 + "accnut_ym",
  854 + "sn"
  855 + ],
  856 + "compareKey": "compare_ky",
  857 + "amtField": "sum(delng_amt) as delng_amt",
  858 + "compareField": [
  859 + "accnut_ym",
  860 + "delng_amt"
  861 + ],
  862 + "matchingType": "mtch_ty",
  863 + "matchingTypeName": "mtch_ty_nm",
  864 + "matchingNumber": "mtch_ky"
  865 + },
  866 + {
  867 + "active": true,
  868 + "type": "H-AG",
  869 + "typeName": "자기비용(전표번호),개별상대수익,비교(년월,거래금액)",
  870 +
  871 + "condOne": {
  872 + "cond": [
  873 + "dta_ty in ('12','22')",
  874 + "mtch_ty is null",
  875 + "chit_no is not null",
  876 + "chit_no != ''"
  877 + ],
  878 + "makeCompareKey": [
  879 + "sys_se",
  880 + "accnut_ym",
  881 + "chit_no" ]
  882 + },
  883 + "condTwo": {
  884 + "cond": [
  885 + "dta_ty in ('11','21')",
  886 + "mtch_ty is null"
  887 + ],
  888 + "makeCompareKey": [
  889 + "sys_se",
  890 + "accnut_ym",
  891 + "cast(sn as text)"
  892 + ]
  893 + },
  894 + "uniqueKey": [
  895 + "sys_se",
  896 + "accnut_ym",
  897 + "sn"
  898 + ],
  899 + "compareKey": "compare_ky",
  900 + "amtField": "sum(delng_amt) as delng_amt",
  901 + "compareField": [
  902 + "accnut_ym",
  903 + "delng_amt"
  904 + ],
  905 + "matchingType": "mtch_ty",
  906 + "matchingTypeName": "mtch_ty_nm",
  907 + "matchingNumber": "mtch_ky"
  908 + },
  909 + {
  910 + "active": true,
  911 + "type": "H-AH",
  912 + "typeName": "자기비용(합산키),개별상대수익,비교(년월,거래금액)",
  913 +
  914 + "condOne": {
  915 + "cond": [
  916 + "dta_ty in ('12','22')",
  917 + "mtch_ty is null",
  918 + "ext_key1 is not null",
  919 + "ext_key1 != ''"
  920 + ],
  921 + "makeCompareKey": [
  922 + "sys_se",
  923 + "accnut_ym",
  924 + "ext_key1" ]
  925 + },
  926 + "condTwo": {
  927 + "cond": [
  928 + "dta_ty in ('11','21')",
  929 + "mtch_ty is null"
  930 + ],
  931 + "makeCompareKey": [
  932 + "sys_se",
  933 + "accnut_ym",
  934 + "cast(sn as text)"
  935 + ]
  936 + },
  937 + "uniqueKey": [
  938 + "sys_se",
  939 + "accnut_ym",
  940 + "sn"
  941 + ],
  942 + "compareKey": "compare_ky",
  943 + "amtField": "sum(delng_amt) as delng_amt",
  944 + "compareField": [
  945 + "accnut_ym",
  946 + "delng_amt"
  947 + ],
  948 + "matchingType": "mtch_ty",
  949 + "matchingTypeName": "mtch_ty_nm",
  950 + "matchingNumber": "mtch_ky"
  951 + },
  952 +
  953 +
  954 +
  955 + {
  956 + "active": true,
  957 + "type": "H-BA",
  958 + "typeName": "자기채권(거래일자),개별상대채무,비교(년월,거래금액)",
  959 +
  960 + "condOne": {
  961 + "cond": [
  962 + "dta_ty in ('31','33','35','37','41')",
  963 + "mtch_ty is null"
  964 + ],
  965 + "makeCompareKey": [
  966 + "sys_se",
  967 + "accnut_ym",
  968 + "delng_de"
  969 + ]
  970 + },
  971 + "condTwo": {
  972 + "cond": [
  973 + "dta_ty in ('32','34','36','38','42')",
  974 + "mtch_ty is null"
  975 + ],
  976 + "makeCompareKey": [
  977 + "sys_se",
  978 + "accnut_ym",
  979 + "cast(sn as text)"
  980 + ]
  981 + },
  982 + "uniqueKey": [
  983 + "sys_se",
  984 + "accnut_ym",
  985 + "sn"
  986 + ],
  987 + "compareKey": "compare_ky",
  988 + "amtField": "sum(delng_amt) as delng_amt",
  989 + "compareField": [
  990 + "accnut_ym",
  991 + "delng_amt"
  992 + ],
  993 + "matchingType": "mtch_ty",
  994 + "matchingTypeName": "mtch_ty_nm",
  995 + "matchingNumber": "mtch_ky"
  996 + },
  997 + {
  998 + "active": true,
  999 + "type": "H-BB",
  1000 + "typeName": "자기채권(거래월),개별상대채무,비교(년월,거래금액)",
  1001 +
  1002 + "condOne": {
  1003 + "cond": [
  1004 + "dta_ty in ('31','33','35','37','41')",
  1005 + "mtch_ty is null"
  1006 + ],
  1007 + "makeCompareKey": [
  1008 + "sys_se",
  1009 + "accnut_ym",
  1010 + "substring(delng_de,1,6)" ]
  1011 + },
  1012 + "condTwo": {
  1013 + "cond": [
  1014 + "dta_ty in ('32','34','36','38','42')",
  1015 + "mtch_ty is null"
  1016 + ],
  1017 + "makeCompareKey": [
  1018 + "sys_se",
  1019 + "accnut_ym",
  1020 + "cast(sn as text)"
  1021 + ]
  1022 + },
  1023 + "uniqueKey": [
  1024 + "sys_se",
  1025 + "accnut_ym",
  1026 + "sn"
  1027 + ],
  1028 + "compareKey": "compare_ky",
  1029 + "amtField": "sum(delng_amt) as delng_amt",
  1030 + "compareField": [
  1031 + "accnut_ym",
  1032 + "delng_amt"
  1033 + ],
  1034 + "matchingType": "mtch_ty",
  1035 + "matchingTypeName": "mtch_ty_nm",
  1036 + "matchingNumber": "mtch_ky"
  1037 + },
  1038 + {
  1039 + "active": true,
  1040 + "type": "H-BC",
  1041 + "typeName": "자기채권(전표번호),개별상대채무,비교(년월,거래금액)",
  1042 +
  1043 + "condOne": {
  1044 + "cond": [
  1045 + "dta_ty in ('31','33','35','37','41')",
  1046 + "mtch_ty is null",
  1047 + "chit_no is not null",
  1048 + "chit_no != ''"
  1049 + ],
  1050 + "makeCompareKey": [
  1051 + "sys_se",
  1052 + "accnut_ym",
  1053 + "chit_no" ]
  1054 + },
  1055 + "condTwo": {
  1056 + "cond": [
  1057 + "dta_ty in ('32','34','36','38','42')",
  1058 + "mtch_ty is null"
  1059 + ],
  1060 + "makeCompareKey": [
  1061 + "sys_se",
  1062 + "accnut_ym",
  1063 + "cast(sn as text)"
  1064 + ]
  1065 + },
  1066 + "uniqueKey": [
  1067 + "sys_se",
  1068 + "accnut_ym",
  1069 + "sn"
  1070 + ],
  1071 + "compareKey": "compare_ky",
  1072 + "amtField": "sum(delng_amt) as delng_amt",
  1073 + "compareField": [
  1074 + "accnut_ym",
  1075 + "delng_amt"
  1076 + ],
  1077 + "matchingType": "mtch_ty",
  1078 + "matchingTypeName": "mtch_ty_nm",
  1079 + "matchingNumber": "mtch_ky"
  1080 + },
  1081 + {
  1082 + "active": true,
  1083 + "type": "H-BD",
  1084 + "typeName": "자기채권(합산키),개별상대채무,비교(년월,거래금액)",
  1085 +
  1086 + "condOne": {
  1087 + "cond": [
  1088 + "dta_ty in ('31','33','35','37','41')",
  1089 + "mtch_ty is null"
  1090 + ],
  1091 + "makeCompareKey": [
  1092 + "sys_se",
  1093 + "accnut_ym",
  1094 + "ext_key1" ]
  1095 + },
  1096 + "condTwo": {
  1097 + "cond": [
  1098 + "dta_ty in ('32','34','36','38','42')",
  1099 + "mtch_ty is null"
  1100 + ],
  1101 + "makeCompareKey": [
  1102 + "sys_se",
  1103 + "accnut_ym",
  1104 + "cast(sn as text)"
  1105 + ]
  1106 + },
  1107 + "uniqueKey": [
  1108 + "sys_se",
  1109 + "accnut_ym",
  1110 + "sn"
  1111 + ],
  1112 + "compareKey": "compare_ky",
  1113 + "amtField": "sum(delng_amt) as delng_amt",
  1114 + "compareField": [
  1115 + "accnut_ym",
  1116 + "delng_amt"
  1117 + ],
  1118 + "matchingType": "mtch_ty",
  1119 + "matchingTypeName": "mtch_ty_nm",
  1120 + "matchingNumber": "mtch_ky"
  1121 + },
  1122 + {
  1123 + "active": true,
  1124 + "type": "H-BE",
  1125 + "typeName": "자기채무(거래일자),개별상대채권,비교(년월,거래금액)",
  1126 +
  1127 + "condOne": {
  1128 + "cond": [
  1129 + "dta_ty in ('32','34','36','38','42')",
  1130 + "mtch_ty is null"
  1131 + ],
  1132 + "makeCompareKey": [
  1133 + "sys_se",
  1134 + "accnut_ym",
  1135 + "delng_de"
  1136 + ]
  1137 + },
  1138 + "condTwo": {
  1139 + "cond": [
  1140 + "dta_ty in ('31','33','35','37','41')",
  1141 + "mtch_ty is null"
  1142 + ],
  1143 + "makeCompareKey": [
  1144 + "sys_se",
  1145 + "accnut_ym",
  1146 + "cast(sn as text)"
  1147 + ]
  1148 + },
  1149 + "uniqueKey": [
  1150 + "sys_se",
  1151 + "accnut_ym",
  1152 + "sn"
  1153 + ],
  1154 + "compareKey": "compare_ky",
  1155 + "amtField": "sum(delng_amt) as delng_amt",
  1156 + "compareField": [
  1157 + "accnut_ym",
  1158 + "delng_amt"
  1159 + ],
  1160 + "matchingType": "mtch_ty",
  1161 + "matchingTypeName": "mtch_ty_nm",
  1162 + "matchingNumber": "mtch_ky"
  1163 + },
  1164 + {
  1165 + "active": true,
  1166 + "type": "H-BF",
  1167 + "typeName": "자기채무(거래월),개별상대채권,비교(년월,거래금액)",
  1168 +
  1169 + "condOne": {
  1170 + "cond": [
  1171 + "dta_ty in ('32','34','36','38','42')",
  1172 + "mtch_ty is null"
  1173 + ],
  1174 + "makeCompareKey": [
  1175 + "sys_se",
  1176 + "accnut_ym",
  1177 + "substring(delng_de,1,6)" ]
  1178 + },
  1179 + "condTwo": {
  1180 + "cond": [
  1181 + "dta_ty in ('31','33','35','37','41')",
  1182 + "mtch_ty is null"
  1183 + ],
  1184 + "makeCompareKey": [
  1185 + "sys_se",
  1186 + "accnut_ym",
  1187 + "cast(sn as text)"
  1188 + ]
  1189 + },
  1190 + "uniqueKey": [
  1191 + "sys_se",
  1192 + "accnut_ym",
  1193 + "sn"
  1194 + ],
  1195 + "compareKey": "compare_ky",
  1196 + "amtField": "sum(delng_amt) as delng_amt",
  1197 + "compareField": [
  1198 + "accnut_ym",
  1199 + "delng_amt"
  1200 + ],
  1201 + "matchingType": "mtch_ty",
  1202 + "matchingTypeName": "mtch_ty_nm",
  1203 + "matchingNumber": "mtch_ky"
  1204 + },
  1205 + {
  1206 + "active": true,
  1207 + "type": "H-BG",
  1208 + "typeName": "자기채무(전표번호),개별상대채권,비교(년월,거래금액)",
  1209 +
  1210 + "condOne": {
  1211 + "cond": [
  1212 + "dta_ty in ('32','34','36','38','42')",
  1213 + "mtch_ty is null",
  1214 + "chit_no is not null",
  1215 + "chit_no != ''"
  1216 + ],
  1217 + "makeCompareKey": [
  1218 + "sys_se",
  1219 + "accnut_ym",
  1220 + "chit_no" ]
  1221 + },
  1222 + "condTwo": {
  1223 + "cond": [
  1224 + "dta_ty in ('31','33','35','37','41')",
  1225 + "mtch_ty is null"
  1226 + ],
  1227 + "makeCompareKey": [
  1228 + "sys_se",
  1229 + "accnut_ym",
  1230 + "cast(sn as text)"
  1231 + ]
  1232 + },
  1233 + "uniqueKey": [
  1234 + "sys_se",
  1235 + "accnut_ym",
  1236 + "sn"
  1237 + ],
  1238 + "compareKey": "compare_ky",
  1239 + "amtField": "sum(delng_amt) as delng_amt",
  1240 + "compareField": [
  1241 + "accnut_ym",
  1242 + "delng_amt"
  1243 + ],
  1244 + "matchingType": "mtch_ty",
  1245 + "matchingTypeName": "mtch_ty_nm",
  1246 + "matchingNumber": "mtch_ky"
  1247 + },
  1248 + {
  1249 + "active": true,
  1250 + "type": "H-BH",
  1251 + "typeName": "자기채무(합산키),개별상대채권,비교(년월,거래금액)",
  1252 +
  1253 + "condOne": {
  1254 + "cond": [
  1255 + "dta_ty in ('32','34','36','38','42')",
  1256 + "mtch_ty is null"
  1257 + ],
  1258 + "makeCompareKey": [
  1259 + "sys_se",
  1260 + "accnut_ym",
  1261 + "ext_key1" ]
  1262 + },
  1263 + "condTwo": {
  1264 + "cond": [
  1265 + "dta_ty in ('31','33','35','37','41')",
  1266 + "mtch_ty is null"
  1267 + ],
  1268 + "makeCompareKey": [
  1269 + "sys_se",
  1270 + "accnut_ym",
  1271 + "cast(sn as text)"
  1272 + ]
  1273 + },
  1274 + "uniqueKey": [
  1275 + "sys_se",
  1276 + "accnut_ym",
  1277 + "sn"
  1278 + ],
  1279 + "compareKey": "compare_ky",
  1280 + "amtField": "sum(delng_amt) as delng_amt",
  1281 + "compareField": [
  1282 + "accnut_ym",
  1283 + "delng_amt"
  1284 + ],
  1285 + "matchingType": "mtch_ty",
  1286 + "matchingTypeName": "mtch_ty_nm",
  1287 + "matchingNumber": "mtch_ky"
  1288 + },
  1289 +
  1290 +
  1291 +
  1292 +
  1293 + {
  1294 + "active": true,
  1295 + "type": "I-AA",
  1296 + "typeName": "자기수익(전체),상대비용(겨래월),비교(년월,거래금액)",
  1297 +
  1298 + "condOne": {
  1299 + "cond": [
  1300 + "dta_ty in ('11','21')",
  1301 + "mtch_ty is null"
  1302 + ],
  1303 + "makeCompareKey": [
  1304 + "sys_se",
  1305 + "accnut_ym"
  1306 + ]
  1307 + },
  1308 + "condTwo": {
  1309 + "cond": [
  1310 + "dta_ty in ('12','22')",
  1311 + "mtch_ty is null"
  1312 + ],
  1313 + "makeCompareKey": [
  1314 + "sys_se",
  1315 + "accnut_ym",
  1316 + "substring(delng_de,1,6)"
  1317 + ]
  1318 + },
  1319 + "uniqueKey": [
  1320 + "sys_se",
  1321 + "accnut_ym",
  1322 + "sn"
  1323 + ],
  1324 + "compareKey": "compare_ky",
  1325 + "amtField": "sum(delng_amt) as delng_amt",
  1326 + "compareField": [
  1327 + "accnut_ym",
  1328 + "delng_amt"
  1329 + ],
  1330 + "matchingType": "mtch_ty",
  1331 + "matchingTypeName": "mtch_ty_nm",
  1332 + "matchingNumber": "mtch_ky"
  1333 + },
  1334 + {
  1335 + "active": true,
  1336 + "type": "I-AB",
  1337 + "typeName": "자기수익(전체),상대비용(겨래일자),비교(년월,거래금액)",
  1338 +
  1339 + "condOne": {
  1340 + "cond": [
  1341 + "dta_ty in ('11','21')",
  1342 + "mtch_ty is null"
  1343 + ],
  1344 + "makeCompareKey": [
  1345 + "sys_se",
  1346 + "accnut_ym"
  1347 + ]
  1348 + },
  1349 + "condTwo": {
  1350 + "cond": [
  1351 + "dta_ty in ('12','22')",
  1352 + "mtch_ty is null"
  1353 + ],
  1354 + "makeCompareKey": [
  1355 + "sys_se",
  1356 + "accnut_ym",
  1357 + "delng_de"
  1358 + ]
  1359 + },
  1360 + "uniqueKey": [
  1361 + "sys_se",
  1362 + "accnut_ym",
  1363 + "sn"
  1364 + ],
  1365 + "compareKey": "compare_ky",
  1366 + "amtField": "sum(delng_amt) as delng_amt",
  1367 + "compareField": [
  1368 + "accnut_ym",
  1369 + "delng_amt"
  1370 + ],
  1371 + "matchingType": "mtch_ty",
  1372 + "matchingTypeName": "mtch_ty_nm",
  1373 + "matchingNumber": "mtch_ky"
  1374 + },
  1375 + {
  1376 + "active": true,
  1377 + "type": "I-AC",
  1378 + "typeName": "자기비용(전체),상대수익(겨래월),비교(년월,거래금액)",
  1379 +
  1380 + "condOne": {
  1381 + "cond": [
  1382 + "dta_ty in ('12','22')",
  1383 + "mtch_ty is null"
  1384 + ],
  1385 + "makeCompareKey": [
  1386 + "sys_se",
  1387 + "accnut_ym"
  1388 + ]
  1389 + },
  1390 + "condTwo": {
  1391 + "cond": [
  1392 + "dta_ty in ('11','21')",
  1393 + "mtch_ty is null"
  1394 + ],
  1395 + "makeCompareKey": [
  1396 + "sys_se",
  1397 + "accnut_ym",
  1398 + "substring(delng_de,1,6)"
  1399 + ]
  1400 + },
  1401 + "uniqueKey": [
  1402 + "sys_se",
  1403 + "accnut_ym",
  1404 + "sn"
  1405 + ],
  1406 + "compareKey": "compare_ky",
  1407 + "amtField": "sum(delng_amt) as delng_amt",
  1408 + "compareField": [
  1409 + "accnut_ym",
  1410 + "delng_amt"
  1411 + ],
  1412 + "matchingType": "mtch_ty",
  1413 + "matchingTypeName": "mtch_ty_nm",
  1414 + "matchingNumber": "mtch_ky"
  1415 + },
  1416 + {
  1417 + "active": true,
  1418 + "type": "I-AD",
  1419 + "typeName": "자기비용(전체),상대수익(겨래일자),비교(년월,거래금액)",
  1420 +
  1421 + "condOne": {
  1422 + "cond": [
  1423 + "dta_ty in ('12','22')",
  1424 + "mtch_ty is null"
  1425 + ],
  1426 + "makeCompareKey": [
  1427 + "sys_se",
  1428 + "accnut_ym"
  1429 + ]
  1430 + },
  1431 + "condTwo": {
  1432 + "cond": [
  1433 + "dta_ty in ('11','21')",
  1434 + "mtch_ty is null"
  1435 + ],
  1436 + "makeCompareKey": [
  1437 + "sys_se",
  1438 + "accnut_ym",
  1439 + "delng_de"
  1440 + ]
  1441 + },
  1442 + "uniqueKey": [
  1443 + "sys_se",
  1444 + "accnut_ym",
  1445 + "sn"
  1446 + ],
  1447 + "compareKey": "compare_ky",
  1448 + "amtField": "sum(delng_amt) as delng_amt",
  1449 + "compareField": [
  1450 + "accnut_ym",
  1451 + "delng_amt"
  1452 + ],
  1453 + "matchingType": "mtch_ty",
  1454 + "matchingTypeName": "mtch_ty_nm",
  1455 + "matchingNumber": "mtch_ky"
  1456 + },
  1457 + {
  1458 + "active": true,
  1459 + "type": "I-AE",
  1460 + "typeName": "자기수익(전체),상대비용(법인계정코드),비교(년월,거래금액)",
  1461 +
  1462 + "condOne": {
  1463 + "cond": [
  1464 + "dta_ty in ('11','21')",
  1465 + "mtch_ty is null"
  1466 + ],
  1467 + "makeCompareKey": [
  1468 + "sys_se",
  1469 + "accnut_ym"
  1470 + ]
  1471 + },
  1472 + "condTwo": {
  1473 + "cond": [
  1474 + "dta_ty in ('12','22')",
  1475 + "mtch_ty is null"
  1476 + ],
  1477 + "makeCompareKey": [
  1478 + "sys_se",
  1479 + "accnut_ym",
  1480 + "cpr_acnt_code"
  1481 + ]
  1482 + },
  1483 + "uniqueKey": [
  1484 + "sys_se",
  1485 + "accnut_ym",
  1486 + "sn"
  1487 + ],
  1488 + "compareKey": "compare_ky",
  1489 + "amtField": "sum(delng_amt) as delng_amt",
  1490 + "compareField": [
  1491 + "accnut_ym",
  1492 + "delng_amt"
  1493 + ],
  1494 + "matchingType": "mtch_ty",
  1495 + "matchingTypeName": "mtch_ty_nm",
  1496 + "matchingNumber": "mtch_ky"
  1497 + },
  1498 + {
  1499 + "active": true,
  1500 + "type": "I-AF",
  1501 + "typeName": "자기비용(전체),상대수익(법인계정코드),비교(년월,거래금액)",
  1502 +
  1503 + "condOne": {
  1504 + "cond": [
  1505 + "dta_ty in ('12','22')",
  1506 + "mtch_ty is null"
  1507 + ],
  1508 + "makeCompareKey": [
  1509 + "sys_se",
  1510 + "accnut_ym"
  1511 + ]
  1512 + },
  1513 + "condTwo": {
  1514 + "cond": [
  1515 + "dta_ty in ('11','21')",
  1516 + "mtch_ty is null"
  1517 + ],
  1518 + "makeCompareKey": [
  1519 + "sys_se",
  1520 + "accnut_ym",
  1521 + "cpr_acnt_code"
  1522 + ]
  1523 + },
  1524 + "uniqueKey": [
  1525 + "sys_se",
  1526 + "accnut_ym",
  1527 + "sn"
  1528 + ],
  1529 + "compareKey": "compare_ky",
  1530 + "amtField": "sum(delng_amt) as delng_amt",
  1531 + "compareField": [
  1532 + "accnut_ym",
  1533 + "delng_amt"
  1534 + ],
  1535 + "matchingType": "mtch_ty",
  1536 + "matchingTypeName": "mtch_ty_nm",
  1537 + "matchingNumber": "mtch_ky"
  1538 + },
  1539 +
  1540 +
  1541 +
  1542 + {
  1543 + "active": true,
  1544 + "type": "I-BA",
  1545 + "typeName": "자기채권(전체),상대채무(겨래월),비교(년월,거래금액)",
  1546 +
  1547 + "condOne": {
  1548 + "cond": [
  1549 + "dta_ty in ('31','33','35','37','41')",
  1550 + "mtch_ty is null"
  1551 + ],
  1552 + "makeCompareKey": [
  1553 + "sys_se",
  1554 + "accnut_ym"
  1555 + ]
  1556 + },
  1557 + "condTwo": {
  1558 + "cond": [
  1559 + "dta_ty in ('32','34','36','38','42')",
  1560 + "mtch_ty is null"
  1561 + ],
  1562 + "makeCompareKey": [
  1563 + "sys_se",
  1564 + "accnut_ym",
  1565 + "substring(delng_de,1,6)"
  1566 + ]
  1567 + },
  1568 + "uniqueKey": [
  1569 + "sys_se",
  1570 + "accnut_ym",
  1571 + "sn"
  1572 + ],
  1573 + "compareKey": "compare_ky",
  1574 + "amtField": "sum(delng_amt) as delng_amt",
  1575 + "compareField": [
  1576 + "accnut_ym",
  1577 + "delng_amt"
  1578 + ],
  1579 + "matchingType": "mtch_ty",
  1580 + "matchingTypeName": "mtch_ty_nm",
  1581 + "matchingNumber": "mtch_ky"
  1582 + },
  1583 + {
  1584 + "active": true,
  1585 + "type": "I-BB",
  1586 + "typeName": "자기채권(전체),상대채무(겨래일자),비교(년월,거래금액)",
  1587 +
  1588 + "condOne": {
  1589 + "cond": [
  1590 + "dta_ty in ('31','33','35','37','41')",
  1591 + "mtch_ty is null"
  1592 + ],
  1593 + "makeCompareKey": [
  1594 + "sys_se",
  1595 + "accnut_ym"
  1596 + ]
  1597 + },
  1598 + "condTwo": {
  1599 + "cond": [
  1600 + "dta_ty in ('32','34','36','38','42')",
  1601 + "mtch_ty is null"
  1602 + ],
  1603 + "makeCompareKey": [
  1604 + "sys_se",
  1605 + "accnut_ym",
  1606 + "delng_de"
  1607 + ]
  1608 + },
  1609 + "uniqueKey": [
  1610 + "sys_se",
  1611 + "accnut_ym",
  1612 + "sn"
  1613 + ],
  1614 + "compareKey": "compare_ky",
  1615 + "amtField": "sum(delng_amt) as delng_amt",
  1616 + "compareField": [
  1617 + "accnut_ym",
  1618 + "delng_amt"
  1619 + ],
  1620 + "matchingType": "mtch_ty",
  1621 + "matchingTypeName": "mtch_ty_nm",
  1622 + "matchingNumber": "mtch_ky"
  1623 + },
  1624 + {
  1625 + "active": true,
  1626 + "type": "I-BC",
  1627 + "typeName": "자기채무(전체),상대채권(겨래월),비교(년월,거래금액)",
  1628 +
  1629 + "condOne": {
  1630 + "cond": [
  1631 + "dta_ty in ('32','34','36','38','42')",
  1632 + "mtch_ty is null"
  1633 + ],
  1634 + "makeCompareKey": [
  1635 + "sys_se",
  1636 + "accnut_ym"
  1637 + ]
  1638 + },
  1639 + "condTwo": {
  1640 + "cond": [
  1641 + "dta_ty in ('31','33','35','37','41')",
  1642 + "mtch_ty is null"
  1643 + ],
  1644 + "makeCompareKey": [
  1645 + "sys_se",
  1646 + "accnut_ym",
  1647 + "substring(delng_de,1,6)"
  1648 + ]
  1649 + },
  1650 + "uniqueKey": [
  1651 + "sys_se",
  1652 + "accnut_ym",
  1653 + "sn"
  1654 + ],
  1655 + "compareKey": "compare_ky",
  1656 + "amtField": "sum(delng_amt) as delng_amt",
  1657 + "compareField": [
  1658 + "accnut_ym",
  1659 + "delng_amt"
  1660 + ],
  1661 + "matchingType": "mtch_ty",
  1662 + "matchingTypeName": "mtch_ty_nm",
  1663 + "matchingNumber": "mtch_ky"
  1664 + },
  1665 + {
  1666 + "active": true,
  1667 + "type": "I-BD",
  1668 + "typeName": "자기채무(전체),상대채권(겨래일자),비교(년월,거래금액)",
  1669 +
  1670 + "condOne": {
  1671 + "cond": [
  1672 + "dta_ty in ('32','34','36','38','42')",
  1673 + "mtch_ty is null"
  1674 + ],
  1675 + "makeCompareKey": [
  1676 + "sys_se",
  1677 + "accnut_ym"
  1678 + ]
  1679 + },
  1680 + "condTwo": {
  1681 + "cond": [
  1682 + "dta_ty in ('31','33','35','37','41')",
  1683 + "mtch_ty is null"
  1684 + ],
  1685 + "makeCompareKey": [
  1686 + "sys_se",
  1687 + "accnut_ym",
  1688 + "delng_de"
  1689 + ]
  1690 + },
  1691 + "uniqueKey": [
  1692 + "sys_se",
  1693 + "accnut_ym",
  1694 + "sn"
  1695 + ],
  1696 + "compareKey": "compare_ky",
  1697 + "amtField": "sum(delng_amt) as delng_amt",
  1698 + "compareField": [
  1699 + "accnut_ym",
  1700 + "delng_amt"
  1701 + ],
  1702 + "matchingType": "mtch_ty",
  1703 + "matchingTypeName": "mtch_ty_nm",
  1704 + "matchingNumber": "mtch_ky"
  1705 + },
  1706 + {
  1707 + "active": true,
  1708 + "type": "I-BE",
  1709 + "typeName": "자기채권(전체),상대채무(계정코드),비교(년월,거래금액)",
  1710 +
  1711 + "condOne": {
  1712 + "cond": [
  1713 + "dta_ty in ('31','33','35','37','41')",
  1714 + "mtch_ty is null"
  1715 + ],
  1716 + "makeCompareKey": [
  1717 + "sys_se",
  1718 + "cpr_acnt_code"
  1719 + ]
  1720 + },
  1721 + "condTwo": {
  1722 + "cond": [
  1723 + "dta_ty in ('32','34','36','38','42')",
  1724 + "mtch_ty is null"
  1725 + ],
  1726 + "makeCompareKey": [
  1727 + "sys_se",
  1728 + "accnut_ym",
  1729 + "delng_de"
  1730 + ]
  1731 + },
  1732 + "uniqueKey": [
  1733 + "sys_se",
  1734 + "accnut_ym",
  1735 + "sn"
  1736 + ],
  1737 + "compareKey": "compare_ky",
  1738 + "amtField": "sum(delng_amt) as delng_amt",
  1739 + "compareField": [
  1740 + "accnut_ym",
  1741 + "delng_amt"
  1742 + ],
  1743 + "matchingType": "mtch_ty",
  1744 + "matchingTypeName": "mtch_ty_nm",
  1745 + "matchingNumber": "mtch_ky"
  1746 + },
  1747 + {
  1748 + "active": true,
  1749 + "type": "I-BF",
  1750 + "typeName": "자기채무(전체),상대채권(계정코드),비교(년월,거래금액)",
  1751 +
  1752 + "condOne": {
  1753 + "cond": [
  1754 + "dta_ty in ('32','34','36','38','42')",
  1755 + "mtch_ty is null"
  1756 + ],
  1757 + "makeCompareKey": [
  1758 + "sys_se",
  1759 + "cpr_acnt_code"
  1760 + ]
  1761 + },
  1762 + "condTwo": {
  1763 + "cond": [
  1764 + "dta_ty in ('31','33','35','37','41')",
  1765 + "mtch_ty is null"
  1766 + ],
  1767 + "makeCompareKey": [
  1768 + "sys_se",
  1769 + "accnut_ym",
  1770 + "delng_de"
  1771 + ]
  1772 + },
  1773 + "uniqueKey": [
  1774 + "sys_se",
  1775 + "accnut_ym",
  1776 + "sn"
  1777 + ],
  1778 + "compareKey": "compare_ky",
  1779 + "amtField": "sum(delng_amt) as delng_amt",
  1780 + "compareField": [
  1781 + "accnut_ym",
  1782 + "delng_amt"
  1783 + ],
  1784 + "matchingType": "mtch_ty",
  1785 + "matchingTypeName": "mtch_ty_nm",
  1786 + "matchingNumber": "mtch_ky"
  1787 + },
  1788 +
  1789 +
  1790 +
  1791 +
  1792 + {
  1793 + "active": true,
  1794 + "type": "J-AA",
  1795 + "typeName": "자기수익(거래월),상대비용(겨래일자),비교(년월,거래금액)",
  1796 +
  1797 + "condOne": {
  1798 + "cond": [
  1799 + "dta_ty in ('11','21')",
  1800 + "mtch_ty is null"
  1801 + ],
  1802 + "makeCompareKey": [
  1803 + "sys_se",
  1804 + "accnut_ym",
  1805 + "substring(delng_de,1,6)"
  1806 + ]
  1807 + },
  1808 + "condTwo": {
  1809 + "cond": [
  1810 + "dta_ty in ('12','22')",
  1811 + "mtch_ty is null"
  1812 + ],
  1813 + "makeCompareKey": [
  1814 + "sys_se",
  1815 + "accnut_ym",
  1816 + "delng_de"
  1817 + ]
  1818 + },
  1819 + "uniqueKey": [
  1820 + "sys_se",
  1821 + "accnut_ym",
  1822 + "sn"
  1823 + ],
  1824 + "compareKey": "compare_ky",
  1825 + "amtField": "sum(delng_amt) as delng_amt",
  1826 + "compareField": [
  1827 + "accnut_ym",
  1828 + "delng_amt"
  1829 + ],
  1830 + "matchingType": "mtch_ty",
  1831 + "matchingTypeName": "mtch_ty_nm",
  1832 + "matchingNumber": "mtch_ky"
  1833 + },
  1834 + {
  1835 + "active": true,
  1836 + "type": "J-AB",
  1837 + "typeName": "자기비용(거래월),상대수익(겨래일자),비교(년월,거래금액)",
  1838 +
  1839 + "condOne": {
  1840 + "cond": [
  1841 + "dta_ty in ('12','22')",
  1842 + "mtch_ty is null"
  1843 + ],
  1844 + "makeCompareKey": [
  1845 + "sys_se",
  1846 + "accnut_ym",
  1847 + "substring(delng_de,1,6)"
  1848 + ]
  1849 + },
  1850 + "condTwo": {
  1851 + "cond": [
  1852 + "dta_ty in ('11','21')",
  1853 + "mtch_ty is null"
  1854 + ],
  1855 + "makeCompareKey": [
  1856 + "sys_se",
  1857 + "accnut_ym",
  1858 + "delng_de"
  1859 + ]
  1860 + },
  1861 + "uniqueKey": [
  1862 + "sys_se",
  1863 + "accnut_ym",
  1864 + "sn"
  1865 + ],
  1866 + "compareKey": "compare_ky",
  1867 + "amtField": "sum(delng_amt) as delng_amt",
  1868 + "compareField": [
  1869 + "accnut_ym",
  1870 + "delng_amt"
  1871 + ],
  1872 + "matchingType": "mtch_ty",
  1873 + "matchingTypeName": "mtch_ty_nm",
  1874 + "matchingNumber": "mtch_ky"
  1875 + },
  1876 + {
  1877 + "active": true,
  1878 + "type": "J-AC",
  1879 + "typeName": "자기수익(거래월),상대비용(계정코드),비교(년월,거래금액)",
  1880 +
  1881 + "condOne": {
  1882 + "cond": [
  1883 + "dta_ty in ('11','21')",
  1884 + "mtch_ty is null"
  1885 + ],
  1886 + "makeCompareKey": [
  1887 + "sys_se",
  1888 + "accnut_ym",
  1889 + "substring(delng_de,1,6)"
  1890 + ]
  1891 + },
  1892 + "condTwo": {
  1893 + "cond": [
  1894 + "dta_ty in ('12','22')",
  1895 + "mtch_ty is null"
  1896 + ],
  1897 + "makeCompareKey": [
  1898 + "sys_se",
  1899 + "accnut_ym",
  1900 + "cpr_acnt_code"
  1901 + ]
  1902 + },
  1903 + "uniqueKey": [
  1904 + "sys_se",
  1905 + "accnut_ym",
  1906 + "sn"
  1907 + ],
  1908 + "compareKey": "compare_ky",
  1909 + "amtField": "sum(delng_amt) as delng_amt",
  1910 + "compareField": [
  1911 + "accnut_ym",
  1912 + "delng_amt"
  1913 + ],
  1914 + "matchingType": "mtch_ty",
  1915 + "matchingTypeName": "mtch_ty_nm",
  1916 + "matchingNumber": "mtch_ky"
  1917 + },
  1918 + {
  1919 + "active": true,
  1920 + "type": "J-AD",
  1921 + "typeName": "자기비용(거래월),상대수익(계정코드),비교(년월,거래금액)",
  1922 +
  1923 + "condOne": {
  1924 + "cond": [
  1925 + "dta_ty in ('12','22')",
  1926 + "mtch_ty is null"
  1927 + ],
  1928 + "makeCompareKey": [
  1929 + "sys_se",
  1930 + "accnut_ym",
  1931 + "substring(delng_de,1,6)"
  1932 + ]
  1933 + },
  1934 + "condTwo": {
  1935 + "cond": [
  1936 + "dta_ty in ('11','21')",
  1937 + "mtch_ty is null"
  1938 + ],
  1939 + "makeCompareKey": [
  1940 + "sys_se",
  1941 + "accnut_ym",
  1942 + "cpr_acnt_code"
  1943 + ]
  1944 + },
  1945 + "uniqueKey": [
  1946 + "sys_se",
  1947 + "accnut_ym",
  1948 + "sn"
  1949 + ],
  1950 + "compareKey": "compare_ky",
  1951 + "amtField": "sum(delng_amt) as delng_amt",
  1952 + "compareField": [
  1953 + "accnut_ym",
  1954 + "delng_amt"
  1955 + ],
  1956 + "matchingType": "mtch_ty",
  1957 + "matchingTypeName": "mtch_ty_nm",
  1958 + "matchingNumber": "mtch_ky"
  1959 + },
  1960 +
  1961 + {
  1962 + "active": true,
  1963 + "type": "J-BA",
  1964 + "typeName": "자기채권(거래월),상대채무(겨래일자),비교(년월,거래금액)",
  1965 +
  1966 + "condOne": {
  1967 + "cond": [
  1968 + "dta_ty in ('31','33','35','37','41')",
  1969 + "mtch_ty is null"
  1970 + ],
  1971 + "makeCompareKey": [
  1972 + "sys_se",
  1973 + "accnut_ym",
  1974 + "substring(delng_de,1,6)"
  1975 + ]
  1976 + },
  1977 + "condTwo": {
  1978 + "cond": [
  1979 + "dta_ty in ('32','34','36','38','42')",
  1980 + "mtch_ty is null"
  1981 + ],
  1982 + "makeCompareKey": [
  1983 + "sys_se",
  1984 + "accnut_ym",
  1985 + "delng_de"
  1986 + ]
  1987 + },
  1988 + "uniqueKey": [
  1989 + "sys_se",
  1990 + "accnut_ym",
  1991 + "sn"
  1992 + ],
  1993 + "compareKey": "compare_ky",
  1994 + "amtField": "sum(delng_amt) as delng_amt",
  1995 + "compareField": [
  1996 + "accnut_ym",
  1997 + "delng_amt"
  1998 + ],
  1999 + "matchingType": "mtch_ty",
  2000 + "matchingTypeName": "mtch_ty_nm",
  2001 + "matchingNumber": "mtch_ky"
  2002 + },
  2003 + {
  2004 + "active": true,
  2005 + "type": "J-BB",
  2006 + "typeName": "자기채무(거래월),상대채권(겨래일자),비교(년월,거래금액)",
  2007 +
  2008 + "condOne": {
  2009 + "cond": [
  2010 + "dta_ty in ('32','34','36','38','42')",
  2011 + "mtch_ty is null"
  2012 + ],
  2013 + "makeCompareKey": [
  2014 + "sys_se",
  2015 + "accnut_ym",
  2016 + "substring(delng_de,1,6)"
  2017 + ]
  2018 + },
  2019 + "condTwo": {
  2020 + "cond": [
  2021 + "dta_ty in ('31','33','35','37','41')",
  2022 + "mtch_ty is null"
  2023 + ],
  2024 + "makeCompareKey": [
  2025 + "sys_se",
  2026 + "accnut_ym",
  2027 + "delng_de"
  2028 + ]
  2029 + },
  2030 + "uniqueKey": [
  2031 + "sys_se",
  2032 + "accnut_ym",
  2033 + "sn"
  2034 + ],
  2035 + "compareKey": "compare_ky",
  2036 + "amtField": "sum(delng_amt) as delng_amt",
  2037 + "compareField": [
  2038 + "accnut_ym",
  2039 + "delng_amt"
  2040 + ],
  2041 + "matchingType": "mtch_ty",
  2042 + "matchingTypeName": "mtch_ty_nm",
  2043 + "matchingNumber": "mtch_ky"
  2044 + },
  2045 + {
  2046 + "active": true,
  2047 + "type": "J-BC",
  2048 + "typeName": "자기채권(거래월),상대채무(계정코드),비교(년월,거래금액)",
  2049 +
  2050 + "condOne": {
  2051 + "cond": [
  2052 + "dta_ty in ('31','33','35','37','41')",
  2053 + "mtch_ty is null"
  2054 + ],
  2055 + "makeCompareKey": [
  2056 + "sys_se",
  2057 + "accnut_ym",
  2058 + "substring(delng_de,1,6)"
  2059 + ]
  2060 + },
  2061 + "condTwo": {
  2062 + "cond": [
  2063 + "dta_ty in ('32','34','36','38','42')",
  2064 + "mtch_ty is null"
  2065 + ],
  2066 + "makeCompareKey": [
  2067 + "sys_se",
  2068 + "accnut_ym",
  2069 + "cpr_acnt_code"
  2070 + ]
  2071 + },
  2072 + "uniqueKey": [
  2073 + "sys_se",
  2074 + "accnut_ym",
  2075 + "sn"
  2076 + ],
  2077 + "compareKey": "compare_ky",
  2078 + "amtField": "sum(delng_amt) as delng_amt",
  2079 + "compareField": [
  2080 + "accnut_ym",
  2081 + "delng_amt"
  2082 + ],
  2083 + "matchingType": "mtch_ty",
  2084 + "matchingTypeName": "mtch_ty_nm",
  2085 + "matchingNumber": "mtch_ky"
  2086 + },
  2087 + {
  2088 + "active": true,
  2089 + "type": "J-BD",
  2090 + "typeName": "자기채무(거래월),상대채권(계정코드),비교(년월,거래금액)",
  2091 +
  2092 + "condOne": {
  2093 + "cond": [
  2094 + "dta_ty in ('32','34','36','38','42')",
  2095 + "mtch_ty is null"
  2096 + ],
  2097 + "makeCompareKey": [
  2098 + "sys_se",
  2099 + "accnut_ym",
  2100 + "substring(delng_de,1,6)"
  2101 + ]
  2102 + },
  2103 + "condTwo": {
  2104 + "cond": [
  2105 + "dta_ty in ('31','33','35','37','41')",
  2106 + "mtch_ty is null"
  2107 + ],
  2108 + "makeCompareKey": [
  2109 + "sys_se",
  2110 + "accnut_ym",
  2111 + "cpr_acnt_code"
  2112 + ]
  2113 + },
  2114 + "uniqueKey": [
  2115 + "sys_se",
  2116 + "accnut_ym",
  2117 + "sn"
  2118 + ],
  2119 + "compareKey": "compare_ky",
  2120 + "amtField": "sum(delng_amt) as delng_amt",
  2121 + "compareField": [
  2122 + "accnut_ym",
  2123 + "delng_amt"
  2124 + ],
  2125 + "matchingType": "mtch_ty",
  2126 + "matchingTypeName": "mtch_ty_nm",
  2127 + "matchingNumber": "mtch_ky"
  2128 + },
  2129 +
  2130 +
  2131 +
  2132 +
  2133 +
  2134 +
  2135 +
  2136 +
  2137 +
  2138 +
  2139 +
  2140 +
  2141 +
  2142 + {
  2143 + "active": true,
  2144 + "type": "K-AA",
  2145 + "typeName": "자기수익(적요),상대비용(적요),비교(년월,거래금액)",
  2146 +
  2147 + "condOne": {
  2148 + "cond": [
  2149 + "dta_ty in ('11','21')",
  2150 + "mtch_ty is null"
  2151 + ],
  2152 + "makeCompareKey": [
  2153 + "sys_se",
  2154 + "accnut_ym",
  2155 + "substring(sumry, 1, 80)"
  2156 + ]
  2157 + },
  2158 + "condTwo": {
  2159 + "cond": [
  2160 + "dta_ty in ('12','22')",
  2161 + "mtch_ty is null"
  2162 + ],
  2163 + "makeCompareKey": [
  2164 + "sys_se",
  2165 + "accnut_ym",
  2166 + "substring(sumry, 1, 80)"
  2167 + ]
  2168 + },
  2169 + "uniqueKey": [
  2170 + "sys_se",
  2171 + "accnut_ym",
  2172 + "sn"
  2173 + ],
  2174 + "compareKey": "compare_ky",
  2175 + "amtField": "sum(delng_amt) as delng_amt",
  2176 + "compareField": [
  2177 + "accnut_ym",
  2178 + "delng_amt"
  2179 + ],
  2180 + "matchingType": "mtch_ty",
  2181 + "matchingTypeName": "mtch_ty_nm",
  2182 + "matchingNumber": "mtch_ky"
  2183 + },
  2184 + {
  2185 + "active": true,
  2186 + "type": "K-AB",
  2187 + "typeName": "자기비용(적요),상대수익(겨래일자),비교(년월,거래금액)",
  2188 +
  2189 + "condOne": {
  2190 + "cond": [
  2191 + "dta_ty in ('12','22')",
  2192 + "mtch_ty is null"
  2193 + ],
  2194 + "makeCompareKey": [
  2195 + "sys_se",
  2196 + "accnut_ym",
  2197 + "substring(sumry, 1, 80)"
  2198 + ]
  2199 + },
  2200 + "condTwo": {
  2201 + "cond": [
  2202 + "dta_ty in ('11','21')",
  2203 + "mtch_ty is null"
  2204 + ],
  2205 + "makeCompareKey": [
  2206 + "sys_se",
  2207 + "accnut_ym",
  2208 + "delng_de"
  2209 + ]
  2210 + },
  2211 + "uniqueKey": [
  2212 + "sys_se",
  2213 + "accnut_ym",
  2214 + "sn"
  2215 + ],
  2216 + "compareKey": "compare_ky",
  2217 + "amtField": "sum(delng_amt) as delng_amt",
  2218 + "compareField": [
  2219 + "accnut_ym",
  2220 + "delng_amt"
  2221 + ],
  2222 + "matchingType": "mtch_ty",
  2223 + "matchingTypeName": "mtch_ty_nm",
  2224 + "matchingNumber": "mtch_ky"
  2225 + },
  2226 + {
  2227 + "active": true,
  2228 + "type": "K-AC",
  2229 + "typeName": "자기수익(적요),개별상대비용,비교(년월,거래금액)",
  2230 +
  2231 + "condOne": {
  2232 + "cond": [
  2233 + "dta_ty in ('11','21')",
  2234 + "mtch_ty is null"
  2235 + ],
  2236 + "makeCompareKey": [
  2237 + "sys_se",
  2238 + "accnut_ym",
  2239 + "substring(sumry, 1, 80)"
  2240 + ]
  2241 + },
  2242 + "condTwo": {
  2243 + "cond": [
  2244 + "dta_ty in ('12','22')",
  2245 + "mtch_ty is null"
  2246 + ],
  2247 + "makeCompareKey": [
  2248 + "sys_se",
  2249 + "accnut_ym",
  2250 + "cast(sn as text)"
  2251 + ]
  2252 + },
  2253 + "uniqueKey": [
  2254 + "sys_se",
  2255 + "accnut_ym",
  2256 + "sn"
  2257 + ],
  2258 + "compareKey": "compare_ky",
  2259 + "amtField": "sum(delng_amt) as delng_amt",
  2260 + "compareField": [
  2261 + "accnut_ym",
  2262 + "delng_amt"
  2263 + ],
  2264 + "matchingType": "mtch_ty",
  2265 + "matchingTypeName": "mtch_ty_nm",
  2266 + "matchingNumber": "mtch_ky"
  2267 + },
  2268 + {
  2269 + "active": true,
  2270 + "type": "K-AD",
  2271 + "typeName": "자기비용(적요),개별상대수익,비교(년월,거래금액)",
  2272 +
  2273 + "condOne": {
  2274 + "cond": [
  2275 + "dta_ty in ('12','22')",
  2276 + "mtch_ty is null"
  2277 + ],
  2278 + "makeCompareKey": [
  2279 + "sys_se",
  2280 + "accnut_ym",
  2281 + "substring(sumry, 1, 80)"
  2282 + ]
  2283 + },
  2284 + "condTwo": {
  2285 + "cond": [
  2286 + "dta_ty in ('11','21')",
  2287 + "mtch_ty is null"
  2288 + ],
  2289 + "makeCompareKey": [
  2290 + "sys_se",
  2291 + "accnut_ym",
  2292 + "cast(sn as text)"
  2293 + ]
  2294 + },
  2295 + "uniqueKey": [
  2296 + "sys_se",
  2297 + "accnut_ym",
  2298 + "sn"
  2299 + ],
  2300 + "compareKey": "compare_ky",
  2301 + "amtField": "sum(delng_amt) as delng_amt",
  2302 + "compareField": [
  2303 + "accnut_ym",
  2304 + "delng_amt"
  2305 + ],
  2306 + "matchingType": "mtch_ty",
  2307 + "matchingTypeName": "mtch_ty_nm",
  2308 + "matchingNumber": "mtch_ky"
  2309 + },
  2310 + {
  2311 + "active": true,
  2312 + "type": "K-BA",
  2313 + "typeName": "자기채권(적요),상대채무(겨래일자),비교(년월,거래금액)",
  2314 +
  2315 + "condOne": {
  2316 + "cond": [
  2317 + "dta_ty in ('31','33','35','37','41')",
  2318 + "mtch_ty is null"
  2319 + ],
  2320 + "makeCompareKey": [
  2321 + "sys_se",
  2322 + "accnut_ym",
  2323 + "substring(sumry, 1, 80)"
  2324 + ]
  2325 + },
  2326 + "condTwo": {
  2327 + "cond": [
  2328 + "dta_ty in ('32','34','36','38','42')",
  2329 + "mtch_ty is null"
  2330 + ],
  2331 + "makeCompareKey": [
  2332 + "sys_se",
  2333 + "accnut_ym",
  2334 + "delng_de"
  2335 + ]
  2336 + },
  2337 + "uniqueKey": [
  2338 + "sys_se",
  2339 + "accnut_ym",
  2340 + "sn"
  2341 + ],
  2342 + "compareKey": "compare_ky",
  2343 + "amtField": "sum(delng_amt) as delng_amt",
  2344 + "compareField": [
  2345 + "accnut_ym",
  2346 + "delng_amt"
  2347 + ],
  2348 + "matchingType": "mtch_ty",
  2349 + "matchingTypeName": "mtch_ty_nm",
  2350 + "matchingNumber": "mtch_ky"
  2351 + },
  2352 + {
  2353 + "active": true,
  2354 + "type": "K-BB",
  2355 + "typeName": "자기채무(적요),상대채권(겨래일자),비교(년월,거래금액)",
  2356 +
  2357 + "condOne": {
  2358 + "cond": [
  2359 + "dta_ty in ('32','34','36','38','42')",
  2360 + "mtch_ty is null"
  2361 + ],
  2362 + "makeCompareKey": [
  2363 + "sys_se",
  2364 + "accnut_ym",
  2365 + "substring(sumry, 1, 80)"
  2366 + ]
  2367 + },
  2368 + "condTwo": {
  2369 + "cond": [
  2370 + "dta_ty in ('31','33','35','37','41')",
  2371 + "mtch_ty is null"
  2372 + ],
  2373 + "makeCompareKey": [
  2374 + "sys_se",
  2375 + "accnut_ym",
  2376 + "delng_de"
  2377 + ]
  2378 + },
  2379 + "uniqueKey": [
  2380 + "sys_se",
  2381 + "accnut_ym",
  2382 + "sn"
  2383 + ],
  2384 + "compareKey": "compare_ky",
  2385 + "amtField": "sum(delng_amt) as delng_amt",
  2386 + "compareField": [
  2387 + "accnut_ym",
  2388 + "delng_amt"
  2389 + ],
  2390 + "matchingType": "mtch_ty",
  2391 + "matchingTypeName": "mtch_ty_nm",
  2392 + "matchingNumber": "mtch_ky"
  2393 + },
  2394 + {
  2395 + "active": true,
  2396 + "type": "K-BC",
  2397 + "typeName": "자기채권(적요),개별상대채무,비교(년월,거래금액)",
  2398 +
  2399 + "condOne": {
  2400 + "cond": [
  2401 + "dta_ty in ('31','33','35','37','41')",
  2402 + "mtch_ty is null"
  2403 + ],
  2404 + "makeCompareKey": [
  2405 + "sys_se",
  2406 + "accnut_ym",
  2407 + "substring(sumry, 1, 80)"
  2408 + ]
  2409 + },
  2410 + "condTwo": {
  2411 + "cond": [
  2412 + "dta_ty in ('32','34','36','38','42')",
  2413 + "mtch_ty is null"
  2414 + ],
  2415 + "makeCompareKey": [
  2416 + "sys_se",
  2417 + "accnut_ym",
  2418 + "cast(sn as text)"
  2419 + ]
  2420 + },
  2421 + "uniqueKey": [
  2422 + "sys_se",
  2423 + "accnut_ym",
  2424 + "sn"
  2425 + ],
  2426 + "compareKey": "compare_ky",
  2427 + "amtField": "sum(delng_amt) as delng_amt",
  2428 + "compareField": [
  2429 + "accnut_ym",
  2430 + "delng_amt"
  2431 + ],
  2432 + "matchingType": "mtch_ty",
  2433 + "matchingTypeName": "mtch_ty_nm",
  2434 + "matchingNumber": "mtch_ky"
  2435 + },
  2436 + {
  2437 + "active": true,
  2438 + "type": "K-BD",
  2439 + "typeName": "자기채무(적요),개별상대채권,비교(년월,거래금액)",
  2440 +
  2441 + "condOne": {
  2442 + "cond": [
  2443 + "dta_ty in ('32','34','36','38','42')",
  2444 + "mtch_ty is null"
  2445 + ],
  2446 + "makeCompareKey": [
  2447 + "sys_se",
  2448 + "accnut_ym",
  2449 + "substring(sumry, 1, 80)"
  2450 + ]
  2451 + },
  2452 + "condTwo": {
  2453 + "cond": [
  2454 + "dta_ty in ('31','33','35','37','41')",
  2455 + "mtch_ty is null"
  2456 + ],
  2457 + "makeCompareKey": [
  2458 + "sys_se",
  2459 + "accnut_ym",
  2460 + "cast(sn as text)"
  2461 + ]
  2462 + },
  2463 + "uniqueKey": [
  2464 + "sys_se",
  2465 + "accnut_ym",
  2466 + "sn"
  2467 + ],
  2468 + "compareKey": "compare_ky",
  2469 + "amtField": "sum(delng_amt) as delng_amt",
  2470 + "compareField": [
  2471 + "accnut_ym",
  2472 + "delng_amt"
  2473 + ],
  2474 + "matchingType": "mtch_ty",
  2475 + "matchingTypeName": "mtch_ty_nm",
  2476 + "matchingNumber": "mtch_ky"
  2477 + },
  2478 +
  2479 +
  2480 +
  2481 +
  2482 + {
  2483 + "active": true,
  2484 + "type": "L-A",
  2485 + "typeName": "자기수익(회계일자),상대비용(회계일자),비교(년월,거래금액)",
  2486 +
  2487 + "condOne": {
  2488 + "cond": [
  2489 + "dta_ty in ('11','21')",
  2490 + "mtch_ty is null",
  2491 + "elcty_de is not null",
  2492 + "elcty_de != ''"
  2493 + ],
  2494 + "makeCompareKey": [
  2495 + "elcty_de"
  2496 + ]
  2497 + },
  2498 + "condTwo": {
  2499 + "cond": [
  2500 + "dta_ty in ('12','22')",
  2501 + "mtch_ty is null",
  2502 + "elcty_de is not null",
  2503 + "elcty_de != ''"
  2504 + ],
  2505 + "makeCompareKey": [
  2506 + "elcty_de"
  2507 + ]
  2508 + },
  2509 + "uniqueKey": [
  2510 + "sys_se",
  2511 + "accnut_ym",
  2512 + "sn"
  2513 + ],
  2514 + "compareKey": "compare_ky",
  2515 + "amtField": "sum(delng_amt) as delng_amt",
  2516 + "compareField": [
  2517 + "accnut_ym",
  2518 + "delng_amt"
  2519 + ],
  2520 + "matchingType": "mtch_ty",
  2521 + "matchingTypeName": "mtch_ty_nm",
  2522 + "matchingNumber": "mtch_ky"
  2523 + },
  2524 + {
  2525 + "active": true,
  2526 + "type": "L-AA",
  2527 + "typeName": "자기수익(회계일자),개별상대비용,비교(년월,거래금액)",
  2528 +
  2529 + "condOne": {
  2530 + "cond": [
  2531 + "dta_ty in ('11','21')",
  2532 + "mtch_ty is null",
  2533 + "elcty_de is not null",
  2534 + "elcty_de != ''"
  2535 + ],
  2536 + "makeCompareKey": [
  2537 + "elcty_de"
  2538 + ]
  2539 + },
  2540 + "condTwo": {
  2541 + "cond": [
  2542 + "dta_ty in ('12','22')",
  2543 + "mtch_ty is null"
  2544 + ],
  2545 + "makeCompareKey": [
  2546 + "sys_se",
  2547 + "accnut_ym",
  2548 + "cast(sn as text)"
  2549 + ]
  2550 + },
  2551 + "uniqueKey": [
  2552 + "sys_se",
  2553 + "accnut_ym",
  2554 + "sn"
  2555 + ],
  2556 + "compareKey": "compare_ky",
  2557 + "amtField": "sum(delng_amt) as delng_amt",
  2558 + "compareField": [
  2559 + "accnut_ym",
  2560 + "delng_amt"
  2561 + ],
  2562 + "matchingType": "mtch_ty",
  2563 + "matchingTypeName": "mtch_ty_nm",
  2564 + "matchingNumber": "mtch_ky"
  2565 + },
  2566 + {
  2567 + "active": true,
  2568 + "type": "L-AB",
  2569 + "typeName": "자기비용(회계일자),개별상대수익,비교(년월,거래금액)",
  2570 +
  2571 + "condOne": {
  2572 + "cond": [
  2573 + "dta_ty in ('12','22')",
  2574 + "mtch_ty is null",
  2575 + "elcty_de is not null",
  2576 + "elcty_de != ''"
  2577 + ],
  2578 + "makeCompareKey": [
  2579 + "elcty_de"
  2580 + ]
  2581 + },
  2582 + "condTwo": {
  2583 + "cond": [
  2584 + "dta_ty in ('11','21')",
  2585 + "mtch_ty is null"
  2586 + ],
  2587 + "makeCompareKey": [
  2588 + "sys_se",
  2589 + "accnut_ym",
  2590 + "cast(sn as text)"
  2591 + ]
  2592 + },
  2593 + "uniqueKey": [
  2594 + "sys_se",
  2595 + "accnut_ym",
  2596 + "sn"
  2597 + ],
  2598 + "compareKey": "compare_ky",
  2599 + "amtField": "sum(delng_amt) as delng_amt",
  2600 + "compareField": [
  2601 + "accnut_ym",
  2602 + "delng_amt"
  2603 + ],
  2604 + "matchingType": "mtch_ty",
  2605 + "matchingTypeName": "mtch_ty_nm",
  2606 + "matchingNumber": "mtch_ky"
  2607 + },
  2608 +
  2609 +
  2610 +
  2611 +
  2612 +
  2613 + {
  2614 + "active": true,
  2615 + "type": "M-A",
  2616 + "typeName": "자기수익(법인계정코드),상대비용(법인계정코드),비교(년월,거래금액)",
  2617 +
  2618 + "condOne": {
  2619 + "cond": [
  2620 + "dta_ty in ('11','21')",
  2621 + "mtch_ty is null"
  2622 + ],
  2623 + "makeCompareKey": [
  2624 + "cpr_acnt_code"
  2625 + ]
  2626 + },
  2627 + "condTwo": {
  2628 + "cond": [
  2629 + "dta_ty in ('12','22')",
  2630 + "mtch_ty is null"
  2631 + ],
  2632 + "makeCompareKey": [
  2633 + "cpr_acnt_code"
  2634 + ]
  2635 + },
  2636 + "uniqueKey": [
  2637 + "sys_se",
  2638 + "accnut_ym",
  2639 + "sn"
  2640 + ],
  2641 + "compareKey": "compare_ky",
  2642 + "amtField": "sum(delng_amt) as delng_amt",
  2643 + "compareField": [
  2644 + "accnut_ym",
  2645 + "delng_amt"
  2646 + ],
  2647 + "matchingType": "mtch_ty",
  2648 + "matchingTypeName": "mtch_ty_nm",
  2649 + "matchingNumber": "mtch_ky"
  2650 + },
  2651 + {
  2652 + "active": true,
  2653 + "type": "M-AA",
  2654 + "typeName": "자기수익(법인계정코드),개별상대비용,비교(년월,거래금액)",
  2655 +
  2656 + "condOne": {
  2657 + "cond": [
  2658 + "dta_ty in ('11','21')",
  2659 + "mtch_ty is null"
  2660 + ],
  2661 + "makeCompareKey": [
  2662 + "cpr_acnt_code"
  2663 + ]
  2664 + },
  2665 + "condTwo": {
  2666 + "cond": [
  2667 + "dta_ty in ('12','22')",
  2668 + "mtch_ty is null"
  2669 + ],
  2670 + "makeCompareKey": [
  2671 + "sys_se",
  2672 + "accnut_ym",
  2673 + "cast(sn as text)"
  2674 + ]
  2675 + },
  2676 + "uniqueKey": [
  2677 + "sys_se",
  2678 + "accnut_ym",
  2679 + "sn"
  2680 + ],
  2681 + "compareKey": "compare_ky",
  2682 + "amtField": "sum(delng_amt) as delng_amt",
  2683 + "compareField": [
  2684 + "accnut_ym",
  2685 + "delng_amt"
  2686 + ],
  2687 + "matchingType": "mtch_ty",
  2688 + "matchingTypeName": "mtch_ty_nm",
  2689 + "matchingNumber": "mtch_ky"
  2690 + },
  2691 + {
  2692 + "active": true,
  2693 + "type": "M-AB",
  2694 + "typeName": "자기비용(법인계정코드),개별상대수익,비교(년월,거래금액)",
  2695 +
  2696 + "condOne": {
  2697 + "cond": [
  2698 + "dta_ty in ('12','22')",
  2699 + "mtch_ty is null"
  2700 + ],
  2701 + "makeCompareKey": [
  2702 + "cpr_acnt_code"
  2703 + ]
  2704 + },
  2705 + "condTwo": {
  2706 + "cond": [
  2707 + "dta_ty in ('11','21')",
  2708 + "mtch_ty is null"
  2709 + ],
  2710 + "makeCompareKey": [
  2711 + "sys_se",
  2712 + "accnut_ym",
  2713 + "cast(sn as text)"
  2714 + ]
  2715 + },
  2716 + "uniqueKey": [
  2717 + "sys_se",
  2718 + "accnut_ym",
  2719 + "sn"
  2720 + ],
  2721 + "compareKey": "compare_ky",
  2722 + "amtField": "sum(delng_amt) as delng_amt",
  2723 + "compareField": [
  2724 + "accnut_ym",
  2725 + "delng_amt"
  2726 + ],
  2727 + "matchingType": "mtch_ty",
  2728 + "matchingTypeName": "mtch_ty_nm",
  2729 + "matchingNumber": "mtch_ky"
  2730 + },
  2731 +
  2732 +
  2733 +
  2734 +
  2735 + {
  2736 + "active": true,
  2737 + "type": "N-A",
  2738 + "typeName": "자기수익(계정코드),상대비용(계정코드),비교(년월,거래금액)",
  2739 +
  2740 + "condOne": {
  2741 + "cond": [
  2742 + "dta_ty in ('11','21')",
  2743 + "mtch_ty is null"
  2744 + ],
  2745 + "makeCompareKey": [
  2746 + "cnnc_acnt_code"
  2747 + ]
  2748 + },
  2749 + "condTwo": {
  2750 + "cond": [
  2751 + "dta_ty in ('12','22')",
  2752 + "mtch_ty is null"
  2753 + ],
  2754 + "makeCompareKey": [
  2755 + "cnnc_acnt_code"
  2756 + ]
  2757 + },
  2758 + "uniqueKey": [
  2759 + "sys_se",
  2760 + "accnut_ym",
  2761 + "sn"
  2762 + ],
  2763 + "compareKey": "compare_ky",
  2764 + "amtField": "sum(delng_amt) as delng_amt",
  2765 + "compareField": [
  2766 + "accnut_ym",
  2767 + "delng_amt"
  2768 + ],
  2769 + "matchingType": "mtch_ty",
  2770 + "matchingTypeName": "mtch_ty_nm",
  2771 + "matchingNumber": "mtch_ky"
  2772 + },
  2773 + {
  2774 + "active": true,
  2775 + "type": "N-AA",
  2776 + "typeName": "자기수익(계정코드),개별상대비용,비교(년월,거래금액)",
  2777 +
  2778 + "condOne": {
  2779 + "cond": [
  2780 + "dta_ty in ('11','21')",
  2781 + "mtch_ty is null"
  2782 + ],
  2783 + "makeCompareKey": [
  2784 + "cnnc_acnt_code"
  2785 + ]
  2786 + },
  2787 + "condTwo": {
  2788 + "cond": [
  2789 + "dta_ty in ('12','22')",
  2790 + "mtch_ty is null"
  2791 + ],
  2792 + "makeCompareKey": [
  2793 + "sys_se",
  2794 + "accnut_ym",
  2795 + "cast(sn as text)"
  2796 + ]
  2797 + },
  2798 + "uniqueKey": [
  2799 + "sys_se",
  2800 + "accnut_ym",
  2801 + "sn"
  2802 + ],
  2803 + "compareKey": "compare_ky",
  2804 + "amtField": "sum(delng_amt) as delng_amt",
  2805 + "compareField": [
  2806 + "accnut_ym",
  2807 + "delng_amt"
  2808 + ],
  2809 + "matchingType": "mtch_ty",
  2810 + "matchingTypeName": "mtch_ty_nm",
  2811 + "matchingNumber": "mtch_ky"
  2812 + },
  2813 + {
  2814 + "active": true,
  2815 + "type": "N-AB",
  2816 + "typeName": "자기비용(계정코드),개별상대수익,비교(년월,비교키,거래금액)",
  2817 +
  2818 + "condOne": {
  2819 + "cond": [
  2820 + "dta_ty in ('12','22')",
  2821 + "mtch_ty is null"
  2822 + ],
  2823 + "makeCompareKey": [
  2824 + "cnnc_acnt_code"
  2825 + ]
  2826 + },
  2827 + "condTwo": {
  2828 + "cond": [
  2829 + "dta_ty in ('11','21')",
  2830 + "mtch_ty is null"
  2831 + ],
  2832 + "makeCompareKey": [
  2833 + "sys_se",
  2834 + "accnut_ym",
  2835 + "cast(sn as text)"
  2836 + ]
  2837 + },
  2838 + "uniqueKey": [
  2839 + "sys_se",
  2840 + "accnut_ym",
  2841 + "sn"
  2842 + ],
  2843 + "compareKey": "compare_ky",
  2844 + "amtField": "sum(delng_amt) as delng_amt",
  2845 + "compareField": [
  2846 + "accnut_ym",
  2847 + "delng_amt"
  2848 + ],
  2849 + "matchingType": "mtch_ty",
  2850 + "matchingTypeName": "mtch_ty_nm",
  2851 + "matchingNumber": "mtch_ky"
  2852 + },
  2853 + {
  2854 + "active": true,
  2855 + "type": "N-AC",
  2856 + "typeName": "자기수익(계정코드),상대비용(법인계정코드),비교(년월,거래금액)",
  2857 +
  2858 + "condOne": {
  2859 + "cond": [
  2860 + "dta_ty in ('11','21')",
  2861 + "mtch_ty is null"
  2862 + ],
  2863 + "makeCompareKey": [
  2864 + "cnnc_acnt_code"
  2865 + ]
  2866 + },
  2867 + "condTwo": {
  2868 + "cond": [
  2869 + "dta_ty in ('12','22')",
  2870 + "mtch_ty is null"
  2871 + ],
  2872 + "makeCompareKey": [
  2873 + "cpr_acnt_code"
  2874 + ]
  2875 + },
  2876 + "uniqueKey": [
  2877 + "sys_se",
  2878 + "accnut_ym",
  2879 + "sn"
  2880 + ],
  2881 + "compareKey": "compare_ky",
  2882 + "amtField": "sum(delng_amt) as delng_amt",
  2883 + "compareField": [
  2884 + "accnut_ym",
  2885 + "delng_amt"
  2886 + ],
  2887 + "matchingType": "mtch_ty",
  2888 + "matchingTypeName": "mtch_ty_nm",
  2889 + "matchingNumber": "mtch_ky"
  2890 + },
  2891 + {
  2892 + "active": true,
  2893 + "type": "N-AD",
  2894 + "typeName": "자기비용(계정코드),상대수익(법인계정코드),비교(년월,거래금액)",
  2895 +
  2896 + "condOne": {
  2897 + "cond": [
  2898 + "dta_ty in ('12','22')",
  2899 + "mtch_ty is null"
  2900 + ],
  2901 + "makeCompareKey": [
  2902 + "cnnc_acnt_code"
  2903 + ]
  2904 + },
  2905 + "condTwo": {
  2906 + "cond": [
  2907 + "dta_ty in ('11','21')",
  2908 + "mtch_ty is null"
  2909 + ],
  2910 + "makeCompareKey": [
  2911 + "cpr_acnt_code"
  2912 + ]
  2913 + },
  2914 + "uniqueKey": [
  2915 + "sys_se",
  2916 + "accnut_ym",
  2917 + "sn"
  2918 + ],
  2919 + "compareKey": "compare_ky",
  2920 + "amtField": "sum(delng_amt) as delng_amt",
  2921 + "compareField": [
  2922 + "accnut_ym",
  2923 + "delng_amt"
  2924 + ],
  2925 + "matchingType": "mtch_ty",
  2926 + "matchingTypeName": "mtch_ty_nm",
  2927 + "matchingNumber": "mtch_ky"
  2928 + },
  2929 +
  2930 +
  2931 +
  2932 +
  2933 + {
  2934 + "active": true,
  2935 + "type": "O-A",
  2936 + "typeName": "자기수익(INVOICE),상대비용(INVOICE),비교(년월,거래금액)",
  2937 +
  2938 + "condOne": {
  2939 + "cond": [
  2940 + "dta_ty in ('11','21')",
  2941 + "mtch_ty is null",
  2942 + "ext_key2 is not null",
  2943 + "ext_key2 != ''"
  2944 + ],
  2945 + "makeCompareKey": [
  2946 + "ext_key2"
  2947 + ]
  2948 + },
  2949 + "condTwo": {
  2950 + "cond": [
  2951 + "dta_ty in ('12','22')",
  2952 + "mtch_ty is null",
  2953 + "ext_key2 is not null",
  2954 + "ext_key2 != ''"
  2955 + ],
  2956 + "makeCompareKey": [
  2957 + "ext_key2"
  2958 + ]
  2959 + },
  2960 + "uniqueKey": [
  2961 + "sys_se",
  2962 + "accnut_ym",
  2963 + "sn"
  2964 + ],
  2965 + "compareKey": "compare_ky",
  2966 + "amtField": "sum(delng_amt) as delng_amt",
  2967 + "compareField": [
  2968 + "accnut_ym",
  2969 + "delng_amt"
  2970 + ],
  2971 + "matchingType": "mtch_ty",
  2972 + "matchingTypeName": "mtch_ty_nm",
  2973 + "matchingNumber": "mtch_ky"
  2974 + },
  2975 + {
  2976 + "active": true,
  2977 + "type": "O-AA",
  2978 + "typeName": "자기수익(INVOICE),개별상대비용,비교(년월,거래금액)",
  2979 +
  2980 + "condOne": {
  2981 + "cond": [
  2982 + "dta_ty in ('11','21')",
  2983 + "mtch_ty is null",
  2984 + "ext_key2 is not null",
  2985 + "ext_key2 != ''"
  2986 + ],
  2987 + "makeCompareKey": [
  2988 + "ext_key2"
  2989 + ]
  2990 + },
  2991 + "condTwo": {
  2992 + "cond": [
  2993 + "dta_ty in ('12','22')",
  2994 + "mtch_ty is null"
  2995 + ],
  2996 + "makeCompareKey": [
  2997 + "sys_se",
  2998 + "accnut_ym",
  2999 + "cast(sn as text)"
  3000 + ]
  3001 + },
  3002 + "uniqueKey": [
  3003 + "sys_se",
  3004 + "accnut_ym",
  3005 + "sn"
  3006 + ],
  3007 + "compareKey": "compare_ky",
  3008 + "amtField": "sum(delng_amt) as delng_amt",
  3009 + "compareField": [
  3010 + "accnut_ym",
  3011 + "delng_amt"
  3012 + ],
  3013 + "matchingType": "mtch_ty",
  3014 + "matchingTypeName": "mtch_ty_nm",
  3015 + "matchingNumber": "mtch_ky"
  3016 + },
  3017 + {
  3018 + "active": true,
  3019 + "type": "O-AB",
  3020 + "typeName": "자기비용(INVOICE),개별상대수익,비교(년월,거래금액)",
  3021 +
  3022 + "condOne": {
  3023 + "cond": [
  3024 + "dta_ty in ('12','22')",
  3025 + "mtch_ty is null",
  3026 + "ext_key2 is not null",
  3027 + "ext_key2 != ''"
  3028 + ],
  3029 + "makeCompareKey": [
  3030 + "ext_key2"
  3031 + ]
  3032 + },
  3033 + "condTwo": {
  3034 + "cond": [
  3035 + "dta_ty in ('11','21')",
  3036 + "mtch_ty is null"
  3037 + ],
  3038 + "makeCompareKey": [
  3039 + "sys_se",
  3040 + "accnut_ym",
  3041 + "cast(sn as text)"
  3042 + ]
  3043 + },
  3044 + "uniqueKey": [
  3045 + "sys_se",
  3046 + "accnut_ym",
  3047 + "sn"
  3048 + ],
  3049 + "compareKey": "compare_ky",
  3050 + "amtField": "sum(delng_amt) as delng_amt",
  3051 + "compareField": [
  3052 + "accnut_ym",
  3053 + "delng_amt"
  3054 + ],
  3055 + "matchingType": "mtch_ty",
  3056 + "matchingTypeName": "mtch_ty_nm",
  3057 + "matchingNumber": "mtch_ky"
  3058 + },
  3059 +
  3060 +
  3061 +
  3062 + {
  3063 + "active": true,
  3064 + "type": "P-A",
  3065 + "typeName": "자기수익(BL),상대비용(BL),비교(년월,거래금액)",
  3066 +
  3067 + "condOne": {
  3068 + "cond": [
  3069 + "dta_ty in ('11','21')",
  3070 + "mtch_ty is null",
  3071 + "ext_key3 is not null",
  3072 + "ext_key3 != ''"
  3073 + ],
  3074 + "makeCompareKey": [
  3075 + "ext_key3"
  3076 + ]
  3077 + },
  3078 + "condTwo": {
  3079 + "cond": [
  3080 + "dta_ty in ('12','22')",
  3081 + "mtch_ty is null",
  3082 + "ext_key3 is not null",
  3083 + "ext_key3 != ''"
  3084 + ],
  3085 + "makeCompareKey": [
  3086 + "ext_key3"
  3087 + ]
  3088 + },
  3089 + "uniqueKey": [
  3090 + "sys_se",
  3091 + "accnut_ym",
  3092 + "sn"
  3093 + ],
  3094 + "compareKey": "compare_ky",
  3095 + "amtField": "sum(delng_amt) as delng_amt",
  3096 + "compareField": [
  3097 + "accnut_ym",
  3098 + "delng_amt"
  3099 + ],
  3100 + "matchingType": "mtch_ty",
  3101 + "matchingTypeName": "mtch_ty_nm",
  3102 + "matchingNumber": "mtch_ky"
  3103 + },
  3104 + {
  3105 + "active": true,
  3106 + "type": "P-AA",
  3107 + "typeName": "자기수익(BL),개별상대비용,비교(년월,거래금액)",
  3108 +
  3109 + "condOne": {
  3110 + "cond": [
  3111 + "dta_ty in ('11','21')",
  3112 + "mtch_ty is null",
  3113 + "ext_key3 is not null",
  3114 + "ext_key3 != ''"
  3115 + ],
  3116 + "makeCompareKey": [
  3117 + "ext_key3"
  3118 + ]
  3119 + },
  3120 + "condTwo": {
  3121 + "cond": [
  3122 + "dta_ty in ('12','22')",
  3123 + "mtch_ty is null"
  3124 + ],
  3125 + "makeCompareKey": [
  3126 + "sys_se",
  3127 + "accnut_ym",
  3128 + "cast(sn as text)"
  3129 + ]
  3130 + },
  3131 + "uniqueKey": [
  3132 + "sys_se",
  3133 + "accnut_ym",
  3134 + "sn"
  3135 + ],
  3136 + "compareKey": "compare_ky",
  3137 + "amtField": "sum(delng_amt) as delng_amt",
  3138 + "compareField": [
  3139 + "accnut_ym",
  3140 + "delng_amt"
  3141 + ],
  3142 + "matchingType": "mtch_ty",
  3143 + "matchingTypeName": "mtch_ty_nm",
  3144 + "matchingNumber": "mtch_ky"
  3145 + },
  3146 + {
  3147 + "active": true,
  3148 + "type": "P-AB",
  3149 + "typeName": "자기비용(BL),개별상대수익,비교(년월,거래금액)",
  3150 +
  3151 + "condOne": {
  3152 + "cond": [
  3153 + "dta_ty in ('12','22')",
  3154 + "mtch_ty is null",
  3155 + "ext_key3 is not null",
  3156 + "ext_key3 != ''"
  3157 + ],
  3158 + "makeCompareKey": [
  3159 + "ext_key3"
  3160 + ]
  3161 + },
  3162 + "condTwo": {
  3163 + "cond": [
  3164 + "dta_ty in ('11','21')",
  3165 + "mtch_ty is null"
  3166 + ],
  3167 + "makeCompareKey": [
  3168 + "sys_se",
  3169 + "accnut_ym",
  3170 + "cast(sn as text)"
  3171 + ]
  3172 + },
  3173 + "uniqueKey": [
  3174 + "sys_se",
  3175 + "accnut_ym",
  3176 + "sn"
  3177 + ],
  3178 + "compareKey": "compare_ky",
  3179 + "amtField": "sum(delng_amt) as delng_amt",
  3180 + "compareField": [
  3181 + "accnut_ym",
  3182 + "delng_amt"
  3183 + ],
  3184 + "matchingType": "mtch_ty",
  3185 + "matchingTypeName": "mtch_ty_nm",
  3186 + "matchingNumber": "mtch_ky"
  3187 + },
  3188 +
  3189 +
  3190 +
  3191 + {
  3192 + "active": true,
  3193 + "type": "Q-A",
  3194 + "typeName": "자기수익(LC),상대비용(LC),비교(년월,거래금액)",
  3195 +
  3196 + "condOne": {
  3197 + "cond": [
  3198 + "dta_ty in ('11','21')",
  3199 + "mtch_ty is null",
  3200 + "ext_key4 is not null",
  3201 + "ext_key4 != ''"
  3202 + ],
  3203 + "makeCompareKey": [
  3204 + "ext_key4"
  3205 + ]
  3206 + },
  3207 + "condTwo": {
  3208 + "cond": [
  3209 + "dta_ty in ('12','22')",
  3210 + "mtch_ty is null",
  3211 + "ext_key4 is not null",
  3212 + "ext_key4 != ''"
  3213 + ],
  3214 + "makeCompareKey": [
  3215 + "ext_key4"
  3216 + ]
  3217 + },
  3218 + "uniqueKey": [
  3219 + "sys_se",
  3220 + "accnut_ym",
  3221 + "sn"
  3222 + ],
  3223 + "compareKey": "compare_ky",
  3224 + "amtField": "sum(delng_amt) as delng_amt",
  3225 + "compareField": [
  3226 + "accnut_ym",
  3227 + "delng_amt"
  3228 + ],
  3229 + "matchingType": "mtch_ty",
  3230 + "matchingTypeName": "mtch_ty_nm",
  3231 + "matchingNumber": "mtch_ky"
  3232 + },
  3233 + {
  3234 + "active": true,
  3235 + "type": "Q-AA",
  3236 + "typeName": "자기수익(LC),개별상대비용,비교(년월,거래금액)",
  3237 +
  3238 + "condOne": {
  3239 + "cond": [
  3240 + "dta_ty in ('11','21')",
  3241 + "mtch_ty is null",
  3242 + "ext_key4 is not null",
  3243 + "ext_key4 != ''"
  3244 + ],
  3245 + "makeCompareKey": [
  3246 + "ext_key4"
  3247 + ]
  3248 + },
  3249 + "condTwo": {
  3250 + "cond": [
  3251 + "dta_ty in ('12','22')",
  3252 + "mtch_ty is null"
  3253 + ],
  3254 + "makeCompareKey": [
  3255 + "sys_se",
  3256 + "accnut_ym",
  3257 + "cast(sn as text)"
  3258 + ]
  3259 + },
  3260 + "uniqueKey": [
  3261 + "sys_se",
  3262 + "accnut_ym",
  3263 + "sn"
  3264 + ],
  3265 + "compareKey": "compare_ky",
  3266 + "amtField": "sum(delng_amt) as delng_amt",
  3267 + "compareField": [
  3268 + "accnut_ym",
  3269 + "delng_amt"
  3270 + ],
  3271 + "matchingType": "mtch_ty",
  3272 + "matchingTypeName": "mtch_ty_nm",
  3273 + "matchingNumber": "mtch_ky"
  3274 + },
  3275 + {
  3276 + "active": true,
  3277 + "type": "Q-AB",
  3278 + "typeName": "자기비용(LC),개별상대수익,비교(년월,거래금액)",
  3279 +
  3280 + "condOne": {
  3281 + "cond": [
  3282 + "dta_ty in ('12','22')",
  3283 + "mtch_ty is null",
  3284 + "ext_key4 is not null",
  3285 + "ext_key4 != ''"
  3286 + ],
  3287 + "makeCompareKey": [
  3288 + "ext_key4"
  3289 + ]
  3290 + },
  3291 + "condTwo": {
  3292 + "cond": [
  3293 + "dta_ty in ('11','21')",
  3294 + "mtch_ty is null"
  3295 + ],
  3296 + "makeCompareKey": [
  3297 + "sys_se",
  3298 + "accnut_ym",
  3299 + "cast(sn as text)"
  3300 + ]
  3301 + },
  3302 + "uniqueKey": [
  3303 + "sys_se",
  3304 + "accnut_ym",
  3305 + "sn"
  3306 + ],
  3307 + "compareKey": "compare_ky",
  3308 + "amtField": "sum(delng_amt) as delng_amt",
  3309 + "compareField": [
  3310 + "accnut_ym",
  3311 + "delng_amt"
  3312 + ],
  3313 + "matchingType": "mtch_ty",
  3314 + "matchingTypeName": "mtch_ty_nm",
  3315 + "matchingNumber": "mtch_ky"
  3316 + },
  3317 +
  3318 +
  3319 +
  3320 +
  3321 +
  3322 + {
  3323 + "active": true,
  3324 + "type": "Z-AA",
  3325 + "typeName": "[재실행]자기수익(거래일자),상대비용(거래일자),비교(년월,거래금액)",
  3326 +
  3327 + "condOne": {
  3328 + "cond": [
  3329 + "dta_ty in ('11','21')",
  3330 + "mtch_ty is null"
  3331 + ],
  3332 + "makeCompareKey": [
  3333 + "sys_se",
  3334 + "accnut_ym",
  3335 + "delng_de"
  3336 + ]
  3337 + },
  3338 + "condTwo": {
  3339 + "cond": [
  3340 + "dta_ty in ('12','22')",
  3341 + "mtch_ty is null"
  3342 + ],
  3343 + "makeCompareKey": [
  3344 + "sys_se",
  3345 + "accnut_ym",
  3346 + "delng_de"
  3347 + ]
  3348 + },
  3349 + "uniqueKey": [
  3350 + "sys_se",
  3351 + "accnut_ym",
  3352 + "sn"
  3353 + ],
  3354 + "compareKey": "compare_ky",
  3355 + "amtField": "sum(delng_amt) as delng_amt",
  3356 + "compareField": [
  3357 + "accnut_ym",
  3358 + "delng_amt"
  3359 + ],
  3360 + "matchingType": "mtch_ty",
  3361 + "matchingTypeName": "mtch_ty_nm",
  3362 + "matchingNumber": "mtch_ky"
  3363 + },
  3364 + {
  3365 + "active": true,
  3366 + "type": "Z-AB",
  3367 + "typeName": "[재실행]자기수익(거래월),상대비용(거래월),비교(년월,거래금액)",
  3368 +
  3369 + "condOne": {
  3370 + "cond": [
  3371 + "dta_ty in ('11','21')",
  3372 + "mtch_ty is null"
  3373 + ],
  3374 + "makeCompareKey": [
  3375 + "sys_se",
  3376 + "accnut_ym",
  3377 + "substring(delng_de,1,6)"
  3378 + ]
  3379 + },
  3380 + "condTwo": {
  3381 + "cond": [
  3382 + "dta_ty in ('12','22')",
  3383 + "mtch_ty is null"
  3384 + ],
  3385 + "makeCompareKey": [
  3386 + "sys_se",
  3387 + "accnut_ym",
  3388 + "substring(delng_de,1,6)"
  3389 + ]
  3390 + },
  3391 + "uniqueKey": [
  3392 + "sys_se",
  3393 + "accnut_ym",
  3394 + "sn"
  3395 + ],
  3396 + "compareKey": "compare_ky",
  3397 + "amtField": "sum(delng_amt) as delng_amt",
  3398 + "compareField": [
  3399 + "accnut_ym",
  3400 + "delng_amt"
  3401 + ],
  3402 + "matchingType": "mtch_ty",
  3403 + "matchingTypeName": "mtch_ty_nm",
  3404 + "matchingNumber": "mtch_ky"
  3405 + },
  3406 + {
  3407 + "active": true,
  3408 + "type": "Z-AC",
  3409 + "typeName": "[재실행]자기수익(전체),상대비용(전체),비교(년월,거래금액)",
  3410 +
  3411 + "condOne": {
  3412 + "cond": [
  3413 + "dta_ty in ('11','21')",
  3414 + "mtch_ty is null"
  3415 + ],
  3416 + "makeCompareKey": [
  3417 + "sys_se",
  3418 + "accnut_ym"
  3419 + ]
  3420 + },
  3421 + "condTwo": {
  3422 + "cond": [
  3423 + "dta_ty in ('12','22')",
  3424 + "mtch_ty is null"
  3425 + ],
  3426 + "makeCompareKey": [
  3427 + "sys_se",
  3428 + "accnut_ym"
  3429 + ]
  3430 + },
  3431 + "uniqueKey": [
  3432 + "sys_se",
  3433 + "accnut_ym",
  3434 + "sn"
  3435 + ],
  3436 + "compareKey": "compare_ky",
  3437 + "amtField": "sum(delng_amt) as delng_amt",
  3438 + "compareField": [
  3439 + "accnut_ym",
  3440 + "delng_amt"
  3441 + ],
  3442 + "matchingType": "mtch_ty",
  3443 + "matchingTypeName": "mtch_ty_nm",
  3444 + "matchingNumber": "mtch_ky"
  3445 + },
  3446 + {
  3447 + "active": true,
  3448 + "type": "Z-BA",
  3449 + "typeName": "[재실행]자기채권(거래일자),상대채무(거래일자),비교(년월,거래금액)",
  3450 +
  3451 + "condOne": {
  3452 + "cond": [
  3453 + "dta_ty in ('31','33','35','37','41')",
  3454 + "mtch_ty is null"
  3455 + ],
  3456 + "makeCompareKey": [
  3457 + "sys_se",
  3458 + "accnut_ym",
  3459 + "delng_de"
  3460 + ]
  3461 + },
  3462 + "condTwo": {
  3463 + "cond": [
  3464 + "dta_ty in ('32','34','36','38','42')",
  3465 + "mtch_ty is null"
  3466 + ],
  3467 + "makeCompareKey": [
  3468 + "sys_se",
  3469 + "accnut_ym",
  3470 + "delng_de"
  3471 + ]
  3472 + },
  3473 + "uniqueKey": [
  3474 + "sys_se",
  3475 + "accnut_ym",
  3476 + "sn"
  3477 + ],
  3478 + "compareKey": "compare_ky",
  3479 + "amtField": "sum(delng_amt) as delng_amt",
  3480 + "compareField": [
  3481 + "accnut_ym",
  3482 + "delng_amt"
  3483 + ],
  3484 + "matchingType": "mtch_ty",
  3485 + "matchingTypeName": "mtch_ty_nm",
  3486 + "matchingNumber": "mtch_ky"
  3487 + },
  3488 + {
  3489 + "active": true,
  3490 + "type": "Z-BB",
  3491 + "typeName": "[재실행]자기채권(거래월),상대채무(거래월),비교(년월,거래금액)",
  3492 +
  3493 + "condOne": {
  3494 + "cond": [
  3495 + "dta_ty in ('31','33','35','37','41')",
  3496 + "mtch_ty is null"
  3497 + ],
  3498 + "makeCompareKey": [
  3499 + "sys_se",
  3500 + "accnut_ym",
  3501 + "substring(delng_de,1,6)"
  3502 + ]
  3503 + },
  3504 + "condTwo": {
  3505 + "cond": [
  3506 + "dta_ty in ('32','34','36','38','42')",
  3507 + "mtch_ty is null"
  3508 + ],
  3509 + "makeCompareKey": [
  3510 + "sys_se",
  3511 + "accnut_ym",
  3512 + "substring(delng_de,1,6)"
  3513 + ]
  3514 + },
  3515 + "uniqueKey": [
  3516 + "sys_se",
  3517 + "accnut_ym",
  3518 + "sn"
  3519 + ],
  3520 + "compareKey": "compare_ky",
  3521 + "amtField": "sum(delng_amt) as delng_amt",
  3522 + "compareField": [
  3523 + "accnut_ym",
  3524 + "delng_amt"
  3525 + ],
  3526 + "matchingType": "mtch_ty",
  3527 + "matchingTypeName": "mtch_ty_nm",
  3528 + "matchingNumber": "mtch_ky"
  3529 + },
  3530 + {
  3531 + "active": true,
  3532 + "type": "Z-BC",
  3533 + "typeName": "[재실행]자기채권(전체),상대채무(전체),비교(년월,거래금액)",
  3534 +
  3535 + "condOne": {
  3536 + "cond": [
  3537 + "dta_ty in ('31','33','35','37','41')",
  3538 + "mtch_ty is null"
  3539 + ],
  3540 + "makeCompareKey": [
  3541 + "sys_se",
  3542 + "accnut_ym"
  3543 + ]
  3544 + },
  3545 + "condTwo": {
  3546 + "cond": [
  3547 + "dta_ty in ('32','34','36','38','42')",
  3548 + "mtch_ty is null"
  3549 + ],
  3550 + "makeCompareKey": [
  3551 + "sys_se",
  3552 + "accnut_ym"
  3553 + ]
  3554 + },
  3555 + "uniqueKey": [
  3556 + "sys_se",
  3557 + "accnut_ym",
  3558 + "sn"
  3559 + ],
  3560 + "compareKey": "compare_ky",
  3561 + "amtField": "sum(delng_amt) as delng_amt",
  3562 + "compareField": [
  3563 + "accnut_ym",
  3564 + "delng_amt"
  3565 + ],
  3566 + "matchingType": "mtch_ty",
  3567 + "matchingTypeName": "mtch_ty_nm",
  3568 + "matchingNumber": "mtch_ky"
  3569 + }
  3570 +
  3571 +
  3572 + ]
  3573 +}
0 3574 \ No newline at end of file
... ...
src/main/resources/mybatis/mybatis-config.xml 0 → 100644
  1 +++ a/src/main/resources/mybatis/mybatis-config.xml
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE configuration
  3 + PUBLIC "-//mybatis.org//DTD Config 3.0//EN"
  4 + "http://mybatis.org/dtd/mybatis-3-config.dtd">
  5 +
  6 +<configuration>
  7 + <settings>
  8 + <setting name="cacheEnabled" value="true" />
  9 + <setting name="aggressiveLazyLoading" value="true" />
  10 + <setting name="multipleResultSetsEnabled" value="true" />
  11 + <setting name="useColumnLabel" value="true" />
  12 + <setting name="useGeneratedKeys" value="true" />
  13 + <setting name="autoMappingBehavior" value="PARTIAL"/>
  14 + <!--setting name="defaultExecutorType" value="SIMPLE" /-->
  15 + <setting name="defaultExecutorType" value="SIMPLE" />
  16 + <setting name="defaultStatementTimeout" value="600" />
  17 + <setting name="safeRowBoundsEnabled" value="false" />
  18 + <setting name="mapUnderscoreToCamelCase" value="true" />
  19 + <setting name="localCacheScope" value="SESSION" />
  20 + </settings>
  21 +
  22 + <!-- 별칭 -->
  23 + <typeAliases>
  24 + <typeAlias type="daeucna.system.code.CodeDto" alias="CodeDto"/>
  25 + </typeAliases>
  26 +
  27 +</configuration>
0 28 \ No newline at end of file
... ...
src/main/resources/mybatis/primary/batch/MatchingInnerDelingMapper.xml 0 → 100644
  1 +++ a/src/main/resources/mybatis/primary/batch/MatchingInnerDelingMapper.xml
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
  3 +<mapper namespace="daeucna.mapper.primary.batch.MatchingInnerDelingMapper">
  4 +
  5 + <!-- 작업리스트 -->
  6 + <select id="getCustomItemReadData" parameterType="map" resultType="map">
  7 + SELECT
  8 + sys_se
  9 + , accnut_ym
  10 + , cpr_code
  11 + , partn_cpr
  12 + FROM
  13 + (
  14 + SELECT
  15 + sys_se
  16 + , accnut_ym
  17 + , cpr_code
  18 + , partn_cpr
  19 + , case when count(*) > 0 then 1 else 0 end as cnt
  20 + FROM
  21 + public.batch_tbcr_inner_delng
  22 + WHERE
  23 + sys_se = #{sysSe}
  24 + and accnut_ym = #{accnutYm}
  25 + and mtch_ty is null
  26 + and dta_ty in ('11','21','31','33','35','37','41')
  27 + GROUP BY
  28 + sys_se
  29 + , accnut_ym
  30 + , cpr_code
  31 + , partn_cpr
  32 + union all
  33 + SELECT
  34 + sys_se
  35 + , accnut_ym
  36 + , partn_cpr as cpr_code
  37 + , cpr_code as partn_cpr
  38 + , case when count(*) > 0 then 1 else 0 end as cnt
  39 + FROM
  40 + public.batch_tbcr_inner_delng
  41 + WHERE
  42 + sys_se = #{sysSe}
  43 + and accnut_ym = #{accnutYm}
  44 + and mtch_ty is null
  45 + and dta_ty in ('12','22','32','34','36','38','42')
  46 + GROUP BY
  47 + sys_se
  48 + , accnut_ym
  49 + , cpr_code
  50 + , partn_cpr
  51 + ) m
  52 + GROUP BY
  53 + sys_se
  54 + , accnut_ym
  55 + , cpr_code
  56 + , partn_cpr
  57 + HAVING sum(cnt) > 1
  58 + </select>
  59 +
  60 + <!-- 작업키 업데이트 -->
  61 + <update id="setDataMakeCompareKy" parameterType="map">
  62 + UPDATE public.batch_tbcr_inner_delng
  63 + SET
  64 + ${compareKey} = ${makeCompareKey}
  65 + WHERE
  66 + sys_se = #{sysSe}
  67 + and accnut_ym = #{accnutYm}
  68 + and cpr_code = #{cprCode}
  69 + and partn_cpr = #{partnCpr}
  70 + <foreach collection="cond" item="item" open="" close="" separator="">
  71 + and ${item}
  72 + </foreach>
  73 + </update>
  74 +
  75 + <!-- 매칭작업할 데이타 가져오기 -->
  76 + <select id="getMatchingData" parameterType="map" resultType="map">
  77 + SELECT
  78 + accnut_ym
  79 + , compare_ky
  80 + , ${amtField}
  81 + FROM
  82 + public.batch_tbcr_inner_delng
  83 + WHERE
  84 + sys_se = #{sysSe}
  85 + and accnut_ym = #{accnutYm}
  86 + and compare_ky is not null
  87 + and cpr_code = #{cprCode}
  88 + and partn_cpr = #{partnCpr}
  89 + <foreach collection="cond" item="item" open="" close="" separator="">
  90 + and ${item}
  91 + </foreach>
  92 + group by
  93 + accnut_ym,
  94 + compare_ky
  95 + </select>
  96 +
  97 + <!-- 매칭결과 업데이트 -->
  98 + <select id="getMatchingResult" parameterType="map" resultType="map">
  99 + SELECT
  100 + sys_se
  101 + , accnut_ym
  102 + , sn
  103 + , compare_ky
  104 + FROM
  105 + public.batch_tbcr_inner_delng
  106 + WHERE
  107 + sys_se = #{sysSe}
  108 + and accnut_ym = #{accnutYm}
  109 + and compare_ky is not null
  110 + and cpr_code = #{cprCode}
  111 + and partn_cpr = #{partnCpr}
  112 + <foreach collection="cond" item="item" open="" close="" separator="">
  113 + and ${item}
  114 + </foreach>
  115 + </select>
  116 +
  117 +
  118 + <update id="setResult" parameterType="map">
  119 + <foreach collection="itemList" item="item" separator=";">
  120 + UPDATE public.batch_tbcr_inner_delng
  121 + SET
  122 + mtch_sys = 'AUTO',
  123 + ${item.matchingType} = #{item.matchingTypeVal},
  124 + ${item.matchingTypeName} = #{item.matchingTypeNameVal},
  125 + ${item.matchingNumber} = #{item.matchingNumberVal}
  126 + WHERE
  127 + sys_se = #{item.sys_se}
  128 + and accnut_ym = #{item.accnut_ym}
  129 + and sn = #{item.sn}
  130 + </foreach>
  131 + </update>
  132 +
  133 +
  134 +
  135 +
  136 +
  137 +
  138 + <update id="deleteOriginalData" parameterType="map">
  139 + DELETE FROM tbcr_transaction_history
  140 + WHERE
  141 + cons_group = #{sysSe}
  142 + and account_period = #{accnutYm}
  143 +
  144 + </update>
  145 +
  146 +
  147 + <update id="insertOriginalData" parameterType="map">
  148 + INSERT INTO tbcr_transaction_history (
  149 + session_id,
  150 + cons_group,
  151 + ledger,
  152 + account_period,
  153 + seq,
  154 + tran_type,
  155 + own_comp,
  156 + tran_comp,
  157 + comp_acct_code,
  158 + comp_prod_code,
  159 + recon_key,
  160 + tran_date,
  161 + tran_currency,
  162 + tran_amt,
  163 + book_amt,
  164 + group_amt,
  165 + book_cost,
  166 + document_no,
  167 + remark,
  168 + cons_acct_code,
  169 + cons_acct_name,
  170 + prod_code,
  171 + adjust_type,
  172 + adjust_remark,
  173 + if_account_period,
  174 + if_comp_code,
  175 + if_file_id,
  176 + if_source,
  177 + equal_check,
  178 + cons_own_comp,
  179 + cons_tran_comp,
  180 + invoice_no,
  181 + lc_no,
  182 + bl_no,
  183 + own_biz_no,
  184 + partner_biz_no,
  185 + acct_date,
  186 + matching_cause,
  187 + match_key
  188 + ) values
  189 + <foreach collection="itemList" item="item" separator=",">
  190 + (
  191 + #{item.SESSION_ID},
  192 + #{item.CONS_GROUP},
  193 + #{item.LEDGER},
  194 + #{item.ACCOUNT_PERIOD},
  195 + #{item.SEQ},
  196 + #{item.TRAN_TYPE},
  197 + #{item.OWN_COMP},
  198 + #{item.TRAN_COMP},
  199 + #{item.COMP_ACCT_CODE},
  200 + #{item.COMP_PROD_CODE},
  201 + #{item.RECON_KEY},
  202 + #{item.TRAN_DATE},
  203 + #{item.TRAN_CURRENCY},
  204 + #{item.TRAN_AMT},
  205 + #{item.BOOK_AMT},
  206 + #{item.GROUP_AMT},
  207 + #{item.BOOK_COST},
  208 + #{item.DOCUMENT_NO},
  209 + #{item.REMARK},
  210 + #{item.CONS_ACCT_CODE},
  211 + #{item.CONS_ACCT_NAME},
  212 + #{item.PROD_CODE},
  213 + #{item.ADJUST_TYPE},
  214 + #{item.ADJUST_REMARK},
  215 + #{item.IF_ACCOUNT_PERIOD},
  216 + #{item.IF_COMP_CODE},
  217 + #{item.IF_FILE_ID},
  218 + #{item.IF_SOURCE},
  219 + #{item.EQUAL_CHECK},
  220 + #{item.CONS_OWN_COMP},
  221 + #{item.CONS_TRAN_COMP},
  222 + #{item.INVOICE_NO},
  223 + #{item.LC_NO},
  224 + #{item.BL_NO},
  225 + #{item.OWN_BIZ_NO},
  226 + #{item.PARTNER_BIZ_NO},
  227 + #{item.ACCT_DATE},
  228 + #{item.MATCHING_CAUSE},
  229 + #{item.MATCH_KEY}
  230 + )
  231 + </foreach>
  232 + </update>
  233 +
  234 + <update id="deleteData" parameterType="map">
  235 + DELETE FROM batch_tbcr_inner_delng
  236 + WHERE
  237 + sys_se = #{sysSe}
  238 + and accnut_ym = #{accnutYm}
  239 + </update>
  240 +
  241 + <update id="insertDataFromOriginal" parameterType="map">
  242 + INSERT INTO
  243 + batch_tbcr_inner_delng
  244 + (
  245 + sys_se
  246 + , accnut_ym
  247 + , sn
  248 + , dta_ty
  249 + , cpr_code
  250 + , partn_cpr
  251 + , cpr_acnt_code
  252 + , cnnc_acnt_code
  253 + , cnnc_acnt_nm
  254 + , delng_de
  255 + , elcty_de
  256 + , chit_no
  257 + , cmpnsp_ky
  258 + , ext_key1
  259 + , ext_key2
  260 + , ext_key3
  261 + , ext_key4
  262 + , ext_key5
  263 + , delng_crncy
  264 + , delng_amt
  265 + , acntbk_amt
  266 + , group_amt
  267 + , suply_amount
  268 + , sumry
  269 + , org_mtch_ty
  270 + , org_mtch_ky
  271 + , new_mtch_ty
  272 + , new_mtch_ky
  273 + , compare_ky
  274 + , mtch_ty
  275 + , mtch_ty_nm
  276 + , mtch_ky
  277 + )
  278 + SELECT
  279 + cons_group
  280 + , account_period
  281 + , seq
  282 + , tran_type
  283 + , own_comp
  284 + , tran_comp
  285 + , comp_acct_code
  286 + , cons_acct_code
  287 + , cons_acct_name
  288 + , tran_date
  289 + , acct_date
  290 + , document_no
  291 + , recon_key
  292 + , null
  293 + , invoice_no
  294 + , lc_no
  295 + , bl_no
  296 + , null
  297 + , tran_currency
  298 + , tran_amt
  299 + , book_amt
  300 + , group_amt
  301 + , book_cost
  302 + , remark
  303 + , matching_cause
  304 + , match_key
  305 + , null
  306 + , null
  307 + , null
  308 + , null
  309 + , null
  310 + , null
  311 + FROM
  312 + tbcr_transaction_history
  313 + WHERE
  314 + cons_group = #{sysSe}
  315 + and account_period = #{accnutYm}
  316 + </update>
  317 +
  318 + <update id="deleteDataAi" parameterType="map">
  319 + DELETE FROM batch_tbcr_inner_delng_ai
  320 + WHERE
  321 + sys_se = #{sysSe}
  322 + and accnut_ym = #{accnutYm}
  323 +
  324 + </update>
  325 +
  326 + <update id="insertDataAiFromOriginal" parameterType="map">
  327 + INSERT INTO
  328 + batch_tbcr_inner_delng_ai
  329 + (
  330 + sys_se
  331 + , accnut_ym
  332 + , sn
  333 + , ai_key1
  334 + , ai_key2
  335 + , ai_key3
  336 + , ai_key4
  337 + , ai_key5
  338 + , ai_key6
  339 + , ai_key7
  340 + , ai_key8
  341 + , ai_key9
  342 + , ai_key10
  343 + )
  344 + SELECT
  345 + cons_group
  346 + , account_period
  347 + , seq
  348 + , regexp_replace(document_no, '[^0-9a-zA-Z]', '',1,0) as ai_key1
  349 + , regexp_replace(recon_key, '[^0-9a-zA-Z]', '',1,0) as ai_key2
  350 + , '' as ai_key3
  351 + , '' as ai_key4
  352 + , '' as ai_key5
  353 + , '' as ai_key6
  354 + , '' as ai_key7
  355 + , '' as ai_key8
  356 + , '' as ai_key9
  357 + , '' as ai_key10
  358 + FROM
  359 + tbcr_transaction_history
  360 + WHERE
  361 + cons_group = #{sysSe}
  362 + and account_period = #{accnutYm}
  363 + </update>
  364 +
  365 + <update id="updateNewMatchKey" parameterType="map">
  366 + merge into batch_tbcr_inner_delng m
  367 + using
  368 + (
  369 + select
  370 + sys_se,
  371 + accnut_ym,
  372 + sn,
  373 + org_mtch_ty,
  374 + org_mtch_ky,
  375 + mtch_ty as new_mtch_ty,
  376 + mtch_ky,
  377 + DENSE_RANK() over (order by mtch_ty, mtch_ky) AS new_mtch_ky
  378 + from batch_tbcr_inner_delng
  379 + where
  380 + sys_se = #{sysSe}
  381 + AND accnut_ym = #{accnutYm}
  382 + AND mtch_ty is not null
  383 + ) t
  384 + on
  385 + m.sys_se = t.sys_se
  386 + and m.accnut_ym = t.accnut_ym
  387 + and m.sn = t.sn
  388 + when matched then
  389 + update set
  390 + new_mtch_ty = t.new_mtch_ty,
  391 + new_mtch_ky = t.new_mtch_ky
  392 + </update>
  393 +
  394 +
  395 +
  396 + <!-- 매칭작업할 데이타 가져오기 -->
  397 + <select id="getMatchingExtraDataOne" parameterType="map" resultType="map">
  398 + SELECT
  399 + sys_se
  400 + , accnut_ym
  401 + , sn
  402 + , '' as compare_ky
  403 + , delng_de
  404 + , delng_amt
  405 + FROM
  406 + public.batch_tbcr_inner_delng
  407 + WHERE
  408 + sys_se = #{sysSe}
  409 + and accnut_ym = #{accnutYm}
  410 + and cpr_code = #{cprCode}
  411 + and partn_cpr = #{partnCpr}
  412 + and mtch_ky is null
  413 + and dta_ty in ('11','21','31','33','35','37','41')
  414 + and delng_amt != 0
  415 + ORDER BY
  416 + delng_de
  417 + </select>
  418 +
  419 + <!-- 매칭작업할 데이타 가져오기 -->
  420 + <select id="getMatchingExtraDataTwo" parameterType="map" resultType="map">
  421 + SELECT
  422 + sys_se
  423 + , accnut_ym
  424 + , sn
  425 + , '' as compare_ky
  426 + , delng_de
  427 + , delng_amt
  428 + FROM
  429 + public.batch_tbcr_inner_delng
  430 + WHERE
  431 + sys_se = #{sysSe}
  432 + and accnut_ym = #{accnutYm}
  433 + and cpr_code = #{cprCode}
  434 + and partn_cpr = #{partnCpr}
  435 + and mtch_ky is null
  436 + and dta_ty in ('12','22','32','34','36','38','42')
  437 + and delng_amt != 0
  438 + ORDER BY
  439 + delng_de
  440 + </select>
  441 +
  442 + <update id="setExtraResult" parameterType="map">
  443 + <foreach collection="itemList" item="item" separator=";">
  444 + UPDATE public.batch_tbcr_inner_delng
  445 + SET
  446 + mtch_sys = #{item.mtch_sys},
  447 + mtch_ty = #{item.mtch_ty},
  448 + mtch_ty_nm = #{item.mtch_ty_nm},
  449 + mtch_ky = #{item.mtch_ky}
  450 + WHERE
  451 + sys_se = #{item.sys_se}
  452 + and accnut_ym = #{item.accnut_ym}
  453 + and sn = #{item.sn}
  454 + </foreach>
  455 + </update>
  456 +
  457 + <update id="createUserJob" parameterType="map">
  458 + INSERT INTO public.batch_user_job_status (
  459 + user_job_id,
  460 + user_job_name,
  461 + start_time,
  462 + status
  463 + ) VALUES (
  464 + #{user_job_id},
  465 + #{user_job_name},
  466 + now(),
  467 + 'Started'
  468 + )
  469 + </update>
  470 +
  471 + <update id="finishUserJob" parameterType="map">
  472 + UPDATE public.batch_user_job_status
  473 + SET
  474 + end_time = now(),
  475 + status = 'Finished',
  476 + exit_code = #{exit_code},
  477 + exit_message = #{exit_message}
  478 + WHERE
  479 + user_job_id = #{user_job_id}
  480 + </update>
  481 +
  482 + <!-- AI 작업리스트 -->
  483 + <select id="getAiReadData" parameterType="map" resultType="map">
  484 + SELECT
  485 + sys_se
  486 + , accnut_ym
  487 + , cpr_code
  488 + , partn_cpr
  489 + , delng_crncy
  490 + FROM
  491 + (
  492 + SELECT
  493 + sys_se
  494 + , accnut_ym
  495 + , cpr_code
  496 + , partn_cpr
  497 + , delng_crncy
  498 + , case when count(*) > 0 then 1 else 0 end as cnt
  499 + FROM
  500 + public.batch_tbcr_inner_delng
  501 + WHERE
  502 + sys_se = #{sysSe}
  503 + and accnut_ym = #{accnutYm}
  504 + and mtch_ty is null
  505 + and dta_ty in ('11','21','31','33','35','37','41')
  506 + GROUP BY
  507 + sys_se
  508 + , accnut_ym
  509 + , cpr_code
  510 + , partn_cpr
  511 + , delng_crncy
  512 + union all
  513 + SELECT
  514 + sys_se
  515 + , accnut_ym
  516 + , partn_cpr as cpr_code
  517 + , cpr_code as partn_cpr
  518 + , delng_crncy
  519 + , case when count(*) > 0 then 1 else 0 end as cnt
  520 + FROM
  521 + public.batch_tbcr_inner_delng
  522 + WHERE
  523 + sys_se = #{sysSe}
  524 + and accnut_ym = #{accnutYm}
  525 + and mtch_ty is null
  526 + and dta_ty in ('12','22','32','34','36','38','42')
  527 + GROUP BY
  528 + sys_se
  529 + , accnut_ym
  530 + , cpr_code
  531 + , partn_cpr
  532 + , delng_crncy
  533 + ) m
  534 + GROUP BY
  535 + sys_se
  536 + , accnut_ym
  537 + , cpr_code
  538 + , partn_cpr
  539 + , delng_crncy
  540 + HAVING sum(cnt) > 1
  541 + </select>
  542 +</mapper>
0 543 \ No newline at end of file
... ...
src/main/resources/mybatis/primary/system/CodeMapper.xml 0 → 100644
  1 +++ a/src/main/resources/mybatis/primary/system/CodeMapper.xml
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
  3 +<mapper namespace="daeucna.mapper.primary.system.CodeMapper">
  4 +
  5 + <select id="getCmmnCode"
  6 + parameterType="CodeDto"
  7 + resultType="CodeDto">
  8 + SELECT
  9 + m.code_ty
  10 + , m.cmmn_code
  11 + , m.mng_iem_1
  12 + , m.mng_iem_2
  13 + , m.mng_iem_3
  14 + , m.mng_iem_4
  15 + , m.ordr
  16 + , m.use_at
  17 + , m.register
  18 + , m.input_de
  19 + , m.updusr
  20 + , m.updt_de
  21 + , s.lcal
  22 + , s.cmmn_code_nm
  23 + FROM
  24 + public.sy_cmmn_code_mng m
  25 + LEFT OUTER JOIN public.sy_cmmn_code_mng_nls s
  26 + ON
  27 + m.code_ty = s.code_ty
  28 + and m.cmmn_code = s.cmmn_code
  29 + and lcal = #{lcal};
  30 + </select>
  31 +
  32 +</mapper>
0 33 \ No newline at end of file
... ...
src/main/resources/mybatis/secondary/OracleMapper.HN 0 → 100644
  1 +++ a/src/main/resources/mybatis/secondary/OracleMapper.HN
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
  3 +<mapper namespace="daeucna.mapper.secondary.batch.OracleMapper">
  4 +
  5 + <!-- 작업리스트 -->
  6 + <select id="getOriginalData" parameterType="map" resultType="map">
  7 + SELECT
  8 + A.SESSION_ID,
  9 + A.CONS_GROUP,
  10 + A.LEDGER,
  11 + A.ACCOUNT_PERIOD,
  12 + A.SEQ,
  13 + A.TRAN_TYPE,
  14 + A.OWN_COMP,
  15 + A.TRAN_COMP,
  16 + A.COMP_ACCT_CODE,
  17 + A.COMP_PROD_CODE,
  18 + A.RECON_KEY,
  19 + A.TRAN_DATE,
  20 + A.TRAN_CURRENCY,
  21 + A.TRAN_AMT,
  22 + A.BOOK_AMT,
  23 + A.GROUP_AMT,
  24 + A.BOOK_COST,
  25 + A.DOCUMENT_NO,
  26 + A.REMARK,
  27 + A.CONS_ACCT_CODE,
  28 + B.CONS_ACCT_KR_SNAME AS CONS_ACCT_NAME,
  29 + A.PROD_CODE,
  30 + A.ADJUST_TYPE,
  31 + A.ADJUST_REMARK,
  32 + A.IF_ACCOUNT_PERIOD,
  33 + A.IF_COMP_CODE,
  34 + A.IF_FILE_ID,
  35 + A.IF_SOURCE,
  36 + A.EQUAL_CHECK,
  37 + A.CONS_OWN_COMP,
  38 + A.CONS_TRAN_COMP,
  39 + A.INVOICE_NO,
  40 + A.LC_NO,
  41 + A.BL_NO,
  42 + A.OWN_BIZ_NO,
  43 + A.PARTNER_BIZ_NO,
  44 + A.ACCT_DATE
  45 + FROM
  46 + TBCR_TRANSACTION_HISTORY A
  47 + LEFT OUTER JOIN TBBC_ACCT_CODE B
  48 + ON
  49 + B.CONS_ACCT_CODE = A.CONS_ACCT_CODE
  50 + AND B.SESSION_ID = 'XNER'
  51 + AND B.CONS_COA = 'GOV_I_COA'
  52 + AND B.FS_TYPE = '1'
  53 + AND TO_CHAR(SYSDATE, 'YYYYMM') BETWEEN B.START_YYMM AND B.END_YYMM
  54 + WHERE
  55 + A.CONS_GROUP = #{sysSe}
  56 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  57 + </select>
  58 +
  59 + <select id="getMatchingInfo" parameterType="map" resultType="map">
  60 + SELECT
  61 + A.MATCH_KEY,
  62 + A.MATCHING_CAUSE,
  63 + B.SEQ
  64 + FROM TBCR_MATCHING A,
  65 + TBCR_MATCHING_DETAIL B
  66 + WHERE
  67 + A.MATCH_KEY = B.MATCH_KEY
  68 + AND A.ACCOUNT_PERIOD = B.ACCOUNT_PERIOD
  69 + AND A.CONS_GROUP = #{sysSe}
  70 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  71 + </select>
  72 +
  73 + <update id="updateMatchingResult" parameterType="map">
  74 + --결과 업데이트
  75 + </update>
  76 +
  77 +</mapper>
0 78 \ No newline at end of file
... ...
src/main/resources/mybatis/secondary/OracleMapper.LS 0 → 100644
  1 +++ a/src/main/resources/mybatis/secondary/OracleMapper.LS
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
  3 +<mapper namespace="daeucna.mapper.secondary.batch.OracleMapper">
  4 +
  5 + <!-- 작업리스트 -->
  6 + <select id="getOriginalData" parameterType="map" resultType="map">
  7 + SELECT
  8 + A.SESSION_ID,
  9 + A.CONS_GROUP,
  10 + A.LEDGER,
  11 + A.ACCOUNT_PERIOD,
  12 + A.SEQ,
  13 + A.TRAN_TYPE,
  14 + A.OWN_COMP,
  15 + A.TRAN_COMP,
  16 + A.COMP_ACCT_CODE,
  17 + A.COMP_PROD_CODE,
  18 + A.RECON_KEY,
  19 + A.TRAN_DATE,
  20 + A.TRAN_CURRENCY,
  21 + A.TRAN_AMT,
  22 + A.BOOK_AMT,
  23 + A.GROUP_AMT,
  24 + A.BOOK_COST,
  25 + A.DOCUMENT_NO,
  26 + A.REMARK,
  27 + A.CONS_ACCT_CODE,
  28 + B.CONS_ACCT_NAME_0 AS CONS_ACCT_NAME,
  29 + A.PROD_CODE,
  30 + A.ADJUST_TYPE,
  31 + A.ADJUST_REMARK,
  32 + A.IF_ACCOUNT_PERIOD,
  33 + A.IF_COMP_CODE,
  34 + A.IF_FILE_ID,
  35 + A.IF_SOURCE,
  36 + A.EQUAL_CHECK,
  37 + A.CONS_OWN_COMP,
  38 + A.CONS_TRAN_COMP,
  39 + A.INVOICE_NO,
  40 + A.LC_NO,
  41 + A.BL_NO,
  42 + A.OWN_BIZ_NO,
  43 + A.PARTNER_BIZ_NO,
  44 + A.ACCT_DATE
  45 + FROM
  46 + TBCR_TRANSACTION_HISTORY A
  47 + LEFT OUTER JOIN TBBC_ACCT_CODE_NLS B
  48 + ON
  49 + B.CONS_ACCT_CODE = A.CONS_ACCT_CODE
  50 + AND B.CONS_COA = 'LS_COA'
  51 + AND B.FS_TYPE = '1'
  52 + AND TO_CHAR(SYSDATE, 'YYYYMM') BETWEEN B.START_YYMM AND B.END_YYMM
  53 + WHERE
  54 + A.CONS_GROUP = #{sysSe}
  55 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  56 + </select>
  57 +
  58 + <select id="getMatchingInfo" parameterType="map" resultType="map">
  59 + SELECT
  60 + A.MATCH_KEY,
  61 + A.MATCHING_CAUSE,
  62 + B.SEQ
  63 + FROM TBCR_MATCHING A,
  64 + TBCR_MATCHING_DETAIL B
  65 + WHERE
  66 + A.SESSION_ID = B.SESSION_ID
  67 + AND A.CONS_GROUP = B.CONS_GROUP
  68 + AND A.LEDGER = B.LEDGER
  69 + AND A.MATCH_KEY = B.MATCH_KEY
  70 + AND A.ACCOUNT_PERIOD = B.ACCOUNT_PERIOD
  71 + AND A.CONS_GROUP = #{sysSe}
  72 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  73 + </select>
  74 +
  75 + <update id="updateMatchingResult" parameterType="map">
  76 + --결과 업데이트
  77 + </update>
  78 +
  79 +</mapper>
0 80 \ No newline at end of file
... ...
src/main/resources/mybatis/secondary/OracleMapper.xml 0 → 100644
  1 +++ a/src/main/resources/mybatis/secondary/OracleMapper.xml
  1 +<?xml version="1.0" encoding="UTF-8"?>
  2 +<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
  3 +<mapper namespace="daeucna.mapper.secondary.batch.OracleMapper">
  4 +
  5 + <!-- 작업리스트 -->
  6 + <select id="getOriginalData" parameterType="map" resultType="map">
  7 + SELECT
  8 + A.SESSION_ID,
  9 + A.CONS_GROUP,
  10 + A.LEDGER,
  11 + A.ACCOUNT_PERIOD,
  12 + A.SEQ,
  13 + A.TRAN_TYPE,
  14 + A.OWN_COMP,
  15 + A.TRAN_COMP,
  16 + A.COMP_ACCT_CODE,
  17 + A.COMP_PROD_CODE,
  18 + A.RECON_KEY,
  19 + A.TRAN_DATE,
  20 + A.TRAN_CURRENCY,
  21 + A.TRAN_AMT,
  22 + A.BOOK_AMT,
  23 + A.GROUP_AMT,
  24 + A.BOOK_COST,
  25 + A.DOCUMENT_NO,
  26 + A.REMARK,
  27 + A.CONS_ACCT_CODE,
  28 + B.CONS_ACCT_NAME_0 AS CONS_ACCT_NAME,
  29 + A.PROD_CODE,
  30 + A.ADJUST_TYPE,
  31 + A.ADJUST_REMARK,
  32 + A.IF_ACCOUNT_PERIOD,
  33 + A.IF_COMP_CODE,
  34 + A.IF_FILE_ID,
  35 + A.IF_SOURCE,
  36 + A.EQUAL_CHECK,
  37 + A.CONS_OWN_COMP,
  38 + A.CONS_TRAN_COMP,
  39 + A.INVOICE_NO,
  40 + A.LC_NO,
  41 + A.BL_NO,
  42 + A.OWN_BIZ_NO,
  43 + A.PARTNER_BIZ_NO,
  44 + A.ACCT_DATE
  45 + FROM
  46 + TBCR_TRANSACTION_HISTORY A
  47 + LEFT OUTER JOIN TBBC_ACCT_CODE_NLS B
  48 + ON
  49 + B.CONS_ACCT_CODE = A.CONS_ACCT_CODE
  50 + AND B.CONS_COA = 'LS_COA'
  51 + AND B.FS_TYPE = '1'
  52 + AND TO_CHAR(SYSDATE, 'YYYYMM') BETWEEN B.START_YYMM AND B.END_YYMM
  53 + WHERE
  54 + A.CONS_GROUP = #{sysSe}
  55 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  56 + </select>
  57 +
  58 + <select id="getMatchingInfo" parameterType="map" resultType="map">
  59 + SELECT
  60 + A.MATCH_KEY,
  61 + A.MATCHING_CAUSE,
  62 + B.SEQ
  63 + FROM TBCR_MATCHING A,
  64 + TBCR_MATCHING_DETAIL B
  65 + WHERE
  66 + A.SESSION_ID = B.SESSION_ID
  67 + AND A.CONS_GROUP = B.CONS_GROUP
  68 + AND A.LEDGER = B.LEDGER
  69 + AND A.MATCH_KEY = B.MATCH_KEY
  70 + AND A.ACCOUNT_PERIOD = B.ACCOUNT_PERIOD
  71 + AND A.CONS_GROUP = #{sysSe}
  72 + AND A.ACCOUNT_PERIOD = #{accnutYm}
  73 + </select>
  74 +
  75 + <update id="updateMatchingResult" parameterType="map">
  76 + --결과 업데이트
  77 + </update>
  78 +
  79 +</mapper>
0 80 \ No newline at end of file
... ...
src/main/resources/schema.sql 0 → 100644
  1 +++ a/src/main/resources/schema.sql
  1 +CREATE TABLE IF NOT EXISTS batch_tbcr_inner_delng
  2 +(
  3 + sys_se character varying(10) NOT NULL,
  4 + accnut_ym character varying(6) NOT NULL,
  5 + sn bigint NOT NULL DEFAULT 0,
  6 + dta_ty character varying(3),
  7 + cpr_code character varying(10),
  8 + partn_cpr character varying(10),
  9 + cpr_acnt_code character varying(20),
  10 + cnnc_acnt_code character varying(20),
  11 + cnnc_acnt_nm character varying(100),
  12 + delng_de character varying(8),
  13 + elcty_de character varying(8),
  14 + chit_no character varying(100),
  15 + cmpnsp_ky character varying(100),
  16 + ext_key1 character varying(100),
  17 + ext_key2 character varying(100),
  18 + ext_key3 character varying(100),
  19 + ext_key4 character varying(100),
  20 + ext_key5 character varying(100),
  21 + delng_crncy character varying(3),
  22 + delng_amt numeric(19,2) DEFAULT 0,
  23 + acntbk_amt numeric(19,2) DEFAULT 0,
  24 + group_amt numeric(19,2) DEFAULT 0,
  25 + suply_amount numeric(19,2) DEFAULT 0,
  26 + sumry character varying(500),
  27 + org_mtch_ty character varying(10),
  28 + org_mtch_ky numeric(10,0),
  29 + new_mtch_ty character varying(10),
  30 + new_mtch_ky numeric(10,0),
  31 + compare_ky character varying(100),
  32 + mtch_sys character varying(10),
  33 + mtch_ty character varying(10),
  34 + mtch_ty_nm character varying(100),
  35 + mtch_ky bigint DEFAULT 0,
  36 + CONSTRAINT batch_tbcr_inner_delng_pkey PRIMARY KEY (sys_se, accnut_ym, sn)
  37 +);
  38 +
  39 +COMMENT ON TABLE batch_tbcr_inner_delng
  40 + IS '내부거래대사자료';
  41 +
  42 +COMMENT ON COLUMN batch_tbcr_inner_delng.sys_se
  43 + IS '시스템구분';
  44 +
  45 +COMMENT ON COLUMN batch_tbcr_inner_delng.accnut_ym
  46 + IS '회계연월';
  47 +
  48 +COMMENT ON COLUMN batch_tbcr_inner_delng.sn
  49 + IS '순번';
  50 +
  51 +COMMENT ON COLUMN batch_tbcr_inner_delng.dta_ty
  52 + IS '거래유형';
  53 +
  54 +COMMENT ON COLUMN batch_tbcr_inner_delng.cpr_code
  55 + IS '자기법인';
  56 +
  57 +COMMENT ON COLUMN batch_tbcr_inner_delng.partn_cpr
  58 + IS '상대법인';
  59 +
  60 +COMMENT ON COLUMN batch_tbcr_inner_delng.cpr_acnt_code
  61 + IS '법인계정코드';
  62 +
  63 +COMMENT ON COLUMN batch_tbcr_inner_delng.cnnc_acnt_code
  64 + IS '연결계정코드';
  65 +
  66 +COMMENT ON COLUMN batch_tbcr_inner_delng.cnnc_acnt_nm
  67 + IS '연결계정명';
  68 +
  69 +COMMENT ON COLUMN batch_tbcr_inner_delng.delng_de
  70 + IS '거래일자';
  71 +
  72 +COMMENT ON COLUMN batch_tbcr_inner_delng.elcty_de
  73 + IS '전기일자';
  74 +
  75 +COMMENT ON COLUMN batch_tbcr_inner_delng.chit_no
  76 + IS '법인전표번호';
  77 +
  78 +COMMENT ON COLUMN batch_tbcr_inner_delng.cmpnsp_ky
  79 + IS '대사 Key';
  80 +
  81 +COMMENT ON COLUMN batch_tbcr_inner_delng.ext_key1
  82 + IS '합산Key';
  83 +
  84 +COMMENT ON COLUMN batch_tbcr_inner_delng.ext_key2
  85 + IS 'INVOICE번호';
  86 +
  87 +COMMENT ON COLUMN batch_tbcr_inner_delng.ext_key3
  88 + IS 'LC번호';
  89 +
  90 +COMMENT ON COLUMN batch_tbcr_inner_delng.ext_key4
  91 + IS 'BL번호';
  92 +
  93 +COMMENT ON COLUMN batch_tbcr_inner_delng.ext_key5
  94 + IS '기타Key5';
  95 +
  96 +COMMENT ON COLUMN batch_tbcr_inner_delng.delng_crncy
  97 + IS '거래통화';
  98 +
  99 +COMMENT ON COLUMN batch_tbcr_inner_delng.delng_amt
  100 + IS '거래통화금액';
  101 +
  102 +COMMENT ON COLUMN batch_tbcr_inner_delng.acntbk_amt
  103 + IS '장부통화금액';
  104 +
  105 +COMMENT ON COLUMN batch_tbcr_inner_delng.group_amt
  106 + IS '그룹통화금액';
  107 +
  108 +COMMENT ON COLUMN batch_tbcr_inner_delng.suply_amount
  109 + IS '공급가액';
  110 +
  111 +COMMENT ON COLUMN batch_tbcr_inner_delng.sumry
  112 + IS '적요';
  113 +
  114 +COMMENT ON COLUMN batch_tbcr_inner_delng.org_mtch_ty
  115 + IS 'Org.일치유형';
  116 +
  117 +COMMENT ON COLUMN batch_tbcr_inner_delng.org_mtch_ky
  118 + IS 'Org.일치KEY';
  119 +
  120 +COMMENT ON COLUMN batch_tbcr_inner_delng.new_mtch_ty
  121 + IS 'New.일치유형';
  122 +
  123 +COMMENT ON COLUMN batch_tbcr_inner_delng.new_mtch_ky
  124 + IS 'New.일치KEY';
  125 +
  126 +COMMENT ON COLUMN batch_tbcr_inner_delng.compare_ky
  127 + IS '비교키(시스템)';
  128 +
  129 +COMMENT ON COLUMN batch_tbcr_inner_delng.mtch_sys
  130 + IS '일치시스템';
  131 +
  132 +COMMENT ON COLUMN batch_tbcr_inner_delng.mtch_ty
  133 + IS '일치유형';
  134 +
  135 +COMMENT ON COLUMN batch_tbcr_inner_delng.mtch_ty_nm
  136 + IS '일치유형명칭';
  137 +
  138 +COMMENT ON COLUMN batch_tbcr_inner_delng.mtch_ky
  139 + IS '일치KEY';
  140 +
  141 +CREATE INDEX IF NOT EXISTS batch_tbcr_inner_delng_idx1
  142 + ON batch_tbcr_inner_delng USING btree
  143 + (sys_se ASC NULLS LAST, accnut_ym ASC NULLS LAST, cpr_code ASC NULLS LAST, dta_ty ASC NULLS LAST, partn_cpr ASC NULLS LAST);
  144 +
  145 +CREATE INDEX IF NOT EXISTS batch_tbcr_inner_delng_idx2
  146 + ON batch_tbcr_inner_delng USING btree
  147 + (sys_se ASC NULLS LAST, accnut_ym ASC NULLS LAST, cpr_code ASC NULLS LAST, partn_cpr ASC NULLS LAST, compare_ky ASC NULLS LAST);
  148 +
  149 +
  150 +
  151 +
  152 +CREATE TABLE IF NOT EXISTS tbcr_transaction_history
  153 +(
  154 + session_id character varying(5) NOT NULL,
  155 + cons_group character varying(10) NOT NULL,
  156 + ledger character varying(3) NOT NULL,
  157 + account_period character varying(6) NOT NULL,
  158 + seq numeric NOT NULL,
  159 + tran_type character varying(3),
  160 + own_comp character varying(10),
  161 + tran_comp character varying(10),
  162 + comp_acct_code character varying(20),
  163 + comp_prod_code character varying(20),
  164 + recon_key character varying(100),
  165 + tran_date character varying(8),
  166 + tran_currency character varying(3),
  167 + tran_amt numeric(17,2) DEFAULT 0,
  168 + book_amt numeric(17,2) DEFAULT 0,
  169 + group_amt numeric(17,2) DEFAULT 0,
  170 + book_cost numeric(17,2) DEFAULT 0,
  171 + document_no character varying(50),
  172 + remark character varying(500),
  173 + cons_acct_code character varying(10),
  174 + cons_acct_name character varying(100),
  175 + prod_code character varying(10),
  176 + adjust_type character varying(3),
  177 + adjust_remark character varying(255),
  178 + if_account_period character varying(6),
  179 + if_comp_code character varying(10),
  180 + if_file_id character varying(3),
  181 + if_source character varying(3),
  182 + equal_check character varying(3),
  183 + cons_own_comp character varying(10),
  184 + cons_tran_comp character varying(10),
  185 + invoice_no character varying(80),
  186 + lc_no character varying(80),
  187 + bl_no character varying(80),
  188 + own_biz_no character varying(20),
  189 + partner_biz_no character varying(20),
  190 + acct_date character varying(8),
  191 + matching_cause character varying(10),
  192 + match_key numeric(10,0),
  193 + CONSTRAINT tbcr_transaction_history_ky PRIMARY KEY (session_id, cons_group, ledger, account_period, seq)
  194 +);
  195 +
  196 +
  197 +CREATE TABLE IF NOT EXISTS batch_tbcr_inner_delng_ai
  198 +(
  199 + sys_se character varying(10) NOT NULL,
  200 + accnut_ym character varying(6) NOT NULL,
  201 + sn bigint NOT NULL DEFAULT 0,
  202 + ai_key1 character varying(100) ,
  203 + ai_key2 character varying(100) ,
  204 + ai_key3 character varying(100) ,
  205 + ai_key4 character varying(100) ,
  206 + ai_key5 character varying(100) ,
  207 + ai_key6 character varying(100) ,
  208 + ai_key7 character varying(100) ,
  209 + ai_key8 character varying(100) ,
  210 + ai_key9 character varying(100) ,
  211 + ai_key10 character varying(100) ,
  212 + CONSTRAINT batch_tbcr_inner_delng_aikey PRIMARY KEY (sys_se, accnut_ym, sn)
  213 +);
  214 +
  215 +
  216 +CREATE TABLE IF NOT EXISTS batch_user_job_status
  217 +(
  218 + user_job_id character varying(128) COLLATE pg_catalog."default" NOT NULL,
  219 + user_job_name character varying(200) COLLATE pg_catalog."default",
  220 + start_time timestamp with time zone,
  221 + end_time timestamp with time zone,
  222 + status character varying(50) COLLATE pg_catalog."default",
  223 + exit_code character varying(10) COLLATE pg_catalog."default",
  224 + exit_message character varying(2000) COLLATE pg_catalog."default",
  225 + CONSTRAINT batch_user_job_status_pkey PRIMARY KEY (user_job_id)
  226 + USING INDEX TABLESPACE account
  227 +);
  228 +
  229 +COMMENT ON TABLE batch_user_job_status
  230 + IS 'User Job Status';
  231 +
  232 +
  233 +
  234 +-- Table: users
  235 +
  236 +-- DROP TABLE IF EXISTS users;
  237 +
  238 +CREATE TABLE IF NOT EXISTS users
  239 +(
  240 + user_id bigint NOT NULL DEFAULT nextval('users_user_id_seq'::regclass),
  241 + activated boolean,
  242 + nickname character varying(50) COLLATE pg_catalog."default",
  243 + password character varying(100) COLLATE pg_catalog."default",
  244 + username character varying(50) COLLATE pg_catalog."default",
  245 + CONSTRAINT users_pkey PRIMARY KEY (user_id),
  246 + CONSTRAINT uk_r43af9ap4edm43mmtq01oddj6 UNIQUE (username)
  247 +);
  248 +
  249 +-- Table: authority
  250 +
  251 +-- DROP TABLE IF EXISTS authority;
  252 +
  253 +CREATE TABLE IF NOT EXISTS authority
  254 +(
  255 + authority_name character varying(50) COLLATE pg_catalog."default" NOT NULL,
  256 + CONSTRAINT authority_pkey PRIMARY KEY (authority_name)
  257 +);
  258 +
  259 +-- Table: user_authority
  260 +
  261 +-- DROP TABLE IF EXISTS user_authority;
  262 +
  263 +CREATE TABLE IF NOT EXISTS user_authority
  264 +(
  265 + user_id bigint NOT NULL,
  266 + authority_name character varying(50) COLLATE pg_catalog."default" NOT NULL,
  267 + CONSTRAINT user_authority_pkey PRIMARY KEY (user_id, authority_name),
  268 + CONSTRAINT fk6ktglpl5mjosa283rvken2py5 FOREIGN KEY (authority_name)
  269 + REFERENCES authority (authority_name) MATCH SIMPLE
  270 + ON UPDATE NO ACTION
  271 + ON DELETE NO ACTION,
  272 + CONSTRAINT fkhi46vu7680y1hwvmnnuh4cybx FOREIGN KEY (user_id)
  273 + REFERENCES users (user_id) MATCH SIMPLE
  274 + ON UPDATE NO ACTION
  275 + ON DELETE NO ACTION
  276 +);
  277 +
  278 +-- Table: sy_cmmn_code_mng
  279 +
  280 +-- DROP TABLE IF EXISTS sy_cmmn_code_mng;
  281 +
  282 +CREATE TABLE IF NOT EXISTS sy_cmmn_code_mng
  283 +(
  284 + code_ty character varying(20) COLLATE pg_catalog."default" NOT NULL,
  285 + cmmn_code character varying(20) COLLATE pg_catalog."default" NOT NULL,
  286 + mng_iem_1 character varying(50) COLLATE pg_catalog."default",
  287 + mng_iem_2 character varying(50) COLLATE pg_catalog."default",
  288 + mng_iem_3 character varying(50) COLLATE pg_catalog."default",
  289 + mng_iem_4 character varying(50) COLLATE pg_catalog."default",
  290 + ordr bigint DEFAULT 0,
  291 + use_at character varying(1) COLLATE pg_catalog."default",
  292 + register character varying(20) COLLATE pg_catalog."default",
  293 + input_de timestamp without time zone,
  294 + updusr character varying(20) COLLATE pg_catalog."default",
  295 + updt_de timestamp without time zone,
  296 + CONSTRAINT sy_cmmn_code_mng_pkey PRIMARY KEY (code_ty, cmmn_code)
  297 +);
  298 +
  299 +COMMENT ON TABLE sy_cmmn_code_mng
  300 + IS 'SY_공통코드관리';
  301 +
  302 +COMMENT ON COLUMN sy_cmmn_code_mng.code_ty
  303 + IS '코드타입';
  304 +
  305 +COMMENT ON COLUMN sy_cmmn_code_mng.cmmn_code
  306 + IS '공통코드';
  307 +
  308 +COMMENT ON COLUMN sy_cmmn_code_mng.mng_iem_1
  309 + IS '관리항목1';
  310 +
  311 +COMMENT ON COLUMN sy_cmmn_code_mng.mng_iem_2
  312 + IS '관리항목2';
  313 +
  314 +COMMENT ON COLUMN sy_cmmn_code_mng.mng_iem_3
  315 + IS '관리항목3';
  316 +
  317 +COMMENT ON COLUMN sy_cmmn_code_mng.mng_iem_4
  318 + IS '관리항목4';
  319 +
  320 +COMMENT ON COLUMN sy_cmmn_code_mng.ordr
  321 + IS '순서';
  322 +
  323 +COMMENT ON COLUMN sy_cmmn_code_mng.use_at
  324 + IS '사용여부';
  325 +
  326 +COMMENT ON COLUMN sy_cmmn_code_mng.register
  327 + IS '입력자';
  328 +
  329 +COMMENT ON COLUMN sy_cmmn_code_mng.input_de
  330 + IS '입력일자';
  331 +
  332 +COMMENT ON COLUMN sy_cmmn_code_mng.updusr
  333 + IS '수정자';
  334 +
  335 +COMMENT ON COLUMN sy_cmmn_code_mng.updt_de
  336 + IS '수정일자';
  337 +
  338 +
  339 +-- Table: sy_cmmn_code_mng_nls
  340 +
  341 +-- DROP TABLE IF EXISTS sy_cmmn_code_mng_nls;
  342 +
  343 +CREATE TABLE IF NOT EXISTS sy_cmmn_code_mng_nls
  344 +(
  345 + code_ty character varying(20) COLLATE pg_catalog."default" NOT NULL,
  346 + cmmn_code character varying(20) COLLATE pg_catalog."default" NOT NULL,
  347 + lcal character varying(5) COLLATE pg_catalog."default" NOT NULL,
  348 + cmmn_code_nm character varying(100) COLLATE pg_catalog."default",
  349 + register character varying(20) COLLATE pg_catalog."default",
  350 + input_de timestamp without time zone,
  351 + updusr character varying(20) COLLATE pg_catalog."default",
  352 + updt_de timestamp without time zone,
  353 + CONSTRAINT sy_cmmn_code_mng_nls_pkey PRIMARY KEY (code_ty, cmmn_code, lcal),
  354 + CONSTRAINT fk_s_mng_to_s_mng_nls FOREIGN KEY (code_ty, cmmn_code)
  355 + REFERENCES sy_cmmn_code_mng (code_ty, cmmn_code) MATCH SIMPLE
  356 + ON UPDATE NO ACTION
  357 + ON DELETE CASCADE
  358 +);
  359 +
  360 +COMMENT ON TABLE sy_cmmn_code_mng_nls
  361 + IS 'SY_공통코드관리_NLS';
  362 +
  363 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.code_ty
  364 + IS '코드타입';
  365 +
  366 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.cmmn_code
  367 + IS '공통코드';
  368 +
  369 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.lcal
  370 + IS '로케일';
  371 +
  372 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.cmmn_code_nm
  373 + IS '공통코드명';
  374 +
  375 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.register
  376 + IS '입력자';
  377 +
  378 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.input_de
  379 + IS '입력일자';
  380 +
  381 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.updusr
  382 + IS '수정자';
  383 +
  384 +COMMENT ON COLUMN sy_cmmn_code_mng_nls.updt_de
  385 + IS '수정일자';
0 386 \ No newline at end of file
... ...
src/test/java/daeucna/MatchingAiApplicationTests.java 0 → 100644
  1 +++ a/src/test/java/daeucna/MatchingAiApplicationTests.java
  1 +package daeucna;
  2 +
  3 +import static org.hamcrest.CoreMatchers.containsString;
  4 +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
  5 +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post;
  6 +import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
  7 +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content;
  8 +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;
  9 +
  10 +import java.util.Arrays;
  11 +import java.util.HashMap;
  12 +import java.util.HashSet;
  13 +
  14 +import javax.crypto.SecretKey;
  15 +
  16 +import org.junit.jupiter.api.Test;
  17 +import org.springframework.beans.factory.annotation.Autowired;
  18 +import org.springframework.beans.factory.annotation.Value;
  19 +import org.springframework.boot.test.autoconfigure.web.servlet.AutoConfigureMockMvc;
  20 +import org.springframework.boot.test.context.SpringBootTest;
  21 +import org.springframework.http.MediaType;
  22 +import org.springframework.test.context.ContextConfiguration;
  23 +import org.springframework.test.web.servlet.MockMvc;
  24 +import org.springframework.test.web.servlet.MvcResult;
  25 +
  26 +import daeucna.config.security.dto.AuthorityDto;
  27 +import daeucna.config.security.dto.LoginDto;
  28 +import daeucna.config.security.dto.UserDto;
  29 +import daeucna.config.security.jwt.JwtFilter;
  30 +import daeucna.config.security.utils.CommonJson;
  31 +import io.jsonwebtoken.Claims;
  32 +import io.jsonwebtoken.Jws;
  33 +import io.jsonwebtoken.Jwts;
  34 +import io.jsonwebtoken.io.Decoders;
  35 +import io.jsonwebtoken.security.Keys;
  36 +import lombok.extern.slf4j.Slf4j;
  37 +
  38 +@SpringBootTest
  39 +@ContextConfiguration(classes = MatchingAiApplication.class)
  40 +@AutoConfigureMockMvc
  41 +@Slf4j
  42 +class MatchingAiApplicationTests {
  43 +
  44 + @Autowired
  45 + private MockMvc mockMvc;
  46 +
  47 + @Test
  48 + void userSignup() throws Exception {
  49 + AuthorityDto authorityDto = AuthorityDto.builder().authorityName("ROLE_ADMIN").build();
  50 + UserDto userDto = UserDto.builder()
  51 + .username("sangkiTest")
  52 + .password("sangkiTest")
  53 + .nickname("sangkiTest")
  54 + .authorityDtoSet(new HashSet<AuthorityDto>( Arrays.asList(authorityDto) ))
  55 + .build();
  56 +
  57 + String body = CommonJson.objectToString(userDto);
  58 + this.mockMvc.perform(
  59 + post("/api/signup")
  60 + .contentType(MediaType.APPLICATION_JSON)
  61 + .content(body)
  62 + )
  63 + .andDo(print())
  64 + .andExpect(status().isOk())
  65 + .andExpect(content().string(containsString("sangkiTest")));
  66 + }
  67 +
  68 + @Test
  69 + void authenticate() throws Exception {
  70 + fnAuthenticate();
  71 + }
  72 +
  73 + MvcResult fnAuthenticate() throws Exception {
  74 + LoginDto loginDto = LoginDto.builder()
  75 + .username("sangkiTest")
  76 + .password("sangkiTest")
  77 + .build();
  78 +
  79 + String body = CommonJson.objectToString(loginDto);
  80 + MvcResult mvcResult = this.mockMvc.perform(
  81 + post("/api/authenticate")
  82 + .contentType(MediaType.APPLICATION_JSON)
  83 + .content(body)
  84 + )
  85 + .andDo(print())
  86 + .andExpect(status().isOk())
  87 + .andExpect(content().string(containsString("token")))
  88 + .andReturn();
  89 +
  90 + return mvcResult;
  91 + }
  92 +
  93 + @SuppressWarnings("unchecked")
  94 + @Test
  95 + void user() throws Exception {
  96 + MvcResult mvcResult = fnAuthenticate();
  97 + String sReturn = mvcResult.getResponse().getContentAsString();
  98 + log.debug("sReturn = " + sReturn);
  99 +
  100 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  101 + log.debug("token = " + mapVal.get("token") );
  102 +
  103 + this.mockMvc.perform(
  104 + get("/api/user")
  105 + .header("Authorization", "Bearer " + mapVal.get("token"))
  106 + )
  107 + .andDo(print())
  108 + .andExpect(status().isOk());
  109 +
  110 + }
  111 +
  112 + @SuppressWarnings("unchecked")
  113 + @Test
  114 + void testRedirect() throws Exception {
  115 + MvcResult mvcResult = fnAuthenticate();
  116 + String sReturn = mvcResult.getResponse().getContentAsString();
  117 + log.debug("sReturn = " + sReturn);
  118 +
  119 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  120 + log.debug("token = " + mapVal.get("token") );
  121 +
  122 + this.mockMvc.perform(
  123 + post("/api/test-redirect")
  124 + .header("Authorization", "Bearer " + mapVal.get("token"))
  125 + )
  126 + .andDo(print())
  127 + .andExpect(status().isOk());
  128 +
  129 + }
  130 +
  131 + @SuppressWarnings("unchecked")
  132 + @Test
  133 + void userSangki() throws Exception {
  134 + MvcResult mvcResult = fnAuthenticate();
  135 + String sReturn = mvcResult.getResponse().getContentAsString();
  136 + log.debug("sReturn = " + sReturn);
  137 +
  138 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  139 + log.debug("token = " + mapVal.get("token") );
  140 +
  141 + this.mockMvc.perform(
  142 + get("/api/user/sangki")
  143 + .header("Authorization", "Bearer " + mapVal.get("token"))
  144 + )
  145 + .andDo(print())
  146 + .andExpect(status().isOk())
  147 + .andExpect(content().string(containsString("sangki")));
  148 +
  149 + }
  150 +
  151 + @SuppressWarnings("unchecked")
  152 + @Test
  153 + void hello() throws Exception {
  154 + MvcResult mvcResult = fnAuthenticate();
  155 + String sReturn = mvcResult.getResponse().getContentAsString();
  156 + log.debug("sReturn = " + sReturn);
  157 +
  158 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  159 + log.debug("token = " + mapVal.get("token") );
  160 +
  161 + this.mockMvc.perform(
  162 + get("/api/hello")
  163 + .header("Authorization", "Bearer " + mapVal.get("token"))
  164 + )
  165 + .andDo(print())
  166 + .andExpect(status().isOk())
  167 + .andExpect(content().string(containsString("hello")));
  168 +
  169 + }
  170 +
  171 + @Test
  172 + void parseJwt(@Value("${jwt.secret}") String secret) throws Exception {
  173 + MvcResult mvcResult = fnAuthenticate();
  174 + String sReturn = mvcResult.getResponse().getContentAsString();
  175 +
  176 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  177 + String accessToken = (String) mapVal.get("token");
  178 + byte[] keyBytes = Decoders.BASE64URL.decode(secret);
  179 + SecretKey key = Keys.hmacShaKeyFor(keyBytes);
  180 + Jws<Claims> claims;
  181 + try{
  182 + claims = Jwts.parser()
  183 + .verifyWith(key)
  184 + .build()
  185 + .parseSignedClaims(accessToken);
  186 + log.debug("parseJwt = " + CommonJson.objectToString(claims));
  187 + log.debug("parseJwt(getSubject) = " + claims.getBody().getSubject());
  188 + log.debug("parseJwt(claims) = " + CommonJson.objectToString(claims.getBody()));
  189 + } catch (Exception ignored) {
  190 + log.debug("parseJwt = " + ignored.getLocalizedMessage());
  191 + }
  192 + }
  193 +
  194 + @Test
  195 + void refreshToken() throws Exception {
  196 +
  197 + MvcResult mvcResult = fnAuthenticate();
  198 + String sReturn = mvcResult.getResponse().getContentAsString();
  199 +
  200 + HashMap<String, String> mapVal = (HashMap<String, String>) CommonJson.stringToObject(sReturn, HashMap.class);
  201 + String refreshToken = (String) mapVal.get("refreshToken");
  202 +
  203 + this.mockMvc.perform(
  204 + post("/api/refreshtoken")
  205 + .header(JwtFilter.AUTHORIZATION_REFRESH_HEADER, refreshToken)
  206 + )
  207 + .andDo(print())
  208 + .andExpect(status().isOk())
  209 + .andExpect(content().string(containsString("token")))
  210 + .andReturn();
  211 + }
  212 +
  213 +}
... ...