59925c2787
Build and Test j3270 / Build JAR & Run Tests (Java 17) (push) Successful in 34s
Build and Test j3270 / Build JAR & Run Tests (Java 11) (push) Successful in 42s
Build and Test j3270 / Build JAR & Run Tests (Java 21) (push) Successful in 1m13s
Release j3270 / Build & Publish Release (push) Successful in 1m8s
429 lines
14 KiB
Bash
Executable File
429 lines
14 KiB
Bash
Executable File
#!/bin/sh
|
|
# ==============================================================================
|
|
# j3270 Setup Script (POSIX Shell)
|
|
# Detects Java 11+ JDK and builds j3270 standalone executable JAR.
|
|
#
|
|
# Usage:
|
|
# ./setup.sh [options] [-- run-arguments]
|
|
#
|
|
# Options:
|
|
# -r, --run Launch j3270 immediately after successful build
|
|
# -t, --test Run test suite after build
|
|
# -c, --clean Clean build directory before compiling
|
|
# -h, --help Show this help message
|
|
# ==============================================================================
|
|
set -e
|
|
|
|
# Resolve directory of this script
|
|
SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)"
|
|
cd "$SCRIPT_DIR"
|
|
|
|
# ANSI color codes (if output is to an interactive terminal)
|
|
if [ -t 1 ]; then
|
|
BOLD="\033[1m"
|
|
GREEN="\033[1;32m"
|
|
YELLOW="\033[1;33m"
|
|
CYAN="\033[1;36m"
|
|
RED="\033[1;31m"
|
|
RESET="\033[0m"
|
|
else
|
|
BOLD=""
|
|
GREEN=""
|
|
YELLOW=""
|
|
CYAN=""
|
|
RED=""
|
|
RESET=""
|
|
fi
|
|
|
|
log_info() { printf "%b[INFO]%b %s\n" "$CYAN" "$RESET" "$*"; }
|
|
log_success() { printf "%b[OK]%b %s\n" "$GREEN" "$RESET" "$*"; }
|
|
log_warn() { printf "%b[WARN]%b %s\n" "$YELLOW" "$RESET" "$*"; }
|
|
log_error() { printf "%b[ERROR]%b %s\n" "$RED" "$RESET" "$*"; }
|
|
|
|
show_help() {
|
|
cat << EOF
|
|
j3270 Terminal Emulator - Setup and Build Script
|
|
|
|
Usage:
|
|
./setup.sh [options] [-- run-arguments]
|
|
|
|
Options:
|
|
-r, --run Build and immediately launch j3270
|
|
-t, --test Run automated unit tests after build
|
|
-c, --clean Remove previous build artifacts before building
|
|
-h, --help Show this help message
|
|
|
|
Examples:
|
|
./setup.sh
|
|
./setup.sh --clean
|
|
./setup.sh --run
|
|
./setup.sh --run -- mainframe.example.com 23 4
|
|
./setup.sh --test
|
|
EOF
|
|
}
|
|
|
|
# Parse command line flags
|
|
DO_RUN=0
|
|
DO_TEST=0
|
|
DO_CLEAN=0
|
|
RUN_ARGS=""
|
|
|
|
while [ $# -gt 0 ]; do
|
|
case "$1" in
|
|
-r|--run)
|
|
DO_RUN=1
|
|
shift
|
|
;;
|
|
-t|--test)
|
|
DO_TEST=1
|
|
shift
|
|
;;
|
|
-c|--clean)
|
|
DO_CLEAN=1
|
|
shift
|
|
;;
|
|
-h|--help)
|
|
show_help
|
|
exit 0
|
|
;;
|
|
--)
|
|
shift
|
|
RUN_ARGS="$*"
|
|
break
|
|
;;
|
|
*)
|
|
RUN_ARGS="$*"
|
|
break
|
|
;;
|
|
esac
|
|
done
|
|
|
|
printf "\n%b=== j3270 Setup & Build ===%b\n\n" "$BOLD" "$RESET"
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 1. Java Version & JDK Toolchain Detection
|
|
# ------------------------------------------------------------------------------
|
|
|
|
# Extracts the integer major version from a javac or java version string
|
|
# Examples: "javac 11.0.19" -> 11, "javac 17.0.2" -> 17, "javac 1.8.0_292" -> 8
|
|
parse_major_version() {
|
|
raw_str="$1"
|
|
ver_token=$(echo "$raw_str" | sed -n \
|
|
-e 's/.*javac *\([0-9][0-9._]*\).*/\1/p' \
|
|
-e 's/.*version *"\([0-9][0-9._]*\)".*/\1/p' \
|
|
-e 's/.*version *\([0-9][0-9._]*\).*/\1/p' | head -n 1)
|
|
|
|
if [ -n "$ver_token" ]; then
|
|
echo "$ver_token" | sed -e 's/^1\.//' -e 's/[^0-9].*//'
|
|
fi
|
|
}
|
|
|
|
# Checks if a given directory contains a valid JDK >= 11
|
|
# Sets JAVAC_BIN, JAR_BIN, JAVA_BIN, JAVA_VERSION if valid
|
|
test_jdk_candidate() {
|
|
cand_home="$1"
|
|
cand_javac=""
|
|
cand_jar=""
|
|
cand_java=""
|
|
|
|
if [ -n "$cand_home" ] && [ -d "$cand_home" ]; then
|
|
if [ -x "$cand_home/bin/javac" ]; then cand_javac="$cand_home/bin/javac"; fi
|
|
if [ -x "$cand_home/bin/jar" ]; then cand_jar="$cand_home/bin/jar"; fi
|
|
if [ -x "$cand_home/bin/java" ]; then cand_java="$cand_home/bin/java"; fi
|
|
fi
|
|
|
|
if [ -z "$cand_javac" ] || [ -z "$cand_jar" ] || [ -z "$cand_java" ]; then
|
|
return 1
|
|
fi
|
|
|
|
# Verify that javac actually executes successfully
|
|
if ! "$cand_javac" -version >/dev/null 2>&1; then
|
|
return 1
|
|
fi
|
|
|
|
raw_ver=$("$cand_javac" -version 2>&1)
|
|
major_num=$(parse_major_version "$raw_ver")
|
|
|
|
if [ -n "$major_num" ] && [ "$major_num" -ge 11 ] 2>/dev/null; then
|
|
JAVAC_BIN="$cand_javac"
|
|
JAR_BIN="$cand_jar"
|
|
JAVA_BIN="$cand_java"
|
|
JAVA_VERSION="$raw_ver"
|
|
DETECTED_JAVA_HOME="$cand_home"
|
|
return 0
|
|
fi
|
|
|
|
return 1
|
|
}
|
|
|
|
JAVAC_BIN=""
|
|
JAR_BIN=""
|
|
JAVA_BIN=""
|
|
JAVA_VERSION=""
|
|
DETECTED_JAVA_HOME=""
|
|
|
|
log_info "Searching for a compatible Java Development Kit (JDK 11+)..."
|
|
|
|
# Strategy A: Check user-specified JAVA_HOME
|
|
if [ -n "$JAVA_HOME" ]; then
|
|
if test_jdk_candidate "$JAVA_HOME"; then
|
|
log_info "Found valid JDK in \$JAVA_HOME"
|
|
fi
|
|
fi
|
|
|
|
# Strategy B: Check current PATH commands (handling potential macOS /usr/bin stubs)
|
|
if [ -z "$JAVAC_BIN" ] && command -v javac >/dev/null 2>&1 && command -v jar >/dev/null 2>&1 && command -v java >/dev/null 2>&1; then
|
|
if javac -version >/dev/null 2>&1; then
|
|
raw_ver=$(javac -version 2>&1)
|
|
major_num=$(parse_major_version "$raw_ver")
|
|
if [ -n "$major_num" ] && [ "$major_num" -ge 11 ] 2>/dev/null; then
|
|
JAVAC_BIN="$(command -v javac)"
|
|
JAR_BIN="$(command -v jar)"
|
|
JAVA_BIN="$(command -v java)"
|
|
JAVA_VERSION="$raw_ver"
|
|
log_info "Found valid JDK on system PATH"
|
|
fi
|
|
fi
|
|
fi
|
|
|
|
# Strategy C: macOS java_home utility
|
|
if [ -z "$JAVAC_BIN" ] && [ -x /usr/libexec/java_home ]; then
|
|
for v in 11 17 21 24 ""; do
|
|
if [ -n "$v" ]; then
|
|
mhome="$(/usr/libexec/java_home -v "$v+" 2>/dev/null || true)"
|
|
else
|
|
mhome="$(/usr/libexec/java_home 2>/dev/null || true)"
|
|
fi
|
|
if [ -n "$mhome" ] && test_jdk_candidate "$mhome"; then
|
|
log_info "Found macOS JDK via /usr/libexec/java_home: $mhome"
|
|
break
|
|
fi
|
|
done
|
|
fi
|
|
|
|
# Strategy D: Check standard package manager & OS installation directories
|
|
if [ -z "$JAVAC_BIN" ]; then
|
|
candidate_paths="
|
|
/opt/homebrew/opt/openjdk/libexec/openjdk.jdk/Contents/Home
|
|
/opt/homebrew/opt/openjdk@21/libexec/openjdk.jdk/Contents/Home
|
|
/opt/homebrew/opt/openjdk@17/libexec/openjdk.jdk/Contents/Home
|
|
/opt/homebrew/opt/openjdk@11/libexec/openjdk.jdk/Contents/Home
|
|
/opt/homebrew/opt/openjdk
|
|
/opt/homebrew/opt/openjdk@21
|
|
/opt/homebrew/opt/openjdk@17
|
|
/opt/homebrew/opt/openjdk@11
|
|
/usr/local/opt/openjdk/libexec/openjdk.jdk/Contents/Home
|
|
/usr/local/opt/openjdk@21/libexec/openjdk.jdk/Contents/Home
|
|
/usr/local/opt/openjdk@17/libexec/openjdk.jdk/Contents/Home
|
|
/usr/local/opt/openjdk@11/libexec/openjdk.jdk/Contents/Home
|
|
/usr/local/opt/openjdk
|
|
/Library/Java/JavaVirtualMachines/*/Contents/Home
|
|
$HOME/Library/Java/JavaVirtualMachines/*/Contents/Home
|
|
/usr/lib/jvm/default-java
|
|
/usr/lib/jvm/java-21-openjdk*
|
|
/usr/lib/jvm/java-17-openjdk*
|
|
/usr/lib/jvm/java-11-openjdk*
|
|
/usr/lib/jvm/temurin-21*
|
|
/usr/lib/jvm/temurin-17*
|
|
/usr/lib/jvm/temurin-11*
|
|
/usr/lib/jvm/semeru-21*
|
|
/usr/lib/jvm/semeru-17*
|
|
/usr/lib/jvm/semeru-11*
|
|
/usr/lib/jvm/zulu-21*
|
|
/usr/lib/jvm/zulu-17*
|
|
/usr/lib/jvm/zulu-11*
|
|
/usr/lib/jvm/*
|
|
/usr/java/*
|
|
/usr/local/openjdk21
|
|
/usr/local/openjdk17
|
|
/usr/local/openjdk11
|
|
/usr/local/openjdk*
|
|
$HOME/.sdkman/candidates/java/current
|
|
$HOME/.sdkman/candidates/java/*
|
|
$HOME/.asdf/installs/java/*
|
|
$HOME/.jenv/versions/*
|
|
"
|
|
|
|
for cand in $candidate_paths; do
|
|
if [ -d "$cand" ] && test_jdk_candidate "$cand"; then
|
|
log_info "Found compatible JDK at: $cand"
|
|
break
|
|
fi
|
|
done
|
|
fi
|
|
|
|
# If no compatible JDK is found, provide OS-tailored installation help
|
|
if [ -z "$JAVAC_BIN" ] || [ -z "$JAR_BIN" ] || [ -z "$JAVA_BIN" ]; then
|
|
log_error "No compatible Java Development Kit (JDK 11+) was found on your system."
|
|
printf "\n"
|
|
printf "j3270 requires a Java Development Kit (JDK) version 11 or higher (LTS 11, 17, or 21).\n"
|
|
printf "Note: A JRE (runtime only) is not sufficient; the compiler (javac) and archiver (jar) are required.\n\n"
|
|
printf "%bTo install JDK 11+ on your system:%b\n\n" "$BOLD" "$RESET"
|
|
|
|
UNAME_S="$(uname -s 2>/dev/null || echo "Unknown")"
|
|
case "$UNAME_S" in
|
|
Darwin)
|
|
printf " • Using Homebrew:\n"
|
|
printf " brew install openjdk@17\n"
|
|
printf " sudo ln -sfn /opt/homebrew/opt/openjdk@17/libexec/openjdk.jdk /Library/Java/JavaVirtualMachines/openjdk-17.jdk\n\n"
|
|
printf " • Or download Eclipse Temurin (Adoptium PKG installer):\n"
|
|
printf " https://adoptium.net\n\n"
|
|
;;
|
|
Linux)
|
|
if command -v apt-get >/dev/null 2>&1; then
|
|
printf " • Debian / Ubuntu / Linux Mint:\n"
|
|
printf " sudo apt update && sudo apt install -y openjdk-17-jdk\n\n"
|
|
elif command -v dnf >/dev/null 2>&1; then
|
|
printf " • Fedora / RHEL / CentOS / Rocky / AlmaLinux:\n"
|
|
printf " sudo dnf install -y java-17-openjdk-devel\n\n"
|
|
elif command -v pacman >/dev/null 2>&1; then
|
|
printf " • Arch Linux / Manjaro:\n"
|
|
printf " sudo pacman -S jdk17-openjdk\n\n"
|
|
elif command -v apk >/dev/null 2>&1; then
|
|
printf " • Alpine Linux:\n"
|
|
printf " sudo apk add openjdk17\n\n"
|
|
elif command -v zypper >/dev/null 2>&1; then
|
|
printf " • openSUSE:\n"
|
|
printf " sudo zypper install -y java-17-openjdk-devel\n\n"
|
|
else
|
|
printf " • Install JDK 17 via your system package manager or SDKMAN:\n"
|
|
printf " curl -s \"https://get.sdkman.io\" | bash\n"
|
|
printf " sdk install java 17.0.10-tem\n\n"
|
|
fi
|
|
;;
|
|
FreeBSD|OpenBSD|NetBSD)
|
|
printf " • BSD package manager:\n"
|
|
printf " pkg install openjdk17\n\n"
|
|
;;
|
|
*)
|
|
printf " • Download Eclipse Temurin JDK:\n"
|
|
printf " https://adoptium.net\n\n"
|
|
;;
|
|
esac
|
|
|
|
printf "After installing, re-run ./setup.sh\n\n"
|
|
exit 1
|
|
fi
|
|
|
|
if [ -n "$DETECTED_JAVA_HOME" ]; then
|
|
export JAVA_HOME="$DETECTED_JAVA_HOME"
|
|
fi
|
|
|
|
log_success "JDK verified: $JAVA_VERSION"
|
|
log_info "Java compiler: $JAVAC_BIN"
|
|
log_info "JAR packager: $JAR_BIN"
|
|
log_info "Java runtime: $JAVA_BIN"
|
|
if [ -n "$JAVA_HOME" ]; then
|
|
log_info "JAVA_HOME: $JAVA_HOME"
|
|
fi
|
|
printf "\n"
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 2. Preparation & Clean
|
|
# ------------------------------------------------------------------------------
|
|
BUILD_DIR="$SCRIPT_DIR/build"
|
|
|
|
if [ "$DO_CLEAN" -eq 1 ]; then
|
|
log_info "Cleaning build directory ($BUILD_DIR)..."
|
|
rm -rf "$BUILD_DIR/lib3270j" "$BUILD_DIR/j3270" "$BUILD_DIR/MANIFEST.MF" "$BUILD_DIR/j3270.jar"
|
|
fi
|
|
|
|
mkdir -p "$BUILD_DIR/lib3270j" "$BUILD_DIR/j3270"
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 3. Compile Core Protocol Engine (lib3270j)
|
|
# ------------------------------------------------------------------------------
|
|
log_info "Compiling lib3270j core engine..."
|
|
find "$SCRIPT_DIR/lib3270j/src/main/java" -name "*.java" | sed 's/^/"/;s/$/"/' > "$BUILD_DIR/lib_sources.txt"
|
|
|
|
if [ ! -s "$BUILD_DIR/lib_sources.txt" ]; then
|
|
log_error "No source files found in lib3270j/src/main/java"
|
|
exit 1
|
|
fi
|
|
|
|
"$JAVAC_BIN" -d "$BUILD_DIR/lib3270j" @"$BUILD_DIR/lib_sources.txt"
|
|
rm -f "$BUILD_DIR/lib_sources.txt"
|
|
log_success "lib3270j compiled successfully."
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 4. Compile Desktop Application (j3270)
|
|
# ------------------------------------------------------------------------------
|
|
log_info "Compiling j3270 terminal emulator..."
|
|
find "$SCRIPT_DIR/j3270/src/main/java" -name "*.java" | sed 's/^/"/;s/$/"/' > "$BUILD_DIR/app_sources.txt"
|
|
|
|
if [ ! -s "$BUILD_DIR/app_sources.txt" ]; then
|
|
log_error "No source files found in j3270/src/main/java"
|
|
exit 1
|
|
fi
|
|
|
|
"$JAVAC_BIN" -cp "$BUILD_DIR/lib3270j" -d "$BUILD_DIR/j3270" @"$BUILD_DIR/app_sources.txt"
|
|
rm -f "$BUILD_DIR/app_sources.txt"
|
|
log_success "j3270 application compiled successfully."
|
|
|
|
# Copy any resources if present
|
|
if [ -d "$SCRIPT_DIR/j3270/src/main/resources" ]; then
|
|
cp -r "$SCRIPT_DIR/j3270/src/main/resources/"* "$BUILD_DIR/j3270/" 2>/dev/null || true
|
|
fi
|
|
if [ -d "$SCRIPT_DIR/lib3270j/src/main/resources" ]; then
|
|
cp -r "$SCRIPT_DIR/lib3270j/src/main/resources/"* "$BUILD_DIR/lib3270j/" 2>/dev/null || true
|
|
fi
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 5. Package Standalone Executable JAR
|
|
# ------------------------------------------------------------------------------
|
|
log_info "Packaging standalone executable JAR..."
|
|
|
|
cat << 'EOF' > "$BUILD_DIR/MANIFEST.MF"
|
|
Manifest-Version: 1.0
|
|
Main-Class: haus.nightmare.j3270.J3270App
|
|
Implementation-Title: j3270
|
|
Implementation-Version: 0.1.0
|
|
Created-By: j3270 setup.sh
|
|
|
|
EOF
|
|
|
|
"$JAR_BIN" cvfm "$BUILD_DIR/j3270.jar" "$BUILD_DIR/MANIFEST.MF" \
|
|
-C "$BUILD_DIR/lib3270j" . \
|
|
-C "$BUILD_DIR/j3270" . > /dev/null
|
|
|
|
if [ ! -f "$BUILD_DIR/j3270.jar" ]; then
|
|
log_error "Failed to create $BUILD_DIR/j3270.jar"
|
|
exit 1
|
|
fi
|
|
|
|
JAR_SIZE=$(ls -lh "$BUILD_DIR/j3270.jar" | awk '{print $5}')
|
|
printf "\n%b=== Build Successful ===%b\n" "$BOLD" "$RESET"
|
|
log_success "Executable JAR: $BUILD_DIR/j3270.jar ($JAR_SIZE)"
|
|
|
|
printf "\n%bTo run j3270:%b\n" "$BOLD" "$RESET"
|
|
printf " ./run.sh\n"
|
|
printf " # Or directly:\n"
|
|
printf " %s -jar \"%s/build/j3270.jar\"\n\n" "$JAVA_BIN" "$SCRIPT_DIR"
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 6. Run Tests (if requested)
|
|
# ------------------------------------------------------------------------------
|
|
if [ "$DO_TEST" -eq 1 ]; then
|
|
printf "%b=== Running Unit Tests ===%b\n" "$BOLD" "$RESET"
|
|
if [ -x "$SCRIPT_DIR/test_all.sh" ]; then
|
|
sh "$SCRIPT_DIR/test_all.sh"
|
|
elif [ -x "$SCRIPT_DIR/build_all.sh" ]; then
|
|
sh "$SCRIPT_DIR/build_all.sh" test
|
|
fi
|
|
fi
|
|
|
|
# ------------------------------------------------------------------------------
|
|
# 7. Launch Application (if requested)
|
|
# ------------------------------------------------------------------------------
|
|
if [ "$DO_RUN" -eq 1 ]; then
|
|
log_info "Launching j3270..."
|
|
if [ "$(uname -s)" = "Darwin" ]; then
|
|
# On macOS, enable native application menu bar
|
|
exec "$JAVA_BIN" -Dapple.laf.useScreenMenuBar=true \
|
|
-Dapple.awt.application.name=j3270 \
|
|
-jar "$BUILD_DIR/j3270.jar" $RUN_ARGS
|
|
else
|
|
exec "$JAVA_BIN" -jar "$BUILD_DIR/j3270.jar" $RUN_ARGS
|
|
fi
|
|
fi
|