Spring Boot 项目打包部署到云服务器:从开发到上线的完整实践指南
在 Java Web 开发的学习中,Spring Boot 凭借其 “约定大于配置” 的理念,极大简化了项目搭建与开发流程,让我们能快速实现业务接口与功能模块。然而,本地 IDE 中运行成功的项目,仅仅是开发流程的第一步。一个真正可用的后端服务,最终需要部署到公网服务器上,才能被外部用户访问,实现业务价值。
在本次课程实践中,我以一个用户管理 Spring Boot 项目为例,完整走完了从本地开发、打包构建、云服务器环境配置,到最终部署上线、公网访问的全流程。过程中我踩了大量新手常见的 “部署坑”,也摸索出了一套稳定、可复用的部署方案。本文将从准备工作、本地打包、服务器配置、部署运行、问题排查、优化方案等多个维度,详细记录我的实践过程与心得,希望能为同样在学习 Spring Boot 部署的同学提供一份可直接参考的指南。
一、部署前的准备工作
部署的稳定性,很大程度上取决于前期准备工作是否充分。我将整个部署流程的前置条件,分为项目侧、服务器侧和工具侧三个部分,逐一完成准备。
1.1 项目侧准备:确保本地项目可稳定运行
部署前最关键的一步,是保证本地项目能 100% 正常运行,避免带着 Bug 上线。我以一个用户管理项目为例,做了以下检查:
功能完整性:确保所有核心接口(如用户查询、新增、修改)在本地 Postman 中调用正常,无逻辑错误。
配置文件适配:修改application.yml中的配置,适配部署环境:
yaml
server:
port: 8080 # 后续云服务器需要开放该端口
spring:
datasource:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://localhost:3306/user_db?useSSL=false&serverTimezone=UTC
username: root
password: 123456
注意:如果数据库部署在服务器上,需要将localhost改为服务器内网 IP;如果使用本地数据库,需确保云服务器能访问本地数据库端口(不推荐,建议部署到服务器端)。
依赖与版本确认:确认项目依赖的 JDK 版本为 1.8(云服务器也使用 JDK1.8,避免版本不兼容),Maven 依赖无冲突、无冗余。
1.2 服务器侧准备:云服务器选型与安全配置
我选择了阿里云 ECS 入门级服务器,配置为 1 核 2G、40G 系统盘,操作系统为 CentOS 7.9,足够支撑学习项目的部署。服务器侧的核心准备工作如下:
购买与初始化服务器:
在阿里云控制台购买 ECS 实例,选择 CentOS 7.9 公共镜像。
设置服务器登录密码,记录服务器公网 IP 地址(后续远程连接、公网访问都需要用到)。
配置安全组规则:
安全组是云服务器的 “防火墙”,默认会拦截所有外部端口的访问,必须手动开放需要的端口:
进入阿里云 ECS 控制台的「安全组」页面,找到实例对应的安全组。
进入「入方向规则」,添加以下规则:
表格
协议类型 端口范围 授权对象 说明
SSH(22) 22/22 0.0.0.0/0 远程连接服务器用
自定义 TCP 8080/8080 0.0.0.0/0 Spring Boot 项目端口
自定义 TCP 3306/3306 0.0.0.0/0 MySQL 数据库端口(可选)
配置完成后,规则会立即生效,后续外部就能访问这些端口了。
服务器基础环境准备:
服务器需要提前安装 JDK、Maven、MySQL(可选)等基础环境,我使用 Xshell 远程连接服务器,执行以下命令安装:
安装 JDK 1.8:
bash
运行
yum install -y java-1.8.0-openjdk-devel
# 验证安装
java -version
安装 Maven(可选,用于服务器端打包):
bash
运行
wget https://archive.apache.org/dist/maven/maven-3/3.6.3/binaries/apache-maven-3.6.3-bin.tar.gz
tar -zxvf apache-maven-3.6.3-bin.tar.gz
mv apache-maven-3.6.3 /usr/local/maven
# 配置环境变量
echo 'export PATH=/usr/local/maven/bin:$PATH' >> /etc/profile
source /etc/profile
# 验证安装
mvn -v
1.3 工具侧准备:远程连接与文件传输工具
为了方便操作服务器和上传文件,我准备了以下工具:
Xshell:用于远程连接 CentOS 服务器,执行 Linux 命令。
Xftp:用于将本地打包好的 JAR 文件上传到云服务器。
Postman:用于后续测试公网接口是否正常访问。
二、本地项目打包:生成可执行 JAR 包
Spring Boot 项目部署的主流方式,是打成可执行的 JAR 包,这种方式无需额外配置 Tomcat 容器,Java 环境即可直接运行。我尝试了两种打包方式,这里详细记录操作步骤与注意事项。
2.1 方式一:IDEA 图形化打包(适合新手)
这是最直观的打包方式,全程通过 IDEA 界面操作,无需输入命令,步骤如下:
打开 IDEA,找到右侧边栏的「Maven」面板,展开当前项目的生命周期。
先执行clean命令:双击Lifecycle下的clean,该命令会清理项目之前编译生成的文件,避免旧文件干扰打包结果。
再执行package命令:双击Lifecycle下的package,IDEA 会自动执行编译、单元测试、打包流程。
查看打包结果:打包完成后,在项目的target目录下,会生成一个.jar文件,例如user-manage-0.0.1-SNAPSHOT.jar,这个文件就是我们后续要部署到服务器的可执行包。
注意:如果项目单元测试报错,会导致打包失败,可以在 IDEA 中点击右侧 Maven 面板的「跳过测试」按钮(闪电图标),再执行package命令,即可跳过单元测试,快速完成打包。
2.2 方式二:命令行打包(更通用、适合自动化场景)
在项目根目录下打开终端(或 IDEA 自带的 Terminal),执行以下 Maven 命令,即可完成打包:
bash
运行
mvn clean package -DskipTests
clean:清理旧的编译文件,保证打包环境干净。
package:执行项目打包,生成可执行 JAR 包。
-DskipTests:跳过单元测试,加快打包速度,适合学习场景使用。
命令执行过程中,终端会输出项目编译、依赖处理、打包的日志,当出现BUILD SUCCESS时,说明打包成功,JAR 包同样会生成在target目录下。
2.3 打包常见问题与解决方法
打包过程中,我遇到了两个典型问题,这里分享给大家避坑:
依赖缺失导致打包失败:报错信息为Could not find artifact xxx,原因是 Maven 仓库中缺少项目依赖的第三方库。解决方法:
检查pom.xml中依赖的坐标是否正确,版本号是否存在。
在 IDEA 中执行Maven面板的「Reload」按钮,重新加载依赖。
手动下载依赖到本地 Maven 仓库,或更换国内 Maven 镜像源(如阿里云镜像)。
Spring Boot 插件未配置导致 JAR 无法执行:打包生成的 JAR 文件在服务器上运行报错no main manifest attribute,原因是pom.xml中未配置 Spring Boot 的 Maven 打包插件。解决方法:在pom.xml中添加以下配置:
xml
<build>
<plugins>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
</plugins>
</build>
添加后重新打包,即可生成可直接运行的可执行 JAR 包。
三、上传 JAR 包到云服务器
打包完成后,需要将本地的 JAR 文件上传到云服务器,我使用了两种方式,分别适合不同场景。
3.1 方式一:Xftp 图形化上传(适合新手)
打开 Xftp,新建会话,输入服务器公网 IP、用户名(默认 root)、密码,连接到服务器。
在左侧本地文件栏,找到项目的target目录,选中生成的 JAR 文件。
在右侧服务器文件栏,进入/usr/local/目录(该目录为 Linux 常用软件安装目录,方便后续管理)。
将 JAR 文件拖拽到右侧服务器目录中,等待上传完成即可。
3.2 方式二:scp 命令上传(无需额外工具)
如果不想安装 Xftp,也可以在本地终端使用scp命令直接上传文件,格式如下:
bash
运行
scp /本地项目路径/target/user-manage-0.0.1-SNAPSHOT.jar root@服务器公网IP:/usr/local/
执行命令后,输入服务器的登录密码,文件就会自动上传到服务器的/usr/local/目录下。
四、服务器上部署并运行 Spring Boot 项目
文件上传完成后,就可以在服务器上启动项目了,这里我会详细记录后台启动、进程管理、日志排查的完整流程,以及新手常见的启动失败问题解决方法。
4.1 后台启动项目(避免终端关闭后项目停止)
直接在服务器终端执行java -jar xxx.jar启动项目,会导致关闭 Xshell 终端后,项目进程也随之停止。因此,我们需要使用nohup命令让项目在后台运行,同时将日志输出到文件中,方便后续排查问题。
操作步骤:
用 Xshell 连接服务器,进入 JAR 文件所在目录:
bash
运行
cd /usr/local/
执行后台启动命令:
bash
运行
nohup java -jar user-manage-0.0.1-SNAPSHOT.jar > app.log 2>&1 &
命令参数说明:
nohup:全称 no hangup,让程序在后台运行,忽略挂断信号(关闭终端不会停止进程)。
java -jar xxx.jar:启动 Spring Boot 项目的核心命令。
> app.log:将标准输出(控制台日志)重定向到app.log文件中。
2>&1:将标准错误输出(报错日志)重定向到和标准输出相同的位置,也就是app.log文件。
&:表示在后台执行该命令,不占用当前终端。
执行命令后,终端会返回一个进程 ID(如[1] 1234),说明项目已经在后台启动了。
4.2 检查项目是否启动成功
启动命令执行后,需要通过以下几种方式确认项目是否真正启动成功:
查看进程是否存在:执行jps命令(JDK 自带的进程查看工具),如果能看到项目对应的进程 ID,说明项目进程已经启动:
bash
运行
[root@ecs ~]# jps
1234 jar
5678 Jps
也可以使用ps -ef | grep java命令,查看所有 Java 进程:
bash
运行
ps -ef | grep java
查看启动日志:执行tail -f app.log命令,实时查看日志文件的输出:
bash
运行
tail -f app.log
当看到日志中出现Started UserManageApplication in X seconds (JVM running for Y)时,说明项目已经成功启动,没有报错。
本地端口检查:执行netstat -tulnp | grep 8080命令,查看 8080 端口是否被项目占用:
bash
运行
netstat -tulnp | grep 8080
如果输出结果中能看到项目进程 ID 和端口号,说明项目已经在 8080 端口正常监听请求了。
4.3 公网访问测试
项目启动成功后,就可以在本地电脑上测试公网访问了:
打开 Postman,新建一个 GET 请求,请求地址为http://服务器公网IP:8080/user/list(项目中的用户列表接口)。
发送请求,如果能正常返回接口数据,说明公网访问成功,部署完成。
也可以直接在浏览器中输入接口地址(GET 请求),查看是否能正常访问。
4.4 启动失败常见问题与排查方法
部署过程中,我遇到了多次启动失败的情况,这里把最常见的问题和排查方法整理出来:
端口被占用:
报错信息:Port 8080 was already in use
排查与解决:执行netstat -tulnp | grep 8080找到占用端口的进程 ID,执行kill -9 进程ID关闭进程;或者修改项目application.yml中的server.port配置,更换为其他未被占用的端口。
数据库连接失败:
报错信息:Failed to obtain JDBC Connection
排查与解决:检查数据库地址、用户名、密码是否正确;如果数据库部署在服务器上,确认数据库服务已启动(systemctl status mysqld);如果数据库在本地,确认服务器和本地网络能连通,且本地数据库已开放 3306 端口。
JDK 版本不兼容:
报错信息:Unsupported major.minor version 52.0
排查与解决:该报错表示服务器的 JDK 版本低于项目编译时的 JDK 版本,需要在服务器上安装与本地一致的 JDK 版本(如 JDK1.8)。
项目启动后自动退出:
排查与解决:执行tail -f app.log查看日志,通常是因为项目启动时遇到了致命错误(如配置文件错误、依赖缺失),根据日志报错信息定位问题并修复。
五、项目进程管理与维护技巧
项目部署完成后,还需要进行简单的进程管理,方便后续重启、停止项目,这里分享几个实用的 Linux 命令和技巧。
5.1 停止正在运行的 Spring Boot 项目
如果需要更新项目、重启服务,需要先停止正在运行的进程:
执行ps -ef | grep java,找到项目对应的进程 ID(PID)。
执行kill -9 进程ID,强制关闭项目进程:
bash
运行
kill -9 1234
也可以结合jps命令快速停止进程:
bash
运行
jps | grep jar | awk '{print $1}' | xargs kill -9
5.2 重启项目的完整流程
更新项目 JAR 包后,重启项目的步骤如下:
停止旧的项目进程。
将新的 JAR 包上传到服务器,替换旧文件。
再次执行后台启动命令:
bash
运行
nohup java -jar user-manage-0.0.1-SNAPSHOT.jar > app.log 2>&1 &
5.3 日志管理与查看技巧
日志是排查项目问题的关键,这里分享几个实用的日志查看命令:
实时查看日志:tail -f app.log(按Ctrl+C退出查看)
查看最后 100 行日志:tail -n 100 app.log
搜索日志中的错误信息:grep "ERROR" app.log
清空日志文件(避免文件过大):echo "" > app.log
六、部署优化与进阶方案
基础的后台启动方式虽然能实现部署,但在实际生产环境中,还存在日志文件过大、进程管理不便、无法开机自启等问题。在本次实践中,我也尝试了几种进阶的优化方案,这里简单分享给大家。
6.1 使用 Systemd 管理项目进程(实现开机自启)
通过配置 Systemd 服务,可以让 Spring Boot 项目随服务器开机自动启动,同时方便管理进程状态,步骤如下:
在服务器上新建服务配置文件:
bash
运行
vi /etc/systemd/system/user-manage.service
写入以下配置:
ini
[Unit]
Description=UserManage Spring Boot Application
After=network.target
[Service]
User=root
ExecStart=/usr/bin/java -jar /usr/local/user-manage-0.0.1-SNAPSHOT.jar
SuccessExitStatus=143
Restart=on-failure
RestartSec=5
[Install]
WantedBy=multi-user.target
重新加载 Systemd 配置:
bash
运行
systemctl daemon-reload
启动服务并设置开机自启:
bash
运行
# 启动服务
systemctl start user-manage
# 设置开机自启
systemctl enable user-manage
# 查看服务状态
systemctl status user-manage
配置完成后,就可以通过systemctl start/stop/restart user-manage命令管理项目进程,服务器重启后项目也会自动启动。
6.2 使用 Docker 容器化部署项目
Docker 容器化部署可以解决环境不一致、依赖冲突的问题,实现 “一次打包,到处运行”,步骤如下:
在服务器上安装 Docker:
bash
运行
yum install -y docker
systemctl start docker
systemctl enable docker
在项目根目录下新建Dockerfile文件:
dockerfile
FROM openjdk:8-jdk-alpine
VOLUME /tmp
COPY target/user-manage-0.0.1-SNAPSHOT.jar app.jar
ENTRYPOINT ["java","-jar","/app.jar"]
本地构建 Docker 镜像(或上传Dockerfile和 JAR 包到服务器构建):
bash
运行
docker build -t user-manage:v1 .
运行 Docker 容器:
bash
运行
docker run -d -p 8080:8080 --name user-manage user-manage:v1
使用 Docker 部署后,项目运行在独立的容器中,不会污染服务器环境,也方便后续的扩容和迁移。
七、实践心得与总结
本次 Spring Boot 项目部署实践,是我第一次将本地开发的项目真正部署到公网服务器上,整个过程从准备、打包、部署到优化,让我收获了远超课堂学习的实战经验,也对后端开发的全流程有了更完整的认知。
首先,我深刻体会到了 “细节决定成败”。部署过程中,安全组端口配置、JDK 版本一致性、配置文件适配这些看似微小的细节,任何一个环节出错,都会导致项目无法正常访问。尤其是端口开放和日志排查,几乎是每个新手都会踩的坑,而通过日志定位问题的能力,也是后端开发中非常重要的技能。
其次,我对 Linux 服务器的操作、进程管理、环境配置有了更直观的理解。以前在课堂上学习的 Linux 命令,大多停留在理论层面,而这次实践中,从文件上传、目录操作,到进程查看、日志分析,让我真正掌握了这些命令的实际用法,也明白了服务器环境和本地开发环境的差异。
最后,这次实践也让我意识到了后端部署优化的重要性。基础的后台启动方式虽然简单,但无法满足生产环境的需求,而 Systemd 和 Docker 的实践,让我了解了进程管理、容器化部署这些进阶方案,也为后续学习微服务、DevOps 打下了基础。
总的来说,这次部署实践不仅让我掌握了 Spring Boot 项目从开发到上线的完整流程,更让我明白,后端开发不仅仅是写代码,项目的部署、运维、优化同样是不可或缺的环节。后续我还会继续学习 Nginx 反向代理、负载均衡、日志收集等知识,进一步提升自己的全流程开发能力。
openEuler 是由开放原子开源基金会孵化的全场景开源操作系统项目,面向数字基础设施四大核心场景(服务器、云计算、边缘计算、嵌入式),全面支持 ARM、x86、RISC-V、loongArch、PowerPC、SW-64 等多样性计算架构
更多推荐



所有评论(0)