生成视频时发送通知,其他调整

This commit is contained in:
Jerry Yan 2025-01-06 18:44:53 +08:00
parent 9b32c2fd75
commit 00d53dd197
30 changed files with 403 additions and 83 deletions

View File

@ -1,6 +1,8 @@
package com.ycwl.basic.controller.mobile;
import com.ycwl.basic.annotation.IgnoreToken;
import com.ycwl.basic.constant.BaseContextHandler;
import com.ycwl.basic.exception.CheckTokenException;
import com.ycwl.basic.model.jwt.JwtInfo;
import com.ycwl.basic.model.mobile.goods.*;
import com.ycwl.basic.service.mobile.GoodsService;
@ -45,9 +47,14 @@ public class AppGoodsController {
@ApiOperation("成片vlog商品详情")
@GetMapping("/getVideoGoodsDetail/{videoId}")
@IgnoreToken
public ApiResponse<VideoGoodsDetailVO> videoGoodsDetail(@PathVariable("videoId") Long videoId) {
JwtInfo worker = JwtTokenUtil.getWorker();
return goodsService.videoGoodsDetail(worker.getUserId(), videoId);
try {
JwtInfo worker = JwtTokenUtil.getWorker();
return goodsService.videoGoodsDetail(worker.getUserId(), videoId);
} catch (CheckTokenException e) {
return goodsService.videoGoodsDetail(null, videoId);
}
}
@GetMapping("/sourceGoods/{sourceId}")

View File

@ -33,10 +33,10 @@ public class AppMemberController {
* @throws Exception
*/
@ApiOperation("登录")
@PostMapping("/login")
@PostMapping("/{scenicId}/login")
@IgnoreToken
public ApiResponse<?> login(@RequestBody WeChatUserInfoDTO userInfoDTO) throws Exception {
return memberService.login(userInfoDTO.getCode(), userInfoDTO);
public ApiResponse<?> login(@PathVariable("scenicId") Long scenicId ,@RequestBody WeChatUserInfoDTO userInfoDTO) throws Exception {
return memberService.login(scenicId, userInfoDTO.getCode(), userInfoDTO);
}
/**

View File

@ -0,0 +1,9 @@
package com.ycwl.basic.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.ycwl.basic.model.pc.mp.MpConfigEntity;
import org.apache.ibatis.annotations.Mapper;
@Mapper
public interface MpConfigMapper extends BaseMapper<MpConfigEntity> {
}

View File

@ -0,0 +1,12 @@
package com.ycwl.basic.mapper;
import com.baomidou.mybatisplus.core.mapper.BaseMapper;
import com.ycwl.basic.model.pc.mp.MpNotifyConfigEntity;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
@Mapper
public interface MpNotifyConfigMapper extends BaseMapper<MpNotifyConfigEntity> {
List<MpNotifyConfigEntity> listByMpId(Integer mpId);
}

View File

@ -34,6 +34,8 @@ public interface VideoMapper {
List<MemberVideoEntity> userFaceTemplateVideo(Long userId, Long faceId, Long templateId);
MemberVideoEntity queryRelationByMemberTask(Long userId, Long taskId);
List<MemberVideoEntity> listRelationByTask(Long taskId);
List<MemberVideoEntity> listRelationByFace(Long userId, Long faceId);
List<MemberVideoEntity> listRelationByFaceAndTemplate(Long userId, Long faceId, Long templateId);

View File

@ -39,6 +39,8 @@ public class VideoGoodsDetailVO {
private String videoUrl;
@JsonFormat(pattern = "yyyy-MM-dd HH:mm:ss", timezone = "GMT+8")
private Date createTime;
@JsonFormat(pattern = "yyyy-MM-dd", timezone = "GMT+8")
private Date shotTime;
@ApiModelProperty("价格")
private String price;
private String slashPrice;
@ -47,4 +49,5 @@ public class VideoGoodsDetailVO {
@ApiModelProperty("镜头数")
private Integer lensNum;
private Long faceId;
private boolean share = false;
}

View File

@ -15,6 +15,7 @@ import java.util.Date;
public class MemberEntity {
@TableId
private Long id;
private Long scenicId;
/**
* 微信openId
*/

View File

@ -16,6 +16,7 @@ import java.util.Date;
@Data
@ApiModel("查询用户列表请求参数")
public class MemberReqQuery extends BaseQueryParameterReq {
private Long scenicId;
/**
* 微信openId
*/

View File

@ -15,6 +15,7 @@ import java.util.Date;
@ApiModel("查询用户信息响应参数")
public class MemberRespVO {
private Long id;
private Long scenicId;
/**
* 微信openId
*/

View File

@ -0,0 +1,24 @@
package com.ycwl.basic.model.pc.mp;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import java.util.Map;
@TableName("mp_config")
@Data
public class MpConfigEntity {
private Integer id;
private String name;
private String appId;
private String appSecret;
private String state;
public Map<String, String> toMap() {
Map<String, String> map = new java.util.HashMap<>();
map.put("appId", this.getAppId());
map.put("appSecret", this.getAppSecret());
map.put("state", this.getState());
return map;
}
}

View File

@ -0,0 +1,13 @@
package com.ycwl.basic.model.pc.mp;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
@TableName("mp_notify_config")
@Data
public class MpNotifyConfigEntity {
private Integer id;
private Integer mpId;
private String templateId;
private Integer type;
}

View File

@ -0,0 +1,13 @@
package com.ycwl.basic.model.pc.mp;
import lombok.Data;
@Data
public class ScenicMpNotifyVO {
private Long scenicId;
private Integer mpId;
private String appId;
private String appSecret;
private String appState;
private String videoGeneratedTemplateId;
}

View File

@ -22,6 +22,7 @@ public class ScenicEntity {
* 景区名称
*/
private String name;
private Integer mpId;
/**
* 景区介绍
*/

View File

@ -1,22 +1,35 @@
package com.ycwl.basic.repository;
import com.alibaba.fastjson.JSONObject;
import com.ycwl.basic.mapper.MpConfigMapper;
import com.ycwl.basic.mapper.MpNotifyConfigMapper;
import com.ycwl.basic.mapper.ScenicMapper;
import com.ycwl.basic.model.pc.mp.MpConfigEntity;
import com.ycwl.basic.model.pc.mp.MpNotifyConfigEntity;
import com.ycwl.basic.model.pc.mp.ScenicMpNotifyVO;
import com.ycwl.basic.model.pc.scenic.entity.ScenicConfigEntity;
import com.ycwl.basic.model.pc.scenic.entity.ScenicEntity;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.stereotype.Component;
import java.util.List;
@Component
public class ScenicRepository {
@Autowired
private ScenicMapper scenicMapper;
@Autowired
private MpConfigMapper mpConfigMapper;
@Autowired
private RedisTemplate<String, String> redisTemplate;
public static final String SCENIC_CACHE_KEY = "scenic:%s";
public static final String SCENIC_CONFIG_CACHE_KEY = "scenic:%s:config";
public static final String SCENIC_MP_CACHE_KEY = "scenic:%s:mp";
public static final String SCENIC_MP_NOTIFY_CACHE_KEY = "scenic:%s:mpNotify";
@Autowired
private MpNotifyConfigMapper mpNotifyConfigMapper;
public ScenicEntity getScenic(Long id) {
if (redisTemplate.hasKey(String.format(SCENIC_CACHE_KEY, id))) {
@ -40,8 +53,51 @@ public class ScenicRepository {
return scenicConfig;
}
public MpConfigEntity getScenicMpConfig(Long scenicId) {
if (redisTemplate.hasKey(String.format(SCENIC_MP_CACHE_KEY, scenicId))) {
return JSONObject.parseObject(redisTemplate.opsForValue().get(String.format(SCENIC_MP_CACHE_KEY, scenicId)), MpConfigEntity.class);
}
ScenicEntity scenic = getScenic(scenicId);
MpConfigEntity mpConfigEntity = mpConfigMapper.selectById(scenic.getMpId());
if (mpConfigEntity != null) {
redisTemplate.opsForValue().set(String.format(SCENIC_MP_CACHE_KEY, scenicId), JSONObject.toJSONString(mpConfigEntity));
}
return mpConfigEntity;
}
public ScenicMpNotifyVO getScenicMpNotifyConfig(Long scenicId) {
if (redisTemplate.hasKey(String.format(SCENIC_MP_NOTIFY_CACHE_KEY, scenicId))) {
return JSONObject.parseObject(redisTemplate.opsForValue().get(String.format(SCENIC_MP_NOTIFY_CACHE_KEY, scenicId)), ScenicMpNotifyVO.class);
}
MpConfigEntity mpConfig = getScenicMpConfig(scenicId);
ScenicMpNotifyVO mpNotifyConfig = new ScenicMpNotifyVO();
mpNotifyConfig.setAppId(mpConfig.getAppId());
mpNotifyConfig.setAppSecret(mpConfig.getAppSecret());
mpNotifyConfig.setMpId(mpConfig.getId());
mpNotifyConfig.setAppState(mpConfig.getState());
List<MpNotifyConfigEntity> mpNotifyConfigList = mpNotifyConfigMapper.listByMpId(mpConfig.getId());
mpNotifyConfigList.forEach(item -> {
switch (item.getType()) {
case 0:
mpNotifyConfig.setVideoGeneratedTemplateId(item.getTemplateId());
break;
}
});
redisTemplate.opsForValue().set(String.format(SCENIC_MP_NOTIFY_CACHE_KEY, scenicId), JSONObject.toJSONString(mpNotifyConfig));
return mpNotifyConfig;
}
public String getVideoGeneratedTemplateId(Long scenicId) {
ScenicMpNotifyVO scenicMpNotifyConfig = getScenicMpNotifyConfig(scenicId);
if (scenicMpNotifyConfig != null) {
return scenicMpNotifyConfig.getVideoGeneratedTemplateId();
}
return null;
}
public void clearCache(Long scenicId) {
redisTemplate.delete(String.format(SCENIC_CACHE_KEY, scenicId));
redisTemplate.delete(String.format(SCENIC_CONFIG_CACHE_KEY, scenicId));
}
}

View File

@ -16,6 +16,8 @@ import com.ycwl.basic.model.mobile.weChat.DTO.WeChatUserInfoUpdateDTO;
import com.ycwl.basic.model.pc.member.entity.MemberEntity;
import com.ycwl.basic.model.pc.member.req.MemberReqQuery;
import com.ycwl.basic.model.pc.member.resp.MemberRespVO;
import com.ycwl.basic.model.pc.mp.MpConfigEntity;
import com.ycwl.basic.repository.ScenicRepository;
import com.ycwl.basic.service.HttpService;
import com.ycwl.basic.service.mobile.AppMemberService;
import com.ycwl.basic.utils.ApiResponse;
@ -50,13 +52,17 @@ public class AppMemberServiceImpl implements AppMemberService {
@Autowired
private JwtTokenUtil jwtTokenUtil;
@Autowired
private ScenicRepository scenicRepository;
@Override
public Map<String, Object> getOpenId(String code) {
public Map<String, Object> getOpenId(Long scenicId, String code) {
Map<String, String> paramMap = new HashMap<>(NumberConstant.FOUR);
paramMap.put("appid", config.getMiniProgramAppId());
paramMap.put("secret", config.getMiniProgramSecret());
MpConfigEntity scenicMpConfig = scenicRepository.getScenicMpConfig(scenicId);
paramMap.put("appid", scenicMpConfig.getAppId());
paramMap.put("secret", scenicMpConfig.getAppSecret());
paramMap.put("js_code", code);
paramMap.put("grant_type", config.getGrandType());
paramMap.put("grant_type", "authorization_code");
try {
String response = httpService.doHttpsPost(WeiXinConstant.GET_OPEN_ID, paramMap, "UTF-8");
if (StringUtils.isBlank(response)) {
@ -72,8 +78,8 @@ public class AppMemberServiceImpl implements AppMemberService {
@Override
public ApiResponse login(String code, WeChatUserInfoDTO userInfoDTO) throws Exception {
Map<String, Object> weixinResponse = this.getOpenId(code);
public ApiResponse login(Long scenicId, String code, WeChatUserInfoDTO userInfoDTO) throws Exception {
Map<String, Object> weixinResponse = this.getOpenId(scenicId, code);
if (CollectionUtils.isEmpty(weixinResponse)) {
throw new AppException(BizCodeEnum.SERVER_INTERNAL_ERROR);
}
@ -100,6 +106,7 @@ public class AppMemberServiceImpl implements AppMemberService {
MemberEntity memberEntity = new MemberEntity();
BeanCopierUtils.copyProperties(userInfoDTO, memberEntity);
memberEntity.setId(SnowFlakeUtil.getLongId());
memberEntity.setScenicId(scenicId);
memberEntity.setOpenId(openId.toString());
memberMapper.add(memberEntity);
BeanCopierUtils.copyProperties(memberEntity, memberRespVO);

View File

@ -3,11 +3,13 @@ package com.ycwl.basic.service.impl.mobile;
import cn.hutool.core.bean.BeanUtil;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.ycwl.basic.biz.OrderBiz;
import com.ycwl.basic.constant.BaseContextHandler;
import com.ycwl.basic.constant.NumberConstant;
import com.ycwl.basic.mapper.*;
import com.ycwl.basic.model.jwt.JwtInfo;
import com.ycwl.basic.model.mobile.index.TopStateResp;
import com.ycwl.basic.model.mobile.order.IsBuyRespVO;
import com.ycwl.basic.model.mobile.scenic.ScenicAppVO;
import com.ycwl.basic.model.mobile.scenic.ScenicDeviceCountVO;
import com.ycwl.basic.model.mobile.scenic.ScenicIndexVO;
@ -67,6 +69,8 @@ public class AppScenicServiceImpl implements AppScenicService {
private BigDecimal faceScore;
@Autowired
private TemplateRepository templateRepository;
@Autowired
private OrderBiz orderBiz;
@Override
public ApiResponse<PageInfo<ScenicAppVO>> pageQuery(ScenicReqQuery scenicReqQuery) {
@ -125,12 +129,18 @@ public class AppScenicServiceImpl implements AppScenicService {
Integer type = sourceRespVO.getType();
if(type==1){
contentPageVO.setName("原片集");
}else {
} else {
contentPageVO.setName("照片集");
}
IsBuyRespVO isBuyRespVO = orderBiz.isBuy(worker.getUserId(), faceRespVO.getScenicId(), type, faceId);
contentPageVO.setSourceType(isBuyRespVO.getGoodsType());
contentPageVO.setContentId(isBuyRespVO.getGoodsId());
if (isBuyRespVO.isBuy()) {
contentPageVO.setIsBuy(1);
} else {
contentPageVO.setIsBuy(0);
}
contentPageVO.setContentType(2);
contentPageVO.setSourceType(type);
contentPageVO.setIsBuy(sourceRespVO.getIsBuy());
contentList.add(contentPageVO);
});
@ -174,12 +184,18 @@ public class AppScenicServiceImpl implements AppScenicService {
Integer type = sourceRespVO.getType();
if(type==1){
contentPageVO.setName("原片集");
}else {
} else {
contentPageVO.setName("照片集");
}
IsBuyRespVO isBuyRespVO = orderBiz.isBuy(userId, faceRespVO.getScenicId(), type, faceId);
contentPageVO.setSourceType(isBuyRespVO.getGoodsType());
contentPageVO.setContentId(isBuyRespVO.getGoodsId());
if (isBuyRespVO.isBuy()) {
contentPageVO.setIsBuy(1);
} else {
contentPageVO.setIsBuy(0);
}
contentPageVO.setContentType(2);
contentPageVO.setSourceType(type);
contentPageVO.setIsBuy(sourceRespVO.getIsBuy());
contentList.add(contentPageVO);
});

View File

@ -1,6 +1,7 @@
package com.ycwl.basic.service.impl.mobile;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.ycwl.basic.constant.BaseContextHandler;
import com.ycwl.basic.mapper.*;
@ -15,8 +16,11 @@ import com.ycwl.basic.model.pc.video.entity.MemberVideoEntity;
import com.ycwl.basic.model.pc.video.req.VideoReqQuery;
import com.ycwl.basic.model.pc.video.resp.VideoRespVO;
import com.ycwl.basic.repository.VideoTaskRepository;
import com.ycwl.basic.service.impl.pc.TaskServiceImpl;
import com.ycwl.basic.service.impl.task.TaskTaskServiceImpl;
import com.ycwl.basic.service.mobile.GoodsService;
import com.ycwl.basic.repository.TemplateRepository;
import com.ycwl.basic.service.task.TaskService;
import com.ycwl.basic.utils.ApiResponse;
import com.ycwl.basic.utils.DateUtils;
import org.apache.commons.lang3.StringUtils;
@ -27,6 +31,7 @@ import java.math.BigDecimal;
import java.math.RoundingMode;
import java.text.DecimalFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.Optional;
import java.util.stream.Collectors;
@ -42,16 +47,14 @@ public class GoodsServiceImpl implements GoodsService {
private SourceMapper sourceMapper;
@Autowired
private ScenicMapper scenicMapper;
@Autowired
private TaskMapper taskMapper;
@Autowired
private DeviceMapper deviceMapper;
@Autowired
private FaceMapper faceMapper;
@Autowired
private TemplateRepository templateRepository;
@Autowired
private VideoTaskRepository videoTaskRepository;
@Autowired
private TaskService taskTaskService;
public ApiResponse<List<GoodsPageVO>> goodsList(GoodsReqQuery query) {
//查询原素材
@ -194,10 +197,6 @@ public class GoodsServiceImpl implements GoodsService {
@Override
public ApiResponse<VideoGoodsDetailVO> videoGoodsDetail(Long userId, Long videoId) {
MemberVideoEntity entity = videoMapper.queryUserVideo(userId, videoId);
if (entity == null) {
return ApiResponse.fail("该视频不属于您");
}
VideoGoodsDetailVO goodsDetailVO = new VideoGoodsDetailVO();
VideoRespVO videoRespVO = videoMapper.getById(videoId);
if(videoRespVO==null){
@ -211,7 +210,12 @@ public class GoodsServiceImpl implements GoodsService {
goodsDetailVO.setVideoUrl(videoRespVO.getVideoUrl());
goodsDetailVO.setTemplateCoverUrl(videoRespVO.getTemplateCoverUrl());
goodsDetailVO.setCreateTime(videoRespVO.getCreateTime());
if (entity.getIsBuy() == 1) {
MemberVideoEntity entity = videoMapper.queryUserVideo(userId, videoId);
if (entity == null) {
goodsDetailVO.setIsBuy(0);
goodsDetailVO.setShare(true);
goodsDetailVO.setPrice("未登录");
} else if (entity.getIsBuy() == 1) {
goodsDetailVO.setIsBuy(1);
} else {
goodsDetailVO.setIsBuy(0);
@ -222,16 +226,19 @@ public class GoodsServiceImpl implements GoodsService {
goodsDetailVO.setPrice(templatePrice==null?"":df.format(templatePrice.setScale(2, RoundingMode.HALF_UP)));
goodsDetailVO.setSlashPrice(slashPrice==null?null:df.format(slashPrice.setScale(2, RoundingMode.HALF_UP)));
}
TaskRespVO taskRespVO = taskMapper.getById(videoRespVO.getTaskId());
JSONObject paramJson = JSON.parseObject(taskRespVO.getTaskParams());
TaskEntity task = videoTaskRepository.getTaskById(videoRespVO.getTaskId());
JSONObject paramJson = JSON.parseObject(task.getTaskParams());
long deviceCount;
goodsDetailVO.setShotTime(taskTaskService.getTaskShotDate(task.getId()));
if (paramJson == null) {
deviceCount = 1;
} else {
deviceCount = paramJson.keySet().stream().filter(StringUtils::isNumeric).count();
}
goodsDetailVO.setLensNum((int) deviceCount);
goodsDetailVO.setFaceId(entity.getFaceId());
if (entity != null) {
goodsDetailVO.setFaceId(entity.getFaceId());
}
return ApiResponse.success(goodsDetailVO);
}
@ -286,6 +293,7 @@ public class GoodsServiceImpl implements GoodsService {
List<MemberVideoEntity> taskList = videoMapper.listRelationByFaceAndTemplate(userId, faceId, templateId);
VideoTaskStatusVO response = new VideoTaskStatusVO();
response.setFaceId(faceId);
response.setTemplateId(templateId);
if (taskList.isEmpty()) {
response.setStatus(0);
return ApiResponse.success(response);

View File

@ -14,7 +14,6 @@ import com.ycwl.basic.model.mobile.statistic.req.StatisticsRecordAddReq;
import com.ycwl.basic.model.pc.face.entity.FaceEntity;
import com.ycwl.basic.model.pc.face.req.FaceReqQuery;
import com.ycwl.basic.model.pc.face.resp.FaceRespVO;
import com.ycwl.basic.model.pc.faceSample.resp.FaceSampleRespVO;
import com.ycwl.basic.model.pc.source.entity.MemberSourceEntity;
import com.ycwl.basic.model.pc.source.entity.SourceEntity;
import com.ycwl.basic.model.task.resp.SearchFaceRespVo;
@ -56,7 +55,7 @@ public class FaceServiceImpl implements FaceService {
@Value("${face.score}")
private float faceScore;
private float strictScore = 90F;
private final float strictScore = 0.90F;
@Autowired
private TaskService taskTaskService;
@Autowired
@ -181,8 +180,6 @@ public class FaceServiceImpl implements FaceService {
faceEntity.setMemberId(userId);
faceEntity.setFaceUrl(faceUrl);
List<Long> sampleListIds = scenicDbSearchResult.getSampleListIds();
// 匹配原片照片
List<SourceEntity> sourceEntities = sourceMapper.listBySampleIds(sampleListIds);
if (faceEntity.getId()==null) {
//新增人脸
faceEntity.setId(newFaceId);
@ -191,6 +188,11 @@ public class FaceServiceImpl implements FaceService {
//2更新人脸
faceMapper.update(faceEntity);
}
if (sampleListIds == null) {
return ApiResponse.fail("请先游玩后再来获取视频吧");
}
// 匹配原片照片
List<SourceEntity> sourceEntities = sourceMapper.listBySampleIds(sampleListIds);
List<MemberSourceEntity> memberSourceEntityList = sourceEntities.stream().map(sourceEntity -> {
MemberSourceEntity memberSourceEntity = new MemberSourceEntity();
memberSourceEntity.setScenicId(scenicId);
@ -204,7 +206,7 @@ public class FaceServiceImpl implements FaceService {
sourceMapper.addRelations(memberSourceEntityList);
VideoPieceGetter.Task task = new VideoPieceGetter.Task();
task.faceId = faceEntity.getId();
task.faceSampleId = sampleListIds;
task.faceSampleIds = sampleListIds;
task.memberId = userId;
VideoPieceGetter.addTask(task);
taskTaskService.autoCreateTaskByFaceId(faceEntity.getId());

View File

@ -1,13 +1,7 @@
package com.ycwl.basic.service.impl.pc;
import com.aliyuncs.DefaultAcsClient;
import com.aliyuncs.IAcsClient;
import com.aliyuncs.exceptions.ClientException;
import com.aliyuncs.facebody.model.v20191230.CreateFaceDbRequest;
import com.aliyuncs.profile.DefaultProfile;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.ycwl.basic.config.FaceDetectConfig;
import com.ycwl.basic.mapper.ScenicAccountMapper;
import com.ycwl.basic.mapper.ScenicMapper;
import com.ycwl.basic.model.pc.scenic.entity.ScenicAccountEntity;
@ -15,6 +9,7 @@ import com.ycwl.basic.model.pc.scenic.entity.ScenicConfigEntity;
import com.ycwl.basic.model.pc.scenic.req.ScenicAddOrUpdateReq;
import com.ycwl.basic.model.pc.scenic.req.ScenicReqQuery;
import com.ycwl.basic.model.pc.scenic.resp.ScenicRespVO;
import com.ycwl.basic.repository.ScenicRepository;
import com.ycwl.basic.service.pc.ScenicService;
import com.ycwl.basic.service.task.TaskFaceService;
import com.ycwl.basic.utils.ApiResponse;
@ -39,9 +34,9 @@ public class ScenicServiceImpl implements ScenicService {
@Autowired
private ScenicAccountMapper scenicAccountMapper;
@Autowired
private FaceDetectConfig faceDetectConfig;
@Autowired
private TaskFaceService taskFaceService;
@Autowired
private ScenicRepository scenicRepository;
@Override
public ApiResponse<PageInfo<ScenicRespVO>> pageQuery(ScenicReqQuery scenicReqQuery) {
@ -96,6 +91,7 @@ public class ScenicServiceImpl implements ScenicService {
scenicMapper.deleteConfigByScenicId(id);
scenicAccountMapper.deleteByScenicId(id);
taskFaceService.deleteFaceDB(id.toString());
scenicRepository.clearCache(id);
return ApiResponse.success(true);
}else {
return ApiResponse.fail("景区删除失败");
@ -129,6 +125,7 @@ public class ScenicServiceImpl implements ScenicService {
}
int i = scenicMapper.update(scenicUpdateReq);
if (i > 0) {
scenicRepository.clearCache(scenicUpdateReq.getId());
taskFaceService.assureFaceDB(scenicUpdateReq.getId().toString());
return ApiResponse.success(true);
}else {
@ -141,6 +138,7 @@ public class ScenicServiceImpl implements ScenicService {
public ApiResponse<Boolean> updateStatus(Long id) {
int i = scenicMapper.updateStatus(id);
if (i > 0) {
scenicRepository.clearCache(id);
taskFaceService.assureFaceDB(id.toString());
return ApiResponse.success(true);
}else {
@ -152,6 +150,7 @@ public class ScenicServiceImpl implements ScenicService {
public ApiResponse<Boolean> addConfig(ScenicConfigEntity scenicConfig) {
int i = scenicMapper.addConfig(scenicConfig);
if (i > 0) {
scenicRepository.clearCache(scenicConfig.getScenicId());
taskFaceService.assureFaceDB(scenicConfig.getScenicId().toString());
return ApiResponse.success(true);
}else {
@ -163,6 +162,7 @@ public class ScenicServiceImpl implements ScenicService {
public ApiResponse<Boolean> updateConfigById(ScenicConfigEntity scenicConfig) {
int i = scenicMapper.updateConfigById(scenicConfig);
if (i > 0) {
scenicRepository.clearCache(scenicConfig.getScenicId());
taskFaceService.assureFaceDB(scenicConfig.getScenicId().toString());
return ApiResponse.success(true);
}else {
@ -172,27 +172,16 @@ public class ScenicServiceImpl implements ScenicService {
@Override
public ScenicConfigEntity getConfig(Long id) {
ScenicConfigEntity config = scenicMapper.getConfig(id);
if (config == null) {
config = new ScenicConfigEntity();
config.setId(SnowFlakeUtil.getLongId());
config.setScenicId(id);
config.setIsDefault(1);
scenicMapper.addConfig(config);
}
return config;
return scenicRepository.getScenicConfig(id);
}
@Override
public void saveConfig(Long configId, ScenicConfigEntity config) {
config.setId(configId);
if (config.getScenicId() == null) {
throw new RuntimeException("景区ID不能为空");
}
scenicMapper.updateConfigById(config);
}
private IAcsClient getClient() {
DefaultProfile profile = DefaultProfile.getProfile(
faceDetectConfig.getRegion(),faceDetectConfig.getAccessKeyId(), faceDetectConfig.getAccessKeySecret());
IAcsClient client = new DefaultAcsClient(profile);
return client;
scenicRepository.clearCache(config.getScenicId());
}
}

View File

@ -6,6 +6,7 @@ import com.ycwl.basic.mapper.TaskMapper;
import com.ycwl.basic.model.pc.task.entity.TaskEntity;
import com.ycwl.basic.model.pc.task.req.TaskReqQuery;
import com.ycwl.basic.model.pc.task.resp.TaskRespVO;
import com.ycwl.basic.repository.VideoTaskRepository;
import com.ycwl.basic.service.pc.TaskService;
import com.ycwl.basic.utils.ApiResponse;
import org.springframework.beans.factory.annotation.Autowired;
@ -22,6 +23,8 @@ public class TaskServiceImpl implements TaskService {
@Autowired
private TaskMapper taskMapper;
@Autowired
private VideoTaskRepository videoTaskRepository;
@Override
public ApiResponse<PageInfo<TaskRespVO>> pageQuery(TaskReqQuery taskReqQuery) {
@ -44,6 +47,7 @@ public class TaskServiceImpl implements TaskService {
@Override
public ApiResponse<Boolean> deleteById(Long id) {
int i = taskMapper.deleteById(id);
videoTaskRepository.clearTaskCache(id);
if (i > 0) {
return ApiResponse.success(true);
}else {
@ -54,6 +58,7 @@ public class TaskServiceImpl implements TaskService {
@Override
public ApiResponse<Boolean> update(TaskEntity task) {
int i = taskMapper.update(task);
videoTaskRepository.clearTaskCache(task.getId());
if (i > 0) {
return ApiResponse.success(true);
}else {
@ -64,6 +69,7 @@ public class TaskServiceImpl implements TaskService {
@Override
public ApiResponse<Boolean> updateStatus(Long id, Integer status) {
int i = taskMapper.updateStatus(id, status);
videoTaskRepository.clearTaskCache(id);
if (i > 0) {
return ApiResponse.success(true);
}else {

View File

@ -108,7 +108,7 @@ public class TaskFaceServiceImpl implements TaskFaceService {
request.setDbName(dbName);
request.setImageUrl(faceUrl);
request.setLimit(100);
request.setQualityScoreThreshold(80F);
request.setQualityScoreThreshold(60f);
FaceDetectLog log = FaceDetectLog.quickCreate("预留字段", request);
try {
SearchFaceResponse response = client.getAcsResponse(request);

View File

@ -1,10 +1,14 @@
package com.ycwl.basic.service.impl.task;
import cn.hutool.core.date.DateUtil;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.ycwl.basic.biz.OrderBiz;
import com.ycwl.basic.constant.TaskConstant;
import com.ycwl.basic.mapper.FaceMapper;
import com.ycwl.basic.mapper.FaceSampleMapper;
import com.ycwl.basic.mapper.MemberMapper;
import com.ycwl.basic.mapper.RenderWorkerMapper;
import com.ycwl.basic.mapper.SourceMapper;
import com.ycwl.basic.mapper.TaskMapper;
@ -13,7 +17,10 @@ import com.ycwl.basic.mapper.VideoMapper;
import com.ycwl.basic.model.mobile.order.PriceObj;
import com.ycwl.basic.model.pc.face.resp.FaceRespVO;
import com.ycwl.basic.model.pc.faceSample.resp.FaceSampleRespVO;
import com.ycwl.basic.model.pc.member.resp.MemberRespVO;
import com.ycwl.basic.model.pc.mp.MpConfigEntity;
import com.ycwl.basic.model.pc.renderWorker.entity.RenderWorkerEntity;
import com.ycwl.basic.model.pc.scenic.entity.ScenicEntity;
import com.ycwl.basic.model.pc.source.entity.SourceEntity;
import com.ycwl.basic.model.pc.source.resp.SourceRespVO;
import com.ycwl.basic.model.pc.task.entity.TaskEntity;
@ -27,6 +34,11 @@ import com.ycwl.basic.model.task.req.ClientStatusReqVo;
import com.ycwl.basic.model.task.req.TaskReqVo;
import com.ycwl.basic.model.task.req.WorkerAuthReqVo;
import com.ycwl.basic.model.task.resp.TaskSyncRespVo;
import com.ycwl.basic.notify.NotifyFactory;
import com.ycwl.basic.notify.adapters.INotifyAdapter;
import com.ycwl.basic.notify.entity.NotifyContent;
import com.ycwl.basic.notify.enums.NotifyType;
import com.ycwl.basic.repository.ScenicRepository;
import com.ycwl.basic.repository.VideoTaskRepository;
import com.ycwl.basic.service.task.TaskService;
import com.ycwl.basic.storage.StorageFactory;
@ -35,6 +47,7 @@ import com.ycwl.basic.task.VideoPieceGetter;
import com.ycwl.basic.repository.TemplateRepository;
import com.ycwl.basic.utils.SnowFlakeUtil;
import lombok.NonNull;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.redis.core.RedisTemplate;
@ -44,12 +57,15 @@ import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.Arrays;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.Optional;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
@Slf4j
@Service
public class TaskTaskServiceImpl implements TaskService {
@Autowired
@ -74,6 +90,10 @@ public class TaskTaskServiceImpl implements TaskService {
private VideoTaskRepository videoTaskRepository;
@Autowired
private OrderBiz orderBiz;
@Autowired
private MemberMapper memberMapper;
@Autowired
private ScenicRepository scenicRepository;
private RenderWorkerEntity getWorker(@NonNull WorkerAuthReqVo req) {
String accessKey = req.getAccessKey();
@ -207,10 +227,6 @@ public class TaskTaskServiceImpl implements TaskService {
if (templateList == null || templateList.isEmpty()) {
return;
}
TaskEntity faceAutomaticTask = taskMapper.getFaceAutomaticTask(faceId);
if (faceAutomaticTask != null) {
return;
}
createTaskByFaceIdAndTempalteId(faceId, templateList.get(0).getId(), 1);
}
@Override
@ -235,13 +251,31 @@ public class TaskTaskServiceImpl implements TaskService {
taskReqQuery.setFaceId(faceId);
taskReqQuery.setTemplateId(templateId);
List<TaskRespVO> list = taskMapper.list(taskReqQuery);
if (!list.isEmpty()) {
return;
}
list.parallelStream().forEach(task -> {
MemberVideoEntity memberVideo = videoMapper.queryRelationByMemberTask(faceRespVO.getMemberId(), task.getId());
if (memberVideo == null) {
memberVideo = new MemberVideoEntity();
memberVideo.setMemberId(faceRespVO.getMemberId());
memberVideo.setScenicId(task.getScenicId());
memberVideo.setFaceId(faceId);
memberVideo.setTemplateId(task.getTemplateId());
memberVideo.setIsBuy(0);
memberVideo.setTaskId(task.getId());
VideoEntity video = videoMapper.findByTaskId(task.getId());
if (video != null) {
memberVideo.setVideoId(video.getId());
}
videoMapper.addRelation(memberVideo);
new Thread(() -> {
sendVideoGeneratedServiceNotification(list.get(0).getId(), faceRespVO.getMemberId());
}).start();
}
});
return;
}
VideoPieceGetter.Task task = new VideoPieceGetter.Task();
task.faceId = faceId;
task.faceSampleId = faceSampleIds;
task.faceSampleIds = faceSampleIds;
task.memberId = faceRespVO.getMemberId();
task.callback = () -> {
boolean canGenerate = templateRepository.determineTemplateCanGenerate(templateId, faceId);
@ -284,6 +318,10 @@ public class TaskTaskServiceImpl implements TaskService {
memberVideoEntity.setIsBuy(1);
}
memberVideoEntity.setVideoId(video.getId());
// 已经生成了
new Thread(() -> {
sendVideoGeneratedServiceNotification(list.get(0).getId(), faceRespVO.getMemberId());
}).start();
}
}
videoMapper.addRelation(memberVideoEntity);
@ -328,6 +366,9 @@ public class TaskTaskServiceImpl implements TaskService {
isBuy = 1;
}
videoMapper.updateRelationWhenTaskSuccess(taskId, video.getId(), isBuy);
new Thread(() -> {
sendVideoGeneratedServiceNotification(taskId);
}).start();
}
@Override
@ -368,4 +409,83 @@ public class TaskTaskServiceImpl implements TaskService {
}
return adapter.getUrlForUpload(filename);
}
public void sendVideoGeneratedServiceNotification(Long taskId) {
List<MemberVideoEntity> memberVideo = videoMapper.listRelationByTask(taskId);
memberVideo.forEach(item -> {
sendVideoGeneratedServiceNotification(taskId, item.getMemberId());
});
}
@Override
public Date getTaskShotDate(Long taskId) {
TaskRespVO taskRespVO = taskMapper.getById(taskId);
if (taskRespVO == null) {
return null;
}
Date shotTime = taskRespVO.getCreateTime();
JSONObject paramJson = JSON.parseObject(taskRespVO.getTaskParams());
if (paramJson != null) {
Optional<String> any = paramJson.keySet().stream().filter(StringUtils::isNumeric).findAny();
if (any.isPresent()) {
JSONArray jsonArray = paramJson.getJSONArray(any.get());
if (!jsonArray.isEmpty()) {
JSONObject jsonObject = jsonArray.getJSONObject(0);
if (jsonObject.containsKey("createTime")) {
shotTime = new Date(jsonObject.getLong("createTime"));
}
}
}
}
return shotTime;
}
@Override
public void sendVideoGeneratedServiceNotification(Long taskId, Long memberId) {
MemberVideoEntity item = videoMapper.queryRelationByMemberTask(memberId, taskId);
MemberRespVO member = memberMapper.getById(memberId);
String openId = member.getOpenId();
MpConfigEntity scenicMp = scenicRepository.getScenicMpConfig(member.getScenicId());
if (StringUtils.isNotBlank(openId) && scenicMp != null) {
String templateId = scenicRepository.getVideoGeneratedTemplateId(item.getScenicId());
if (StringUtils.isBlank(templateId)) {
log.warn("未配置视频生成通知模板");
return;
}
ScenicEntity scenic = scenicRepository.getScenic(item.getScenicId());
String title = "您在【" + scenic.getName() + "】的影像";
String page = "pages/videoSynthesis/buy?scenicId=" + item.getScenicId() + "&faceId=" + item.getFaceId() + "&id=" + item.getVideoId();
/**
* 景点 {{thing5.DATA}}
* 视频名称 {{thing1.DATA}}
* 游玩时间 {{time2.DATA}}
* 生成时间 {{time4.DATA}}
* 备注 {{thing3.DATA}}
*/
Map<String, Object> params = new HashMap<>();
Map<String, Object> dataParam = new HashMap<>();
Map<String, String> scenicMap = new HashMap<>();
scenicMap.put("value", scenic.getName());
dataParam.put("thing5", scenicMap);
Map<String, String> videoMap = new HashMap<>();
TemplateRespVO template = templateRepository.getTemplate(item.getTemplateId());
videoMap.put("value", template.getName());
dataParam.put("thing1", videoMap);
Map<String, String> timeMap = new HashMap<>();
timeMap.put("value", DateUtil.format(getTaskShotDate(taskId), "yyyy-MM-dd"));
dataParam.put("time2", timeMap);
Map<String, String> timeMap2 = new HashMap<>();
timeMap2.put("value", DateUtil.format(new Date(), "yyyy-MM-dd HH:mm"));
dataParam.put("time4", timeMap2);
Map<String, String> remarkMap = new HashMap<>();
remarkMap.put("value", "您的游玩Vlog已经等候多时快来看看吧");
dataParam.put("thing3", remarkMap);
params.put("data", dataParam);
params.put("page", page);
params.put("template_id", templateId);
log.info("视频生成通知模板参数:{}用户ID{}", params, openId);
INotifyAdapter adapter = NotifyFactory.get(NotifyType.WX_MP_SRV, scenicMp.toMap());
adapter.sendTo(new NotifyContent(title, page, params), openId);
}
}
}

View File

@ -17,16 +17,17 @@ public interface AppMemberService {
*
* @return Map
*/
Map<String, Object> getOpenId(String code);
Map<String, Object> getOpenId(Long scenicId, String code);
/**
* 登录
*
* @param scenicId
* @param code 前端授权码
* @param userInfoDTO 实体信息
* @return
*/
ApiResponse login(String code, WeChatUserInfoDTO userInfoDTO) throws Exception;
ApiResponse login(Long scenicId, String code, WeChatUserInfoDTO userInfoDTO) throws Exception;
/**
* 获取用户信息

View File

@ -5,6 +5,8 @@ import com.ycwl.basic.model.task.req.TaskReqVo;
import com.ycwl.basic.model.task.req.WorkerAuthReqVo;
import com.ycwl.basic.model.task.resp.TaskSyncRespVo;
import java.util.Date;
public interface TaskService {
TaskSyncRespVo handleSyncTask(TaskReqVo req);
void createRenderTask(Long scenicId, Long templateId, Long faceId);
@ -24,4 +26,8 @@ public interface TaskService {
void taskStart(Long taskId, WorkerAuthReqVo req);
void autoCreateTaskByFaceId(Long id);
Date getTaskShotDate(Long taskId);
void sendVideoGeneratedServiceNotification(Long taskId, Long memberId);
}

View File

@ -14,7 +14,6 @@ import com.ycwl.basic.model.pc.source.entity.MemberSourceEntity;
import com.ycwl.basic.model.pc.source.entity.SourceEntity;
import com.ycwl.basic.storage.StorageFactory;
import com.ycwl.basic.storage.adapters.IStorageAdapter;
import com.ycwl.basic.storage.enums.StorageType;
import com.ycwl.basic.utils.SnowFlakeUtil;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
@ -25,8 +24,6 @@ import org.springframework.stereotype.Component;
import java.io.BufferedReader;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
@ -55,7 +52,7 @@ public class VideoPieceGetter {
@Data
public static class Task {
public String type = "normal";
public List<Long> faceSampleId;
public List<Long> faceSampleIds;
public Callback callback;
public Long memberId;
public Long faceId;
@ -86,7 +83,7 @@ public class VideoPieceGetter {
}
log.info("poll task: {}", task);
if (task.getType().equalsIgnoreCase("normal")) {
task.getFaceSampleId().parallelStream().forEach(faceSampleId -> {
task.getFaceSampleIds().parallelStream().forEach(faceSampleId -> {
FaceSampleRespVO faceSample = faceSampleMapper.getById(faceSampleId);
DeviceEntity device = deviceRepository.getDevice(faceSample.getDeviceId());
DeviceConfigEntity config = deviceRepository.getDeviceConfig(faceSample.getDeviceId());

View File

@ -115,7 +115,7 @@ YfkdFNxtYLdVAwuylMoV3fKI
# 人脸合格得分
face:
score: 80
score: 75
# 存储
storage:

View File

@ -2,9 +2,9 @@
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.ycwl.basic.mapper.MemberMapper">
<insert id="add">
insert into member(id, openid,avatar_url, nickname, real_name, promo_code, broker_id, agreement, phone, country, province,
insert into member(id, scenic_id, openid,avatar_url, nickname, real_name, promo_code, broker_id, agreement, phone, country, province,
city)
values (#{id}, #{openId}, #{avatarUrl},#{nickname}, #{realName}, #{promoCode}, #{brokerId}, #{agreement}, #{phone},
values (#{id}, #{scenicId}, #{openId}, #{avatarUrl},#{nickname}, #{realName}, #{promoCode}, #{brokerId}, #{agreement}, #{phone},
#{country}, #{province}, #{city})
</insert>
<insert id="addScenicServiceNoticeStatus">
@ -14,6 +14,9 @@
<update id="update">
update member
<set>
<if test="scenicId!= null">
scenicId = #{scenicId},
</if>
<if test="openId!= null and openId!= ''">
openid = #{openId},
</if>
@ -67,7 +70,7 @@
where id = #{id}
</delete>
<select id="list" resultType="com.ycwl.basic.model.pc.member.resp.MemberRespVO">
select id, openid,avatar_url, nickname, real_name, promo_code, broker_id, agreement, phone, country, province, city,
select id, scenic_id, openid,avatar_url, nickname, real_name, promo_code, broker_id, agreement, phone, country, province, city,
(select count(1) from `order` where `order`.member_id = member.id) as order_count,
create_date
from member
@ -75,6 +78,9 @@
<if test="openId!= null and openId!= ''">
and openid like concat('%',#{openId},'%')
</if>
<if test="scenicId!= null">
and scenic_id = #{scenicId}
</if>
<if test="nickname!= null and nickname!= ''">
and nickname like concat('%',#{nickname},'%')
</if>
@ -106,6 +112,7 @@
</select>
<select id="getById" resultType="com.ycwl.basic.model.pc.member.resp.MemberRespVO">
select id,
scenic_id,
openid,
avatar_url,
nickname,

View File

@ -0,0 +1,9 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd" >
<mapper namespace="com.ycwl.basic.mapper.MpNotifyConfigMapper">
<select id="listByMpId" resultType="com.ycwl.basic.model.pc.mp.MpNotifyConfigEntity">
select *
from mp_notify_config
where mp_id = #{mpId}
</select>
</mapper>

View File

@ -73,16 +73,14 @@
where so.id = #{id}
</select>
<select id="listGroupByType" resultType="com.ycwl.basic.model.pc.source.resp.SourceRespVO">
select so.id, ms.scenic_id,sc.name scenicName, sc.longitude ,sc.latitude,so.type,so.is_buy
select ms.type, ms.is_buy
from member_source ms
left join source so on ms.source_id = so.id
left join scenic sc on sc.id = so.scenic_id
<where>
<if test="scenicId!= null">and so.scenic_id = #{scenicId} </if>
<if test="scenicId!= null">and ms.scenic_id = #{scenicId} </if>
<if test="memberId!= null">and ms.member_id = #{memberId} </if>
<if test="isBuy!=null">and ms.is_buy = #{isBuy}</if>
</where>
group by so.type
group by ms.type
</select>
<select id="countByMemberId" resultType="java.lang.Integer">
select count(1) from member_source where member_id = #{userId}

View File

@ -115,6 +115,11 @@
from member_video mv
where mv.member_id = #{userId} and mv.face_id = #{faceId}
</select>
<select id="listRelationByTask" resultType="com.ycwl.basic.model.pc.video.entity.MemberVideoEntity">
select mv.*
from member_video mv
where mv.task_id = #{taskId}
</select>
<select id="listRelationByFaceAndTemplate" resultType="com.ycwl.basic.model.pc.video.entity.MemberVideoEntity">
select mv.*
from member_video mv
@ -132,4 +137,10 @@
where member_id = #{userId} and video_id = #{videoId}
limit 1
</select>
<select id="queryRelationByMemberTask" resultType="com.ycwl.basic.model.pc.video.entity.MemberVideoEntity">
select *
from member_video
where member_id = #{userId} and task_id = #{taskId}
limit 1
</select>
</mapper>