
目录
👋前言
小伙伴们大家好,上篇文章本地实践了如何将本地项目部署到服务器上,从服务器的选择、服务器环境搭建、项目上传启动等方面走了一遍流程,基本上没什么问题; 接着上次的项目更新了部分页面功能,之前的文章链接如下:
【服务器项目部署】⭐️将本地项目部署到服务器!_如何把本地项目部署到服务器上-CSDN博客
👀一、功能调整
上次本地 项目只是可以流式输出问题答案,并没有别的页面;所以这次静态资源加了一个注册登录页面,后端对应的提供相关的接口;整体的开发流程就是本地调试,没问题之后把本地环境同步到服务器上,然后打个jar包,放到服务器上运行起来,测试下数据就可以了。
· 先把项目部署到服务器上看下页面效果,再来分析具体的实现(页面可能会比较简陋,只在学校的时候了解过 html,css,js,凑合着看。。。)

🌱二、服务部署
2.1 本地增加了 redis 的使用,所以要在服务器上部署好一个 redis 服务;主要跟之前文章里的步骤一样,把本地安装的 redis 文件上传到服务器上;连接到远程后,找到对应的文件夹,复制粘贴就可以上传了;

上传成功之后,在 redis 当前路径中输入 cmd 快速进入当前文件夹命令页面,使用以下命令启动服务即可,启动后的页面如下,注意下启动占用的端口号,一般都是 6379:
redis-server.exe redis.windows.conf

注:redis 下载安装就不说了,以及如何更改账号密码,以及spriongboot 如何整合,不复杂,大家自行查阅

2.2 新增表,本地创建的一些表也要同步到服务器的数据库中

2.3 打包上传,这里不做赘述了,IDEA中打包好之后上传到服务器,使用 java -jar 命令启动,如下:

2.4 测试下,可以短暂将端口开放出来,方便使用电脑访问;
注册登录页面如下,比较简单,邮箱注册后会收到验证码,在有效期之内使用即可注册成功跳转到登录页面;

登录使用的是注册的邮箱加密码,登录成功之后会跳转到上篇文章的问答页面,在左下角增加了一个个人中心的按钮,从这里可以进行退出操作,为了清除登录产生的 token


另外一个就是调整答案的分段显示,调整前是直接流式按行输出,调整为分段处理之后再显示。时间比较零碎,目前的调整就是这些,主要是在下班后和周末的时候调整,整体速度比较慢

💞️三、代码调整
后端新增的代码不全部沾出来了,只挑以下部分:发送验证码、登录、token创建、接口鉴权
3.1 验证码发送
可以参考之前的文章,链接如下:
基于Springboot框架实现Java发送邮件详解_springboot邮件发送功能 java-CSDN博客
3.2 token 创建
可以参考这篇文章,链接如下:
JWT - 生成token并配置过期时间_jwt设置过期时间-CSDN博客
3.3 登录
比较简单,先根据邮箱查询用户,在对比密码,如果通过了的话就将 userId 放入到生成的 token 中,然后同时将 token 做缓存;
java
@PostMapping("/userLogin")
public Response<LoginResp> login(@RequestBody @Valid LoginReq req){
QueryWrapper<StUser> wrapper = new QueryWrapper<>();
StUser stUser = new StUser();
stUser.setEmail(req.getEmail());
wrapper.setEntity(stUser);
StUser user = stUserMapper.selectOne(wrapper);
if(user != null && user.getPassword().equals(req.getPwd())){
String token = jwtUtil.sign(user.getId());
LoginResp loginResp = new LoginResp();
loginResp.setToken(token);
loginResp.setUserId(user.getId());
loginResp.setUserName(user.getLoginName());
redisUtil.setValueWithExpire(RedisUrlEnum.LOGIN_TOKEN.getKey() + req.getEmail(), token,60*60*24*30L);
return Response.success(loginResp);
}
throw new RuntimeException("error pwd or email");
}
3.4 接口鉴权
登录之后用户会有一个 token, 后续访问部分接口需要先校验请求头中是否包含有效的 token ,后端校验如下:aop 注解 + 切面类
java
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface Valid {
}
java
@Aspect
@Component
public class ValidAspect {
@Resource
private JWTUtil jwtUtil;
@Pointcut("@annotation(org.example.aop.Valid)")
public void validMethod() {}
// 在方法执行前执行 token 校验
@Before("validMethod()")
public void validateToken(JoinPoint joinPoint) throws Exception {
// 获取请求头中的 token
String token = getRequestToken();
if (token == null || token.isEmpty()) {
throw new TokenExpiredException("Token is missing or empty.");
}
// 校验 token 是否过期
if (jwtUtil.getUserIdByToken(token) == null) {
throw new TokenExpiredException("Token has expired.");
}
}
// 获取请求头中的 token
private String getRequestToken() {
// 获取当前请求的 HttpServletRequest 对象
ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
if (attributes != null) {
HttpServletRequest request = attributes.getRequest();
// 从请求头中获取 Authorization 字段
return request.getHeader(HttpHeaders.AUTHORIZATION);
}
return null; // 如果 RequestContextHolder 没有有效的请求上下文,返回 null
}
// 自定义异常类,用于抛出 token 过期的异常
public static class TokenExpiredException extends Exception {
public TokenExpiredException(String message) {
super(message);
}
}
}
3.5 前端保存参数
登录时,后端接口返回的 token 等用户参数,可以放到 localStorage 中,后续有需要鉴权的请求,可以从这里取值然后放到请求头中再进行访问即可

🍻四、章末
简单的小项目,主要是熟悉服务器的部署,以及前后端请求的一些交互 ;后面有时间的话再进行更新,整理下项目结构,推到远程仓库中,可以更方便操作
文章到这里就结束了~
