8.10 删空间id同时删关联图片、修复bug
This commit is contained in:
parent
1a02275023
commit
44e3bd9270
@ -10,48 +10,91 @@ events {
|
||||
http {
|
||||
include /etc/nginx/mime.types;
|
||||
default_type application/octet-stream;
|
||||
sendfile on;
|
||||
sendfile on;
|
||||
keepalive_timeout 65;
|
||||
|
||||
# 访问日志(含握手关键头,用于排查)
|
||||
log_format dbg '$remote_addr "$request" $status '
|
||||
'cliUpg:$http_upgrade cliConn:$http_connection '
|
||||
'upUpg:$upstream_http_upgrade upConn:$upstream_http_connection';
|
||||
access_log /var/log/nginx/access.log dbg;
|
||||
|
||||
# ---- 动态设置 Connection,只有在有 Upgrade 时才 upgrade,否则 close
|
||||
map $http_upgrade $connection_upgrade {
|
||||
default upgrade;
|
||||
'' close;
|
||||
}
|
||||
|
||||
# 上游后端定义
|
||||
upstream picture_backend {
|
||||
server smile-picture-backend:8096;
|
||||
keepalive 32;
|
||||
}
|
||||
|
||||
# -------------------- 80 端口:可选,统一跳转到 HTTPS --------------------
|
||||
server {
|
||||
listen 80;
|
||||
server_name _;
|
||||
server_name picture.bitday.top _;
|
||||
return 301 https://$host$request_uri;
|
||||
}
|
||||
|
||||
root /usr/share/nginx/html;
|
||||
# -------------------- 443 端口:HTTPS + WebSocket 透传 --------------------
|
||||
server {
|
||||
listen 443 ssl http2;
|
||||
server_name picture.bitday.top _;
|
||||
|
||||
# 替换为你的证书路径
|
||||
ssl_certificate /etc/ssl/certs/your.crt;
|
||||
ssl_certificate_key /etc/ssl/private/your.key;
|
||||
|
||||
# (可选)基础 SSL 设置
|
||||
ssl_session_cache shared:SSL:10m;
|
||||
ssl_session_timeout 10m;
|
||||
|
||||
root /usr/share/nginx/html;
|
||||
index index.html;
|
||||
|
||||
# ---------- REST API 代理 ----------
|
||||
location /api/ {
|
||||
proxy_pass http://picture_backend;
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
client_max_body_size 10M; # 允许上传 100MB
|
||||
# 添加代理超时设置(单位:秒)
|
||||
proxy_connect_timeout 600s;
|
||||
proxy_send_timeout 600s;
|
||||
proxy_read_timeout 600s;
|
||||
}
|
||||
|
||||
# ---------- WebSocket 代理 ----------
|
||||
# ---------- WebSocket 代理(放在 /api/ 之前) ----------
|
||||
location /api/ws/ {
|
||||
proxy_pass http://picture_backend;
|
||||
proxy_http_version 1.1;
|
||||
|
||||
# 关键:Upgrade / Connection 透传(动态)
|
||||
proxy_set_header Upgrade $http_upgrade;
|
||||
proxy_set_header Connection "upgrade";
|
||||
proxy_set_header Connection $connection_upgrade;
|
||||
|
||||
# 透传常用头
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
proxy_set_header Origin $http_origin;
|
||||
|
||||
proxy_buffering off;
|
||||
proxy_read_timeout 86400s;
|
||||
proxy_send_timeout 600s;
|
||||
proxy_connect_timeout 600s;
|
||||
|
||||
# (可选)显式禁止缓存
|
||||
add_header Cache-Control "no-store" always;
|
||||
}
|
||||
|
||||
# ---------- 前端路由兼容 ----------
|
||||
# HTML5 history-mode:找不到文件时回退到 index.html 交给前端渲染
|
||||
# ---------- REST API 代理 ----------
|
||||
location /api/ {
|
||||
proxy_pass http://picture_backend;
|
||||
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
|
||||
client_max_body_size 10M; # 允许上传 10MB
|
||||
proxy_connect_timeout 600s;
|
||||
proxy_send_timeout 600s;
|
||||
proxy_read_timeout 600s;
|
||||
}
|
||||
|
||||
# ---------- 前端路由兼容(SPA) ----------
|
||||
location / {
|
||||
try_files $uri $uri/ /index.html;
|
||||
}
|
||||
|
@ -1 +1 @@
|
||||
import{_ as o,c as s,a as t,o as a}from"./index-DXhv3sfF.js";const n={},c={class:"about"};function r(_,e){return a(),s("div",c,e[0]||(e[0]=[t("h1",null,"This is an about page",-1)]))}const l=o(n,[["render",r]]);export{l as default};
|
||||
import{_ as o,c as s,a as t,o as a}from"./index-DM764s2i.js";const n={},c={class:"about"};function r(_,e){return a(),s("div",c,e[0]||(e[0]=[t("h1",null,"This is an about page",-1)]))}const l=o(n,[["render",r]]);export{l as default};
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Binary file not shown.
Before Width: | Height: | Size: 1.1 KiB After Width: | Height: | Size: 101 KiB |
@ -6,8 +6,8 @@
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Smile云图库</title>
|
||||
<meta name="description" content="Smile云图库,海量图片素材免费获取">
|
||||
<script type="module" crossorigin src="/assets/index-DXhv3sfF.js"></script>
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-DVYdPOkg.css">
|
||||
<script type="module" crossorigin src="/assets/index-DM764s2i.js"></script>
|
||||
<link rel="stylesheet" crossorigin href="/assets/index-Bv_ENDgz.css">
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
|
@ -267,8 +267,8 @@ public class PictureController {
|
||||
@GetMapping("/tag_category")
|
||||
public BaseResponse<PictureTagCategory> listPictureTagCategory() {
|
||||
PictureTagCategory pictureTagCategory = new PictureTagCategory();
|
||||
List<String> tagList = Arrays.asList("热门", "搞笑", "生活", "高清", "艺术", "校园", "背景", "简历", "创意");
|
||||
List<String> categoryList = Arrays.asList("模板", "电商", "表情包", "素材", "海报");
|
||||
List<String> tagList = Arrays.asList("热门", "搞笑", "生活", "艺术", "校园", "学习", "简历", "游戏", "动漫");
|
||||
List<String> categoryList = Arrays.asList("模板", "表情包", "素材", "原创","高清");
|
||||
pictureTagCategory.setTagList(tagList);
|
||||
pictureTagCategory.setCategoryList(categoryList);
|
||||
return ResultUtils.success(pictureTagCategory);
|
||||
|
@ -15,6 +15,7 @@ import edu.whut.smilepicturebackend.model.entity.Space;
|
||||
import edu.whut.smilepicturebackend.model.entity.User;
|
||||
import edu.whut.smilepicturebackend.model.enums.SpaceLevelEnum;
|
||||
import edu.whut.smilepicturebackend.model.vo.SpaceVO;
|
||||
import edu.whut.smilepicturebackend.service.PictureService;
|
||||
import edu.whut.smilepicturebackend.service.SpaceService;
|
||||
import edu.whut.smilepicturebackend.service.UserService;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
@ -41,6 +42,8 @@ public class SpaceController {
|
||||
|
||||
private final SpaceUserAuthManager spaceUserAuthManager;
|
||||
|
||||
private final PictureService pictureService;
|
||||
|
||||
@PostMapping("/add")
|
||||
public BaseResponse<Long> addSpace(@RequestBody SpaceAddRequest spaceAddRequest, HttpServletRequest request) {
|
||||
ThrowUtils.throwIf(spaceAddRequest == null, ErrorCode.PARAMS_ERROR);
|
||||
@ -56,15 +59,16 @@ public class SpaceController {
|
||||
throw new BusinessException(ErrorCode.PARAMS_ERROR);
|
||||
}
|
||||
User loginUser = userService.getLoginUser(request);
|
||||
Long id = deleteRequest.getId();
|
||||
Long spaceId = deleteRequest.getId();
|
||||
// 判断是否存在
|
||||
Space oldSpace = spaceService.getById(id);
|
||||
Space oldSpace = spaceService.getById(spaceId);
|
||||
ThrowUtils.throwIf(oldSpace == null, ErrorCode.NOT_FOUND_ERROR);
|
||||
// 仅本人或者管理员可删除
|
||||
spaceService.checkSpaceAuth(loginUser, oldSpace);
|
||||
// 操作数据库
|
||||
boolean result = spaceService.removeById(id);
|
||||
boolean result = spaceService.removeById(spaceId);
|
||||
ThrowUtils.throwIf(!result, ErrorCode.OPERATION_ERROR);
|
||||
pictureService.deleteAllBySpaceIdAsync(spaceId);
|
||||
return ResultUtils.success(true);
|
||||
}
|
||||
|
||||
@ -152,7 +156,7 @@ public class SpaceController {
|
||||
long current = spaceQueryRequest.getCurrent();
|
||||
long size = spaceQueryRequest.getPageSize();
|
||||
// 限制爬虫
|
||||
ThrowUtils.throwIf(size > 20, ErrorCode.PARAMS_ERROR);
|
||||
ThrowUtils.throwIf(size > 30, ErrorCode.PARAMS_ERROR);
|
||||
// 查询数据库
|
||||
Page<Space> spacePage = spaceService.page(new Page<>(current, size),
|
||||
spaceService.getQueryWrapper(spaceQueryRequest));
|
||||
|
@ -151,4 +151,6 @@ public interface PictureService extends IService<Picture> {
|
||||
* @param loginUser
|
||||
*/
|
||||
CreateOutPaintingTaskResponse createPictureOutPaintingTask(CreatePictureOutPaintingTaskRequest createPictureOutPaintingTaskRequest, User loginUser);
|
||||
|
||||
void deleteAllBySpaceIdAsync(Long spaceId);
|
||||
}
|
||||
|
@ -701,9 +701,9 @@ public class PictureServiceImpl extends ServiceImpl<PictureMapper, Picture>
|
||||
// 2. 校验空间权限
|
||||
Space space = spaceService.getById(spaceId);
|
||||
ThrowUtils.throwIf(space == null, ErrorCode.NOT_FOUND_ERROR, "空间不存在");
|
||||
if (!space.getUserId().equals(loginUser.getId())) {
|
||||
throw new BusinessException(ErrorCode.NO_AUTH_ERROR, "没有空间访问权限");
|
||||
}
|
||||
// if (!space.getUserId().equals(loginUser.getId())) {
|
||||
// throw new BusinessException(ErrorCode.NO_AUTH_ERROR, "没有空间访问权限");
|
||||
// }
|
||||
// 3. 查询该空间下的所有图片(必须要有主色调)
|
||||
List<Picture> pictureList = this.lambdaQuery()
|
||||
.eq(Picture::getSpaceId, spaceId)
|
||||
@ -798,6 +798,49 @@ public class PictureServiceImpl extends ServiceImpl<PictureMapper, Picture>
|
||||
return aliYunAiApi.createOutPaintingTask(createOutPaintingTaskRequest);
|
||||
}
|
||||
|
||||
/**
|
||||
* 批量删除该spaceId下的所有图片
|
||||
* @param spaceId
|
||||
*/
|
||||
@Override
|
||||
@Async
|
||||
public void deleteAllBySpaceIdAsync(Long spaceId) {
|
||||
final int pageSize = 500;
|
||||
long current = 1;
|
||||
while (true) {
|
||||
// 只查必要字段,避免大对象占内存
|
||||
Page<Picture> page = this.page(
|
||||
new Page<>(current, pageSize),
|
||||
this.lambdaQuery()
|
||||
.eq(Picture::getSpaceId, spaceId)
|
||||
.select(Picture::getId, Picture::getSpaceId,
|
||||
Picture::getUrl, Picture::getOriginalUrl, Picture::getThumbnailUrl)
|
||||
.getWrapper()
|
||||
);
|
||||
List<Picture> batch = page.getRecords();
|
||||
if (batch.isEmpty()) break;
|
||||
|
||||
// 先删数据库记录
|
||||
List<Long> ids = batch.stream().map(Picture::getId).toList();
|
||||
boolean removed = this.removeBatchByIds(ids);
|
||||
if (!removed) {
|
||||
//不中断主流程,记录日志继续
|
||||
log.warn("removeBatchByIds failed, spaceId={}, ids={}", spaceId, ids);
|
||||
}
|
||||
|
||||
// 再删物理文件(仅当不再被其他记录引用时)
|
||||
for (Picture p : batch) {
|
||||
cosManager.deleteIfNotBlank(p.getUrl());
|
||||
cosManager.deleteIfNotBlank(p.getOriginalUrl());
|
||||
cosManager.deleteIfNotBlank(p.getThumbnailUrl());
|
||||
}
|
||||
|
||||
if (current >= page.getPages()) break;
|
||||
current++;
|
||||
}
|
||||
log.info("deleteAllBySpaceIdAsync finished, spaceId={}", spaceId);
|
||||
}
|
||||
|
||||
/**
|
||||
* nameRule 格式:图片-{序号} =>图片-1 图片-2 ...
|
||||
*
|
||||
|
Loading…
x
Reference in New Issue
Block a user