Reviewed-on: http://39.105.23.186:3000/develop/digimeta-MultiSaas/pulls/134tags/B.2.2.0.3_20230925_base
| @@ -31,6 +31,9 @@ public interface RemoteFileService { | |||
| @PostMapping(value = "/inner/upload", consumes = MediaType.MULTIPART_FORM_DATA_VALUE) | |||
| R<SysFile> upload(@RequestPart(value = "file") MultipartFile file); | |||
| @PostMapping(value = "/inner/upload-temp", consumes = MediaType.MULTIPART_FORM_DATA_VALUE) | |||
| R<SysFile> uploadTemp(@RequestPart(value = "file") MultipartFile file); | |||
| /** | |||
| * 上传pdf文件 | |||
| * | |||
| @@ -28,6 +28,11 @@ public class RemoteFileFallbackFactory implements FallbackFactory<RemoteFileServ | |||
| return R.fail("上传文件失败:" + throwable.getMessage()); | |||
| } | |||
| @Override | |||
| public R<SysFile> uploadTemp(MultipartFile file) { | |||
| return null; | |||
| } | |||
| @Override | |||
| public R<List<SysFile>> uploadPdf(MultipartFile file) { | |||
| return R.fail("上传文件失败:" + throwable.getMessage() ); | |||
| @@ -0,0 +1,24 @@ | |||
| package com.xueyi.nlt.api.nlt.domain.vo; | |||
| import lombok.Data; | |||
| import lombok.NoArgsConstructor; | |||
| @Data | |||
| @NoArgsConstructor | |||
| public class WenxinErnieBotResponse { | |||
| protected String id; | |||
| protected String object; | |||
| protected String created; | |||
| protected String result; | |||
| protected String is_truncated; | |||
| protected String need_clear_history; | |||
| protected Usage usage; | |||
| @Data | |||
| class Usage { | |||
| protected String prompt_tokens; | |||
| protected String completion_tokens; | |||
| protected String total_tokens; | |||
| } | |||
| } | |||
| @@ -0,0 +1,25 @@ | |||
| package com.xueyi.nlt.api.nlt.feign; | |||
| import com.alibaba.fastjson2.JSONObject; | |||
| import com.xueyi.nlt.api.nlt.domain.vo.WenxinErnieBotResponse; | |||
| import com.xueyi.nlt.api.nlt.feign.factory.RemoteLandingLlmFallbackFactory; | |||
| import org.springframework.cloud.openfeign.FeignClient; | |||
| import org.springframework.web.bind.annotation.GetMapping; | |||
| import org.springframework.web.bind.annotation.PostMapping; | |||
| import org.springframework.web.bind.annotation.RequestBody; | |||
| import org.springframework.web.bind.annotation.RequestParam; | |||
| @FeignClient(url = "${notification.wenxin-llm.url}",name = "wenxin-llm", fallbackFactory = RemoteLandingLlmFallbackFactory.class) | |||
| public interface RemoteWenxinLlmService { | |||
| @GetMapping("/oauth/2.0/token") | |||
| void getToken(@RequestParam(value = "grant_type",defaultValue = "client_credentials") String grantType, | |||
| @RequestParam("client_id") String clientId, | |||
| @RequestParam("client_secret") String clientSecret); | |||
| @PostMapping("/rpc/2.0/ai_custom/v1/wenxinworkshop/chat/eb-instant") | |||
| WenxinErnieBotResponse ebInstant(@RequestParam("access-token") String accessToken, @RequestBody JSONObject message); | |||
| } | |||
| @@ -1,5 +1,7 @@ | |||
| package com.xueyi.system.api.digitalmans.domain.dto; | |||
| import com.xueyi.common.core.annotation.Correlation; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmModelPo; | |||
| import com.xueyi.system.api.resource.domain.po.DmResourcesPo; | |||
| import lombok.Data; | |||
| @@ -8,6 +10,8 @@ import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import java.util.List; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Model_DmModelIcon_GROUP; | |||
| /** | |||
| * 模型 数据传输对象 | |||
| * | |||
| @@ -36,5 +40,7 @@ public class DmModelDto extends DmModelPo { | |||
| // 数字人昵称 | |||
| protected String name; | |||
| // @Correlation(groupName = Model_DmModelIcon_GROUP, keyType = OperateConstants.SubKeyType.RECEIVE) | |||
| protected List<DmScreenIconDto> dmScreenIconDtos; | |||
| } | |||
| @@ -0,0 +1,25 @@ | |||
| package com.xueyi.system.api.digitalmans.domain.dto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| /** | |||
| * 数字人主界面图标 数据传输对象 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Data | |||
| @EqualsAndHashCode(callSuper = true) | |||
| public class DmScreenIconDto extends DmScreenIconPo { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| private String iconUrl; | |||
| private Integer pos; | |||
| } | |||
| @@ -0,0 +1,52 @@ | |||
| package com.xueyi.system.api.digitalmans.domain.merge; | |||
| import com.baomidou.mybatisplus.annotation.TableName; | |||
| import com.xueyi.common.core.annotation.Correlation; | |||
| import com.xueyi.common.core.annotation.Correlations; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.core.web.tenant.base.TBasisEntity; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import lombok.NoArgsConstructor; | |||
| import java.io.Serial; | |||
| /** | |||
| * 任务访客关联 持久化对象 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Data | |||
| @NoArgsConstructor | |||
| @EqualsAndHashCode(callSuper = true) | |||
| @TableName("dm_model_icon_merge") | |||
| public class DmModelIconMerge extends TBasisEntity { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| /** 招待任务id */ | |||
| @Correlations({ | |||
| @Correlation(groupName = MergeGroup.Model_DmModelIcon_GROUP, keyType = OperateConstants.SubKeyType.MERGE_MAIN), | |||
| @Correlation(groupName = MergeGroup.Icon_DmModelIcon_GROUP, keyType = OperateConstants.SubKeyType.MERGE_SLAVE) | |||
| }) | |||
| protected Long modelId; | |||
| /** 访客id */ | |||
| @Correlations({ | |||
| @Correlation(groupName = MergeGroup.Icon_DmModelIcon_GROUP, keyType = OperateConstants.SubKeyType.MERGE_MAIN), | |||
| @Correlation(groupName = MergeGroup.Model_DmModelIcon_GROUP, keyType = OperateConstants.SubKeyType.MERGE_SLAVE) | |||
| }) | |||
| protected Long iconId; | |||
| /** 优先级 */ | |||
| protected Integer pos; | |||
| public DmModelIconMerge(Long modelId, Long iconId, Integer pos) { | |||
| this.modelId = modelId; | |||
| this.iconId = iconId; | |||
| this.pos = pos; | |||
| } | |||
| } | |||
| @@ -1,4 +1,4 @@ | |||
| package com.xueyi.system.digitalmans.domain.merge; | |||
| package com.xueyi.system.api.digitalmans.domain.merge; | |||
| public interface MergeGroup { | |||
| @@ -11,5 +11,6 @@ public interface MergeGroup { | |||
| String Visitor_DmReceptionVisitorMerge_GROUP = "Visitor_DmReceptionVisitorMerge_GROUP"; | |||
| String Broadcast_DmBroadcastResource_GROUP = "Broadcast_DmBroadcastResource_GROUP"; | |||
| String Resource_DmBroadcastResource_GROUP = "Resource_DmBroadcastResource_GROUP"; | |||
| String Model_DmModelIcon_GROUP = "Model_DmModelIcon_GROUP"; | |||
| String Icon_DmModelIcon_GROUP = "Icon_DmModelIcon_GROUP"; | |||
| } | |||
| @@ -0,0 +1,40 @@ | |||
| package com.xueyi.system.api.digitalmans.domain.po; | |||
| import com.baomidou.mybatisplus.annotation.TableName; | |||
| import com.xueyi.common.core.annotation.Excel; | |||
| import com.xueyi.common.core.web.tenant.base.TBaseEntity; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import static com.xueyi.common.core.constant.basic.EntityConstants.*; | |||
| /** | |||
| * 数字人主界面图标 持久化对象 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Data | |||
| @EqualsAndHashCode(callSuper = true) | |||
| @TableName(value = "dm_model_icon_merge", excludeProperty = { STATUS,SORT,CREATE_TIME,CREATE_BY,UPDATE_TIME,UPDATE_BY,DEL_FLAG,REMARK }) | |||
| public class DmModelIconPo extends TBaseEntity { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| /** 图片id */ | |||
| @Excel(name = "图片id") | |||
| protected Long modelId; | |||
| /** 广播id */ | |||
| @Excel(name = "广播id") | |||
| protected Long iconId; | |||
| /** 状态(0:正常;1:停用) */ | |||
| @Excel(name = "状态", readConverterExp = "0=:正常;1:停用") | |||
| protected Integer pos; | |||
| } | |||
| @@ -0,0 +1,42 @@ | |||
| package com.xueyi.system.api.digitalmans.domain.po; | |||
| import com.xueyi.common.core.web.tenant.base.TBaseEntity; | |||
| import com.xueyi.common.core.annotation.Excel; | |||
| import com.baomidou.mybatisplus.annotation.TableName; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| /** | |||
| * 数字人主界面图标 持久化对象 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Data | |||
| @EqualsAndHashCode(callSuper = true) | |||
| @TableName("dm_screen_icon") | |||
| public class DmScreenIconPo extends TBaseEntity { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| /** 图片id */ | |||
| @Excel(name = "图片id") | |||
| protected Long resourceId; | |||
| /** 广播id */ | |||
| @Excel(name = "广播id") | |||
| protected Long broadcastId; | |||
| /** 状态(0:正常;1:停用) */ | |||
| @Excel(name = "状态", readConverterExp = "0=:正常;1:停用") | |||
| protected String status; | |||
| /** 备注 */ | |||
| @Excel(name = "备注") | |||
| protected String remark; | |||
| } | |||
| @@ -26,6 +26,8 @@ public class DmResourcesPo extends TBaseEntity { | |||
| public static final Integer TYPE_PIC = 1; | |||
| public static final Integer TYPE_VIDEO = 2; | |||
| public static final Integer TYPE_PDF = 3; | |||
| /** 资源tag */ | |||
| @Excel(name = "资源tag") | |||
| protected String tag; | |||
| @@ -8,4 +8,16 @@ import com.xueyi.common.core.utils.core.pool.NumberPool; | |||
| * @author xueyi | |||
| */ | |||
| public class NumberUtil extends cn.hutool.core.util.NumberUtil implements NumberPool { | |||
| /** | |||
| * @Author yangkai | |||
| * @Description 判断数字是否为null,为null返回0 | |||
| * @Date 2023/9/21 | |||
| * @Param | |||
| * @return | |||
| **/ | |||
| public static int getNumber(Integer number) { | |||
| return number == null ? 0 : number; | |||
| } | |||
| } | |||
| @@ -24,7 +24,9 @@ public class MimeTypeUtil { | |||
| public static final String[] MEDIA_EXTENSION = {"swf", "flv", "mp3", "wav", "wma", "wmv", "mid", "avi", "mpg", | |||
| "asf", "rm", "rmvb"}; | |||
| public static final String[] VIDEO_EXTENSION = {"mp4", "avi", "rmvb", "webm"}; | |||
| public static final String[] VIDEO_EXTENSION = {"mp4", "avi", "rmvb", "mkv", "wmv", "rm", "rmvb", "flv", "webm","mov","3gp","flv","mpeg"}; | |||
| public static final String PDF_EXTENSION = "pdf"; | |||
| public static final String[] DEFAULT_ALLOWED_EXTENSION = { | |||
| // 图片 | |||
| @@ -34,7 +36,15 @@ public class MimeTypeUtil { | |||
| // 压缩文件 | |||
| "rar", "zip", "gz", "bz2", | |||
| // 视频格式 | |||
| "mp4", "avi", "rmvb", | |||
| "mp4", "avi", "rmvb", "mkv", "wmv", "rm", "rmvb", "flv", "webm","mov","3gp","flv","mpeg", | |||
| "pdf"}; | |||
| public static final String[] EXCEPT_ALLOWED_EXTENSION = { | |||
| // 图片 | |||
| "bmp", "gif", "jpg", "jpeg", "png", | |||
| // 视频格式 | |||
| "mp4", "avi", "rmvb", "mkv", "wmv", "rm", "rmvb", "flv", "webm","mov","3gp","flv","mpeg", | |||
| "pdf"}; | |||
| @@ -0,0 +1,46 @@ | |||
| package com.xueyi.common.redis.utils; | |||
| import com.alibaba.fastjson2.JSONObject; | |||
| import com.xueyi.common.core.utils.core.NumberUtil; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.data.redis.core.RedisTemplate; | |||
| import javax.annotation.PostConstruct; | |||
| import java.io.Serializable; | |||
| import java.util.List; | |||
| import java.util.concurrent.TimeUnit; | |||
| import java.util.stream.Collectors; | |||
| /** | |||
| * @author yk | |||
| * @description | |||
| * @date 2023-09-21 13:57 | |||
| */ | |||
| public class RedisUtil { | |||
| private static RedisTemplate<String, Serializable> redisTemplate; | |||
| @Autowired | |||
| RedisTemplate<String, Serializable> redisTemplate2; | |||
| @PostConstruct | |||
| public void init() { | |||
| redisTemplate = redisTemplate2; | |||
| } | |||
| public static Integer getNumberVal(String key) { | |||
| return NumberUtil.getNumber((Integer) redisTemplate.opsForValue().get(key)); | |||
| } | |||
| public static void expire(String key, int seconds) { | |||
| redisTemplate.expire(key, seconds, TimeUnit.SECONDS); | |||
| } | |||
| public static List<JSONObject> getJsonList(String key) { | |||
| return redisTemplate.opsForList().range(key, 0, -1).stream().map(json-> JSONObject.parseObject(json.toString())).collect(Collectors.toList()); | |||
| } | |||
| public static Boolean existed(String key){ | |||
| return redisTemplate.hasKey(key); | |||
| } | |||
| } | |||
| @@ -1,2 +1,3 @@ | |||
| com.xueyi.common.redis.configure.RedisConfig | |||
| com.xueyi.common.redis.service.RedisService | |||
| com.xueyi.common.redis.service.RedisService | |||
| com.xueyi.common.redis.utils.RedisUtil | |||
| @@ -37,7 +37,7 @@ public class AuthFilter implements GlobalFilter, Ordered { | |||
| @Autowired | |||
| private RedisService redisService; | |||
| private static final String[] whitePrefix = {"/message/api", "/pass/api", "/meeting/api", "/visit/api", "/file/api","/staff/api","/apkversion/api","/man/api","/holiday/api", "/skill/api", "/intent/api"}; | |||
| private static final String[] whitePrefix = {"/message/api", "/pass/api", "/meeting/api", "/visit/api", "/file/api","/staff/api","/apkversion/api","/man/api","/holiday/api", "/skill/api", "/intent/api","/system/api"}; | |||
| @Override | |||
| public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) { | |||
| @@ -1,6 +1,7 @@ | |||
| package com.xueyi.file.config; | |||
| import io.minio.MinioClient; | |||
| import lombok.Data; | |||
| import org.springframework.boot.context.properties.ConfigurationProperties; | |||
| import org.springframework.context.annotation.Bean; | |||
| import org.springframework.context.annotation.Configuration; | |||
| @@ -12,6 +13,7 @@ import org.springframework.context.annotation.Configuration; | |||
| */ | |||
| @Configuration | |||
| @ConfigurationProperties(prefix = "minio") | |||
| @Data | |||
| public class MinioConfig { | |||
| /** 服务地址 */ | |||
| @@ -26,37 +28,8 @@ public class MinioConfig { | |||
| /** 存储桶名称 */ | |||
| private String bucketName; | |||
| public String getUrl() { | |||
| return url; | |||
| } | |||
| public void setUrl(String url) { | |||
| this.url = url; | |||
| } | |||
| public String getAccessKey() { | |||
| return accessKey; | |||
| } | |||
| public void setAccessKey(String accessKey) { | |||
| this.accessKey = accessKey; | |||
| } | |||
| public String getSecretKey() { | |||
| return secretKey; | |||
| } | |||
| public void setSecretKey(String secretKey) { | |||
| this.secretKey = secretKey; | |||
| } | |||
| public String getBucketName() { | |||
| return bucketName; | |||
| } | |||
| public void setBucketName(String bucketName) { | |||
| this.bucketName = bucketName; | |||
| } | |||
| /** 临时存储桶名称 */ | |||
| private String tempBucketName; | |||
| @Bean | |||
| public MinioClient getMinioClient() { | |||
| @@ -14,7 +14,8 @@ import com.xueyi.file.config.MinioConfig; | |||
| import com.xueyi.file.service.ISysFileService; | |||
| import com.xueyi.file.service.MinioSysFileServiceImpl; | |||
| import com.xueyi.file.utils.PdfToImageUtil; | |||
| import lombok.extern.slf4j.Slf4j; | |||
| import org.slf4j.Logger; | |||
| import org.slf4j.LoggerFactory; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.web.bind.annotation.DeleteMapping; | |||
| import org.springframework.web.bind.annotation.PathVariable; | |||
| @@ -34,10 +35,11 @@ import java.util.List; | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Slf4j | |||
| @RestController | |||
| public class SysFileController { | |||
| private static final Logger log = LoggerFactory.getLogger(SysFileController.class); | |||
| @Autowired | |||
| private ISysFileService sysFileService; | |||
| @@ -56,7 +58,7 @@ public class SysFileController { | |||
| @PostMapping("/inner/upload") | |||
| public R<SysFile> uploadInner(MultipartFile file) { | |||
| try { | |||
| System.out.println("文件上传开始:" + file.getName()); | |||
| log.info("文件上传开始:" + file.getName()); | |||
| // 上传并返回访问地址 | |||
| String url = sysFileService.uploadFile(file); | |||
| SysFile sysFile = new SysFile(); | |||
| @@ -73,24 +75,49 @@ public class SysFileController { | |||
| } | |||
| @PostMapping("/inner/upload-temp") | |||
| public R<SysFile> uploadTempInner(MultipartFile file) { | |||
| try { | |||
| log.info("文件上传开始:" + file.getName()); | |||
| // 上传并返回访问地址 | |||
| String url = sysFileService.uploadTempFile(file); | |||
| SysFile sysFile = new SysFile(); | |||
| sysFile.setUrl(url); | |||
| sysFile.setSize(file.getSize()); | |||
| sysFile.setName(FileUtil.getName(url)); | |||
| sysFile.setNick(sysFile.getName()); | |||
| remoteFileManageService.saveFileLog(sysFile, SecurityConstants.INNER); | |||
| return R.ok(sysFile); | |||
| } catch (Exception e) { | |||
| log.error("上传文件失败", e); | |||
| return R.fail(e.getMessage()); | |||
| } | |||
| } | |||
| /** | |||
| * 文件上传 | 内部调用 | |||
| */ | |||
| @PostMapping("/inner/uploadpdf") | |||
| public R<List<SysFile>> uploadPdfInner(MultipartFile file) { | |||
| try { | |||
| System.out.println("文件上传开始:" + file.getName()); | |||
| Long startTs = System.currentTimeMillis(); | |||
| log.info("文件上传开始:" + file.getName()+"; start ts:"+startTs); | |||
| // pdf文件转成图片集合 | |||
| List<File> fileList = PdfToImageUtil.pdfToTransformationList(file); | |||
| Long pdfTs = System.currentTimeMillis(); | |||
| log.info("PDF转换图片完成, 用时:"+(pdfTs-startTs)+"ms"); | |||
| List<SysFile> results = new ArrayList<>(); | |||
| int num = 0; | |||
| int num = 1; | |||
| log.info("开始上传图片。。。"); | |||
| // 循环上传并返回日志集合 | |||
| for (File f : fileList) { | |||
| //将file的文件名重命名为file文件名+两位数的num | |||
| log.info("上传第"+num+"张图片开始。。。"); | |||
| String fileName = f.getName(); | |||
| String suffix = fileName.substring(fileName.lastIndexOf(".")); | |||
| String name = fileName.substring(0, fileName.lastIndexOf(".")); | |||
| String newName = name + String.format("%02d", num) + suffix; | |||
| String newName = name + String.format("%02d", num++) + suffix; | |||
| // 上传并返回访问地址 | |||
| String url = sysFileService.uploadFile(newName, f); | |||
| SysFile sysFile = new SysFile(); | |||
| @@ -100,7 +127,10 @@ public class SysFileController { | |||
| sysFile.setNick(sysFile.getName()); | |||
| remoteFileManageService.saveFileLog(sysFile, SecurityConstants.INNER); | |||
| results.add(sysFile); | |||
| log.info("上传第"+(num-1)+"张图片完成。。。"); | |||
| }; | |||
| long endTs = System.currentTimeMillis(); | |||
| log.info("上传图片结束。。。,用时:"+(endTs-pdfTs)+"ms"); | |||
| return R.ok(results); | |||
| } catch (Exception e) { | |||
| @@ -41,6 +41,11 @@ public class FastDfsSysFileServiceImpl implements ISysFileService { | |||
| return domain + "/" + storePath.getFullPath(); | |||
| } | |||
| @Override | |||
| public String uploadTempFile(MultipartFile file) throws Exception { | |||
| return null; | |||
| } | |||
| @Override | |||
| public String uploadFile(String fileName, File file) throws Exception { | |||
| return null; | |||
| @@ -18,13 +18,15 @@ public interface ISysFileService { | |||
| * @return 访问地址 | |||
| */ | |||
| String uploadFile(MultipartFile file) throws Exception; | |||
| String uploadTempFile(MultipartFile file) throws Exception; | |||
| String uploadFile(String fileName, File file) throws Exception; | |||
| /** | |||
| * 文件删除接口 | |||
| * | |||
| * @param url 文件地址 | |||
| * @param fileName 文件名 | |||
| * @return 结果 | |||
| */ | |||
| Boolean deleteFile(String url) throws Exception; | |||
| Boolean deleteFile(String fileName) throws Exception; | |||
| } | |||
| @@ -40,6 +40,11 @@ public class LocalSysFileServiceImpl implements ISysFileService { | |||
| return domain + localFilePrefix + name; | |||
| } | |||
| @Override | |||
| public String uploadTempFile(MultipartFile file) throws Exception { | |||
| return null; | |||
| } | |||
| @Override | |||
| public String uploadFile(String fileName, File file) throws Exception { | |||
| return null; | |||
| @@ -4,8 +4,11 @@ import com.xueyi.file.config.MinioConfig; | |||
| import com.xueyi.file.utils.FileUploadUtils; | |||
| import io.minio.MinioClient; | |||
| import io.minio.PutObjectArgs; | |||
| import io.minio.RemoveObjectArgs; | |||
| import org.apache.commons.io.FileUtils; | |||
| import org.apache.commons.io.IOUtils; | |||
| import org.slf4j.Logger; | |||
| import org.slf4j.LoggerFactory; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.context.annotation.Primary; | |||
| import org.springframework.stereotype.Service; | |||
| @@ -26,6 +29,7 @@ import java.net.URLEncoder; | |||
| @Service | |||
| public class MinioSysFileServiceImpl implements ISysFileService { | |||
| private static final Logger log = LoggerFactory.getLogger(MinioSysFileServiceImpl.class); | |||
| @Autowired | |||
| private MinioConfig minioConfig; | |||
| @@ -43,7 +47,7 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| String fileName = FileUploadUtils.extractFilename(file); | |||
| //fileName = URLEncoder.encode(fileName, "UTF-8"); | |||
| System.out.println("Minio filename:" + fileName); | |||
| log.info("Minio filename:" + fileName); | |||
| PutObjectArgs args = PutObjectArgs.builder() | |||
| .bucket(minioConfig.getBucketName()) | |||
| .object(fileName) | |||
| @@ -51,7 +55,7 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| .contentType(file.getContentType()) | |||
| .build(); | |||
| client.putObject(args); | |||
| System.out.println("Minio 文件上传成功"); | |||
| log.info("Minio 文件上传成功"); | |||
| // 获取fileName的最后一个'/'的位置的字符串,并用URLEncoder进行UTF-8编码后,再拼接到fileName中 | |||
| String splitStr = fileName.substring(fileName.lastIndexOf("/") + 1); | |||
| splitStr = URLEncoder.encode(splitStr, "UTF-8"); | |||
| @@ -59,12 +63,40 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| return minioConfig.getUrl() + "/" + minioConfig.getBucketName() + "/" + fileName; | |||
| } | |||
| @Override | |||
| public String uploadTempFile(MultipartFile file) throws Exception { | |||
| return null; | |||
| } | |||
| @Override | |||
| public String uploadFile(String fileName, File file) throws Exception { | |||
| fileName = FileUploadUtils.extractFilename(fileName); | |||
| InputStream inputStream = FileUtils.openInputStream(file); | |||
| System.out.println("file original filename = " + fileName); | |||
| System.out.println("file size = " + file.length()); | |||
| log.info("file original filename = " + fileName); | |||
| log.info("file size = " + file.length()); | |||
| // 使用IOUtils.toByteArray()方法确保正确地读取输入流中的数据 | |||
| byte[] fileBytes = IOUtils.toByteArray(inputStream); | |||
| // 上传文件到MinIO | |||
| String minioFileName = uploadFileToMinIO(fileName, fileBytes); | |||
| log.info("MinIO 文件上传成功,Minio 文件名:" + minioFileName); | |||
| // 获取fileName的最后一个'/'的位置的字符串,并用URLEncoder进行UTF-8编码后,再拼接到fileName中 | |||
| String splitStr = fileName.substring(fileName.lastIndexOf("/") + 1); | |||
| splitStr = URLEncoder.encode(splitStr, "UTF-8"); | |||
| fileName = fileName.substring(0, fileName.lastIndexOf("/") + 1) + splitStr; | |||
| return minioConfig.getUrl() + "/" + minioConfig.getBucketName() + "/" + fileName; | |||
| } | |||
| public String uploadTempFile(String fileName, File file) throws Exception { | |||
| fileName = FileUploadUtils.extractFilename(fileName); | |||
| InputStream inputStream = FileUtils.openInputStream(file); | |||
| log.info("file original filename = " + fileName); | |||
| log.info("file size = " + file.length()); | |||
| // 使用IOUtils.toByteArray()方法确保正确地读取输入流中的数据 | |||
| byte[] fileBytes = IOUtils.toByteArray(inputStream); | |||
| @@ -72,7 +104,7 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| // 上传文件到MinIO | |||
| String minioFileName = uploadFileToMinIO(fileName, fileBytes); | |||
| System.out.println("MinIO 文件上传成功,Minio 文件名:" + minioFileName); | |||
| log.info("MinIO Temp文件上传成功,Minio 文件名:" + minioFileName); | |||
| // 获取fileName的最后一个'/'的位置的字符串,并用URLEncoder进行UTF-8编码后,再拼接到fileName中 | |||
| String splitStr = fileName.substring(fileName.lastIndexOf("/") + 1); | |||
| @@ -108,7 +140,7 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| .build() | |||
| ); | |||
| System.out.println("文件上传到MinIO成功:" + fileName); | |||
| log.info("文件上传到MinIO成功:" + fileName); | |||
| String splitStr = fileName.substring(fileName.lastIndexOf("/") + 1); | |||
| splitStr = URLEncoder.encode(splitStr, "UTF-8"); | |||
| fileName = fileName.substring(0, fileName.lastIndexOf("/") + 1) + splitStr; | |||
| @@ -118,12 +150,15 @@ public class MinioSysFileServiceImpl implements ISysFileService { | |||
| /** | |||
| * 文件删除接口 | |||
| * 文件删除接口,通过minio的文件url进行删除 | |||
| * | |||
| * @param url 文件地址 | |||
| * @param url 文件url | |||
| * @return 结果 | |||
| */ | |||
| public Boolean deleteFile(String url) throws Exception { | |||
| String bucketName = minioConfig.getBucketName(); | |||
| String fileName = url.substring(url.indexOf(bucketName) + bucketName.length() + 1); | |||
| client.removeObject(RemoveObjectArgs.builder().bucket(minioConfig.getBucketName()).object(fileName).build()); | |||
| return true; | |||
| } | |||
| } | |||
| @@ -47,6 +47,10 @@ | |||
| <groupId>org.springframework.boot</groupId> | |||
| <artifactId>spring-boot-starter-actuator</artifactId> | |||
| </dependency> | |||
| <dependency> | |||
| <groupId>org.springframework.kafka</groupId> | |||
| <artifactId>spring-kafka</artifactId> | |||
| </dependency> | |||
| <!-- XueYi Common Log --> | |||
| <dependency> | |||
| @@ -6,16 +6,19 @@ import com.alibaba.nacos.shaded.com.google.gson.JsonArray; | |||
| import com.alibaba.nacos.shaded.com.google.gson.JsonObject; | |||
| import com.baomidou.mybatisplus.core.toolkit.StringUtils; | |||
| import com.xueyi.nlt.api.netty.domain.vo.DmWebSocketMessageVo; | |||
| import com.xueyi.nlt.nlt.domain.vo.LlmQueryVo; | |||
| import okhttp3.*; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.beans.factory.annotation.Value; | |||
| import org.springframework.data.redis.core.RedisTemplate; | |||
| import org.springframework.data.redis.core.StringRedisTemplate; | |||
| import org.springframework.kafka.core.KafkaTemplate; | |||
| import org.springframework.stereotype.Component; | |||
| import javax.annotation.PostConstruct; | |||
| import javax.crypto.Mac; | |||
| import javax.crypto.spec.SecretKeySpec; | |||
| import java.io.Serializable; | |||
| import java.net.URL; | |||
| import java.nio.charset.Charset; | |||
| import java.text.SimpleDateFormat; | |||
| @@ -30,6 +33,7 @@ public class WebSocketClient extends WebSocketListener { | |||
| @Autowired | |||
| private StringRedisTemplate stringRedisTemplate; | |||
| @Value("${secret.spark.appId}") | |||
| private String appId; | |||
| @@ -85,6 +89,18 @@ public class WebSocketClient extends WebSocketListener { | |||
| } | |||
| /** | |||
| * 调用讯飞开放平台接口发送消息,并将消息存入redis队列 | |||
| * @param message | |||
| * @param key | |||
| */ | |||
| public void sendMsg(String message,String key){ | |||
| LlmQueryVo vo = new LlmQueryVo(); | |||
| vo.setQuestion(message); | |||
| vo.setTemplate(key); | |||
| redisTemplate.opsForList().rightPush("group:websocket:quary",vo); | |||
| sendMsg(message); | |||
| } | |||
| public void sendMsg(String message){ | |||
| question = message; | |||
| @@ -0,0 +1,7 @@ | |||
| package com.xueyi.nlt.nlt.config; | |||
| import org.springframework.context.annotation.Bean; | |||
| public class MeetingParam { | |||
| } | |||
| @@ -11,6 +11,7 @@ import com.xueyi.common.cache.utils.SourceUtil; | |||
| import com.xueyi.common.core.constant.basic.SecurityConstants; | |||
| import com.xueyi.common.core.constant.digitalman.MessageConstants; | |||
| import com.xueyi.common.core.context.SecurityContextHolder; | |||
| import com.xueyi.common.core.utils.core.ListUtil; | |||
| import com.xueyi.common.core.web.result.AjaxResult; | |||
| import com.xueyi.common.core.web.result.R; | |||
| import com.xueyi.common.core.web.validate.V_A; | |||
| @@ -35,10 +36,12 @@ import com.xueyi.nlt.nlt.template.FreeChatTemplate; | |||
| import com.xueyi.nlt.nlt.template.GenerativeKnowledgeTemplate; | |||
| import com.xueyi.nlt.nlt.template.MeetingOrderTemplate; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmManDeviceDto; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmSkillDto; | |||
| import com.xueyi.system.api.digitalmans.domain.vo.DmBatchQuestionsVo; | |||
| import com.xueyi.system.api.digitalmans.feign.RemoteDigitalmanService; | |||
| import com.xueyi.system.api.digitalmans.feign.RemoteManDeviceService; | |||
| import com.xueyi.system.api.digitalmans.feign.RemoteQuestionanswersService; | |||
| import com.xueyi.system.api.digitalmans.feign.RemoteSkillService; | |||
| import com.xueyi.system.api.model.Source; | |||
| import com.xueyi.system.api.organize.domain.dto.SysEnterpriseDto; | |||
| import com.xueyi.system.api.organize.feign.RemoteEnterpriseService; | |||
| @@ -58,13 +61,10 @@ import java.io.IOException; | |||
| import java.io.Serializable; | |||
| import java.text.DateFormat; | |||
| import java.text.SimpleDateFormat; | |||
| import java.util.Arrays; | |||
| import java.util.*; | |||
| import java.time.Instant; | |||
| import java.time.LocalDateTime; | |||
| import java.time.ZoneId; | |||
| import java.util.Date; | |||
| import java.util.List; | |||
| import java.util.Map; | |||
| import java.util.regex.Matcher; | |||
| import java.util.regex.Pattern; | |||
| import java.util.concurrent.TimeUnit; | |||
| @@ -116,6 +116,9 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| @Autowired | |||
| private RemoteQuestionanswersService questionanswersService; | |||
| @Autowired | |||
| private RemoteSkillService remoteskillService; | |||
| @Autowired | |||
| RemoteEnterpriseService enterpriseService; | |||
| @@ -128,6 +131,8 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| @Autowired | |||
| RemoteDigitalmanService remoteDigitalmanService; | |||
| @Autowired | |||
| RemoteEnterpriseService remoteEnterpriseService; | |||
| @Autowired | |||
| private ElasticsearchClient esClient; | |||
| /** | |||
| @@ -201,6 +206,18 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| if (jo.containsKey("json") && StringUtils.isNotEmpty(jo.getString("json"))) { | |||
| String skillCode = jo.getJSONObject("json").getString("skillCode"); | |||
| intent.setSkillCode(skillCode); | |||
| R<List<DmSkillDto>> skilllistInner = remoteskillService.skilllistInner(intent.getDevId(),"1",manDeviceDtoR.getData().getTId(), source.getMaster(), SecurityConstants.INNER); | |||
| if(skilllistInner.isOk()){ | |||
| List<DmSkillDto> skilllist=skilllistInner.getData(); | |||
| for (DmSkillDto dmSkillDto : skilllist) { | |||
| if (dmSkillDto.getSkillCode().equals(skillCode)) { | |||
| if(dmSkillDto.getStatus().equals("0")){ | |||
| return AjaxResult.error(10001,"操作无权限"); | |||
| } | |||
| voResult.setMotion(dmSkillDto.getMotionName()); | |||
| } | |||
| } | |||
| } | |||
| voResult.setJsonFormat(jo.getJSONObject("json")); | |||
| voResult.setType("1"); | |||
| } | |||
| @@ -346,6 +363,13 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| joResult = freeChatTemplate.handle(intent.getDevId(),intent.getContent()); | |||
| return R.ok(joResult); | |||
| } | |||
| String enterpriseId = (String)SecurityContextHolder.getLocalMap().get("enterprise_id"); | |||
| String enterpriseName = ""; | |||
| R<SysEnterpriseDto> enterpriseDtoR = remoteEnterpriseService.getInfo(Long.valueOf(enterpriseId)); | |||
| if (enterpriseDtoR.isOk()) { | |||
| enterpriseName = enterpriseDtoR.getData().getName(); | |||
| } | |||
| // 获取设备号对应缓存 | |||
| CoversationSessionVo sessionObject = (CoversationSessionVo) redisTemplate2.opsForValue().get("group:device" + ":" + intent.getDevId() + ":" +"session"); //category | |||
| if (sessionObject != null) { | |||
| @@ -358,28 +382,39 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| if (StringUtils.isEmpty(intent.getSkillCode())) { | |||
| // 调用知识库问答 | |||
| AjaxResult qaAjax = searchQA(intent); | |||
| String content = ""; | |||
| if (qaAjax.toJson().containsKey("data") && StringUtils.isNotEmpty(qaAjax.toJson().getJSONObject("data").getJSONObject("format").getString("result"))) { | |||
| content = qaAjax.toJson().getJSONObject("data").getJSONObject("format").getJSONArray("result").getJSONObject(0).getJSONObject("knowledge_lib").toString(); | |||
| } | |||
| pushIntoDashboardRedis(enterpriseName,content,"knowledge"); | |||
| return R.ok(JSONObject.from(qaAjax.get("data"))); | |||
| } | |||
| SkillType.BOOK_MEETING_ROOM.getCode(); | |||
| // 判断skill code的值 | |||
| if (SkillType.BOOK_MEETING_ROOM.getCode().equals(intent.getSkillCode())) { | |||
| // 获取名称为"meeting-order"的BaseTemplate的实例 | |||
| redisTemplate.opsForValue().increment("dashboard:meeting", 1); | |||
| joResult = meetingOrderTemplate.handle(intent.getDevId(),intent.getContent(), Long.parseLong(SecurityContextHolder.getLocalMap().get("enterprise_id").toString())); | |||
| if (SkillType.BOOK_MEETING_ROOM.getCode().equals(intent.getSkillCode()) ) { | |||
| if (!redisTemplate2.hasKey("group:device" + ":" + intent.getDevId() + ":" +"session")) { | |||
| // 获取名称为"meeting-order"的BaseTemplate的实例 | |||
| redisTemplate.opsForValue().increment("dashboard:meeting", 1); | |||
| pushIntoDashboardRedis(enterpriseName, "会议室预定", "skill"); | |||
| } | |||
| joResult = meetingOrderTemplate.handle(intent.getDevId(), intent.getContent(), Long.parseLong(SecurityContextHolder.getLocalMap().get("enterprise_id").toString())); | |||
| } else if (SkillType.CREATE_VISITOR_INFO.getCode().equals(intent.getSkillCode())) { | |||
| // 访客预定 | |||
| redisTemplate.opsForValue().increment("dashboard:create_visitor_info", 1); | |||
| pushIntoDashboardRedis(enterpriseName,"访客邀约","skill"); | |||
| } else if (SkillType.REGISTER_VISITOR.getCode().equals(intent.getSkillCode())) { | |||
| // 访客登记 | |||
| redisTemplate.opsForValue().increment("dashboard:register_visitor", 1); | |||
| pushIntoDashboardRedis(enterpriseName,"陌生人登记","skill"); | |||
| } else if (SkillType.BROADCAST_DISPLAY.getCode().equals(intent.getSkillCode())) { | |||
| // 播报展示 | |||
| redisTemplate.opsForValue().increment("dashboard:broadcast_display", 1); | |||
| pushIntoDashboardRedis(enterpriseName,"播报展示","skill"); | |||
| } else if (SkillType.OPEN_DOOR.getCode().equals(intent.getSkillCode())) { | |||
| // 开门记录 | |||
| redisTemplate.opsForValue().increment("dashboard:open_door", 1); | |||
| pushIntoDashboardRedis(enterpriseName,"开门","skill"); | |||
| } | |||
| return R.ok(joResult); | |||
| } | |||
| @@ -580,6 +615,22 @@ public class DmIntentController extends BaseController<DmIntentQuery, DmIntentDt | |||
| return joResult; | |||
| } | |||
| private int pushIntoDashboardRedis(String name,String content,String type) { | |||
| try { | |||
| JSONObject object = new JSONObject(); | |||
| object.put("tenantName", name); | |||
| object.put("content", content); | |||
| if (type.equals("skill")) { | |||
| redisTemplate2.opsForList().leftPush("dashboard:skill-consume", object.toJSONString()); | |||
| } else if (type.equals("knowledge")) { | |||
| redisTemplate2.opsForList().leftPush("dashboard:knowledge-consume", object.toJSONString()); | |||
| } | |||
| return 1; | |||
| } catch (Exception e) { | |||
| log.error("推送到仪表盘失败:{}",e.getMessage()); | |||
| return 0; | |||
| } | |||
| } | |||
| interface Auth { | |||
| /** 系统 - 意图管理 | |||
| 管理 - 列表 */ | |||
| @@ -0,0 +1,40 @@ | |||
| package com.xueyi.nlt.nlt.domain; | |||
| import com.alibaba.fastjson2.JSONArray; | |||
| import lombok.Data; | |||
| import lombok.NoArgsConstructor; | |||
| import java.io.Serializable; | |||
| import java.util.ArrayList; | |||
| import java.util.List; | |||
| import java.util.stream.Collectors; | |||
| @Data | |||
| @NoArgsConstructor | |||
| public class LlmContext implements Serializable { | |||
| List<Context> contextList; | |||
| @Data | |||
| public class Context { | |||
| private String role; | |||
| private String content; | |||
| } | |||
| public LlmContext(String message) { | |||
| contextList = new ArrayList<>(); | |||
| Context ctx = new Context(); | |||
| ctx.setRole("user"); | |||
| ctx.setContent(message); | |||
| contextList.add(ctx); | |||
| } | |||
| public JSONArray toJson() { | |||
| //解释一下代码 | |||
| //1. contextList.stream() 生成一个流 | |||
| //2. collect(Collectors.toCollection(JSONArray::new)) 将流转换成JSONArray | |||
| return contextList.stream().collect(Collectors.toCollection(JSONArray::new)); | |||
| } | |||
| } | |||
| @@ -0,0 +1,12 @@ | |||
| package com.xueyi.nlt.nlt.domain; | |||
| import lombok.Data; | |||
| @Data | |||
| public class LlmParam { | |||
| protected Integer maxTokens; | |||
| protected Double temperature; | |||
| protected Integer topK; | |||
| } | |||
| @@ -0,0 +1,10 @@ | |||
| package com.xueyi.nlt.nlt.domain; | |||
| import lombok.Data; | |||
| @Data | |||
| public class LlmResponse { | |||
| protected String content; | |||
| protected Integer totalToken; | |||
| } | |||
| @@ -15,5 +15,6 @@ public class IntentTemplateVo { | |||
| private Integer target; | |||
| private String skillCode; | |||
| private JSONObject jsonFormat; | |||
| private String motion; | |||
| private String type ="0"; | |||
| } | |||
| @@ -0,0 +1,25 @@ | |||
| package com.xueyi.nlt.nlt.domain.vo; | |||
| import com.alibaba.fastjson2.JSONObject; | |||
| import lombok.Data; | |||
| import java.io.Serial; | |||
| import java.io.Serializable; | |||
| @Data | |||
| public class LlmQueryVo implements Serializable { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| protected Long id; | |||
| /** 调用模版 */ | |||
| protected String template; | |||
| /** 问题 */ | |||
| protected JSONObject format; | |||
| protected String answer; | |||
| /** 答案 */ | |||
| protected String question; | |||
| /** 评分 */ | |||
| protected Double score; | |||
| } | |||
| @@ -0,0 +1,19 @@ | |||
| package com.xueyi.nlt.nlt.domain.vo; | |||
| import lombok.Data; | |||
| import lombok.NoArgsConstructor; | |||
| @Data | |||
| @NoArgsConstructor | |||
| public class MeetingParamVo { | |||
| protected String name; | |||
| protected String content; | |||
| // 分钟 | |||
| protected Integer minute; | |||
| protected Integer hour; | |||
| protected Integer day; | |||
| protected Integer month; | |||
| protected Integer dayOfWeek; | |||
| protected Integer offset; | |||
| protected int[] compareArray; | |||
| } | |||
| @@ -0,0 +1,11 @@ | |||
| package com.xueyi.nlt.nlt.service; | |||
| import com.xueyi.nlt.nlt.domain.LlmContext; | |||
| import com.xueyi.nlt.nlt.domain.LlmParam; | |||
| import com.xueyi.nlt.nlt.domain.LlmResponse; | |||
| public interface ISysLlmService { | |||
| LlmResponse chat(LlmContext context, LlmParam param); | |||
| } | |||
| @@ -0,0 +1,44 @@ | |||
| package com.xueyi.nlt.nlt.service.impl; | |||
| import com.xueyi.nlt.netty.client.WebSocketClient; | |||
| import com.xueyi.nlt.nlt.domain.LlmContext; | |||
| import com.xueyi.nlt.nlt.domain.LlmParam; | |||
| import com.xueyi.nlt.nlt.domain.LlmResponse; | |||
| import com.xueyi.nlt.nlt.service.ISysLlmService; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.context.annotation.Primary; | |||
| import org.springframework.data.redis.core.StringRedisTemplate; | |||
| import org.springframework.stereotype.Service; | |||
| import java.util.List; | |||
| import java.util.stream.Collectors; | |||
| @Primary | |||
| @Service | |||
| public class SparkServiceImpl implements ISysLlmService { | |||
| @Autowired | |||
| WebSocketClient webSocketClient; | |||
| @Autowired | |||
| private StringRedisTemplate redisTemplate; | |||
| @Override | |||
| public LlmResponse chat(LlmContext context, LlmParam param) { | |||
| List<String> contentArr = context.getContextList().stream().map(LlmContext.Context::getContent).collect(Collectors.toList()); | |||
| synchronized (WebSocketClient.LOCK) { | |||
| webSocketClient.sendMsg(contentArr); | |||
| try { | |||
| WebSocketClient.LOCK.wait(); | |||
| } catch (InterruptedException e) { | |||
| e.printStackTrace(); | |||
| } | |||
| String result = redisTemplate.opsForValue().get("group:websocket:content"); | |||
| LlmResponse response = new LlmResponse(); | |||
| response.setContent(result); | |||
| return response; | |||
| } | |||
| } | |||
| } | |||
| @@ -5,6 +5,7 @@ import co.elastic.clients.elasticsearch._types.query_dsl.MatchQuery; | |||
| import co.elastic.clients.elasticsearch._types.query_dsl.Query; | |||
| import co.elastic.clients.elasticsearch.core.SearchResponse; | |||
| import co.elastic.clients.elasticsearch.core.search.Hit; | |||
| import com.alibaba.cloud.nacos.NacosConfigManager; | |||
| import com.alibaba.fastjson2.JSONArray; | |||
| import com.alibaba.fastjson2.JSONException; | |||
| import com.alibaba.fastjson2.JSONObject; | |||
| @@ -15,7 +16,13 @@ import com.xueyi.common.core.constant.digitalman.SkillConstants; | |||
| import com.xueyi.common.core.web.result.R; | |||
| import com.xueyi.nlt.api.nlt.domain.vo.CoversationSessionVo; | |||
| import com.xueyi.nlt.netty.client.WebSocketClient; | |||
| import com.xueyi.nlt.nlt.config.MeetingParam; | |||
| import com.xueyi.nlt.nlt.controller.DmIntentController; | |||
| import com.xueyi.nlt.nlt.domain.LlmContext; | |||
| import com.xueyi.nlt.nlt.domain.LlmParam; | |||
| import com.xueyi.nlt.nlt.domain.LlmResponse; | |||
| import com.xueyi.nlt.nlt.domain.vo.MeetingParamVo; | |||
| import com.xueyi.nlt.nlt.service.ISysLlmService; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmDigitalmanExtPo; | |||
| import com.xueyi.system.api.digitalmans.feign.RemoteDigitalmanService; | |||
| import com.xueyi.system.api.meeting.domain.dto.DmMeetingRoomsDto; | |||
| @@ -32,12 +39,17 @@ import org.springframework.data.redis.core.StringRedisTemplate; | |||
| import org.springframework.stereotype.Component; | |||
| import org.springframework.stereotype.Service; | |||
| import javax.annotation.PostConstruct; | |||
| import java.io.IOException; | |||
| import java.time.LocalDate; | |||
| import java.time.LocalDateTime; | |||
| import java.time.format.DateTimeFormatter; | |||
| import java.util.ArrayList; | |||
| import java.util.Arrays; | |||
| import java.util.List; | |||
| import java.util.concurrent.TimeUnit; | |||
| import java.util.regex.Matcher; | |||
| import java.util.regex.Pattern; | |||
| import java.util.stream.Collectors; | |||
| @@ -66,6 +78,74 @@ public class MeetingOrderTemplate implements BaseTemplate { | |||
| @Autowired | |||
| private ElasticsearchClient esClient; | |||
| @Autowired | |||
| NacosConfigManager nacosConfigManager; | |||
| @Autowired | |||
| private ISysLlmService sysLlmService; | |||
| private static final List<MeetingParamVo> MEETING_PARAMS = new ArrayList<>(); | |||
| @PostConstruct | |||
| private void init() { | |||
| try { | |||
| String meetingParams = nacosConfigManager.getConfigService().getConfig("meeting_date_and_hour", "DEFAULT_GROUP", 5000); | |||
| if (StringUtils.isNotBlank(meetingParams)) { | |||
| try { | |||
| MEETING_PARAMS.addAll(JSONArray.parseArray(meetingParams, MeetingParamVo.class)); | |||
| MEETING_PARAMS.forEach(item-> { | |||
| // 将item.getContent()按照空格分割成数组,然后将数组转换成流,最后将流转化成整数数组赋值给item.getCompareArray() | |||
| item.setCompareArray(Arrays.stream(item.getContent().split(" ")).mapToInt(Integer::parseInt).toArray()); | |||
| // item.setCompareArray(Arrays.stream(item.getContent().split(" "))); | |||
| String[] split = item.getContent().split(" "); | |||
| if (split != null && split.length > 0) { | |||
| int i =Integer.parseInt(split[0]); | |||
| if (i > -1) { | |||
| item.setMinute(i); | |||
| } else { | |||
| item.setMinute(-1); | |||
| } | |||
| i =Integer.parseInt(split[1]); | |||
| if (i > -1) { | |||
| item.setHour(i); | |||
| } else { | |||
| item.setHour(-1); | |||
| } | |||
| i =Integer.parseInt(split[2]); | |||
| if (i > -1) { | |||
| item.setDay(i); | |||
| } else { | |||
| item.setDay(-1); | |||
| } | |||
| i =Integer.parseInt(split[3]); | |||
| if (i > -1) { | |||
| item.setMonth(i); | |||
| } else { | |||
| item.setMonth(-1); | |||
| } | |||
| i =Integer.parseInt(split[4]); | |||
| if (i > -1) { | |||
| item.setDayOfWeek(i); | |||
| } else { | |||
| item.setDayOfWeek(-1); | |||
| } | |||
| i =Integer.parseInt(split[5]); | |||
| if (i > -1) { | |||
| item.setOffset(i); | |||
| } else { | |||
| item.setOffset(-1); | |||
| } | |||
| } | |||
| }); | |||
| } catch (JSONException e) { | |||
| log.error("解析会议参数失败", e); | |||
| } | |||
| } | |||
| } catch (Exception e) { | |||
| log.error("获取会议参数失败", e); | |||
| } | |||
| } | |||
| @Override | |||
| public JSONObject handle(String devId, String content,Long tenantId) { | |||
| LocalDateTime date = LocalDateTime.now(); | |||
| @@ -93,124 +173,80 @@ public class MeetingOrderTemplate implements BaseTemplate { | |||
| session.getFormat().put("skillCode",SkillConstants.SkillType.BOOK_MEETING_ROOM.getCode()); | |||
| } | |||
| synchronized (WebSocketClient.LOCK) { | |||
| // String prefix = "假设你是一位前台,你需要通过与其他人对话来获取会议相关信息,已知今天是" + | |||
| // date.format(formatter) + ",你需要获取会议日期,开始时间,持续时间,会议地点,会议主题。时间用类似00:00的格式输出。对方的话中可能不包含全部信息,对于未知的信息填充为none。如果所有信息都已知那么commit为true。否则为false。将你获得的信息输出为json格式。对方的话是:“"; | |||
| // String suffix = "”,只输出最后的json。输出只有一行,输出格式为{date:,start_time:,duration:,location:,theme:commit:}。"; | |||
| // remoteMeetingService.roomListInner() | |||
| // String prefix = "我想请你充当[企业前台], 已知现在是" + | |||
| // date.format(formatter) + "。我对你说:”"; | |||
| // String suffix = "”。会议地点:{" + "大会议室,小会议室" + "}。会议内容:{其他会议,例会,访客接待,面试}。未知的项目输出null。输出为{date:,start_time:,duration_hours:,location:,meeting_content:}"; | |||
| String prefix = "当前时间是"+ dateFormatter.format(date)+ " 00:00。我将提供一些用户输入的信息,请提取输入的内容进行结构化转换并输出对应 json 格式的代码。下面是结构的描述:date(格式为YYYY-MM-DD);start_time(格式HH:MM);location; 下面是用户的输入信息:开个会"; | |||
| String suffix = "\"。请开始信息提取,你回复的内容必须是一个json结构,如果没提取到的信息赋值为null,我不需要代码。"; | |||
| log.info(prefix + content + suffix); | |||
| LlmParam param = new LlmParam(); | |||
| LlmContext context = new LlmContext(prefix + content + suffix); | |||
| LlmResponse response = sysLlmService.chat(context,param); | |||
| // String prefix = "当前时间是" + | |||
| // date.format(formatter) + " " + date.getDayOfWeek() + "。我将提供一些用户输入的信息,请提取输入的内容进行结构化转换并输出对应 json 格式的代码。下面是结构的描述:会议日期date(格式为YYYY-MM-DD);具体时间start_time(格式HH:MM);会议室地点location; 下面是用户的输入信息:\""; | |||
| // String suffix = "\"。请开始信息提取,你回复的内容必须是一个json结构,我只要json结果,不需要代码。"; | |||
| // log.info(prefix + content + suffix); | |||
| webSocketClient.sendMsg(prefix + content + suffix); | |||
| try { | |||
| WebSocketClient.LOCK.wait(); | |||
| String result = redisTemplate.opsForValue().get("group:websocket:content"); | |||
| try { | |||
| //对result进行解析,获取字符串第一个与'{'和最后一个'}'之间的字符串,即为json字符串 | |||
| if (!result.contains("{") || !result.contains("}")) { | |||
| // 生成内容无效 | |||
| return session.getFormat(); | |||
| } | |||
| result = result.substring(result.indexOf("{"), result.lastIndexOf("}") + 1); | |||
| System.out.println(result); | |||
| JSONObject jo = JSONObject.parseObject(result); | |||
| String dateStr = jo.getString("date"); | |||
| String timeStr = jo.getString("start_time"); | |||
| String locationStr = jo.getString("location"); | |||
| if (StringUtils.isNotEmpty(locationStr)) { | |||
| roomListR.getData().forEach(item -> { | |||
| if(item.getName().equals(jo.get("location"))){ | |||
| jo.put("locationId",item.getId()); | |||
| } | |||
| }); | |||
| if (jo.get("locationId") != null) { | |||
| session.getFormat().put("location",locationStr); | |||
| session.getFormat().put("locationId",jo.get("locationId")); | |||
| } | |||
| } | |||
| //设置时间参数 | |||
| if (StringUtils.isNotEmpty(dateStr) && dateStr.split(":").length == 3) { | |||
| if (!jo.containsKey("locationId") || !session.getFormat().containsKey("date")) { | |||
| session.getFormat().put("date",dateStr); | |||
| } | |||
| } | |||
| if (StringUtils.isNotEmpty(timeStr) && !timeStr.equals("00:00")) { | |||
| //判断timeStr的格式是否是HH:mm | |||
| if (timeStr.split(":").length == 2) { | |||
| session.getFormat().put("start_time",timeStr); | |||
| } | |||
| String result = response.getContent(); | |||
| try { | |||
| //对result进行解析,获取字符串第一个与'{'和最后一个'}'之间的字符串,即为json字符串 | |||
| if (!result.contains("{") || !result.contains("}")) { | |||
| // 生成内容无效 | |||
| return session.getFormat(); | |||
| } | |||
| result = result.substring(result.indexOf("{"), result.lastIndexOf("}") + 1); | |||
| System.out.println(result); | |||
| JSONObject jo = JSONObject.parseObject(result); | |||
| String dateStr = jo.getString("date"); | |||
| String timeStr = jo.getString("start_time"); | |||
| String locationStr = jo.getString("location"); | |||
| if (StringUtils.isNotEmpty(locationStr)) { | |||
| roomListR.getData().forEach(item -> { | |||
| if(item.getName().equals(jo.get("location"))){ | |||
| jo.put("locationId",item.getId()); | |||
| } | |||
| }); | |||
| if (jo.get("locationId") != null) { | |||
| session.getFormat().put("location",locationStr); | |||
| session.getFormat().put("locationId",jo.get("locationId")); | |||
| } | |||
| } | |||
| //设置时间参数 | |||
| if (StringUtils.isNotEmpty(dateStr) && dateStr.split(":").length == 3) { | |||
| if (!jo.containsKey("locationId") || !session.getFormat().containsKey("date")) { | |||
| session.getFormat().put("date",dateStr); | |||
| } | |||
| // R<List<JSONObject>> recentListR = null; | |||
| // if (jo.get("start_time") != null ) { | |||
| // if (jo.get("start_time").equals("00:00")) { | |||
| // recentListR = remoteMeetingService.ableOrderList(devId, jo.getString("date"), null, null); | |||
| // } else { | |||
| // recentListR = remoteMeetingService.ableOrderList(devId, jo.getString("date"), null, jo.getString("start_time")); | |||
| // } | |||
| // if (recentListR.isOk()) { | |||
| // jo.put("start_time",recentListR.getData().get(0).get("startTime")); | |||
| // jo.put("location",recentListR.getData().get(0).get("roomId")); | |||
| // } | |||
| // } | |||
| // 判断内容是否击中es | |||
| CoversationSessionVo dateSession = processEsDate(content,session); | |||
| if (dateSession != null ){ | |||
| session = dateSession; | |||
| } | |||
| //判断会议室是否冲突,如果冲突,删除时间 | |||
| JSONObject checkObject = session.getFormat(); | |||
| if (checkObject.containsKey("date") && checkObject.containsKey("time") && checkObject.containsKey("location")) { | |||
| JSONObject ret = remoteMeetingService.queryExist(checkObject.getLong("locationId"), checkObject.getString("date"), checkObject.getString("time"),tenantId,source.getMaster(), SecurityConstants.INNER); | |||
| if (StringUtils.isNotEmpty(ret.getString("err"))) { | |||
| // 会议室冲突,删除时间 | |||
| session.getFormat().remove("time"); | |||
| } | |||
| } | |||
| // redis缓存更新session | |||
| objectRedisTemplate.opsForValue().set("group:device" + ":" + devId + ":" +"session", session, 1,TimeUnit.MINUTES); | |||
| session.getFormat().put("skillCode", SkillConstants.SkillType.BOOK_MEETING_ROOM.getCode()); | |||
| return session.getFormat(); | |||
| } catch (JSONException je) { | |||
| // 返回结果错误,计日志,存log,返回空结果 | |||
| log.error(je.getMessage(),je); | |||
| return null; | |||
| } | |||
| if (StringUtils.isNotEmpty(timeStr) && !timeStr.equals("00:00")) { | |||
| //判断timeStr的格式是否是HH:mm | |||
| if (timeStr.split(":").length == 2) { | |||
| session.getFormat().put("start_time",timeStr); | |||
| } | |||
| } catch (InterruptedException e) { | |||
| log.warn(e.getMessage()); | |||
| Thread.currentThread().interrupt(); | |||
| } | |||
| // JSONArray ja = new JSONArray(); | |||
| // R<List<JSONObject>> recentListR = null; | |||
| // recentListR = remoteMeetingService.ableOrderList(devId,null,null,null); | |||
| // if (recentListR.isOk()) { | |||
| // recentListR.getData().forEach(item->{ | |||
| // JSONObject tJson = new JSONObject(); | |||
| // tJson.put("start_time",item.get("startTime")); | |||
| // tJson.put("location",item.get("roomId")); | |||
| // tJson.put("date",item.get(("orderDate"))); | |||
| // tJson.put("duration_hours",0.5); | |||
| // ja.add(tJson); | |||
| // }); | |||
| // JSONObject result = new JSONObject(); | |||
| // result.put("data",ja); | |||
| // return result; | |||
| // } | |||
| // 判断内容是否击中es | |||
| // CoversationSessionVo dateSession = processEsDate(content,session); | |||
| // 判断内容是否击中正则 | |||
| CoversationSessionVo dateSession = processRegexDatetime(content,session); | |||
| if (dateSession != null ){ | |||
| session = dateSession; | |||
| } | |||
| //判断会议室是否冲突,如果冲突,删除时间 | |||
| JSONObject checkObject = session.getFormat(); | |||
| if (checkObject.containsKey("date") && checkObject.containsKey("time") && checkObject.containsKey("location")) { | |||
| JSONObject ret = remoteMeetingService.queryExist(checkObject.getLong("locationId"), checkObject.getString("date"), checkObject.getString("time"),tenantId,source.getMaster(), SecurityConstants.INNER); | |||
| if (StringUtils.isNotEmpty(ret.getString("err"))) { | |||
| // 会议室冲突,删除时间 | |||
| session.getFormat().remove("time"); | |||
| } | |||
| } | |||
| // redis缓存更新session | |||
| objectRedisTemplate.opsForValue().set("group:device" + ":" + devId + ":" +"session", session, 1,TimeUnit.MINUTES); | |||
| session.getFormat().put("skillCode", SkillConstants.SkillType.BOOK_MEETING_ROOM.getCode()); | |||
| return session.getFormat(); | |||
| } catch (JSONException je) { | |||
| // 返回结果错误,计日志,存log,返回空结果 | |||
| log.error(je.getMessage(),je); | |||
| return null; | |||
| } | |||
| return null; | |||
| } | |||
| private CoversationSessionVo processEsDate(String content,CoversationSessionVo session) { | |||
| LocalDateTime date = LocalDateTime.now(); | |||
| @@ -226,8 +262,7 @@ public class MeetingOrderTemplate implements BaseTemplate { | |||
| log.error("esClient search error", ie); | |||
| return null; | |||
| } | |||
| List<JSONObject> dates = dateResponse.hits().hits().stream().map(f->f.source()).collect( | |||
| Collectors.toList() | |||
| List<JSONObject> dates = dateResponse.hits().hits().stream().map(f->f.source()).collect(Collectors.toList() | |||
| ); | |||
| if (dates.size() > 0) { | |||
| Integer dateInt = date.getDayOfWeek().getValue(); | |||
| @@ -238,8 +273,405 @@ public class MeetingOrderTemplate implements BaseTemplate { | |||
| return session; | |||
| } | |||
| public CoversationSessionVo processRegexDatetime(String content,CoversationSessionVo session) { | |||
| List<Integer[]> timeList = new ArrayList<>(); | |||
| MEETING_PARAMS.forEach(item-> { | |||
| if (content.matches(item.getName())) { | |||
| int[] tmp = item.getCompareArray(); | |||
| // 将int[]转化成Integer[] | |||
| Integer[] tmpInteger = new Integer[tmp.length]; | |||
| for (int i = 0; i < tmp.length; i++) { | |||
| tmpInteger[i] = tmp[i]; | |||
| } | |||
| timeList.add(tmpInteger); | |||
| } | |||
| }); | |||
| if (timeList.size() == 0) { | |||
| //没有匹配正则,返回 | |||
| return session; | |||
| } | |||
| Integer results[] = new Integer[6]; | |||
| // 计算二维矩阵每列最大值 | |||
| for (Integer[] item : timeList) { | |||
| for (int i = 0; i < item.length; i++) { | |||
| if (results[i] == null) { | |||
| results[i] = item[i]; | |||
| } else { | |||
| if (results[i] < item[i]) { | |||
| results[i] = item[i]; | |||
| } | |||
| } | |||
| } | |||
| } | |||
| if (results[1] > 0) { | |||
| LocalDateTime date = LocalDateTime.now(); | |||
| DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("HH:mm"); | |||
| date = date.withMinute(results[0]).withHour(results[1]); | |||
| session.getFormat().put("start_time",dateFormatter.format(date)); | |||
| } | |||
| if (results[2] > 0) { | |||
| DateTimeFormatter resultDateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd"); | |||
| DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"); | |||
| if (!session.getFormat().containsKey("date")) { | |||
| session.getFormat().put("date",resultDateFormatter.format(LocalDateTime.now())); | |||
| } | |||
| LocalDateTime date = LocalDateTime.parse(session.getFormat().getString("date") + " 00:00:00",DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")); | |||
| date = date.withDayOfMonth(results[2]); | |||
| if (results[3] > 0) { | |||
| date = date.withMonth(results[3]); | |||
| } | |||
| session.getFormat().put("date",resultDateFormatter.format(date)); | |||
| } | |||
| if (results[4] > 0) { | |||
| LocalDateTime date = LocalDateTime.now(); | |||
| DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd"); | |||
| int offset = results[4] - date.getDayOfWeek().getValue(); | |||
| date = date.plusDays(offset); | |||
| session.getFormat().put("date",dateFormatter.format(date)); | |||
| } | |||
| if (results[5] >= 0) { | |||
| LocalDateTime date = LocalDateTime.now();; | |||
| DateTimeFormatter dateFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd"); | |||
| date = date.plusDays(results[5]); | |||
| session.getFormat().put("date",dateFormatter.format(date)); | |||
| } | |||
| return session; | |||
| } | |||
| @Override | |||
| public JSONObject handle(String dev, String content) { | |||
| return null; | |||
| } | |||
| /** | |||
| * 一个用来匹配日期与时间的正则表达式的方法 | |||
| */ | |||
| private static String matchDate(String content) { | |||
| String regex = "(\\d{4})[-|\\/|年](\\d{1,2})[-|\\/|月](\\d{1,2})[日|号]?\\s*(\\d{1,2})[:|时](\\d{1,2})[:|分]?"; | |||
| Pattern pattern = Pattern.compile(regex); | |||
| Matcher matcher = pattern.matcher(content); | |||
| if (matcher.find()) { | |||
| return matcher.group(); | |||
| } | |||
| return null; | |||
| } | |||
| public static void main(String[] args) { | |||
| String regex = "(\\d{4})[-|\\/|年](\\d{1,2})[-|\\/|月](\\d{1,2})[日|号]?\\s*(\\d{1,2})[:|时](\\d{1,2})[:|分]?"; | |||
| String regexStr = "[\n" + | |||
| " {\"name\":\".*周一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*周二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*周三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*周四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*周五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*周六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*周七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*周日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*周天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这周一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*这周二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*这周三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*这周四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*这周五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*这周六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*这周七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这周日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这周天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本周一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*本周二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*本周三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*本周四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*本周五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*本周六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*本周七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本周日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本周天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*下周一.*\",\"content\":\"-1 -1 -1 -1 8 -1\"},\n" + | |||
| " {\"name\":\".*下周二.*\",\"content\":\"-1 -1 -1 -1 9 -1\"},\n" + | |||
| " {\"name\":\".*下周三.*\",\"content\":\"-1 -1 -1 -1 10 -1\"},\n" + | |||
| " {\"name\":\".*下周四.*\",\"content\":\"-1 -1 -1 -1 11 -1\"},\n" + | |||
| " {\"name\":\".*下周五.*\",\"content\":\"-1 -1 -1 -1 12 -1\"},\n" + | |||
| " {\"name\":\".*下周六.*\",\"content\":\"-1 -1 -1 -1 13 -1\"},\n" + | |||
| " {\"name\":\".*下周七.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下周日.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下周天.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下下周一.*\",\"content\":\"-1 -1 -1 -1 15 -1\"},\n" + | |||
| " {\"name\":\".*下下周二.*\",\"content\":\"-1 -1 -1 -1 16 -1\"},\n" + | |||
| " {\"name\":\".*下下周三.*\",\"content\":\"-1 -1 -1 -1 17 -1\"},\n" + | |||
| " {\"name\":\".*下下周四.*\",\"content\":\"-1 -1 -1 -1 18 -1\"},\n" + | |||
| " {\"name\":\".*下下周五.*\",\"content\":\"-1 -1 -1 -1 19 -1\"},\n" + | |||
| " {\"name\":\".*下下周六.*\",\"content\":\"-1 -1 -1 -1 20 -1\"},\n" + | |||
| " {\"name\":\".*下下周七.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下周日.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下周天.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*星期一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*星期二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*星期三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*星期四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*星期五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*星期六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*星期七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*星期日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*星期天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这星期一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*这星期二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*这星期三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*这星期四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*这星期五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*这星期六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*这星期七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这星期日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这星期天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本星期一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*本星期二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*本星期三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*本星期四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*本星期五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*本星期六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*本星期七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本星期日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本星期天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*下星期一.*\",\"content\":\"-1 -1 -1 -1 8 -1\"},\n" + | |||
| " {\"name\":\".*下星期二.*\",\"content\":\"-1 -1 -1 -1 9 -1\"},\n" + | |||
| " {\"name\":\".*下星期三.*\",\"content\":\"-1 -1 -1 -1 10 -1\"},\n" + | |||
| " {\"name\":\".*下星期四.*\",\"content\":\"-1 -1 -1 -1 11 -1\"},\n" + | |||
| " {\"name\":\".*下星期五.*\",\"content\":\"-1 -1 -1 -1 12 -1\"},\n" + | |||
| " {\"name\":\".*下星期六.*\",\"content\":\"-1 -1 -1 -1 13 -1\"},\n" + | |||
| " {\"name\":\".*下星期七.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下星期日.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下星期天.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下下星期一.*\",\"content\":\"-1 -1 -1 -1 15 -1\"},\n" + | |||
| " {\"name\":\".*小下星期二.*\",\"content\":\"-1 -1 -1 -1 16 -1\"},\n" + | |||
| " {\"name\":\".*下下星期三.*\",\"content\":\"-1 -1 -1 -1 17 -1\"},\n" + | |||
| " {\"name\":\".*下下星期四.*\",\"content\":\"-1 -1 -1 -1 18 -1\"},\n" + | |||
| " {\"name\":\".*下下星期五.*\",\"content\":\"-1 -1 -1 -1 19 -1\"},\n" + | |||
| " {\"name\":\".*下下星期六.*\",\"content\":\"-1 -1 -1 -1 20 -1\"},\n" + | |||
| " {\"name\":\".*下下星期七.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下星期日.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下星期天.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*礼拜一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*礼拜二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*礼拜三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*礼拜四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*礼拜五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*礼拜六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*礼拜七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*礼拜日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*礼拜天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*这礼拜天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜一.*\",\"content\":\"-1 -1 -1 -1 1 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜二.*\",\"content\":\"-1 -1 -1 -1 2 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜三.*\",\"content\":\"-1 -1 -1 -1 3 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜四.*\",\"content\":\"-1 -1 -1 -1 4 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜五.*\",\"content\":\"-1 -1 -1 -1 5 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜六.*\",\"content\":\"-1 -1 -1 -1 6 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜七.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜日.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*本礼拜天.*\",\"content\":\"-1 -1 -1 -1 7 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜一.*\",\"content\":\"-1 -1 -1 -1 8 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜二.*\",\"content\":\"-1 -1 -1 -1 9 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜三.*\",\"content\":\"-1 -1 -1 -1 10 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜四.*\",\"content\":\"-1 -1 -1 -1 11 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜五.*\",\"content\":\"-1 -1 -1 -1 12 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜六.*\",\"content\":\"-1 -1 -1 -1 13 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜七.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜日.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下礼拜天.*\",\"content\":\"-1 -1 -1 -1 14 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜一.*\",\"content\":\"-1 -1 -1 -1 15 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜二.*\",\"content\":\"-1 -1 -1 -1 16 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜三.*\",\"content\":\"-1 -1 -1 -1 17 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜四.*\",\"content\":\"-1 -1 -1 -1 18 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜五.*\",\"content\":\"-1 -1 -1 -1 19 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜六.*\",\"content\":\"-1 -1 -1 -1 20 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜七.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜日.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*下下礼拜天.*\",\"content\":\"-1 -1 -1 -1 21 -1\"},\n" + | |||
| " {\"name\":\".*今天.*\",\"content\":\"-1 -1 -1 -1 -1 0\"},\n" + | |||
| " {\"name\":\".*明天.*\",\"content\":\"-1 -1 -1 -1 -1 1\"},\n" + | |||
| " {\"name\":\".*后天.*\",\"content\":\"-1 -1 -1 -1 -1 2\"},\n" + | |||
| " {\"name\":\".*大后天.*\",\"content\":\"-1 -1 -1 -1 -1 3\"},\n" + | |||
| " {\"name\":\".*1月.*\",\"content\":\"-1 -1 -1 1 -1 -1\"},\n" + | |||
| " {\"name\":\".*2月.*\",\"content\":\"-1 -1 -1 2 -1 -1\"},\n" + | |||
| " {\"name\":\".*3月.*\",\"content\":\"-1 -1 -1 3 -1 -1\"},\n" + | |||
| " {\"name\":\".*4月.*\",\"content\":\"-1 -1 -1 4 -1 -1\"},\n" + | |||
| " {\"name\":\".*5月.*\",\"content\":\"-1 -1 -1 5 -1 -1\"},\n" + | |||
| " {\"name\":\".*6月.*\",\"content\":\"-1 -1 -1 6 -1 -1\"},\n" + | |||
| " {\"name\":\".*7月.*\",\"content\":\"-1 -1 -1 7 -1 -1\"},\n" + | |||
| " {\"name\":\".*8月.*\",\"content\":\"-1 -1 -1 8 -1 -1\"},\n" + | |||
| " {\"name\":\".*9月.*\",\"content\":\"-1 -1 -1 9 -1 -1\"},\n" + | |||
| " {\"name\":\".*10月.*\",\"content\":\"-1 -1 -1 10 -1 -1\"},\n" + | |||
| " {\"name\":\".*11月.*\",\"content\":\"-1 -1 -1 11 -1 -1\"},\n" + | |||
| " {\"name\":\".*12月.*\",\"content\":\"-1 -1 -1 12 -1 -1\"},\n" + | |||
| " {\"name\":\".*1日.*\",\"content\":\"-1 -1 1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*2日.*\",\"content\":\"-1 -1 2 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*3日.*\",\"content\":\"-1 -1 3 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*4日.*\",\"content\":\"-1 -1 4 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*5日.*\",\"content\":\"-1 -1 5 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*6日.*\",\"content\":\"-1 -1 6 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*7日.*\",\"content\":\"-1 -1 7 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*8日.*\",\"content\":\"-1 -1 8 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*9日.*\",\"content\":\"-1 -1 9 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*10日.*\",\"content\":\"-1 -1 10 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*11日.*\",\"content\":\"-1 -1 11 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*12日.*\",\"content\":\"-1 -1 12 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*13日.*\",\"content\":\"-1 -1 13 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*14日.*\",\"content\":\"-1 -1 14 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*15日.*\",\"content\":\"-1 -1 15 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*16日.*\",\"content\":\"-1 -1 16 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*17日.*\",\"content\":\"-1 -1 17 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*18日.*\",\"content\":\"-1 -1 18 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*19日.*\",\"content\":\"-1 -1 19 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*20日.*\",\"content\":\"-1 -1 20 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*21日.*\",\"content\":\"-1 -1 21 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*22日.*\",\"content\":\"-1 -1 22 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*23日.*\",\"content\":\"-1 -1 23 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*24日.*\",\"content\":\"-1 -1 24 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*25日.*\",\"content\":\"-1 -1 25 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*26日.*\",\"content\":\"-1 -1 26 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*27日.*\",\"content\":\"-1 -1 27 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*28日.*\",\"content\":\"-1 -1 28 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*29日.*\",\"content\":\"-1 -1 29 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*30日.*\",\"content\":\"-1 -1 30 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*31日.*\",\"content\":\"-1 -1 31 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*1号.*\",\"content\":\"-1 -1 1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*2号.*\",\"content\":\"-1 -1 2 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*3号.*\",\"content\":\"-1 -1 3 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*4号.*\",\"content\":\"-1 -1 4 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*5号.*\",\"content\":\"-1 -1 5 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*6号.*\",\"content\":\"-1 -1 6 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*7号.*\",\"content\":\"-1 -1 7 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*8号.*\",\"content\":\"-1 -1 8 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*9号.*\",\"content\":\"-1 -1 9 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*10号.*\",\"content\":\"-1 -1 10 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*11号.*\",\"content\":\"-1 -1 11 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*12号.*\",\"content\":\"-1 -1 12 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*13号.*\",\"content\":\"-1 -1 13 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*14号.*\",\"content\":\"-1 -1 14 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*15号.*\",\"content\":\"-1 -1 15 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*16号.*\",\"content\":\"-1 -1 16 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*17号.*\",\"content\":\"-1 -1 17 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*18号.*\",\"content\":\"-1 -1 18 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*19号.*\",\"content\":\"-1 -1 19 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*20号.*\",\"content\":\"-1 -1 20 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*21号.*\",\"content\":\"-1 -1 21 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*22号.*\",\"content\":\"-1 -1 22 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*23号.*\",\"content\":\"-1 -1 23 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*24号.*\",\"content\":\"-1 -1 24 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*25号.*\",\"content\":\"-1 -1 25 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*26号.*\",\"content\":\"-1 -1 26 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*27号.*\",\"content\":\"-1 -1 27 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*28号.*\",\"content\":\"-1 -1 28 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*29号.*\",\"content\":\"-1 -1 29 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*30号.*\",\"content\":\"-1 -1 30 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*31号.*\",\"content\":\"-1 -1 31 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*8点.*\",\"content\":\"0 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*9点.*\",\"content\":\"0 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*10点.*\",\"content\":\"0 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*11点.*\",\"content\":\"0 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*12点.*\",\"content\":\"0 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*13点.*\",\"content\":\"0 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*14点.*\",\"content\":\"0 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*15点.*\",\"content\":\"0 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*16点.*\",\"content\":\"0 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*17点.*\",\"content\":\"0 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*18点.*\",\"content\":\"0 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*19点.*\",\"content\":\"0 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午8点.*\",\"content\":\"0 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午9点.*\",\"content\":\"0 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午10点.*\",\"content\":\"0 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午11点.*\",\"content\":\"0 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午12点.*\",\"content\":\"0 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上8点.*\",\"content\":\"0 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上9点.*\",\"content\":\"0 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上10点.*\",\"content\":\"0 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上11点.*\",\"content\":\"0 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上12点.*\",\"content\":\"0 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午1点.*\",\"content\":\"0 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午2点.*\",\"content\":\"0 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午3点.*\",\"content\":\"0 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午4点.*\",\"content\":\"0 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午5点.*\",\"content\":\"0 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午6点.*\",\"content\":\"0 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午7点.*\",\"content\":\"0 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*晚上6点.*\",\"content\":\"0 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*晚上7点.*\",\"content\":\"0 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*8点半.*\",\"content\":\"30 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*9点半.*\",\"content\":\"300 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*10点半.*\",\"content\":\"30 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*11点半.*\",\"content\":\"30 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*12点半.*\",\"content\":\"30 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*13点半.*\",\"content\":\"30 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*14点半.*\",\"content\":\"30 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*15点半.*\",\"content\":\"30 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*16点半.*\",\"content\":\"30 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*17点半.*\",\"content\":\"30 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*18点半.*\",\"content\":\"30 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*19点半.*\",\"content\":\"30 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午8点半.*\",\"content\":\"30 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午9点半.*\",\"content\":\"30 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午10点半.*\",\"content\":\"30 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午11点半.*\",\"content\":\"30 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*上午12点半.*\",\"content\":\"30 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上8点半.*\",\"content\":\"30 8 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上9点半.*\",\"content\":\"30 9 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上10点半.*\",\"content\":\"30 10 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上11点半.*\",\"content\":\"30 11 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*早上12点半.*\",\"content\":\"30 12 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午1点半.*\",\"content\":\"30 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午2点半.*\",\"content\":\"30 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午3点半.*\",\"content\":\"30 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午4点半.*\",\"content\":\"30 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午5点半.*\",\"content\":\"30 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午6点半.*\",\"content\":\"30 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*下午7点半.*\",\"content\":\"30 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*晚上6点半.*\",\"content\":\"30 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*晚上7点半.*\",\"content\":\"30 19 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*[^1]1点.*\",\"content\":\"-1 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*[^1]2点.*\",\"content\":\"-1 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*3点.*\",\"content\":\"0 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*4点.*\",\"content\":\"0 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*5点.*\",\"content\":\"0 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*6点.*\",\"content\":\"0 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*[^1]1点半.*\",\"content\":\"30 13 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*[^1]2点半.*\",\"content\":\"30 14 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*3点半.*\",\"content\":\"30 15 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*4点半.*\",\"content\":\"30 16 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*5点半.*\",\"content\":\"30 17 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*6点半.*\",\"content\":\"30 18 -1 -1 -1 -1\"},\n" + | |||
| " {\"name\":\".*待会.*\",\"content\":\"-1 -1 -1 -1 -1 0\"},\n" + | |||
| " {\"name\":\".*一会.*\",\"content\":\"-1 -1 -1 -1 -1 0\"},\n" + | |||
| " {\"name\":\".*马上.*\",\"content\":\"-1 -1 -1 -1 -1 0\"},\n" + | |||
| " {\"name\":\".*立刻.*\",\"content\":\"-1 -1 -1 -1 -1 0\"},\n" + | |||
| " {\"name\":\".*现在.*\",\"content\":\"-1 -1 -1 -1 -1 0\"}\n" + | |||
| "]"; | |||
| MEETING_PARAMS.addAll(JSONArray.parseArray(regexStr, MeetingParamVo.class)); | |||
| MEETING_PARAMS.forEach(item-> { | |||
| // 将item.getContent()按照空格分割成数组,然后将数组转换成流,最后将流转化成整数数组赋值给item.getCompareArray() | |||
| item.setCompareArray(Arrays.stream(item.getContent().split(" ")).mapToInt(Integer::parseInt).toArray()); | |||
| }); | |||
| String content = "下午2点"; | |||
| CoversationSessionVo sessionVo = new CoversationSessionVo(); | |||
| sessionVo.setCategory("meeting"); | |||
| sessionVo.setId("1234567890"); | |||
| JSONObject jsonObject = new JSONObject(); | |||
| jsonObject.put("date","2023-09-18"); | |||
| jsonObject.put("start_time","12:00"); | |||
| jsonObject.put("location","大会议室"); | |||
| sessionVo.setFormat(jsonObject); | |||
| MeetingOrderTemplate template = new MeetingOrderTemplate(); | |||
| System.out.println(template.processRegexDatetime(content,sessionVo)); | |||
| } | |||
| } | |||
| @@ -15,6 +15,7 @@ import com.xueyi.common.core.web.validate.V_E; | |||
| import com.xueyi.common.datasource.annotation.Master; | |||
| import com.xueyi.common.log.annotation.Log; | |||
| import com.xueyi.common.log.enums.BusinessType; | |||
| import com.xueyi.common.redis.utils.RedisUtil; | |||
| import com.xueyi.common.security.annotation.InnerAuth; | |||
| import com.xueyi.common.security.annotation.RequiresPermissions; | |||
| import com.xueyi.common.web.entity.controller.BaseController; | |||
| @@ -66,6 +67,7 @@ import org.springframework.web.bind.annotation.RestController; | |||
| import java.io.Serializable; | |||
| import java.text.ParseException; | |||
| import java.time.Duration; | |||
| import java.util.ArrayList; | |||
| import java.util.Date; | |||
| import java.util.List; | |||
| import java.util.stream.Collectors; | |||
| @@ -399,57 +401,66 @@ public class DmDigitalmanController extends BaseController<DmDigitalmanQuery, Dm | |||
| List<DmManDeviceDto> dtos = dmManDeviceService.selectList(new DmManDeviceQuery()); | |||
| List<DmManDeviceDto> dtos2 = dtos.stream().filter(dto -> StringUtils.isNotEmpty(dto.getDeviceId())).collect(Collectors.toList());; | |||
| System.err.println(dtos2.size()); | |||
| Long serviceTimeCount = 0L; | |||
| //当前时间和activateTime时间的差值,activateTime类型是Date,差值返回的单位是小时 | |||
| for (DmManDeviceDto dto : dtos2) { | |||
| serviceTimeCount += (System.currentTimeMillis() - dto.getActivateTime().getTime())/3600000; | |||
| } | |||
| Integer meetingServiceCount = (Integer) redisTemplate.opsForValue().get("dashboard:meeting"); | |||
| Integer serverTimes = (Integer) redisTemplate.opsForValue().get("dashboard:server"); | |||
| Integer recognition = (Integer) redisTemplate.opsForValue().get("dashboard:recognition"); | |||
| Integer receptionCount = (Integer) redisTemplate.opsForValue().get("dashboard:create_visitor_info"); | |||
| Integer visitorCount = (Integer) redisTemplate.opsForValue().get("dashboard:register_visitor"); | |||
| Integer attendanceCount = (Integer) redisTemplate.opsForValue().get("dashboard:attendance"); | |||
| Integer openDoorCount = (Integer) redisTemplate.opsForValue().get("dashboard:open_door"); | |||
| Integer conversationDuration = (Integer) redisTemplate.opsForValue().get("dashboard:conversation-duration"); | |||
| Integer conversationTimes = (Integer) redisTemplate.opsForValue().get("dashboard:conversation-times"); | |||
| Integer meetingServiceCount = RedisUtil.getNumberVal("dashboard:meeting"); | |||
| Integer serverTimes = RedisUtil.getNumberVal("dashboard:server"); | |||
| Integer recognition = RedisUtil.getNumberVal("dashboard:recognition"); | |||
| Integer receptionCount = RedisUtil.getNumberVal("dashboard:create_visitor_info"); | |||
| Integer visitorCount = RedisUtil.getNumberVal("dashboard:register_visitor"); | |||
| Integer attendanceCount = RedisUtil.getNumberVal("dashboard:attendance"); | |||
| Integer openDoorCount = RedisUtil.getNumberVal("dashboard:open_door"); | |||
| Integer conversationDuration = RedisUtil.getNumberVal("dashboard:conversation-duration"); | |||
| Integer conversationTimes = RedisUtil.getNumberVal("dashboard:conversation-times"); | |||
| Integer broadcastCount = RedisUtil.getNumberVal("dashboard:broadcast-count"); | |||
| List<JSONObject> knowledgeList = new ArrayList<>(); | |||
| if (RedisUtil.existed("dashboard:knowledge-consume")) { | |||
| knowledgeList = RedisUtil.getJsonList("dashboard:knowledge-consume"); | |||
| //取值后清除缓存list,5秒后过期 | |||
| RedisUtil.expire("dashboard:knowledge-consume", 5); | |||
| } | |||
| List<JSONObject> skillList = new ArrayList<>(); | |||
| if (RedisUtil.existed("dashboard:skill-consume")) { | |||
| skillList = RedisUtil.getJsonList("dashboard:skill-consume"); | |||
| //取值后清除缓存list,5秒后过期 | |||
| RedisUtil.expire("dashboard:skill-consume", 5); | |||
| } | |||
| JSONArray jsonArray = new JSONArray(); | |||
| // JSONArray jsonArray2 = new JSONArray(); | |||
| for (int i = 0; i < 7; i++) { | |||
| // 最近三十天的数据,服务人次,知识库增量 | |||
| for (int i = 0; i < 30; i++) { | |||
| Date date = DateUtils.addDays(new Date(), -i); | |||
| String dateStr2 = DateUtils.formatDate(date, "yyyy-MM-dd"); | |||
| JSONObject json2 = new JSONObject(); | |||
| json2.put("date", dateStr2); | |||
| json2.put("serviceTimes", (Integer) redisTemplate.opsForValue().get("dashboard:server-chart:"+dateStr2)); | |||
| json2.put("knowledgeNums", (Integer) redisTemplate.opsForValue().get("dashboard:server-chart:"+dateStr2)); | |||
| json2.put("serviceTimes", RedisUtil.getNumberVal("dashboard:server-chart:"+dateStr2)); | |||
| json2.put("knowledgeNums", RedisUtil.getNumberVal("dashboard:server-chart:"+dateStr2)); | |||
| jsonArray.add(json2); | |||
| } | |||
| log.info("meetingServiceCount:{}",meetingServiceCount); | |||
| log.info("serverTimes:{}",serverTimes); | |||
| log.info("recognition:{}",recognition); | |||
| log.info("receptionCount:{}",receptionCount); | |||
| log.info("visitorCount:{}",visitorCount); | |||
| log.info("attendanceCount:{}",attendanceCount); | |||
| log.info("openDoorCount:{}",openDoorCount); | |||
| log.info("chatDurationCount:{}",conversationDuration); | |||
| log.info("chatTimes:{}",conversationTimes); | |||
| log.info("serverCharts:{}",jsonArray.toJSONString()); | |||
| JSONObject json = new JSONObject(); | |||
| json.put("manCount",dtos2.size()); | |||
| json.put("chatTimes",conversationTimes); | |||
| json.put("chatDurationCount",conversationDuration); | |||
| json.put("serviceTimeCount",serviceTimeCount); | |||
| json.put("servicePerCount",serverTimes); | |||
| json.put("recognizedPersonCount",recognition); | |||
| json.put("meetingServiceCount",meetingServiceCount); | |||
| json.put("receptionCount",receptionCount); | |||
| json.put("visitorCount",visitorCount); | |||
| json.put("attendanceCount",attendanceCount); | |||
| json.put("openDoorCount",openDoorCount); | |||
| json.put("serverCharts",jsonArray); | |||
| json.put("manCount",dtos2.size());//数字人数 | |||
| json.put("recognizedPersonCount", recognition);//注册人员总数 | |||
| json.put("serviceTimeCount",serviceTimeCount);//总服务时间 | |||
| json.put("chatTimes",conversationTimes);//对话次数 | |||
| json.put("chatDurationCount",conversationDuration);//对话时长 | |||
| json.put("servicePerCount",serverTimes);//用户使用频次?改成服务人次 | |||
| json.put("serviceTotal",meetingServiceCount+receptionCount+visitorCount+attendanceCount+openDoorCount+broadcastCount); | |||
| json.put("meetingServiceCount", meetingServiceCount);//会议 | |||
| json.put("receptionCount",receptionCount);//接待 | |||
| json.put("visitorCount",visitorCount);//访客 | |||
| json.put("attendanceCount",attendanceCount);//考勤 | |||
| json.put("openDoorCount",openDoorCount);//门禁 | |||
| json.put("broadcastCount",broadcastCount);//播报 | |||
| json.put("knowledgeConsume",knowledgeList);//实时知识库调用 | |||
| json.put("skillConsume",skillList);//实时技能调用 | |||
| json.put("serverCharts",jsonArray);// | |||
| log.info(json.toJSONString()); | |||
| return R.ok(json); | |||
| } | |||
| @@ -0,0 +1,122 @@ | |||
| package com.xueyi.system.digitalmans.controller; | |||
| import com.xueyi.common.core.web.result.AjaxResult; | |||
| import com.xueyi.common.core.web.validate.V_A; | |||
| import com.xueyi.common.core.web.validate.V_E; | |||
| import com.xueyi.common.log.annotation.Log; | |||
| import com.xueyi.common.log.enums.BusinessType; | |||
| import com.xueyi.common.security.annotation.Logical; | |||
| import com.xueyi.common.security.annotation.RequiresPermissions; | |||
| import com.xueyi.common.web.entity.controller.BaseController; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.system.digitalmans.service.IDmScreenIconService; | |||
| import org.springframework.validation.annotation.Validated; | |||
| import org.springframework.web.bind.annotation.*; | |||
| import java.io.Serializable; | |||
| import java.util.List; | |||
| /** | |||
| * 数字人主界面图标管理 业务处理 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @RestController | |||
| @RequestMapping("/screenIcon") | |||
| public class DmScreenIconController extends BaseController<DmScreenIconQuery, DmScreenIconDto, IDmScreenIconService> { | |||
| /** 定义节点名称 */ | |||
| @Override | |||
| protected String getNodeName() { | |||
| return "数字人主界面图标" ; | |||
| } | |||
| /** | |||
| * 查询数字人主界面图标列表 | |||
| */ | |||
| @Override | |||
| @GetMapping("/list") | |||
| @RequiresPermissions(Auth.DM_SCREEN_ICON_LIST) | |||
| public AjaxResult list(DmScreenIconQuery screenIcon) { | |||
| return super.list(screenIcon); | |||
| } | |||
| /** | |||
| * 查询数字人主界面图标详细 | |||
| */ | |||
| @Override | |||
| @GetMapping(value = "/{id}") | |||
| @RequiresPermissions(Auth.DM_SCREEN_ICON_SINGLE) | |||
| public AjaxResult getInfo(@PathVariable Serializable id) { | |||
| return super.getInfo(id); | |||
| } | |||
| /** | |||
| * 数字人主界面图标新增 | |||
| */ | |||
| @Override | |||
| @PostMapping | |||
| @RequiresPermissions(Auth.DM_SCREEN_ICON_ADD) | |||
| @Log(title = "数字人主界面图标管理", businessType = BusinessType.INSERT) | |||
| public AjaxResult add(@Validated({V_A.class}) @RequestBody DmScreenIconDto screenIcon) { | |||
| return super.add(screenIcon); | |||
| } | |||
| /** | |||
| * 数字人主界面图标修改 | |||
| */ | |||
| @Override | |||
| @PutMapping | |||
| @RequiresPermissions(Auth.DM_SCREEN_ICON_EDIT) | |||
| @Log(title = "数字人主界面图标管理", businessType = BusinessType.UPDATE) | |||
| public AjaxResult edit(@Validated({V_E.class}) @RequestBody DmScreenIconDto screenIcon) { | |||
| return super.edit(screenIcon); | |||
| } | |||
| /** | |||
| * 数字人主界面图标修改状态 | |||
| */ | |||
| @Override | |||
| @PutMapping("/status") | |||
| @RequiresPermissions(value = {Auth.DM_SCREEN_ICON_EDIT, Auth.DM_SCREEN_ICON_ES}, logical = Logical.OR) | |||
| @Log(title = "数字人主界面图标管理", businessType = BusinessType.UPDATE_STATUS) | |||
| public AjaxResult editStatus(@RequestBody DmScreenIconDto screenIcon) { | |||
| return super.editStatus(screenIcon); | |||
| } | |||
| /** | |||
| * 数字人主界面图标批量删除 | |||
| */ | |||
| @Override | |||
| @DeleteMapping("/batch/{idList}") | |||
| @RequiresPermissions(Auth.DM_SCREEN_ICON_DEL) | |||
| @Log(title = "数字人主界面图标管理", businessType = BusinessType.DELETE) | |||
| public AjaxResult batchRemove(@PathVariable List<Long> idList) { | |||
| return super.batchRemove(idList); | |||
| } | |||
| /** | |||
| * 获取数字人主界面图标选择框列表 | |||
| */ | |||
| @Override | |||
| @GetMapping("/option") | |||
| public AjaxResult option() { | |||
| return super.option(); | |||
| } | |||
| interface Auth { | |||
| /** 系统 - 数字人主界面图标管理 - 列表 */ | |||
| String DM_SCREEN_ICON_LIST = "digitalmans:screenIcon:list"; | |||
| /** 系统 - 数字人主界面图标管理 - 详情 */ | |||
| String DM_SCREEN_ICON_SINGLE = "digitalmans:screenIcon:single"; | |||
| /** 系统 - 数字人主界面图标管理 - 新增 */ | |||
| String DM_SCREEN_ICON_ADD = "digitalmans:screenIcon:add"; | |||
| /** 系统 - 数字人主界面图标管理 - 修改 */ | |||
| String DM_SCREEN_ICON_EDIT = "digitalmans:screenIcon:edit"; | |||
| /** 系统 - 数字人主界面图标管理 - 修改状态 */ | |||
| String DM_SCREEN_ICON_ES = "digitalmans:screenIcon:es"; | |||
| /** 系统 - 数字人主界面图标管理 - 删除 */ | |||
| String DM_SCREEN_ICON_DEL = "digitalmans:screenIcon:delete"; | |||
| } | |||
| } | |||
| @@ -9,7 +9,7 @@ import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| /** | |||
| * 动作管理 | |||
| @@ -3,13 +3,12 @@ package com.xueyi.system.digitalmans.domain.dto; | |||
| import com.xueyi.common.core.annotation.Correlation; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.system.digitalmans.domain.po.DmInitSkillsPo; | |||
| import com.xueyi.system.resource.domain.dto.DmResourcesDto; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| /** | |||
| * 技能管理 数据传输对象 | |||
| @@ -11,8 +11,8 @@ import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import java.util.List; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| /** | |||
| * 接待模式管理 数据传输对象 | |||
| @@ -11,8 +11,8 @@ import lombok.NoArgsConstructor; | |||
| import java.io.Serial; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Broadcast_DmBroadcastResource_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Resource_DmBroadcastResource_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Broadcast_DmBroadcastResource_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Resource_DmBroadcastResource_GROUP; | |||
| /** | |||
| * 播报资源关联 持久化对象 | |||
| @@ -36,8 +36,6 @@ public class DmBroadcastResourceMerge extends TBasisEntity { | |||
| }) | |||
| protected Long broadcastId; | |||
| ; | |||
| /** 资源id */ | |||
| @Correlations({ | |||
| @Correlation(groupName = Broadcast_DmBroadcastResource_GROUP, keyType = OperateConstants.SubKeyType.MERGE_MAIN), | |||
| @@ -11,10 +11,8 @@ import lombok.NoArgsConstructor; | |||
| import java.io.Serial; | |||
| import static com.xueyi.system.api.organize.domain.merge.MergeGroup.POST_SysUserPostMerge_GROUP; | |||
| import static com.xueyi.system.api.organize.domain.merge.MergeGroup.USER_SysUserPostMerge_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Visitor_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Visitor_DmReceptionVisitorMerge_GROUP; | |||
| /** | |||
| * 任务访客关联 持久化对象 | |||
| @@ -0,0 +1,17 @@ | |||
| package com.xueyi.system.digitalmans.domain.model; | |||
| import com.xueyi.common.core.web.entity.model.BaseConverter; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import org.mapstruct.Mapper; | |||
| import org.mapstruct.MappingConstants; | |||
| /** | |||
| * 数字人主界面图标 对象映射器 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Mapper(componentModel = MappingConstants.ComponentModel.SPRING) | |||
| public interface DmScreenIconConverter extends BaseConverter<DmScreenIconQuery, DmScreenIconDto, DmScreenIconPo> { | |||
| } | |||
| @@ -4,7 +4,6 @@ import com.xueyi.common.core.annotation.Correlation; | |||
| import com.xueyi.common.core.annotation.Correlations; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.core.web.entity.base.BaseEntity; | |||
| import com.xueyi.system.digitalmans.domain.dto.DmActionDto; | |||
| import com.xueyi.common.core.annotation.Excel; | |||
| import com.baomidou.mybatisplus.annotation.TableName; | |||
| import lombok.Data; | |||
| @@ -13,7 +12,7 @@ import lombok.EqualsAndHashCode; | |||
| import javax.validation.constraints.NotNull; | |||
| import java.io.Serial; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| /** | |||
| @@ -12,7 +12,7 @@ import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import static com.xueyi.common.core.constant.basic.EntityConstants.REMARK; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| /** | |||
| * 技能管理 持久化对象 | |||
| @@ -1,14 +1,11 @@ | |||
| package com.xueyi.system.digitalmans.domain.po; | |||
| import java.time.LocalDate; | |||
| import java.time.LocalDateTime; | |||
| import java.util.Date; | |||
| import com.fasterxml.jackson.annotation.JsonFormat; | |||
| import com.xueyi.common.core.annotation.Correlation; | |||
| import com.xueyi.common.core.annotation.Correlations; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.core.web.tenant.base.TBaseEntity; | |||
| import com.xueyi.system.digitalmans.domain.dto.DmReceptionDto; | |||
| import com.xueyi.common.core.annotation.Excel; | |||
| import com.baomidou.mybatisplus.annotation.TableName; | |||
| import lombok.Data; | |||
| @@ -17,7 +14,7 @@ import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| import static com.xueyi.common.core.constant.basic.EntityConstants.REMARK; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| /** | |||
| * 接待模式管理 持久化对象 | |||
| @@ -0,0 +1,20 @@ | |||
| package com.xueyi.system.digitalmans.domain.query; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import lombok.Data; | |||
| import lombok.EqualsAndHashCode; | |||
| import java.io.Serial; | |||
| /** | |||
| * 数字人主界面图标 数据查询对象 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Data | |||
| @EqualsAndHashCode(callSuper = true) | |||
| public class DmScreenIconQuery extends DmScreenIconPo { | |||
| @Serial | |||
| private static final long serialVersionUID = 1L; | |||
| } | |||
| @@ -0,0 +1,13 @@ | |||
| package com.xueyi.system.digitalmans.manager; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.common.web.entity.manager.IBaseManager; | |||
| /** | |||
| * 数字人主界面图标管理 数据封装层 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| public interface IDmScreenIconManager extends IBaseManager<DmScreenIconQuery, DmScreenIconDto> { | |||
| } | |||
| @@ -15,7 +15,7 @@ import org.springframework.stereotype.Component; | |||
| import java.util.ArrayList; | |||
| import java.util.List; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| /** | |||
| * 动作管理 | |||
| @@ -10,6 +10,8 @@ import com.xueyi.system.digitalmans.domain.query.DmBroadcastQuery; | |||
| import com.xueyi.system.digitalmans.manager.IDmBroadcastManager; | |||
| import com.xueyi.system.digitalmans.mapper.DmBroadcastMapper; | |||
| import com.xueyi.system.digitalmans.mapper.merge.DmBroadcastResourceMergeMapper; | |||
| import org.slf4j.Logger; | |||
| import org.slf4j.LoggerFactory; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.stereotype.Component; | |||
| @@ -24,6 +26,8 @@ import java.util.stream.Collectors; | |||
| */ | |||
| @Component | |||
| public class DmBroadcastManager extends BaseManagerImpl<DmBroadcastQuery, DmBroadcastDto, DmBroadcastPo, DmBroadcastMapper, DmBroadcastConverter> implements IDmBroadcastManager { | |||
| private static final Logger log = LoggerFactory.getLogger(DmBroadcastManager.class); | |||
| @Autowired | |||
| private DmBroadcastResourceMergeMapper broadcastResourceMergeMapper; | |||
| @@ -56,18 +60,22 @@ public class DmBroadcastManager extends BaseManagerImpl<DmBroadcastQuery, DmBroa | |||
| List<Long> idList = mergeDtos.stream() | |||
| .map(DmBroadcastResourceMerge::getId) | |||
| .collect(Collectors.toList()); | |||
| log.info("editBroadcastResourceMerge idList:{}",idList); | |||
| List<Long> newList = broadcastResourceMerges.stream() | |||
| .map(DmBroadcastResourceMerge::getId) | |||
| .collect(Collectors.toList()); | |||
| log.info("editBroadcastResourceMerge newList:{}",newList); | |||
| idList.removeAll(newList); | |||
| // idList.removeAll(newList);//从原图片列表中取新列表的差集进行删除 | |||
| //批量删除 | |||
| if (idList.size() > 0) { | |||
| broadcastResourceMergeMapper.deleteBatchIds(idList); | |||
| } | |||
| //批量新增 | |||
| if (broadcastResourceMerges.size() > 0) { | |||
| broadcastResourceMergeMapper.updateBatch(broadcastResourceMerges); | |||
| broadcastResourceMergeMapper.insertBatch(broadcastResourceMerges); | |||
| } | |||
| } | |||
| @@ -9,14 +9,12 @@ import com.xueyi.system.digitalmans.domain.model.DmInitSkillsConverter; | |||
| import com.xueyi.system.digitalmans.mapper.DmInitSkillsMapper; | |||
| import com.xueyi.common.web.entity.manager.impl.BaseManagerImpl; | |||
| import com.xueyi.system.digitalmans.manager.IDmInitSkillsManager; | |||
| import com.xueyi.system.resource.manager.impl.DmResourcesManager; | |||
| import org.springframework.stereotype.Component; | |||
| import java.util.ArrayList; | |||
| import java.util.List; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Skill_Action_GROUP; | |||
| /** | |||
| * 技能管理管理 数据封装层处理 | |||
| @@ -1,22 +1,35 @@ | |||
| package com.xueyi.system.digitalmans.manager.impl; | |||
| import com.baomidou.mybatisplus.core.toolkit.Wrappers; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.web.entity.domain.SlaveRelation; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmModelIconPo; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import com.xueyi.system.digitalmans.controller.DmQAndAController; | |||
| import com.xueyi.system.digitalmans.domain.dto.DmModelUploadDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmDigitalmanPo; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmModelPo; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmModelDto; | |||
| import com.xueyi.system.api.digitalmans.domain.merge.DmModelIconMerge; | |||
| import com.xueyi.system.digitalmans.domain.model.DmScreenIconConverter; | |||
| import com.xueyi.system.digitalmans.domain.query.DmModelQuery; | |||
| import com.xueyi.system.digitalmans.domain.model.DmModelConverter; | |||
| import com.xueyi.system.digitalmans.mapper.DmDigitalmanMapper; | |||
| import com.xueyi.system.digitalmans.mapper.DmModelIconMapper; | |||
| import com.xueyi.system.digitalmans.mapper.DmModelMapper; | |||
| import com.xueyi.common.web.entity.manager.impl.BaseManagerImpl; | |||
| import com.xueyi.system.digitalmans.manager.IDmModelManager; | |||
| import com.xueyi.system.api.resource.domain.po.DmResourcesPo; | |||
| import com.xueyi.system.digitalmans.mapper.DmScreenIconMapper; | |||
| import com.xueyi.system.digitalmans.mapper.merge.DmModelIconMergeMapper; | |||
| import com.xueyi.system.resource.domain.po.DmBackgroundPo; | |||
| import com.xueyi.system.resource.domain.po.DmScreenOffPo; | |||
| import com.xueyi.system.resource.mapper.DmBackgroundMapper; | |||
| import com.xueyi.system.resource.mapper.DmResourcesMapper; | |||
| import com.xueyi.system.resource.mapper.DmScreenOffMapper; | |||
| import org.slf4j.Logger; | |||
| import org.slf4j.LoggerFactory; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.stereotype.Component; | |||
| @@ -25,6 +38,8 @@ import java.util.ArrayList; | |||
| import java.util.Arrays; | |||
| import java.util.List; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Model_DmModelIcon_GROUP; | |||
| /** | |||
| * 模型管理 数据封装层处理 | |||
| @@ -34,6 +49,7 @@ import java.util.List; | |||
| @Component | |||
| public class DmModelManager extends BaseManagerImpl<DmModelQuery, DmModelDto, DmModelPo, DmModelMapper, DmModelConverter> implements IDmModelManager { | |||
| private static final Logger log = LoggerFactory.getLogger(DmModelManager.class); | |||
| @Autowired | |||
| DmResourcesMapper dmResourcesMapper; | |||
| @@ -49,6 +65,22 @@ public class DmModelManager extends BaseManagerImpl<DmModelQuery, DmModelDto, Dm | |||
| @Autowired | |||
| DmDigitalmanMapper digitalmanMapper; | |||
| @Autowired | |||
| DmModelIconMapper dmModelIconMapper; | |||
| @Autowired | |||
| DmScreenIconMapper dmScreenIconMapper; | |||
| @Autowired | |||
| DmScreenIconConverter screenIconConverter; | |||
| // @Override | |||
| // protected List<SlaveRelation> subRelationInit() { | |||
| // List result = new ArrayList<SlaveRelation>(); | |||
| // result.add(new SlaveRelation(Model_DmModelIcon_GROUP, DmModelIconMergeMapper.class, DmModelIconMerge.class, OperateConstants.SubOperateLimit.ONLY_DEL)); | |||
| // return result; | |||
| // } | |||
| @Override | |||
| public DmModelDto selectById(Serializable id) { | |||
| @@ -74,6 +106,8 @@ public class DmModelManager extends BaseManagerImpl<DmModelQuery, DmModelDto, Dm | |||
| List<DmResourcesPo> bResourcesPos = new ArrayList<>(); | |||
| backgroundPos.forEach(rpo->bResourcesPos.add(dmResourcesMapper.selectById(rpo.getResourceId()))); | |||
| modelDto.setRBackgrounds(bResourcesPos); | |||
| /** 新业务 需求变更,代码暂时保留 | |||
| if (modelDto.getBackgroundContain() != null && modelDto.getBackgroundContain().length() > 0) { | |||
| modelDto.setRBackgrounds(new ArrayList<>(modelDto.getBackgroundContain().split(",").length)); | |||
| @@ -92,6 +126,24 @@ public class DmModelManager extends BaseManagerImpl<DmModelQuery, DmModelDto, Dm | |||
| if (modelDto.getIconId() != null) { | |||
| modelDto.setRIcon(dmResourcesMapper.selectById(modelDto.getIconId())); | |||
| } | |||
| // 获取主界面icon | |||
| List<DmModelIconPo> modelIconList = dmModelIconMapper.selectModelIconListByModelId(modelDto.getId()); | |||
| log.info("主界面icon列表:{}", modelIconList); | |||
| if (modelIconList != null && modelIconList.size() > 0) { | |||
| List<DmScreenIconDto> screenIconDtos = new ArrayList<>(); | |||
| modelIconList.forEach(iconItem-> { | |||
| // 获取icon | |||
| DmScreenIconPo iconPo = dmScreenIconMapper.selectById(iconItem.getIconId()); | |||
| DmScreenIconDto temp = screenIconConverter.mapperDto(iconPo); | |||
| DmResourcesPo resourcesPo = dmResourcesMapper.selectById(iconPo.getResourceId()); | |||
| temp.setPos(iconItem.getPos()); | |||
| temp.setIconUrl(resourcesPo.getUrl()); | |||
| screenIconDtos.add(temp); | |||
| }); | |||
| modelDto.setDmScreenIconDtos(screenIconDtos); | |||
| } | |||
| return modelDto; | |||
| } | |||
| @@ -131,6 +183,40 @@ public class DmModelManager extends BaseManagerImpl<DmModelQuery, DmModelDto, Dm | |||
| DmDigitalmanPo po = digitalmanMapper.selectById(dto.getManId()); | |||
| po.setName(dto.getName()); | |||
| digitalmanMapper.updateById(po); | |||
| //更新主界面icon | |||
| List<DmModelIconPo> iconPos = dmModelIconMapper.selectModelIconListByModelId(dto.getId()); | |||
| if (iconPos != null && iconPos.size() > 0) { | |||
| // 删除原有icon | |||
| dmModelIconMapper.deleteMerge(iconPos.get(0)); | |||
| } | |||
| log.info("主界面icon列表:{}",dto.getDmScreenIconDtos()); | |||
| if (dto.getDmScreenIconDtos() != null && dto.getDmScreenIconDtos().size() > 0) { | |||
| // 新增icon | |||
| for (DmScreenIconDto screenIconDto : dto.getDmScreenIconDtos()) { | |||
| DmScreenIconPo screenIconPo = new DmScreenIconPo(); | |||
| if (screenIconDto.getId() != null && screenIconDto.getId().doubleValue() > 0) { | |||
| // 更新模型-主界面icon关系 | |||
| screenIconPo = dmScreenIconMapper.selectById(screenIconDto.getId()); | |||
| screenIconPo.setName(screenIconDto.getName()); | |||
| screenIconPo.setResourceId(screenIconDto.getResourceId()); | |||
| screenIconPo.setBroadcastId(screenIconDto.getBroadcastId()); | |||
| dmScreenIconMapper.updateById(screenIconPo); | |||
| } else { | |||
| screenIconPo = new DmScreenIconPo(); | |||
| screenIconPo.setName(screenIconDto.getName()); | |||
| screenIconPo.setResourceId(screenIconDto.getResourceId()); | |||
| screenIconPo.setBroadcastId(screenIconDto.getBroadcastId()); | |||
| dmScreenIconMapper.insert(screenIconPo); | |||
| } | |||
| // 新增模型-主界面icon关系 | |||
| DmModelIconPo iconPo = new DmModelIconPo(); | |||
| iconPo.setModelId(dto.getId()); | |||
| iconPo.setIconId(screenIconPo.getId()); | |||
| iconPo.setPos(screenIconDto.getPos()); | |||
| dmModelIconMapper.insertMerge(iconPo); | |||
| } | |||
| } | |||
| return super.update(dto); | |||
| } | |||
| } | |||
| @@ -3,9 +3,7 @@ package com.xueyi.system.digitalmans.manager.impl; | |||
| import com.baomidou.mybatisplus.core.toolkit.Wrappers; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.core.utils.core.ArrayUtil; | |||
| import com.xueyi.common.core.utils.core.CollUtil; | |||
| import com.xueyi.common.web.entity.domain.SlaveRelation; | |||
| import com.xueyi.system.api.organize.domain.dto.SysDeptDto; | |||
| import com.xueyi.system.digitalmans.domain.merge.DmReceptionVisitorMerge; | |||
| import com.xueyi.system.digitalmans.domain.po.DmReceptionPo; | |||
| import com.xueyi.system.digitalmans.domain.dto.DmReceptionDto; | |||
| @@ -15,11 +13,7 @@ import com.xueyi.system.digitalmans.mapper.DmReceptionMapper; | |||
| import com.xueyi.common.web.entity.manager.impl.BaseManagerImpl; | |||
| import com.xueyi.system.digitalmans.manager.IDmReceptionManager; | |||
| import com.xueyi.system.digitalmans.mapper.merge.DmReceptionVisitorMergeMapper; | |||
| import com.xueyi.system.organize.domain.merge.SysRoleDeptMerge; | |||
| import com.xueyi.system.organize.domain.merge.SysRolePostMerge; | |||
| import com.xueyi.system.resource.manager.impl.DmResourcesManager; | |||
| import com.xueyi.system.staff.manager.impl.DmStaffManager; | |||
| import org.apache.commons.lang3.ArrayUtils; | |||
| import org.springframework.beans.factory.annotation.Autowired; | |||
| import org.springframework.stereotype.Component; | |||
| @@ -28,8 +22,8 @@ import java.util.Arrays; | |||
| import java.util.List; | |||
| import java.util.stream.Collectors; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Reception_Staff_GROUP; | |||
| @@ -0,0 +1,35 @@ | |||
| package com.xueyi.system.digitalmans.manager.impl; | |||
| import com.xueyi.common.core.constant.basic.OperateConstants; | |||
| import com.xueyi.common.web.entity.domain.SlaveRelation; | |||
| import com.xueyi.system.api.digitalmans.domain.merge.DmModelIconMerge; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.system.digitalmans.domain.model.DmScreenIconConverter; | |||
| import com.xueyi.system.digitalmans.mapper.DmScreenIconMapper; | |||
| import com.xueyi.common.web.entity.manager.impl.BaseManagerImpl; | |||
| import com.xueyi.system.digitalmans.manager.IDmScreenIconManager; | |||
| import com.xueyi.system.digitalmans.mapper.merge.DmModelIconMergeMapper; | |||
| import org.springframework.stereotype.Component; | |||
| import java.util.ArrayList; | |||
| import java.util.List; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Icon_DmModelIcon_GROUP; | |||
| /** | |||
| * 数字人主界面图标管理 数据封装层处理 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Component | |||
| public class DmScreenIconManager extends BaseManagerImpl<DmScreenIconQuery, DmScreenIconDto, DmScreenIconPo, DmScreenIconMapper, DmScreenIconConverter> implements IDmScreenIconManager { | |||
| // @Override | |||
| // protected List<SlaveRelation> subRelationInit() { | |||
| // List result = new ArrayList<SlaveRelation>(); | |||
| // result.add(new SlaveRelation(Icon_DmModelIcon_GROUP, DmModelIconMergeMapper.class, DmModelIconMerge.class, OperateConstants.SubOperateLimit.ONLY_DEL)); | |||
| // return result; | |||
| // } | |||
| } | |||
| @@ -0,0 +1,23 @@ | |||
| package com.xueyi.system.digitalmans.mapper; | |||
| import com.xueyi.common.datasource.annotation.Isolate; | |||
| import com.xueyi.common.web.entity.mapper.BaseMapper; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmModelIconPo; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import org.apache.ibatis.annotations.Param; | |||
| import java.util.List; | |||
| /** | |||
| * 数字人主界面图标管理 数据层 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Isolate | |||
| public interface DmModelIconMapper { | |||
| List<DmModelIconPo> selectModelIconListByModelId(@Param("modelId") Long modelId); | |||
| int insertMerge(DmModelIconPo modelIconPo); | |||
| int deleteMerge(DmModelIconPo modelIconPo); | |||
| } | |||
| @@ -0,0 +1,16 @@ | |||
| package com.xueyi.system.digitalmans.mapper; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmScreenIconPo; | |||
| import com.xueyi.common.web.entity.mapper.BaseMapper; | |||
| import com.xueyi.common.datasource.annotation.Isolate; | |||
| /** | |||
| * 数字人主界面图标管理 数据层 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Isolate | |||
| public interface DmScreenIconMapper extends BaseMapper<DmScreenIconQuery, DmScreenIconDto, DmScreenIconPo> { | |||
| } | |||
| @@ -0,0 +1,14 @@ | |||
| package com.xueyi.system.digitalmans.mapper.merge; | |||
| import com.xueyi.common.datasource.annotation.Isolate; | |||
| import com.xueyi.common.web.entity.mapper.BasicMapper; | |||
| import com.xueyi.system.api.digitalmans.domain.merge.DmModelIconMerge; | |||
| /** | |||
| * 任务访客关联 数据层 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Isolate | |||
| public interface DmModelIconMergeMapper extends BasicMapper<DmModelIconMerge> { | |||
| } | |||
| @@ -0,0 +1,13 @@ | |||
| package com.xueyi.system.digitalmans.service; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.common.web.entity.service.IBaseService; | |||
| /** | |||
| * 数字人主界面图标管理 服务层 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| public interface IDmScreenIconService extends IBaseService<DmScreenIconQuery, DmScreenIconDto> { | |||
| } | |||
| @@ -0,0 +1,32 @@ | |||
| package com.xueyi.system.digitalmans.service.impl; | |||
| import com.xueyi.system.api.digitalmans.domain.dto.DmScreenIconDto; | |||
| import com.xueyi.system.digitalmans.domain.query.DmScreenIconQuery; | |||
| import com.xueyi.system.digitalmans.service.IDmScreenIconService; | |||
| import com.xueyi.system.digitalmans.manager.IDmScreenIconManager; | |||
| import com.xueyi.common.web.entity.service.impl.BaseServiceImpl; | |||
| import org.springframework.stereotype.Service; | |||
| import java.util.List; | |||
| /** | |||
| * 数字人主界面图标管理 服务层处理 | |||
| * | |||
| * @author xueyi | |||
| */ | |||
| @Service | |||
| public class DmScreenIconServiceImpl extends BaseServiceImpl<DmScreenIconQuery, DmScreenIconDto, IDmScreenIconManager> implements IDmScreenIconService { | |||
| /** | |||
| * 查询数字人主界面图标对象列表 | 数据权限 | |||
| * | |||
| * @param screenIcon 数字人主界面图标对象 | |||
| * @return 数字人主界面图标对象集合 | |||
| */ | |||
| @Override | |||
| //@DataScope(userAlias = "createBy", mapperScope = {"DmScreenIconMapper"}) | |||
| public List<DmScreenIconDto> selectListScope(DmScreenIconQuery screenIcon) { | |||
| return baseManager.selectList(screenIcon); | |||
| } | |||
| } | |||
| @@ -1,5 +1,6 @@ | |||
| package com.xueyi.system.pass.controller.api; | |||
| import cn.hutool.core.util.IdUtil; | |||
| import cn.hutool.core.util.ObjectUtil; | |||
| import co.elastic.clients.elasticsearch.ElasticsearchClient; | |||
| import com.alibaba.fastjson.JSONArray; | |||
| @@ -182,6 +183,7 @@ public class DmRecognizedRecordsInnerApiController extends BaseApiController { | |||
| iDmResourcesService.addOne(dmResourcesDto); | |||
| cr.setFaceUrl(url); | |||
| cr.setId(IdUtil.getSnowflakeNextId()); | |||
| cr.setResourceId(dmResourcesDto.getId()); | |||
| } | |||
| // recognizedRecordsService.saveToEs(recordsConverter.mapperDto(cr)); | |||
| @@ -2,7 +2,6 @@ package com.xueyi.system.resource.controller; | |||
| import com.xueyi.common.core.web.result.AjaxResult; | |||
| import com.xueyi.common.core.web.validate.V_A; | |||
| import com.xueyi.common.core.web.validate.V_E; | |||
| import com.xueyi.common.log.annotation.Log; | |||
| import com.xueyi.common.log.enums.BusinessType; | |||
| import com.xueyi.common.security.annotation.RequiresPermissions; | |||
| @@ -11,7 +10,13 @@ import com.xueyi.system.resource.domain.dto.DmBackgroundDto; | |||
| import com.xueyi.system.resource.domain.query.DmBackgroundQuery; | |||
| import com.xueyi.system.resource.service.IDmBackgroundService; | |||
| import org.springframework.validation.annotation.Validated; | |||
| import org.springframework.web.bind.annotation.*; | |||
| import org.springframework.web.bind.annotation.DeleteMapping; | |||
| import org.springframework.web.bind.annotation.GetMapping; | |||
| import org.springframework.web.bind.annotation.PathVariable; | |||
| import org.springframework.web.bind.annotation.PostMapping; | |||
| import org.springframework.web.bind.annotation.RequestBody; | |||
| import org.springframework.web.bind.annotation.RequestMapping; | |||
| import org.springframework.web.bind.annotation.RestController; | |||
| import java.util.List; | |||
| @@ -138,6 +138,8 @@ public class DmResourcesController extends BaseController<DmResourcesQuery, DmRe | |||
| private static final String PARAM_RESOURCE_ID = "resource_id"; | |||
| private static final String PARAM_URL = "url"; | |||
| private static final String PARAM_TYPE = "type"; | |||
| /** | |||
| * 头像上传 | |||
| */ | |||
| @@ -146,37 +148,65 @@ public class DmResourcesController extends BaseController<DmResourcesQuery, DmRe | |||
| public AjaxResult upload(@RequestParam("file") MultipartFile file) { | |||
| if (!file.isEmpty()) { | |||
| String extension = FileTypeUtil.getExtension(file); | |||
| if (!CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.IMAGE_EXTENSION) | |||
| && !CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.VIDEO_EXTENSION)) { | |||
| return error("文件格式不正确,请上传" + Arrays.toString(MimeTypeUtil.IMAGE_EXTENSION) + Arrays.toString(MimeTypeUtil.IMAGE_EXTENSION) + "格式"); | |||
| logger.info("文件类型:" + extension+",上传开始..."); | |||
| if (!CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.EXCEPT_ALLOWED_EXTENSION)) { | |||
| return error("文件格式不正确,请上传" + Arrays.toString(MimeTypeUtil.EXCEPT_ALLOWED_EXTENSION) + "格式"); | |||
| } | |||
| R<SysFile> fileResult = remoteFileService.upload(file); | |||
| if (ObjectUtil.isNull(fileResult) || ObjectUtil.isNull(fileResult.getData())) | |||
| return error("文件服务异常,请联系管理员!"); | |||
| String url = fileResult.getData().getUrl(); | |||
| // 预留人脸识别与图像质量监测接口,如果监测异常返回错误 | |||
| DmResourcesDto dto = new DmResourcesDto(); | |||
| dto.setName(file.getOriginalFilename()); | |||
| dto.setUrl(url); | |||
| if (CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.IMAGE_EXTENSION) ) { | |||
| dto.setType(DmResourcesPo.TYPE_PIC); | |||
| } | |||
| if (CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.VIDEO_EXTENSION)) { | |||
| dto.setType(DmResourcesPo.TYPE_VIDEO); | |||
| } | |||
| dto.setFileSize(fileResult.getData().getSize()); | |||
| if(MimeTypeUtil.PDF_EXTENSION.equalsIgnoreCase(extension)) { | |||
| R<List<SysFile>> fileResult = remoteFileService.uploadPdf(file); | |||
| if (ObjectUtil.isNull(fileResult) || ObjectUtil.isNull(fileResult.getData())) | |||
| return error("文件服务异常,请联系管理员!"); | |||
| JSONArray ja = new JSONArray(); | |||
| for (SysFile sf : fileResult.getData()) { | |||
| String url = sf.getUrl(); | |||
| DmResourcesDto dto = new DmResourcesDto(); | |||
| dto.setName(file.getOriginalFilename()); | |||
| dto.setUrl(url); | |||
| dto.setType(DmResourcesPo.TYPE_PIC); | |||
| dto.setFileSize(sf.getSize()); | |||
| iDmResourcesService.addOne(dto); | |||
| JSONObject jo = new JSONObject(); | |||
| jo.put(PARAM_RESOURCE_ID, dto.getId()); | |||
| jo.put(PARAM_URL, url); | |||
| iDmResourcesService.addOne(dto); | |||
| JSONObject jo = new JSONObject(); | |||
| jo.put(PARAM_RESOURCE_ID, dto.getId()); | |||
| jo.put(PARAM_URL, url); | |||
| jo.put(PARAM_TYPE, dto.getType()); | |||
| ja.add(jo); | |||
| } | |||
| AjaxResult ajax = success(); | |||
| ajax.put(AjaxResult.RESULT_TAG, ja); | |||
| logger.info("上传文件成功,返回数据:" + ajax.toJson().toJSONString()); | |||
| return ajax; | |||
| } else { | |||
| R<SysFile> fileResult = remoteFileService.upload(file); | |||
| if (ObjectUtil.isNull(fileResult) || ObjectUtil.isNull(fileResult.getData())) | |||
| return error("文件服务异常,请联系管理员!"); | |||
| String url = fileResult.getData().getUrl(); | |||
| DmResourcesDto dto = new DmResourcesDto(); | |||
| dto.setName(file.getOriginalFilename()); | |||
| dto.setUrl(url); | |||
| if (CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.IMAGE_EXTENSION) ) { | |||
| dto.setType(DmResourcesPo.TYPE_PIC); | |||
| } | |||
| if (CharSequenceUtil.equalsAnyIgnoreCase(extension, MimeTypeUtil.VIDEO_EXTENSION)) { | |||
| dto.setType(DmResourcesPo.TYPE_VIDEO); | |||
| } | |||
| dto.setFileSize(fileResult.getData().getSize()); | |||
| iDmResourcesService.addOne(dto); | |||
| JSONObject jo = new JSONObject(); | |||
| jo.put(PARAM_RESOURCE_ID, dto.getId()); | |||
| jo.put(PARAM_URL, url); | |||
| jo.put(PARAM_TYPE, dto.getType()); | |||
| AjaxResult ajax = success(); | |||
| ajax.put(AjaxResult.RESULT_TAG, jo); | |||
| logger.info("上传文件成功,返回数据:" + ajax.toJson().toJSONString()); | |||
| return ajax; | |||
| } | |||
| AjaxResult ajax = success(); | |||
| ajax.put(AjaxResult.RESULT_TAG, jo); | |||
| return ajax; | |||
| } | |||
| return error("上传图片异常,请联系管理员!"); | |||
| return error("上传文件异常,请联系管理员!"); | |||
| } | |||
| /** | |||
| @@ -215,7 +245,7 @@ public class DmResourcesController extends BaseController<DmResourcesQuery, DmRe | |||
| ajax.put(AjaxResult.RESULT_TAG, ja); | |||
| return ajax; | |||
| } | |||
| return error("上传图片异常,请联系管理员!"); | |||
| return error("上传PDF文件异常,请联系管理员!"); | |||
| } | |||
| /** | |||
| @@ -7,7 +7,6 @@ import com.xueyi.system.api.digitalmans.domain.dto.DmVisitorsDto; | |||
| import com.xueyi.system.api.digitalmans.domain.po.DmVisitorsPo; | |||
| import com.xueyi.system.digitalmans.domain.merge.DmReceptionVisitorMerge; | |||
| import com.xueyi.system.digitalmans.mapper.merge.DmReceptionVisitorMergeMapper; | |||
| import com.xueyi.system.resource.manager.impl.DmResourcesManager; | |||
| import com.xueyi.system.staff.domain.model.DmVisitorsConverter; | |||
| import com.xueyi.system.staff.domain.query.DmVisitorsQuery; | |||
| import com.xueyi.system.staff.manager.IDmVisitorsManager; | |||
| @@ -17,8 +16,7 @@ import org.springframework.stereotype.Component; | |||
| import java.util.ArrayList; | |||
| import java.util.List; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Action_Resource_GROUP; | |||
| import static com.xueyi.system.digitalmans.domain.merge.MergeGroup.Visitor_DmReceptionVisitorMerge_GROUP; | |||
| import static com.xueyi.system.api.digitalmans.domain.merge.MergeGroup.Visitor_DmReceptionVisitorMerge_GROUP; | |||
| /** | |||
| * 访客管理 数据封装层处理 | |||
| @@ -0,0 +1,27 @@ | |||
| <?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.xueyi.system.digitalmans.mapper.DmModelIconMapper"> | |||
| <resultMap type="DmModelIconPo" id="DmModelIconResult"> | |||
| <result property="modelId" column="model_id" /> | |||
| <result property="iconId" column="icon_id" /> | |||
| <result property="pos" column="pos" /> | |||
| </resultMap> | |||
| <select id="selectModelIconListByModelId" resultMap="DmModelIconResult"> | |||
| select s.model_id, s.icon_id,s.pos from dm_model_icon_merge as s | |||
| where model_id = #{modelId} | |||
| </select> | |||
| <insert id="insertMerge" parameterType="DmModelIconPo" > | |||
| insert into dm_model_icon_merge(model_id,icon_id,pos) values(#{modelId},#{iconId},#{pos}) | |||
| </insert> | |||
| <delete id="deleteMerge" parameterType="DmModelIconPo" > | |||
| delete from dm_model_icon_merge where model_id = #{modelId} | |||
| </delete> | |||
| </mapper> | |||