fix: uploadOnLineResource支持任何网络资源URL,并修复登录状态过期问题
This commit is contained in:
parent
6a8583d634
commit
94c71b10e4
|
|
@ -97,17 +97,25 @@ public class LoginHelper {
|
|||
* @return 登录用户信息,未登录时返回null
|
||||
*/
|
||||
public static LoginUser getLoginUserSafely() {
|
||||
if (!StpUtil.isLogin()) {
|
||||
try {
|
||||
if (!StpUtil.isLogin()) {
|
||||
return null;
|
||||
}
|
||||
LoginUser loginUser = (LoginUser)SaHolder.getStorage().get(CacheConstants.LOGIN_USER_KEY);
|
||||
if (null != loginUser) {
|
||||
return loginUser;
|
||||
}
|
||||
SaSession tokenSession = StpUtil.getTokenSession();
|
||||
loginUser = (LoginUser)tokenSession.get(CacheConstants.LOGIN_USER_KEY);
|
||||
SaHolder.getStorage().set(CacheConstants.LOGIN_USER_KEY, loginUser);
|
||||
return loginUser;
|
||||
} catch (NotLoginException e) {
|
||||
// 捕获未登录异常,返回null
|
||||
return null;
|
||||
} catch (Exception e) {
|
||||
// 捕获其他异常,返回null
|
||||
return null;
|
||||
}
|
||||
LoginUser loginUser = (LoginUser)SaHolder.getStorage().get(CacheConstants.LOGIN_USER_KEY);
|
||||
if (null != loginUser) {
|
||||
return loginUser;
|
||||
}
|
||||
SaSession tokenSession = StpUtil.getTokenSession();
|
||||
loginUser = (LoginUser)tokenSession.get(CacheConstants.LOGIN_USER_KEY);
|
||||
SaHolder.getStorage().set(CacheConstants.LOGIN_USER_KEY, loginUser);
|
||||
return loginUser;
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
|||
|
|
@ -5,12 +5,13 @@ import cn.hutool.core.date.DateUtil;
|
|||
import cn.hutool.core.util.ClassUtil;
|
||||
import cn.hutool.core.util.EscapeUtil;
|
||||
import cn.hutool.core.util.StrUtil;
|
||||
import lombok.RequiredArgsConstructor;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.dromara.x.file.storage.core.FileInfo;
|
||||
import org.dromara.x.file.storage.core.recorder.FileRecorder;
|
||||
import org.dromara.x.file.storage.core.upload.FilePartInfo;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
import top.continew.admin.common.model.dto.LoginUser;
|
||||
import top.continew.admin.common.util.helper.LoginHelper;
|
||||
import top.continew.admin.system.enums.FileTypeEnum;
|
||||
import top.continew.admin.system.mapper.FileMapper;
|
||||
|
|
@ -31,12 +32,16 @@ import java.util.Optional;
|
|||
*/
|
||||
@Slf4j
|
||||
@Component
|
||||
@RequiredArgsConstructor
|
||||
public class FileRecorderImpl implements FileRecorder {
|
||||
|
||||
private final FileMapper fileMapper;
|
||||
private final StorageMapper storageMapper;
|
||||
private final UserService userService;
|
||||
@Autowired
|
||||
private FileMapper fileMapper;
|
||||
|
||||
@Autowired
|
||||
private StorageMapper storageMapper;
|
||||
|
||||
@Autowired
|
||||
private UserService userService;
|
||||
|
||||
@Override
|
||||
public boolean save(FileInfo fileInfo) {
|
||||
|
|
@ -53,16 +58,37 @@ public class FileRecorderImpl implements FileRecorder {
|
|||
file.setThumbnailSize(fileInfo.getThSize());
|
||||
StorageDO storage = (StorageDO)fileInfo.getAttr().get(ClassUtil.getClassName(StorageDO.class, false));
|
||||
file.setStorageId(storage.getId());
|
||||
if (LoginHelper.getLoginUserSafely() == null) {
|
||||
UserDO user = userService.getById(StpUtil.getLoginIdAsLong());
|
||||
file.setDeptId(user.getDeptId());
|
||||
|
||||
// 安全获取登录用户信息
|
||||
Long userId = 0L; // 默认用户ID
|
||||
Long deptId = 0L; // 默认部门ID
|
||||
|
||||
LoginUser loginUser = LoginHelper.getLoginUserSafely();
|
||||
if (loginUser != null) {
|
||||
userId = loginUser.getId();
|
||||
deptId = loginUser.getDeptId();
|
||||
} else {
|
||||
file.setDeptId(LoginHelper.getLoginUserSafely().getDeptId());
|
||||
// 尝试通过StpUtil获取登录ID,同时捕获可能的异常
|
||||
try {
|
||||
// 检查是否登录
|
||||
if (StpUtil.isLogin()) {
|
||||
userId = StpUtil.getLoginIdAsLong();
|
||||
// 获取用户部门信息
|
||||
UserDO user = userService.getById(userId);
|
||||
if (user != null) {
|
||||
deptId = user.getDeptId();
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
// 捕获所有异常,使用默认值
|
||||
log.debug("获取登录用户信息失败: {}", e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
file.setCreateUser(StpUtil.getLoginIdAsLong());
|
||||
file.setDeptId(deptId);
|
||||
file.setCreateUser(userId);
|
||||
file.setCreateTime(DateUtil.toLocalDateTime(fileInfo.getCreateTime()));
|
||||
file.setUpdateUser(StpUtil.getLoginIdAsLong());
|
||||
file.setUpdateUser(userId);
|
||||
file.setUpdateTime(file.getCreateTime());
|
||||
fileMapper.insert(file);
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -0,0 +1,15 @@
|
|||
package top.continew.admin.system.model.req;
|
||||
|
||||
import jakarta.validation.constraints.NotEmpty;
|
||||
import lombok.Data;
|
||||
|
||||
import java.io.Serializable;
|
||||
|
||||
@Data
|
||||
public class uploadOnlineResourceReq implements Serializable {
|
||||
|
||||
private static final long serialVersionUID = 1L;
|
||||
|
||||
@NotEmpty(message = "文件URL不能为空")
|
||||
private String url;
|
||||
}
|
||||
|
|
@ -74,4 +74,6 @@ public interface FileService extends BaseService<FileResp, FileResp, FileQuery,
|
|||
*/
|
||||
PageResp<FileResp> getFilesPage(FileQuery query, PageQuery pageQuery);
|
||||
|
||||
FileInfo uploadOnLineResource(String url);
|
||||
|
||||
}
|
||||
|
|
|
|||
|
|
@ -38,6 +38,10 @@ import top.continew.starter.extension.crud.model.query.PageQuery;
|
|||
import top.continew.starter.extension.crud.model.resp.PageResp;
|
||||
import top.continew.starter.extension.crud.service.impl.BaseServiceImpl;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileNotFoundException;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.time.LocalDate;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
|
@ -201,6 +205,108 @@ public class FileServiceImpl extends BaseServiceImpl<FileMapper, FileDO, FileRes
|
|||
return PageResp.build(page);
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileInfo uploadOnLineResource(String url) {
|
||||
StorageDO storage = storageService.getDefaultStorage();
|
||||
CheckUtils.throwIfNull(storage, "请先指定默认存储");
|
||||
|
||||
// 先检查URL是否有效
|
||||
if (StrUtil.isBlank(url)) {
|
||||
throw new IllegalArgumentException("URL不能为空");
|
||||
}
|
||||
|
||||
// 使用通用HTTP客户端下载任何网络资源到字节数组
|
||||
byte[] bytes;
|
||||
try {
|
||||
java.net.URL resourceUrl = new java.net.URL(url);
|
||||
java.net.HttpURLConnection connection = (java.net.HttpURLConnection)resourceUrl.openConnection();
|
||||
connection.setRequestMethod("GET");
|
||||
connection.setConnectTimeout(5000);
|
||||
connection.setReadTimeout(10000);
|
||||
|
||||
int responseCode = connection.getResponseCode();
|
||||
if (responseCode != 200) {
|
||||
throw new RuntimeException("下载资源失败,HTTP状态码: " + responseCode + ",URL: " + url);
|
||||
}
|
||||
|
||||
try (java.io.InputStream inputStream = connection.getInputStream()) {
|
||||
bytes = inputStream.readAllBytes();
|
||||
}
|
||||
|
||||
connection.disconnect();
|
||||
} catch (Exception e) {
|
||||
throw new RuntimeException("下载资源时发生错误: " + e.getMessage(), e);
|
||||
}
|
||||
|
||||
if (bytes == null || bytes.length == 0) {
|
||||
throw new RuntimeException("下载的文件内容为空: " + url);
|
||||
}
|
||||
|
||||
// 获取文件名和扩展名
|
||||
String filename = URLUtil.decode(FileNameUtil.getName(url));
|
||||
String ext = FileNameUtil.extName(filename);
|
||||
String name = FileNameUtil.mainName(filename);
|
||||
|
||||
LocalDate today = LocalDate.now();
|
||||
String path = today.getYear() + StringConstants.SLASH + today.getMonthValue() + StringConstants.SLASH + today
|
||||
.getDayOfMonth() + StringConstants.SLASH;
|
||||
|
||||
// 创建临时文件
|
||||
File tempFile = null;
|
||||
try {
|
||||
tempFile = File.createTempFile(name, "." + ext);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
try (FileOutputStream fos = new FileOutputStream(tempFile)) {
|
||||
fos.write(bytes);
|
||||
} catch (FileNotFoundException e) {
|
||||
throw new RuntimeException(e);
|
||||
} catch (IOException e) {
|
||||
throw new RuntimeException(e);
|
||||
}
|
||||
|
||||
// 上传到指定存储
|
||||
UploadPretreatment uploadPretreatment = fileStorageService.of(tempFile)
|
||||
.setPlatform(storage.getCode())
|
||||
.putAttr(ClassUtil.getClassName(StorageDO.class, false), storage)
|
||||
.setPath(path);
|
||||
|
||||
// 图片文件生成缩略图
|
||||
if (FileTypeEnum.IMAGE.getExtensions().contains(ext)) {
|
||||
uploadPretreatment.thumbnail(img -> img.size(100, 100));
|
||||
}
|
||||
|
||||
uploadPretreatment.setProgressMonitor(new ProgressListener() {
|
||||
@Override
|
||||
public void start() {
|
||||
log.info("开始上传在线资源: {}", url);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void progress(long progressSize, Long allSize) {
|
||||
if (allSize != null) {
|
||||
log.info("已上传 [{}],总大小 [{}],进度: [{}%]", progressSize, allSize, String
|
||||
.format("%.2f", (double)progressSize / allSize * 100));
|
||||
} else {
|
||||
log.info("已上传 [{}]", progressSize);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void finish() {
|
||||
log.info("上传结束: {}", url);
|
||||
}
|
||||
});
|
||||
|
||||
// 处理本地存储文件 URL
|
||||
FileInfo fileInfo = uploadPretreatment.upload();
|
||||
String domain = StrUtil.appendIfMissing(storage.getDomain(), StringConstants.SLASH);
|
||||
fileInfo.setUrl(URLUtil.normalize(domain + fileInfo.getPath() + fileInfo.getFilename()));
|
||||
|
||||
return fileInfo;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void fill(Object obj) {
|
||||
super.fill(obj);
|
||||
|
|
|
|||
|
|
@ -20,6 +20,7 @@ import top.continew.admin.system.model.query.DeptQuery;
|
|||
import top.continew.admin.system.model.query.MenuQuery;
|
||||
import top.continew.admin.system.model.query.OptionQuery;
|
||||
import top.continew.admin.system.model.query.RoleQuery;
|
||||
import top.continew.admin.system.model.req.uploadOnlineResourceReq;
|
||||
import top.continew.admin.system.model.resp.DeptChildResp;
|
||||
import top.continew.admin.system.model.resp.FileUploadResp;
|
||||
import top.continew.admin.system.service.*;
|
||||
|
|
@ -59,6 +60,13 @@ public class CommonController {
|
|||
return FileUploadResp.builder().url(fileInfo.getUrl()).build();
|
||||
}
|
||||
|
||||
@Operation(summary = "上传文件-将ai生成的网络资源转换成本地资源", description = "上传文件-将ai生成的网络资源转换成本地资源")
|
||||
@PostMapping("/uploadOnLineResource")
|
||||
public FileUploadResp upload(@RequestBody @Validated uploadOnlineResourceReq req) {
|
||||
FileInfo fileInfo = fileService.uploadOnLineResource(req.getUrl());
|
||||
return FileUploadResp.builder().url(fileInfo.getUrl()).build();
|
||||
}
|
||||
|
||||
@Operation(summary = "查询部门树", description = "查询树结构的部门列表")
|
||||
@GetMapping("/tree/dept")
|
||||
public List<Tree<Long>> listDeptTree(DeptQuery query, SortQuery sortQuery) {
|
||||
|
|
|
|||
|
|
@ -227,9 +227,10 @@ justauth:
|
|||
|
||||
--- ### Sa-Token 扩展配置
|
||||
sa-token.extension:
|
||||
# 安全配置:排除(放行)路径配置
|
||||
# 安全获取登录用户信息,如果未登录返回null
|
||||
security.excludes:
|
||||
# 白名单
|
||||
- /common/uploadOnLineResource
|
||||
- /consumptionHistory/add
|
||||
- /taskRecordHistory/add
|
||||
- /consumptionHistory/checkBalance
|
||||
|
|
|
|||
Loading…
Reference in New Issue