package com.fdkankan.fusion.service.impl;
import cn.hutool.core.io.FileUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.fdkankan.fusion.common.ResultCode;
import com.fdkankan.fusion.common.FilePath;
import com.fdkankan.fusion.common.util.RedisKeyUtil;
import com.fdkankan.fusion.common.util.UploadToOssUtil;
import com.fdkankan.fusion.common.util.VideoUtil;
import com.fdkankan.fusion.entity.CaseEntity;
import com.fdkankan.fusion.entity.CaseVideoFolder;
import com.fdkankan.fusion.exception.BusinessException;
import com.fdkankan.fusion.entity.CaseVideo;
import com.fdkankan.fusion.mapper.ICaseVideoMapper;
import com.fdkankan.fusion.service.ICaseService;
import com.fdkankan.fusion.service.ICaseVideoFolderService;
import com.fdkankan.fusion.service.ICaseVideoService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.fdkankan.redis.util.RedisUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service;
import org.springframework.web.multipart.MultipartFile;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.concurrent.ThreadPoolExecutor;
/**
*
* 服务实现类
*
*
* @author
* @since 2022-07-29
*/
@Slf4j
@Service
public class CaseVideoServiceImpl extends ServiceImpl implements ICaseVideoService {
@Autowired
UploadToOssUtil uploadToOssUtil;
@Autowired
ICaseVideoFolderService videoFolderService;
@Autowired
ICaseService caseService;
@Autowired
UploadService uploadService;
@Value("${upload.query-path}")
private String queryPath;
@Value("${spring.profiles.active}")
private String environment;
@Autowired
RedisUtil redisUtil;
@Override
public List getAllList(Integer folderId) {
if(folderId == null){
throw new BusinessException(ResultCode.MISSING_REQUIRED_PARAMETERS);
}
QueryWrapper wrapper = new QueryWrapper<>();
wrapper.lambda().eq(CaseVideo::getFolderId,folderId);
wrapper.lambda().orderByAsc(CaseVideo::getSort);
wrapper.lambda().orderByAsc(CaseVideo::getCreateTime);
return this.list(wrapper);
}
@Override
public CaseVideoFolder uploadAddVideo(MultipartFile[] files, Integer folderId,Integer caseId) throws IOException {
if(files.length <=0 || caseId == null){
throw new BusinessException(ResultCode.MISSING_REQUIRED_PARAMETERS);
}
CaseEntity caseEntity = caseService.getById(caseId);
if(caseEntity == null){
throw new BusinessException(ResultCode.CASE_NOT_EXIST);
}
CaseVideoFolder videoFolder = videoFolderService.getByIdIfNotNew(folderId,caseId);
if(videoFolder == null){
throw new BusinessException(ResultCode.FOLDER_NOT_EXIST);
}
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "0");
//替换文件夹中文件
List videoList = new ArrayList<>();
Integer sort = 1;
LinkedHashSet filePathSet = new LinkedHashSet<>();
for (MultipartFile file : files) {
String localPath = uploadService.uploadFile(file, videoFolder.getVideoFolderId());
if(StringUtils.isEmpty(localPath)){
throw new BusinessException(ResultCode.UPLOAD_ERROR);
}
filePathSet.add(localPath);
CaseVideo caseVideo = new CaseVideo();
caseVideo.setFolderId(videoFolder.getVideoFolderId());
caseVideo.setVideoPath(localPath);
caseVideo.setVideoName(file.getName());
caseVideo.setSort(sort);
videoList.add(caseVideo);
sort++;
}
if (videoList.size() <= 0) {
return videoFolder;
}
this.saveBatch(videoList);
runThread(filePathSet,videoFolder,this);
return videoFolder;
}
public void runThread(LinkedHashSet filePathSet,CaseVideoFolder videoFolder,ICaseVideoService caseVideoService){
new Thread(new Runnable() {
@Override
public void run() {
LinkedHashSet filePathSetAll = new LinkedHashSet<>();
LinkedHashSet ossDelList = new LinkedHashSet<>();
String mergeLocalPath = null;
String mergeLocalPathImg = null;
try {
String mergeVideoUrl = null;
if (StringUtils.isNotBlank(videoFolder.getVideoMergeUrl())) {
mergeVideoUrl = videoFolder.getVideoMergeUrl().replace(queryPath, "/home/");
uploadToOssUtil.downFormAli(videoFolder.getVideoMergeUrl().replace(queryPath, ""), mergeVideoUrl);
ossDelList.add(videoFolder.getVideoMergeUrl());
}
caseVideoService.deleteByFolderId(videoFolder.getVideoFolderId());
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "10");
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "20");
if (StringUtils.isNotBlank(mergeVideoUrl)) {
filePathSetAll.add(mergeVideoUrl);
}
filePathSetAll.addAll(filePathSet);
Boolean newCover = true;
if(StringUtils.isNotBlank(videoFolder.getVideoFolderCover()) && uploadToOssUtil.existKey(videoFolder.getVideoFolderCover().replace(queryPath,""))){
newCover = false;
}
String mergeLocalName = VideoUtil.mergeVideo(filePathSetAll, String.format(FilePath.VIDEO_LOCAL_PATH,environment),newCover);
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "30");
if (mergeLocalName == null) {
updateCaseVideoStatus(videoFolder.getVideoFolderId(), -1);
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "-1");
return;
}
mergeLocalPath = String.format(FilePath.VIDEO_LOCAL_PATH,environment) + "/" + mergeLocalName;
String ossKey = String.format(FilePath.VIDEO_OSS_PATH,environment, videoFolder.getVideoFolderId()) + "/" + mergeLocalName;
uploadToOssUtil.uploadOss(mergeLocalPath, ossKey);
if (!uploadToOssUtil.existKey(ossKey)) {
updateCaseVideoStatus(videoFolder.getVideoFolderId(), -1);
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "-1");
return;
}
if(newCover){
mergeLocalPathImg = String.format(FilePath.VIDEO_LOCAL_PATH,environment) + "/" + mergeLocalName.replace(".mp4", ".jpg");
String ossKeyImg = String.format(FilePath.VIDEO_OSS_PATH, environment,videoFolder.getVideoFolderId()) + "/" + mergeLocalName.replace(".mp4", ".jpg");
uploadToOssUtil.uploadOss(mergeLocalPathImg, ossKeyImg);
if (!uploadToOssUtil.existKey(ossKeyImg)) {
updateCaseVideoStatus(videoFolder.getVideoFolderId(), -1);
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "-1");
return;
}
videoFolder.setVideoFolderCover(queryPath + ossKeyImg);
}
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "70");
videoFolder.setVideoMergeUrl(queryPath + ossKey);
videoFolderService.updateById(videoFolder);
updateCaseVideoStatus(videoFolder.getVideoFolderId(), 1);
//删除oss原资源
for (String path : ossDelList) {
uploadService.deleteOssUrl(path);
}
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "100");
}catch (Exception e){
updateCaseVideoStatus(videoFolder.getVideoFolderId(), -1);
redisUtil.set(RedisKeyUtil.mergerVideoKey + videoFolder.getVideoFolderId(), "-1");
log.info("合并视频出错:",e);
}finally {
for (String path : filePathSetAll) {
FileUtil.del(path);
}
FileUtil.del(mergeLocalPath);
FileUtil.del(mergeLocalPathImg);
}
}
}).start();
}
private void updateCaseVideoStatus(Integer folderId, Integer status) {
LambdaUpdateWrapper wrapper = new LambdaUpdateWrapper<>();
wrapper.in(CaseVideo::getFolderId,folderId)
.set(CaseVideo::getUploadStatus,status);
this.update(wrapper);
LambdaUpdateWrapper wrapperFolder = new LambdaUpdateWrapper<>();
wrapperFolder.eq(CaseVideoFolder::getVideoFolderId,folderId)
.set(CaseVideoFolder::getUploadStatus,status);
videoFolderService.update(wrapperFolder);
}
@Override
public String uploadAddVideoProgress(Integer folderId) {
String redisKey = RedisKeyUtil.mergerVideoKey+folderId;
if(redisUtil.hasKey(redisKey)){
return redisUtil.get(redisKey);
}
return "0";
}
@Override
public void deleteByFolderId(Integer videoFolderId) {
LambdaQueryWrapper wrapper = new LambdaQueryWrapper<>();
wrapper.eq(CaseVideo::getFolderId,videoFolderId);
List list = this.list(wrapper);
if(list.size() <=0){
return;
}
for (CaseVideo caseVideo : list) {
this.delete(caseVideo.getVideoId());
}
}
@Override
public void delete(Integer videoId) {
CaseVideo caseVideo = this.getById(videoId);
this.removeById(videoId);
uploadService.deleteOssUrl(caseVideo.getVideoPath());
uploadService.deleteOssUrl(caseVideo.getVideoCover());
}
}