📚 实战篇 01. 达人探店 - 发布探店笔记学习文档
一、 业务场景介绍
“达人探店”的核心玩法是:用户去某家商户消费后,可以发布包含图片和文字的“探店笔记”(类似于发朋友圈或小红书)。其他用户可以查看这些笔记,并进行点赞、评论等互动。
在“发布探店笔记”这个首要环节中,主要包含两个核心动作:
- 上传图片: 用户在前端选择图片并上传,后端需要将图片保存起来,并返回图片的访问链接。
- 发布笔记: 用户填写标题、正文,关联商户,连同刚才的图片链接一起提交给后端,后端将其存入数据库。
二、 核心业务流程拆解
1. 图片上传接口 (uploadImage)
-
接收请求: 前端会将图片以表单数据(
MultipartFile)的形式发送给后端。 -
保存图片: * 在真实的生产环境中,通常会使用第三方对象存储服务(如 阿里云 OSS、七牛云 等)。
- 在我们的实战学习中,为了方便,通常会将图片保存在 Nginx 服务器的指定静态资源目录下(例如
/nginx-1.18.0/html/hmdp/imgs/)。
- 在我们的实战学习中,为了方便,通常会将图片保存在 Nginx 服务器的指定静态资源目录下(例如
-
返回路径: 图片保存成功后,后端需要生成一个该图片的相对或绝对访问路径,封装在
Result中返回给前端,前端拿到路径后用于数据回显和后续的笔记提交。
2. 发布笔记接口 (saveBlog)
- 接收请求: 前端将组装好的笔记数据(
Blog对象,包含title,images,content,shopId等)发送给后端。 - 补充用户信息: 前端传过来的数据中往往不包含“是谁发的”。我们需要在后端通过拦截器保存的
ThreadLocal来获取当前登录用户的 ID。 - 保存入库: 将补全了用户 ID 的
Blog对象调用 MyBatisPlus 的save()方法存入tb_blog数据库表中。 - 返回结果: 返回生成的笔记 ID 给前端,代表发布成功。
三、 Java 后端代码实现思路
1. 图片上传核心代码逻辑
图片上传的难点在于生成唯一的文件名(防止图片重名被覆盖)以及目录的管理。
Java
@PostMapping("blog/upload")
public Result uploadImage(@RequestParam("file") MultipartFile image) {
try {
// 1. 获取原始文件名
String originalFilename = image.getOriginalFilename();
// 2. 生成唯一的新文件名 (可以使用 UUID,并拼接上原始文件后缀)
String suffix = StrUtil.subAfter(originalFilename, ".", true);
String name = UUID.randomUUID().toString(true) + "." + suffix;
// 3. 将文件保存到 Nginx 的静态资源目录
// 注意:这里的 SystemConstants.IMAGE_UPLOAD_DIR 需要配置为你本地的 nginx 对应目录
File dest = new File(SystemConstants.IMAGE_UPLOAD_DIR, name);
image.transferTo(dest);
// 4. 返回图片的访问相对路径
return Result.ok(name);
} catch (IOException e) {
log.error("图片上传失败", e);
return Result.fail("图片上传失败");
}
}
2. 保存笔记核心代码逻辑
这段逻辑非常纯粹,就是标准的单表插入操作,但一定要记得关联当前用户。
Java
@PostMapping("blog")
public Result saveBlog(@RequestBody Blog blog) {
// 1. 获取当前登录用户
// UserHolder 是我们之前封装的基于 ThreadLocal 的工具类
Long userId = UserHolder.getUser().getId();
// 2. 设置探店笔记的作者 ID
blog.setUserId(userId);
// 3. 保存探店笔记到数据库 (MyBatisPlus 提供的 save 方法)
boolean isSuccess = blogService.save(blog);
if(!isSuccess){
return Result.fail("发布笔记失败!");
}
// 4. 返回笔记的 ID
return Result.ok(blog.getId());
}
四、 学习总结与防坑指南
- 温故知新: 在
saveBlog方法中,我们再次使用了UserHolder.getUser().getId()。这证明了我们之前设计的基于拦截器和 ThreadLocal 的用户鉴权机制是非常通用且强大的,在任何业务接口中都能随时无缝获取当前用户信息。 - Nginx 目录配置: 在做图片上传测试时,最容易踩的坑就是图片上传成功了,但前端页面刷不出来。这通常是因为 Nginx 的目录配置不对,或者上传的文件路径与 Nginx 的代理规则不匹配。一定要确保 Java 代码中写入的目录与 Nginx
nginx.conf中配置的静态资源拦截目录保持一致。