Phase 2a: 모듈서버 패턴 + 재사용 빌드시스템 (ac 모듈 38서비스 실동작)

- ac_svr(30 매입서비스 advertise) + rc_svr/st_svr, dbio 정적라이브러리, common 라이브러리
- app/build.sh: 모듈 자동발견(app/src/<mod>/<mod>_svr.pgc) → ecpg+buildserver+ndrxconfig 생성
- ac 배치 2종, 스키마 9테이블, 검증: 41서비스 AVAIL, 체인·배치 psql 커밋, prepared_xacts=0

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
forge-bot 2026-07-19 09:37:17 +00:00
parent e6e29e6b5d
commit 05a0ff3e56
28 changed files with 1964 additions and 410 deletions

188
app/build.sh Normal file
View file

@ -0,0 +1,188 @@
#!/bin/bash
##
## build.sh - REUSABLE build + Enduro/X config generator for acquire-core-x.
##
## Discovers every module under app/src/<mod>/, ecpg-precompiles its .pgc, builds
## - libacqcommon.a (from app/src/common/*.c) [once]
## - lib<mod>dbio.a (from app/src/<mod>/dbio/*.pgc) [per module]
## - <mod>_svr (from app/src/<mod>/<mod>_svr.pgc) [per module]
## - <mod> batches (from app/src/<mod>/batch/*.pgc) [per module]
## - standalone clients (from app/src/clients/*.c)
## then GENERATES app/conf/ndrxconfig.xml with one <server> entry per <mod>_svr.
##
## Adding a new module later = drop app/src/<mod>/{<mod>_svr.pgc,dbio,batch} and
## re-run build.sh. No hand-editing of config or this script is required: modules,
## servers, dbio libs, batches, and srvids are all DISCOVERED.
##
set -euo pipefail
SRC=/app/src
BIN=/app/bin
LIB=/app/lib
OBJ=/app/obj
UBF=/app/ubftab
CONF=/app/conf
EXINC=/usr/local/include
PGINC="$(pg_config --includedir)"
PGLIB="$(pg_config --libdir)"
mkdir -p "$BIN" "$LIB" "$OBJ"
# Includes for every compile (CFLAGS is honored by buildserver/buildclient and
# by our direct gcc calls). Add every module's dbio dir so headers resolve.
CFLAGS="-I$UBF -I$EXINC -I$PGINC -I$SRC/common"
for d in "$SRC"/*/dbio; do [ -d "$d" ] && CFLAGS="$CFLAGS -I$d"; done
export CFLAGS
PGLINK="-L$PGLIB -lecpg -lpq"
log() { echo "[build] $*"; }
# ---------------------------------------------------------------------------
# discover modules = dirs app/src/<mod>/ that contain <mod>_svr.pgc
# ---------------------------------------------------------------------------
MODS=()
for d in "$SRC"/*/; do
m="$(basename "$d")"
[ -f "$d/${m}_svr.pgc" ] && MODS+=("$m")
done
IFS=$'\n' MODS=($(printf '%s\n' "${MODS[@]}" | sort)); unset IFS
log "modules discovered: ${MODS[*]}"
# ---------------------------------------------------------------------------
# 0. UBF field header
# ---------------------------------------------------------------------------
log "mkfldhdr acq.fd"
( cd "$UBF" && FIELDTBLS=acq.fd FLDTBLDIR="$UBF" mkfldhdr acq.fd >/dev/null )
# ecpg precompile helper: $1 = .pgc path -> echoes generated .c path
ecpg_gen() {
local pgc="$1" base out
base="$(basename "${pgc%.pgc}")"
out="$OBJ/${base}.c"
ecpg -I"$UBF" -I"$(dirname "$pgc")" -o "$out" "$pgc"
echo "$out"
}
# ---------------------------------------------------------------------------
# 1. common lib -> libacqcommon.a
# ---------------------------------------------------------------------------
log "libacqcommon.a"
COMMON_OBJS=()
for c in "$SRC"/common/*.c; do
o="$OBJ/$(basename "${c%.c}").o"
gcc -c $CFLAGS "$c" -o "$o"
COMMON_OBJS+=("$o")
done
ar rcs "$LIB/libacqcommon.a" "${COMMON_OBJS[@]}"
NSVR=0; NDBIO=0; NBATCH=0
# ---------------------------------------------------------------------------
# 2..4 per module: dbio lib, server, batches
# ---------------------------------------------------------------------------
for m in "${MODS[@]}"; do
MDIR="$SRC/$m"
DBIO_LIB=""
# -- dbio static lib (optional) --
if compgen -G "$MDIR/dbio/*.pgc" >/dev/null; then
log "lib${m}dbio.a"
DB_OBJS=()
for pgc in "$MDIR"/dbio/*.pgc; do
c="$(ecpg_gen "$pgc")"
o="${c%.c}.o"
gcc -c $CFLAGS "$c" -o "$o"
DB_OBJS+=("$o")
done
ar rcs "$LIB/lib${m}dbio.a" "${DB_OBJS[@]}"
DBIO_LIB="$LIB/lib${m}dbio.a"
NDBIO=$((NDBIO+1))
fi
# -- module server <mod>_svr --
log "${m}_svr"
SVR_C="$(ecpg_gen "$MDIR/${m}_svr.pgc")"
buildserver -o "$BIN/${m}_svr" -f "$SVR_C" \
-a "$DBIO_LIB $LIB/libacqcommon.a $PGLINK"
NSVR=$((NSVR+1))
# -- batches (optional): each *.pgc -> its own client executable --
if compgen -G "$MDIR/batch/*.pgc" >/dev/null; then
for pgc in "$MDIR"/batch/*.pgc; do
name="$(basename "${pgc%.pgc}")"
log "batch $name"
BC="$(ecpg_gen "$pgc")"
buildclient -o "$BIN/$name" -f "$BC" \
-a "$DBIO_LIB $LIB/libacqcommon.a $PGLINK"
NBATCH=$((NBATCH+1))
done
fi
done
# ---------------------------------------------------------------------------
# 5. standalone clients (plain C, no EXEC SQL)
# ---------------------------------------------------------------------------
NCLI=0
for c in "$SRC"/clients/*.c; do
name="$(basename "${c%.c}")"
log "client $name"
buildclient -o "$BIN/$name" -f "$c"
NCLI=$((NCLI+1))
done
# ---------------------------------------------------------------------------
# 6. GENERATE ndrxconfig.xml (tmsrv fixed at srvid 40; module servers 100 step 10)
# ---------------------------------------------------------------------------
log "generating ndrxconfig.xml for servers: ${MODS[*]/%/_svr}"
gen_servers() {
local srvid=100
for m in "${MODS[@]}"; do
cat <<EOF
<server name="${m}_svr">
<srvid>${srvid}</srvid>
<min>1</min>
<max>1</max>
<sysopt>-e \${NDRX_APPHOME}/log/${m}_svr.log -r</sysopt>
</server>
EOF
srvid=$((srvid+10))
done
}
cat > "$CONF/ndrxconfig.xml" <<EOF
<?xml version="1.0" ?>
<!-- GENERATED by app/build.sh - do not hand-edit. One <server> per discovered
<mod>_svr module server; each advertises its module's services at tpsvrinit. -->
<endurox>
<appconfig>
<sanity>1</sanity>
<brrefresh>5</brrefresh>
<restart_min>1</restart_min>
<restart_step>1</restart_step>
<restart_max>5</restart_max>
<restart_to_check>20</restart_to_check>
<gather_pq_stats>Y</gather_pq_stats>
</appconfig>
<defaults>
<min>1</min>
<max>1</max>
<autokill>1</autokill>
<start_max>20</start_max>
<pingtime>100</pingtime>
<ping_max>800</ping_max>
<end_max>30</end_max>
<killtime>1</killtime>
</defaults>
<servers>
<!-- XA transaction manager for RM1 (ECPG/PostgreSQL). -->
<server name="tmsrv">
<srvid>40</srvid>
<min>1</min>
<max>1</max>
<sysopt>-e \${NDRX_APPHOME}/log/tmsrv-rm1.log -r -- -t1 -l\${NDRX_APPHOME}/tmlogs/rm1 -m10</sysopt>
</server>
$(gen_servers)
</servers>
</endurox>
EOF
log "DONE: modules=${#MODS[@]} servers=$NSVR dbio_libs=$NDBIO batches=$NBATCH clients=$NCLI"
echo "[build] server binaries: ${MODS[*]/%/_svr}"