为Java JAR包项目配置systemd
服务(.service
文件),可以实现项目的开机自启、后台运行、状态管理等功能,以下是详细步骤:
一、创建service配置文件
文件路径:在
/etc/systemd/system/
目录下创建服务文件,命名格式为[项目名].service
(例如fws-billing.service
)。配置内容:
[Unit]
Description=Java Application Service (Managed by start.sh)
After=network.target
# 若依赖数据库等服务,可添加:After=mysql.service redis.service
[Service]
# 运行用户(根据实际情况修改,建议非root用户)
User=ops_app_user
Group=ops_app_user
# 工作目录(脚本所在目录)
WorkingDirectory=/data/shell
# 启动命令:调用start.sh,传递参数(根据实际需求修改参数值)
# 格式:/data/app/start.sh <jar_path> <jar_name> <max_memory>
ExecStart=/data/shell/start.sh ifahan fws-billing 512
# 停止命令:直接调用原有的shutdown.sh(假设其能正确终止进程)
ExecStop=/bin/bash -c "pid=\$(pgrep -f 'ifahan/server/fws-billing.jar'); if [ -n \"\$pid\" ]; then kill -15 \"\$pid\"; sleep 3; if ps -p \"\$pid\" > /dev/null; then kill -9 \"\$pid\"; fi; fi; exit 0;"
Type=forking
# 让Java进程将PID写入文件(需在start.sh中配置)
PIDFile=ifahan/tmp/fws-billing.pid
# # 等待Java进程启动完成的超时时间
TimeoutStartSec=30
# 重启策略:异常退出时自动重启
Restart=on-failure
RestartSec=10
# 环境变量(继承脚本中的JAVA_HOME等配置,也可在此补充)
Environment="BUILD_ID=DONTKILLME"
Environment="TZ=Asia/Shanghai"
# 日志输出(同时保留脚本自身的日志文件和systemd日志)
StandardOutput=journal
StandardError=journal
[Install]
WantedBy=multi-user.target
启动脚本
#!/bin/bash
set -e
BUILD_ID=DONTKILLME
export JAVA_HOME=/data/app/jdk1.8.0_171
export PATH=$JAVA_HOME/bin:$PATH
export CLASSPATH=.:$JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar
source /etc/profile
if [ $# -lt 2 ]; then
echo "Usage: $0 <jar_path> <jar_name> [min_memory] [max_memory]"
exit 1
fi
jar_path=$1
jar_name=$2
min_memory=${3:-512}
max_memory=$4
if [ -n "$max_memory" ] && [ "$max_memory" -lt "$min_memory" ]; then
echo "Error: max_memory cannot be less than min_memory"
exit 1
fi
# Shutdown existing instance
/data/shell/shutdown.sh "$jar_name"
# Navigate to application directory
cd /data/app/
# Start new instance
if [ -z "$max_memory" ]; then
nohup java -Xms${min_memory}m -Duser.timezone=Asia/Shanghai -jar "$jar_path/server/$jar_name.jar" >> "$jar_path/$jar_name.log" 2>&1 &
else
nohup java -Xms${min_memory}m -Xmx${max_memory}m -Duser.timezone=Asia/Shanghai -jar "$jar_path/server/$jar_name.jar" >> "$jar_path/$jar_name.log" 2>&1 &
fi
pid_file="ifahan/tmp/fws-billing.pid"
# 若目录不存在则创建
mkdir -p $(dirname "$pid_file")
# 写入PID
echo $! > "$pid_file"
# Wait for the application to start
sleep 10
echo "--------end $jar_name-------------"
关闭脚本
#!/bin/bash
pid=`jps -l | grep $1 | awk '{print $1}'`
if [[ -n $pid ]]; then
echo "[$1] is running, killing................"
kill -9 $pid
sleep 1
else
echo "[$1] is not running..."
fi
二、配置参数说明
配置项 | 作用说明 |
---|---|
Description |
服务的描述信息,便于识别 |
After=network.target |
表示服务在网络服务启动后再启动,避免因网络未就绪导致启动失败 |
User/Group |
指定运行服务的用户/组,强烈建议非root用户,降低安全风险 |
WorkingDirectory |
服务的工作目录(JAR包所在路径),日志、临时文件等会默认生成在此目录 |
ExecStart |
启动命令,需指定完整的java 路径(可通过which java 查询)和JAR包路径,可添加JVM参数(如内存设置-Xms/-Xmx )、应用参数(如Spring profiles) |
Restart=on-failure |
当服务异常退出(退出码非0)时自动重启,保障服务可用性 |
WantedBy=multi-user.target |
设置服务在多用户模式下开机自启 |
三、服务管理命令
- 重载配置:创建或修改
.service
文件后,需重载systemd配置:
sudo systemctl daemon-reload
sudo systemctl start fws-billing.service
sudo systemctl status fws-billing.service
- 启动服务:
sudo systemctl start fws-billing.service
- 停止服务:
sudo systemctl stop fws-billing.service
- 重启服务:
sudo systemctl restart fws-billing.service
- 查看服务状态:
sudo systemctl status fws-billing.service
# 输出示例:
# ● app-server.service - Java Application Service for MyApp
# Loaded: loaded (/etc/systemd/system/app-server.service; enabled; vendor preset: disabled)
# Active: active (running) since Wed 2025-08-13 10:00:00 CST; 5min ago
# Main PID: 12345 (java)
# Tasks: 30 (limit: 4915)
# Memory: 512.0M
# CGroup: /system.slice/app-server.service
# └─12345 /usr/local/jdk1.8.0_301/bin/java -Xms512m -Xmx1024m -jar /home/app/app-current.jar
- 设置开机自启:
sudo systemctl enable fws-billing.service
- 关闭开机自启:
sudo systemctl disable fws-billing.service
- 查看服务日志(结合journalctl):
# 实时查看日志
sudo journalctl -u fws-billing.service -f
# 查看最近100行日志
sudo journalctl -u fws-billing.service -n 100
# 按时间筛选日志(例如2025-08-13 10:00到10:30)
sudo journalctl -u fws-billing.service --since "2025-08-13 10:00" --until "2025-08-13 10:30"
四. 测试
将进程kill 服务会在10秒后重启