How I Fixed MyBatis <choose> Errors, Groovy AtomicInteger Bugs, and Bash Startup Issues
In this technical diary I walk through three real‑world problems I hit while integrating MyBatis SQL fragments, debugging Groovy constant class compatibility, and crafting a reliable Bash startup script for Java services, sharing the root causes, error messages, and step‑by‑step fixes.
MyBatis <choose> Syntax Error
During integration testing a MyBatis mapper used a <choose> element to select different WHERE clauses based on the parameter type. The when branch for type == 2 omitted the leading AND keyword, so the generated SQL became: ... WHERE t.id = #{testQuery} When the preceding clause already contained conditions, the missing AND caused a MySQL syntax error such as:
java.sql.SQLSyntaxErrorException: You have an error in your SQL syntax ... near 't.id = '123''Fix: add the missing AND before the condition in the type == 2 branch.
<choose>
<when test="type == 1">
AND t.name LIKE CONCAT('%', #{testQuery}, '%')
</when>
<when test="type == 2">
AND t.id = #{testQuery}
</when>
</choose>Groovy Compatibility Issue with AtomicInteger
A constants class defines two static AtomicInteger fields:
public static AtomicInteger RUN_MARK = new AtomicInteger(getMark() % 100_000_000);
public static AtomicInteger COLLECTION_MARK = new AtomicInteger(RUN_MARK.get() / 100);When the class is compiled/run under Groovy, numeric literals are treated as java.math.BigDecimal. Groovy therefore attempts to invoke the non‑existent constructor AtomicInteger(BigDecimal), resulting in:
groovy.lang.GroovyRuntimeException: Could not find matching constructor for: java.util.concurrent.atomic.AtomicInteger(BigDecimal)Work‑arounds:
Explicitly cast literals to int in Groovy code, e.g. (int)100_000_000. This may still fail if the expression involves method calls returning BigDecimal.
Rewrite the constants class in plain Java (or compile it with javac) so that Groovy loads the already‑compiled bytecode. The Java version works without error.
Key lesson: avoid initializing AtomicInteger directly with numeric literals in Groovy source; either use explicit int casts or keep the class in Java.
IntelliJ Remote Host Deployment
When deploying JAR/WAR files to physical servers, the IntelliJ “Remote Host” tool can synchronize files via SFTP/SSH. Required steps:
Open Tools → Deployment → Configuration and add a new SFTP server (host, port, username, password/key).
In the Project view, enable the Remote Host tool window (View → Tool Windows → Remote Host).
Click the “Activate” button in the Remote Host toolbar to make the configured server the active target.
Drag the built JAR/WAR file from the local project pane to the remote directory, or use the “Upload” action.
Forgetting to activate the server disables the upload button, which caused a half‑hour delay in the original workflow.
Multi‑function Bash Service Management Script
The following Bash script provides start, stop, restart, and status commands for a Java application packaged as family-qa.jar. Improvements over a naïve implementation include:
Checking whether the process is already running before starting.
Using kill -9 to force termination when a graceful stop does not succeed.
Displaying colored status messages.
Running the Java process with nohup and common JVM options.
#!/bin/bash
version="1.0.1"
appName="family-qa.jar"
function start() {
count=$(ps -ef | grep java | grep "$appName" | wc -l)
if [ $count -ne 0 ]; then
echo "Maybe $appName is running, please check it..."
else
echo "Starting $appName..."
nohup java -jar "./$appName" -XX:+UseG1GC -XX:+HeapDumpOnOutOfMemoryError -Xms2G -Xmx2G > /dev/null 2>&1 &
fi
}
function stop() {
appId=$(ps -ef | grep java | grep "$appName" | awk '{print $2}')
if [ -z "$appId" ]; then
echo "Maybe $appName not running, please check it..."
else
echo "Stopping $appName (PID $appId)..."
kill -9 "$appId"
fi
}
function restart() {
stop
for i in {5..1}; do
echo -n "$i "
sleep 1
done
echo "0"
start
}
function status() {
appId=$(ps -ef | grep java | grep "$appName" | awk '{print $2}')
if [ -z "$appId" ]; then
echo -e "\033[31mNot running\033[0m"
else
echo -e "\033[32mRunning [PID $appId]\033[0m"
fi
}
function usage() {
echo "Usage: $0 {start|stop|restart|status}"
exit 1
}
case "$1" in
start) start ;;
stop) stop ;;
restart) restart ;;
status) status ;;
*) usage ;;
esacThis script can be placed on each server and invoked directly, reducing manual errors and providing immediate feedback on service state.
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
