diff --git a/stdiet-admin/src/main/java/com/stdiet/web/controller/custom/SysNutritionalVideoController.java b/stdiet-admin/src/main/java/com/stdiet/web/controller/custom/SysNutritionalVideoController.java index 404dc8bb3..5a55b905c 100644 --- a/stdiet-admin/src/main/java/com/stdiet/web/controller/custom/SysNutritionalVideoController.java +++ b/stdiet-admin/src/main/java/com/stdiet/web/controller/custom/SysNutritionalVideoController.java @@ -8,6 +8,7 @@ import com.stdiet.common.core.page.TableDataInfo; import com.stdiet.common.utils.AliyunVideoUtils; import com.stdiet.common.utils.StringUtils; import com.stdiet.common.utils.oss.AliyunOSSUtils; +import org.aspectj.weaver.loadtime.Aj; import org.springframework.security.access.prepost.PreAuthorize; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.*; @@ -54,6 +55,8 @@ public class SysNutritionalVideoController extends BaseController SysNutritionalVideo sysNutritionalVideos = sysNutritionalVideoService.selectSysNutritionalVideoById(id); if(sysNutritionalVideos != null && StringUtils.isNotEmpty(sysNutritionalVideos.getCoverUrl())){ sysNutritionalVideos.setPreviewUrl(AliyunOSSUtils.generatePresignedUrl(sysNutritionalVideos.getCoverUrl())); + }else{ + sysNutritionalVideos.setPreviewUrl(AliyunVideoUtils.getVideoCoverUrl(sysNutritionalVideos.getVideoId())); } return AjaxResult.success(sysNutritionalVideos); } @@ -149,4 +152,47 @@ public class SysNutritionalVideoController extends BaseController return AjaxResult.success(sysNutritionalVideos); } + /** + * 根据视频videoId提交视频截图请求 + */ + @PreAuthorize("@ss.hasPermi('custom:nutritionalVideo:add')") + @GetMapping("/submitVideoSnapshot") + public AjaxResult submitVideoSnapshot(@RequestParam("videoId")String videoId) + { + if(StringUtils.isEmpty(videoId)){ + return AjaxResult.error("视频资源不存在"); + } + AjaxResult result = AjaxResult.error("截图请求失败"); + try { + if(AliyunVideoUtils.submitVideoSnapshot(videoId)){ + result = AjaxResult.success(); + } + }catch (Exception e){ + e.printStackTrace(); + } + return result; + } + + /** + * 根据视频videoId获取视频截图 + */ + @PreAuthorize("@ss.hasPermi('custom:nutritionalVideo:add')") + @GetMapping("/getVideoSnapshot") + public AjaxResult getVideoSnapshot(@RequestParam("videoId")String videoId) + { + if(StringUtils.isEmpty(videoId)){ + return AjaxResult.error("视频资源不存在"); + } + AjaxResult result = AjaxResult.error("截图不存在"); + try { + List videoSnapshotList = AliyunVideoUtils.getVideoSnapshot(videoId); + if(videoSnapshotList != null){ + result = AjaxResult.success(videoSnapshotList); + } + }catch (Exception e){ + e.printStackTrace(); + } + return result; + } + } \ No newline at end of file diff --git a/stdiet-common/src/main/java/com/stdiet/common/utils/AliyunVideoUtils.java b/stdiet-common/src/main/java/com/stdiet/common/utils/AliyunVideoUtils.java index 8a4151073..37e174d34 100644 --- a/stdiet-common/src/main/java/com/stdiet/common/utils/AliyunVideoUtils.java +++ b/stdiet-common/src/main/java/com/stdiet/common/utils/AliyunVideoUtils.java @@ -29,6 +29,9 @@ public class AliyunVideoUtils { public static final String search_field = "VideoId,Title,CoverURL,CateName,Tags,Status,Description,CreationTime"; + //默认截图模板 + public static final String defaultSnapshotTemplateId = "f8ccc3b5113ca8ea356ef9adf8c573b2"; + /** * 初始化视频点播Client * @return @@ -176,7 +179,7 @@ public class AliyunVideoUtils { * @return * @throws Exception */ - public static String updateVideo(String videoId, String title, String tags, String description, Long cateId) throws Exception{ + public static String updateVideo(String videoId, String title, String tags, String description, Long cateId, String coverUrl) throws Exception{ com.aliyun.vod20170321.Client client = AliyunVideoUtils.createClient(); if(StringUtils.isEmpty(videoId)){ return null; @@ -194,6 +197,30 @@ public class AliyunVideoUtils { if(cateId != null && cateId.longValue() > 0){ updateVideoInfoRequest.setCateId(cateId); } + if(StringUtils.isNotEmpty(coverUrl)){ + updateVideoInfoRequest.setCoverURL(coverUrl); + } + UpdateVideoInfoResponse updateVideoInfoResponse = client.updateVideoInfo(updateVideoInfoRequest); + if(updateVideoInfoResponse != null){ + return updateVideoInfoResponse.body.requestId; + } + return null; + } + + /** + * 更新视频封面 + * @param videoId 视频ID必须 + * @param coverUrl 封面 + * @return + * @throws Exception + */ + public static String updateVideoCoverUrl(String videoId, String coverUrl) throws Exception{ + com.aliyun.vod20170321.Client client = AliyunVideoUtils.createClient(); + if(StringUtils.isEmpty(videoId) || StringUtils.isEmpty(coverUrl)){ + return null; + } + UpdateVideoInfoRequest updateVideoInfoRequest = new UpdateVideoInfoRequest().setVideoId(videoId); + updateVideoInfoRequest.setCoverURL(coverUrl); UpdateVideoInfoResponse updateVideoInfoResponse = client.updateVideoInfo(updateVideoInfoRequest); if(updateVideoInfoResponse != null){ return updateVideoInfoResponse.body.requestId; @@ -208,7 +235,7 @@ public class AliyunVideoUtils { * @throws Exception */ public static String delVideo(String videoId) throws Exception{ - return updateVideo(videoId, null,null,null, default_delete_cateId); + return updateVideo(videoId, null,null,null, default_delete_cateId, null); } /** @@ -261,10 +288,52 @@ public class AliyunVideoUtils { return coverUrl; } + /** + * 根据VideoId提交截图请求 + * @param videoId + * @return + */ + public static boolean submitVideoSnapshot(String videoId){ + try{ + com.aliyun.vod20170321.Client client = AliyunVideoUtils.createClient(); + SubmitSnapshotJobRequest submitSnapshotJobRequest = new SubmitSnapshotJobRequest() + .setSnapshotTemplateId(defaultSnapshotTemplateId) + .setVideoId(videoId); + SubmitSnapshotJobResponse response = client.submitSnapshotJob(submitSnapshotJobRequest); + return response != null && response.body != null && response.body.snapshotJob != null; + }catch (Exception e){ + e.printStackTrace(); + } + return false; + } - - + /** + * 根据VideoId获取普通截图信息 + * @param videoId + * @return + */ + public static List getVideoSnapshot(String videoId){ + List snapshotList = new ArrayList<>(); + try{ + com.aliyun.vod20170321.Client client = AliyunVideoUtils.createClient(); + ListSnapshotsRequest listSnapshotsRequest = new ListSnapshotsRequest() + .setVideoId(videoId) + .setSnapshotType("NormalSnapshot"); + ListSnapshotsResponse response = client.listSnapshots(listSnapshotsRequest); + if(response != null && response.body != null){ + List listSnapshots = response.body.mediaSnapshot.snapshots.snapshot; + if(listSnapshots != null && listSnapshots.size() > 0){ + for (ListSnapshotsResponseBody.ListSnapshotsResponseBodyMediaSnapshotSnapshotsSnapshot snapshot : listSnapshots) { + snapshotList.add(snapshot.url); + } + } + } + }catch (Exception e){ + e.printStackTrace(); + } + return snapshotList; + } } diff --git a/stdiet-custom/src/main/java/com/stdiet/custom/service/impl/SysNutritionalVideoServiceImpl.java b/stdiet-custom/src/main/java/com/stdiet/custom/service/impl/SysNutritionalVideoServiceImpl.java index 3fa709ac8..237f05cde 100644 --- a/stdiet-custom/src/main/java/com/stdiet/custom/service/impl/SysNutritionalVideoServiceImpl.java +++ b/stdiet-custom/src/main/java/com/stdiet/custom/service/impl/SysNutritionalVideoServiceImpl.java @@ -106,6 +106,17 @@ public class SysNutritionalVideoServiceImpl implements ISysNutritionalVideoServi public int insertSysNutritionalVideo(SysNutritionalVideo sysNutritionalVideo) { sysNutritionalVideo.setCreateTime(DateUtils.getNowDate()); + //判断封面是上传的还是阿里云视频截图封面 + if(isSnapshot(sysNutritionalVideo.getCoverUrl())){ + //更新阿里云视频封面 + try{ + AliyunVideoUtils.updateVideoCoverUrl(sysNutritionalVideo.getVideoId(), sysNutritionalVideo.getCoverUrl()); + }catch (Exception e){ + e.printStackTrace(); + return 0; + } + sysNutritionalVideo.setCoverUrl(""); + } return sysNutritionalVideoMapper.insertSysNutritionalVideo(sysNutritionalVideo); } @@ -119,19 +130,23 @@ public class SysNutritionalVideoServiceImpl implements ISysNutritionalVideoServi public int updateSysNutritionalVideo(SysNutritionalVideo sysNutritionalVideo) { sysNutritionalVideo.setUpdateTime(DateUtils.getNowDate()); + sysNutritionalVideo.setCoverUrl(sysNutritionalVideo.getCoverUrl() == null ? "" : sysNutritionalVideo.getCoverUrl()); + String coverUrl = sysNutritionalVideo.getCoverUrl(); + //判断封面是上传的还是阿里云视频截图封面 + sysNutritionalVideo.setCoverUrl(isSnapshot(coverUrl) ? "" : coverUrl); int row = sysNutritionalVideoMapper.updateSysNutritionalVideo(sysNutritionalVideo); if(row > 0){ - updateAliyunVideo(sysNutritionalVideo.getId()); + sysNutritionalVideo.setCoverUrl(isSnapshot(coverUrl) ? coverUrl : null); + updateAliyunVideo(sysNutritionalVideo); } return row; } @Async - public void updateAliyunVideo(Long id){ + public void updateAliyunVideo(SysNutritionalVideo sysNutritionalVideo){ try{ - SysNutritionalVideo sysNutritionalVideo = selectSysNutritionalVideoById(id); if(sysNutritionalVideo != null && sysNutritionalVideo.getVideoId() != null){ - AliyunVideoUtils.updateVideo(sysNutritionalVideo.getVideoId(), sysNutritionalVideo.getTitle(), sysNutritionalVideo.getTags(), sysNutritionalVideo.getDescription(), null); + AliyunVideoUtils.updateVideo(sysNutritionalVideo.getVideoId(), sysNutritionalVideo.getTitle(), sysNutritionalVideo.getTags(), sysNutritionalVideo.getDescription(), null, sysNutritionalVideo.getCoverUrl()); } }catch (Exception e){ e.printStackTrace(); @@ -270,4 +285,15 @@ public class SysNutritionalVideoServiceImpl implements ISysNutritionalVideoServi return sysNutritionalVideoMapper.updateVideoPlayNum(videoId); } + /** + * 判断是否为阿里点播的截图 + * @param url + * @return + */ + private boolean isSnapshot(String url){ + return StringUtils.isNotEmpty(url) && url.startsWith("http://outin"); + } + + + } \ No newline at end of file diff --git a/stdiet-ui/src/api/custom/nutritionalVideo.js b/stdiet-ui/src/api/custom/nutritionalVideo.js index 649406caa..d4c88087f 100644 --- a/stdiet-ui/src/api/custom/nutritionalVideo.js +++ b/stdiet-ui/src/api/custom/nutritionalVideo.js @@ -78,3 +78,23 @@ export function getVideoPlayUrlById(id) { }) } +// 根据视频videoId提交视频截图请求 +export function submitVideoSnapshot(id) { + return request({ + url: '/custom/nutritionalVideo/submitVideoSnapshot', + method: 'get', + params: {'videoId': id} + }) +} + +//根据视频videoId获取视频截图 +export function getVideoSnapshot(id) { + return request({ + url: '/custom/nutritionalVideo/getVideoSnapshot', + method: 'get', + params: {'videoId': id} + }) +} + + + diff --git a/stdiet-ui/src/components/FileUpload/UploadFile.vue b/stdiet-ui/src/components/FileUpload/UploadFile.vue index cd1cb78e1..62b4e31b7 100644 --- a/stdiet-ui/src/components/FileUpload/UploadFile.vue +++ b/stdiet-ui/src/components/FileUpload/UploadFile.vue @@ -8,7 +8,7 @@ :accept="'.png,.jpg'" :before-upload="beforeAvatarUpload"> - +
移除 diff --git a/stdiet-ui/src/components/UploadVideo/index.vue b/stdiet-ui/src/components/UploadVideo/index.vue index af0031d96..c8ed8cbfb 100644 --- a/stdiet-ui/src/components/UploadVideo/index.vue +++ b/stdiet-ui/src/components/UploadVideo/index.vue @@ -17,15 +17,11 @@ placeholder="请输入视频描述" v-model.trim="videoFrom.description" maxlength="1000" - rows="3" + rows="2" show-word-limit /> - - - - -
+
-
上传状态:{{statusText}}进度:{{authProgress}}%
- 1、只能上传mp4文件,上传大文件时请使用客户端上传,防止上传超时 + 上传视频1、只能上传mp4格式视频
+
+ + + 选择封面 + + active-text="展示" + inactive-text="不展示"> -
提示:请保证内容正确再展示到小程序
+
提示:开启展示之后客户可看到该视频,请保证内容正确再展示
+ + \ No newline at end of file diff --git a/stdiet-ui/src/views/custom/nutritionalVideo/index.vue b/stdiet-ui/src/views/custom/nutritionalVideo/index.vue index dea7f8b97..fa8e6b55c 100644 --- a/stdiet-ui/src/views/custom/nutritionalVideo/index.vue +++ b/stdiet-ui/src/views/custom/nutritionalVideo/index.vue @@ -9,7 +9,7 @@ size="small" /> - + --> - + @@ -268,6 +282,7 @@ import Treeselect from "@riophae/vue-treeselect"; import "@riophae/vue-treeselect/dist/vue-treeselect.css"; import IconSelect from "@/components/IconSelect"; + import VideoSelectCover from "@/components/VideoSelectCover"; export default { name: "NutritionalVideo", data() { @@ -316,6 +331,8 @@ coverImageList:[], //分类列表 classifyList:[], + //所有分类 + allClassifyList:[], //权限等级列表 payVideoLevelList:[], //视频分类弹窗显示标识 @@ -331,7 +348,7 @@ }); }, components: { - UploadVideo,UploadFile,VideoClassify,AutoHideMessage,Treeselect, IconSelect + UploadVideo,UploadFile,VideoClassify,AutoHideMessage,Treeselect, IconSelect,VideoSelectCover }, methods: { /** 查询营养视频列表 */ @@ -350,6 +367,7 @@ getAllVideoClassify(){ getAllClassify().then(response => { if(response.code == 200){ + this.allClassifyList = response.data; this.classifyList = []; const classify = { id: 0, cateName: '主分类', children: [] }; classify.children = this.handleTree(response.data, "id"); @@ -366,6 +384,7 @@ reset() { this.form = { id: null, + videoId:null, cateId: null, coverUrl: null, title: null, @@ -373,10 +392,18 @@ tags: null, payLevel:null, showFlag: null, - wxShow: false + wxShow: false, + previewUrl: null }; this.resetForm("form"); }, + selectVideoCover(){ + this.$refs.videoSelectCoverRef.showDialog(this.form,(url)=>{ + //console.log(url); + this.form.previewUrl = url; + this.form.coverUrl = url; + }); + }, /** 搜索按钮操作 */ handleQuery() { this.queryParams.pageNum = 1; @@ -394,7 +421,7 @@ this.multiple = !selection.length }, clickUploadVideo(){ - this.$refs.uploadVideoRef.showDialog(this.classifyList, ()=>{ + this.$refs.uploadVideoRef.showDialog(this.allClassifyList, ()=>{ this.getList(); }); }, @@ -443,6 +470,14 @@ this.$refs["form"].validate(valid => { if (valid) { this.form.showFlag = this.form.wxShow ? 1 : 0; + //视频分类不能选择主分类 + if(this.form.cateId == 0){ + this.$message({ + message: "视频分类不能选择主分类", + type: "warning", + }); + return; + } if (this.form.id != null) { updateNutritionalVideo(this.form).then(response => { if (response.code === 200) {