Commit e30795fb69ccbb1f77271abafa4b8bc75e35d3d7
1 parent
261011d1
【代码评审】AI 大模型:知识库的逻辑
Showing
21 changed files
with
111 additions
and
112 deletions
yudao-module-ai/yudao-module-ai-api/src/main/java/cn/iocoder/yudao/module/ai/enums/ErrorCodeConstants.java
| @@ -52,7 +52,6 @@ public interface ErrorCodeConstants { | @@ -52,7 +52,6 @@ public interface ErrorCodeConstants { | ||
| 52 | // ========== API 思维导图 1-040-008-000 ========== | 52 | // ========== API 思维导图 1-040-008-000 ========== |
| 53 | ErrorCode MIND_MAP_NOT_EXISTS = new ErrorCode(1_040_008_000, "思维导图不存在!"); | 53 | ErrorCode MIND_MAP_NOT_EXISTS = new ErrorCode(1_040_008_000, "思维导图不存在!"); |
| 54 | 54 | ||
| 55 | - | ||
| 56 | // ========== API 知识库 1-022-008-000 ========== | 55 | // ========== API 知识库 1-022-008-000 ========== |
| 57 | ErrorCode KNOWLEDGE_NOT_EXISTS = new ErrorCode(1_022_008_000, "知识库不存在!"); | 56 | ErrorCode KNOWLEDGE_NOT_EXISTS = new ErrorCode(1_022_008_000, "知识库不存在!"); |
| 58 | ErrorCode KNOWLEDGE_DOCUMENT_NOT_EXISTS = new ErrorCode(1_022_008_001, "文档不存在!"); | 57 | ErrorCode KNOWLEDGE_DOCUMENT_NOT_EXISTS = new ErrorCode(1_022_008_001, "文档不存在!"); |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/AiKnowledgeController.java
| @@ -22,6 +22,7 @@ import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUti | @@ -22,6 +22,7 @@ import static cn.iocoder.yudao.framework.security.core.util.SecurityFrameworkUti | ||
| 22 | @Tag(name = "管理后台 - AI 知识库") | 22 | @Tag(name = "管理后台 - AI 知识库") |
| 23 | @RestController | 23 | @RestController |
| 24 | @RequestMapping("/ai/knowledge") | 24 | @RequestMapping("/ai/knowledge") |
| 25 | +@Validated | ||
| 25 | public class AiKnowledgeController { | 26 | public class AiKnowledgeController { |
| 26 | 27 | ||
| 27 | @Resource | 28 | @Resource |
| @@ -34,14 +35,12 @@ public class AiKnowledgeController { | @@ -34,14 +35,12 @@ public class AiKnowledgeController { | ||
| 34 | return success(BeanUtils.toBean(pageResult, AiKnowledgeRespVO.class)); | 35 | return success(BeanUtils.toBean(pageResult, AiKnowledgeRespVO.class)); |
| 35 | } | 36 | } |
| 36 | 37 | ||
| 37 | - | ||
| 38 | @PostMapping("/create-my") | 38 | @PostMapping("/create-my") |
| 39 | @Operation(summary = "创建【我的】知识库") | 39 | @Operation(summary = "创建【我的】知识库") |
| 40 | public CommonResult<Long> createKnowledgeMy(@RequestBody @Valid AiKnowledgeCreateMyReqVO createReqVO) { | 40 | public CommonResult<Long> createKnowledgeMy(@RequestBody @Valid AiKnowledgeCreateMyReqVO createReqVO) { |
| 41 | return success(knowledgeService.createKnowledgeMy(createReqVO, getLoginUserId())); | 41 | return success(knowledgeService.createKnowledgeMy(createReqVO, getLoginUserId())); |
| 42 | } | 42 | } |
| 43 | 43 | ||
| 44 | - | ||
| 45 | @PutMapping("/update-my") | 44 | @PutMapping("/update-my") |
| 46 | @Operation(summary = "更新【我的】知识库") | 45 | @Operation(summary = "更新【我的】知识库") |
| 47 | public CommonResult<Boolean> updateKnowledgeMy(@RequestBody @Valid AiKnowledgeUpdateMyReqVO updateReqVO) { | 46 | public CommonResult<Boolean> updateKnowledgeMy(@RequestBody @Valid AiKnowledgeUpdateMyReqVO updateReqVO) { |
| @@ -49,5 +48,4 @@ public class AiKnowledgeController { | @@ -49,5 +48,4 @@ public class AiKnowledgeController { | ||
| 49 | return success(true); | 48 | return success(true); |
| 50 | } | 49 | } |
| 51 | 50 | ||
| 52 | - | ||
| 53 | } | 51 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/AiKnowledgeDocumentController.java
| @@ -12,43 +12,40 @@ import cn.iocoder.yudao.module.ai.service.knowledge.AiKnowledgeDocumentService; | @@ -12,43 +12,40 @@ import cn.iocoder.yudao.module.ai.service.knowledge.AiKnowledgeDocumentService; | ||
| 12 | import io.swagger.v3.oas.annotations.Operation; | 12 | import io.swagger.v3.oas.annotations.Operation; |
| 13 | import io.swagger.v3.oas.annotations.tags.Tag; | 13 | import io.swagger.v3.oas.annotations.tags.Tag; |
| 14 | import jakarta.annotation.Resource; | 14 | import jakarta.annotation.Resource; |
| 15 | +import jakarta.validation.Valid; | ||
| 15 | import org.springframework.validation.annotation.Validated; | 16 | import org.springframework.validation.annotation.Validated; |
| 16 | import org.springframework.web.bind.annotation.*; | 17 | import org.springframework.web.bind.annotation.*; |
| 17 | 18 | ||
| 18 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; | 19 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; |
| 19 | 20 | ||
| 20 | - | ||
| 21 | -@Tag(name = "管理后台 - AI 知识库-文档") | 21 | +@Tag(name = "管理后台 - AI 知识库文档") |
| 22 | @RestController | 22 | @RestController |
| 23 | @RequestMapping("/ai/knowledge/document") | 23 | @RequestMapping("/ai/knowledge/document") |
| 24 | +@Validated | ||
| 24 | public class AiKnowledgeDocumentController { | 25 | public class AiKnowledgeDocumentController { |
| 25 | 26 | ||
| 26 | @Resource | 27 | @Resource |
| 27 | private AiKnowledgeDocumentService documentService; | 28 | private AiKnowledgeDocumentService documentService; |
| 28 | 29 | ||
| 29 | - | ||
| 30 | @PostMapping("/create") | 30 | @PostMapping("/create") |
| 31 | @Operation(summary = "新建文档") | 31 | @Operation(summary = "新建文档") |
| 32 | - public CommonResult<Long> createKnowledgeDocument(@Validated AiKnowledgeDocumentCreateReqVO reqVO) { | 32 | + public CommonResult<Long> createKnowledgeDocument(@Valid AiKnowledgeDocumentCreateReqVO reqVO) { |
| 33 | Long knowledgeDocumentId = documentService.createKnowledgeDocument(reqVO); | 33 | Long knowledgeDocumentId = documentService.createKnowledgeDocument(reqVO); |
| 34 | return success(knowledgeDocumentId); | 34 | return success(knowledgeDocumentId); |
| 35 | } | 35 | } |
| 36 | 36 | ||
| 37 | - | ||
| 38 | @GetMapping("/page") | 37 | @GetMapping("/page") |
| 39 | @Operation(summary = "获取文档分页") | 38 | @Operation(summary = "获取文档分页") |
| 40 | - public CommonResult<PageResult<AiKnowledgeDocumentRespVO>> getKnowledgeDocumentPageMy(@Validated AiKnowledgeDocumentPageReqVO pageReqVO) { | 39 | + public CommonResult<PageResult<AiKnowledgeDocumentRespVO>> getKnowledgeDocumentPageMy(@Valid AiKnowledgeDocumentPageReqVO pageReqVO) { |
| 41 | PageResult<AiKnowledgeDocumentDO> pageResult = documentService.getKnowledgeDocumentPage(pageReqVO); | 40 | PageResult<AiKnowledgeDocumentDO> pageResult = documentService.getKnowledgeDocumentPage(pageReqVO); |
| 42 | return success(BeanUtils.toBean(pageResult, AiKnowledgeDocumentRespVO.class)); | 41 | return success(BeanUtils.toBean(pageResult, AiKnowledgeDocumentRespVO.class)); |
| 43 | } | 42 | } |
| 44 | 43 | ||
| 45 | - | ||
| 46 | @PutMapping("/update") | 44 | @PutMapping("/update") |
| 47 | @Operation(summary = "更新文档") | 45 | @Operation(summary = "更新文档") |
| 48 | - public CommonResult<Boolean> updateKnowledgeDocument(@Validated @RequestBody AiKnowledgeDocumentUpdateReqVO reqVO) { | 46 | + public CommonResult<Boolean> updateKnowledgeDocument(@Valid @RequestBody AiKnowledgeDocumentUpdateReqVO reqVO) { |
| 49 | documentService.updateKnowledgeDocument(reqVO); | 47 | documentService.updateKnowledgeDocument(reqVO); |
| 50 | return success(true); | 48 | return success(true); |
| 51 | } | 49 | } |
| 52 | 50 | ||
| 53 | - | ||
| 54 | } | 51 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/AiKnowledgeSegmentController.java
| @@ -12,15 +12,16 @@ import cn.iocoder.yudao.module.ai.service.knowledge.AiKnowledgeSegmentService; | @@ -12,15 +12,16 @@ import cn.iocoder.yudao.module.ai.service.knowledge.AiKnowledgeSegmentService; | ||
| 12 | import io.swagger.v3.oas.annotations.Operation; | 12 | import io.swagger.v3.oas.annotations.Operation; |
| 13 | import io.swagger.v3.oas.annotations.tags.Tag; | 13 | import io.swagger.v3.oas.annotations.tags.Tag; |
| 14 | import jakarta.annotation.Resource; | 14 | import jakarta.annotation.Resource; |
| 15 | +import jakarta.validation.Valid; | ||
| 15 | import org.springframework.validation.annotation.Validated; | 16 | import org.springframework.validation.annotation.Validated; |
| 16 | import org.springframework.web.bind.annotation.*; | 17 | import org.springframework.web.bind.annotation.*; |
| 17 | 18 | ||
| 18 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; | 19 | import static cn.iocoder.yudao.framework.common.pojo.CommonResult.success; |
| 19 | 20 | ||
| 20 | - | ||
| 21 | -@Tag(name = "管理后台 - AI 知识库-段落") | 21 | +@Tag(name = "管理后台 - AI 知识库段落") |
| 22 | @RestController | 22 | @RestController |
| 23 | @RequestMapping("/ai/knowledge/segment") | 23 | @RequestMapping("/ai/knowledge/segment") |
| 24 | +@Validated | ||
| 24 | public class AiKnowledgeSegmentController { | 25 | public class AiKnowledgeSegmentController { |
| 25 | 26 | ||
| 26 | @Resource | 27 | @Resource |
| @@ -28,22 +29,21 @@ public class AiKnowledgeSegmentController { | @@ -28,22 +29,21 @@ public class AiKnowledgeSegmentController { | ||
| 28 | 29 | ||
| 29 | @GetMapping("/page") | 30 | @GetMapping("/page") |
| 30 | @Operation(summary = "获取段落分页") | 31 | @Operation(summary = "获取段落分页") |
| 31 | - public CommonResult<PageResult<AiKnowledgeSegmentRespVO>> getKnowledgeSegmentPageMy(@Validated AiKnowledgeSegmentPageReqVO pageReqVO) { | 32 | + public CommonResult<PageResult<AiKnowledgeSegmentRespVO>> getKnowledgeSegmentPageMy(@Valid AiKnowledgeSegmentPageReqVO pageReqVO) { |
| 32 | PageResult<AiKnowledgeSegmentDO> pageResult = segmentService.getKnowledgeSegmentPage(pageReqVO); | 33 | PageResult<AiKnowledgeSegmentDO> pageResult = segmentService.getKnowledgeSegmentPage(pageReqVO); |
| 33 | return success(BeanUtils.toBean(pageResult, AiKnowledgeSegmentRespVO.class)); | 34 | return success(BeanUtils.toBean(pageResult, AiKnowledgeSegmentRespVO.class)); |
| 34 | } | 35 | } |
| 35 | 36 | ||
| 36 | - | ||
| 37 | @PutMapping("/update") | 37 | @PutMapping("/update") |
| 38 | @Operation(summary = "更新段落内容") | 38 | @Operation(summary = "更新段落内容") |
| 39 | - public CommonResult<Boolean> updateKnowledgeSegment(@Validated @RequestBody AiKnowledgeSegmentUpdateReqVO reqVO) { | 39 | + public CommonResult<Boolean> updateKnowledgeSegment(@Valid @RequestBody AiKnowledgeSegmentUpdateReqVO reqVO) { |
| 40 | segmentService.updateKnowledgeSegment(reqVO); | 40 | segmentService.updateKnowledgeSegment(reqVO); |
| 41 | return success(true); | 41 | return success(true); |
| 42 | } | 42 | } |
| 43 | 43 | ||
| 44 | @PutMapping("/update-status") | 44 | @PutMapping("/update-status") |
| 45 | @Operation(summary = "启禁用段落内容") | 45 | @Operation(summary = "启禁用段落内容") |
| 46 | - public CommonResult<Boolean> updateKnowledgeSegmentStatus(@Validated @RequestBody AiKnowledgeSegmentUpdateStatusReqVO reqVO) { | 46 | + public CommonResult<Boolean> updateKnowledgeSegmentStatus(@Valid @RequestBody AiKnowledgeSegmentUpdateStatusReqVO reqVO) { |
| 47 | segmentService.updateKnowledgeSegmentStatus(reqVO); | 47 | segmentService.updateKnowledgeSegmentStatus(reqVO); |
| 48 | return success(true); | 48 | return success(true); |
| 49 | } | 49 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/document/AiKnowledgeDocumentPageReqVO.java
| @@ -4,10 +4,11 @@ import cn.iocoder.yudao.framework.common.pojo.PageParam; | @@ -4,10 +4,11 @@ import cn.iocoder.yudao.framework.common.pojo.PageParam; | ||
| 4 | import io.swagger.v3.oas.annotations.media.Schema; | 4 | import io.swagger.v3.oas.annotations.media.Schema; |
| 5 | import lombok.Data; | 5 | import lombok.Data; |
| 6 | 6 | ||
| 7 | -@Schema(description = "管理后台 - AI 知识库-文档 分页 Request VO") | 7 | +@Schema(description = "管理后台 - AI 知识库文档的分页 Request VO") |
| 8 | @Data | 8 | @Data |
| 9 | public class AiKnowledgeDocumentPageReqVO extends PageParam { | 9 | public class AiKnowledgeDocumentPageReqVO extends PageParam { |
| 10 | 10 | ||
| 11 | @Schema(description = "文档名称", example = "Java 开发手册") | 11 | @Schema(description = "文档名称", example = "Java 开发手册") |
| 12 | private String name; | 12 | private String name; |
| 13 | + | ||
| 13 | } | 14 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/document/AiKnowledgeDocumentRespVO.java
| @@ -17,21 +17,22 @@ public class AiKnowledgeDocumentRespVO extends PageParam { | @@ -17,21 +17,22 @@ public class AiKnowledgeDocumentRespVO extends PageParam { | ||
| 17 | @Schema(description = "名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "Java 开发手册") | 17 | @Schema(description = "名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "Java 开发手册") |
| 18 | private String name; | 18 | private String name; |
| 19 | 19 | ||
| 20 | - @Schema(description = "内容", example = "Java 是一门面向对象的语言.....") | 20 | + @Schema(description = "内容", requiredMode = Schema.RequiredMode.REQUIRED, example = "Java 是一门面向对象的语言.....") |
| 21 | private String content; | 21 | private String content; |
| 22 | 22 | ||
| 23 | @Schema(description = "文档 url", requiredMode = Schema.RequiredMode.REQUIRED, example = "https://doc.iocoder.cn") | 23 | @Schema(description = "文档 url", requiredMode = Schema.RequiredMode.REQUIRED, example = "https://doc.iocoder.cn") |
| 24 | private String url; | 24 | private String url; |
| 25 | 25 | ||
| 26 | - @Schema(description = "token 数量", example = "1024") | 26 | + @Schema(description = "token 数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "1024") |
| 27 | private Integer tokens; | 27 | private Integer tokens; |
| 28 | 28 | ||
| 29 | - @Schema(description = "字符数", example = "1008") | 29 | + @Schema(description = "字符数", requiredMode = Schema.RequiredMode.REQUIRED, example = "1008") |
| 30 | private Integer wordCount; | 30 | private Integer wordCount; |
| 31 | 31 | ||
| 32 | - @Schema(description = "切片状态", example = "1") | 32 | + @Schema(description = "切片状态", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 33 | private Integer sliceStatus; | 33 | private Integer sliceStatus; |
| 34 | 34 | ||
| 35 | - @Schema(description = "文档状态", example = "1") | 35 | + @Schema(description = "文档状态", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 36 | private Integer status; | 36 | private Integer status; |
| 37 | + | ||
| 37 | } | 38 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/document/AiKnowledgeDocumentUpdateReqVO.java
| 1 | package cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.document; | 1 | package cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.document; |
| 2 | 2 | ||
| 3 | +import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum; | ||
| 4 | +import cn.iocoder.yudao.framework.common.validation.InEnum; | ||
| 3 | import io.swagger.v3.oas.annotations.media.Schema; | 5 | import io.swagger.v3.oas.annotations.media.Schema; |
| 4 | import jakarta.validation.constraints.NotNull; | 6 | import jakarta.validation.constraints.NotNull; |
| 5 | import lombok.Data; | 7 | import lombok.Data; |
| @@ -15,6 +17,7 @@ public class AiKnowledgeDocumentUpdateReqVO { | @@ -15,6 +17,7 @@ public class AiKnowledgeDocumentUpdateReqVO { | ||
| 15 | private Long id; | 17 | private Long id; |
| 16 | 18 | ||
| 17 | @Schema(description = "是否启用", example = "1") | 19 | @Schema(description = "是否启用", example = "1") |
| 20 | + @InEnum(CommonStatusEnum.class) | ||
| 18 | private Integer status; | 21 | private Integer status; |
| 19 | 22 | ||
| 20 | @Schema(description = "名称", example = "Java 开发手册") | 23 | @Schema(description = "名称", example = "Java 开发手册") |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/knowledge/AiKnowledgeDocumentCreateReqVO.java
| @@ -7,7 +7,7 @@ import lombok.Data; | @@ -7,7 +7,7 @@ import lombok.Data; | ||
| 7 | import org.hibernate.validator.constraints.URL; | 7 | import org.hibernate.validator.constraints.URL; |
| 8 | 8 | ||
| 9 | 9 | ||
| 10 | -@Schema(description = "管理后台 - AI 知识库创建【文档】 Request VO") | 10 | +@Schema(description = "管理后台 - AI 知识库文档的创建 Request VO") |
| 11 | @Data | 11 | @Data |
| 12 | public class AiKnowledgeDocumentCreateReqVO { | 12 | public class AiKnowledgeDocumentCreateReqVO { |
| 13 | 13 |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/knowledge/AiKnowledgeRespVO.java
| @@ -14,12 +14,13 @@ public class AiKnowledgeRespVO { | @@ -14,12 +14,13 @@ public class AiKnowledgeRespVO { | ||
| 14 | @Schema(description = "知识库名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "ruoyi-vue-pro 用户指南") | 14 | @Schema(description = "知识库名称", requiredMode = Schema.RequiredMode.REQUIRED, example = "ruoyi-vue-pro 用户指南") |
| 15 | private String name; | 15 | private String name; |
| 16 | 16 | ||
| 17 | - @Schema(description = "知识库描述", example = "ruoyi-vue-pro 用户指南") | 17 | + @Schema(description = "知识库描述", example = "帮助你快速构建系统") |
| 18 | private String description; | 18 | private String description; |
| 19 | 19 | ||
| 20 | @Schema(description = "模型编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "14") | 20 | @Schema(description = "模型编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "14") |
| 21 | private Long modelId; | 21 | private Long modelId; |
| 22 | 22 | ||
| 23 | - @Schema(description = "模型标识", example = "qwen-72b-chat") | 23 | + @Schema(description = "模型标识", requiredMode = Schema.RequiredMode.REQUIRED, example = "qwen-72b-chat") |
| 24 | private String model; | 24 | private String model; |
| 25 | + | ||
| 25 | } | 26 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/segment/AiKnowledgeSegmentPageReqVO.java
| @@ -4,15 +4,14 @@ import cn.iocoder.yudao.framework.common.pojo.PageParam; | @@ -4,15 +4,14 @@ import cn.iocoder.yudao.framework.common.pojo.PageParam; | ||
| 4 | import io.swagger.v3.oas.annotations.media.Schema; | 4 | import io.swagger.v3.oas.annotations.media.Schema; |
| 5 | import lombok.Data; | 5 | import lombok.Data; |
| 6 | 6 | ||
| 7 | -@Schema(description = "管理后台 - AI 知识库分页 Request VO") | 7 | +@Schema(description = "管理后台 - AI 知识库分段的分页 Request VO") |
| 8 | @Data | 8 | @Data |
| 9 | public class AiKnowledgeSegmentPageReqVO extends PageParam { | 9 | public class AiKnowledgeSegmentPageReqVO extends PageParam { |
| 10 | 10 | ||
| 11 | - | ||
| 12 | @Schema(description = "分段状态", example = "1") | 11 | @Schema(description = "分段状态", example = "1") |
| 13 | private Integer status; | 12 | private Integer status; |
| 14 | 13 | ||
| 15 | - @Schema(description = "文档编号", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") | 14 | + @Schema(description = "文档编号", example = "1") |
| 16 | private Integer documentId; | 15 | private Integer documentId; |
| 17 | 16 | ||
| 18 | @Schema(description = "分段内容关键字", example = "Java 开发") | 17 | @Schema(description = "分段内容关键字", example = "Java 开发") |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/segment/AiKnowledgeSegmentRespVO.java
| @@ -22,12 +22,13 @@ public class AiKnowledgeSegmentRespVO { | @@ -22,12 +22,13 @@ public class AiKnowledgeSegmentRespVO { | ||
| 22 | @Schema(description = "切片内容", requiredMode = Schema.RequiredMode.REQUIRED, example = "Java 开发手册") | 22 | @Schema(description = "切片内容", requiredMode = Schema.RequiredMode.REQUIRED, example = "Java 开发手册") |
| 23 | private String content; | 23 | private String content; |
| 24 | 24 | ||
| 25 | - @Schema(description = "token 数量", example = "1024") | 25 | + @Schema(description = "token 数量", requiredMode = Schema.RequiredMode.REQUIRED, example = "1024") |
| 26 | private Integer tokens; | 26 | private Integer tokens; |
| 27 | 27 | ||
| 28 | - @Schema(description = "字符数", example = "1008") | 28 | + @Schema(description = "字符数", requiredMode = Schema.RequiredMode.REQUIRED, example = "1008") |
| 29 | private Integer wordCount; | 29 | private Integer wordCount; |
| 30 | 30 | ||
| 31 | - @Schema(description = "文档状态", example = "1") | 31 | + @Schema(description = "文档状态", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 32 | private Integer status; | 32 | private Integer status; |
| 33 | + | ||
| 33 | } | 34 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/controller/admin/knowledge/vo/segment/AiKnowledgeSegmentUpdateStatusReqVO.java
| 1 | package cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.segment; | 1 | package cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.segment; |
| 2 | 2 | ||
| 3 | +import cn.iocoder.yudao.framework.common.enums.CommonStatusEnum; | ||
| 4 | +import cn.iocoder.yudao.framework.common.validation.InEnum; | ||
| 3 | import io.swagger.v3.oas.annotations.media.Schema; | 5 | import io.swagger.v3.oas.annotations.media.Schema; |
| 6 | +import jakarta.validation.constraints.NotNull; | ||
| 4 | import lombok.Data; | 7 | import lombok.Data; |
| 5 | 8 | ||
| 6 | 9 | ||
| 7 | -@Schema(description = "管理后台 - AI 更新 知识库-段落 request VO") | 10 | +@Schema(description = "管理后台 - AI 知识库段落的更新状态 Request VO") |
| 8 | @Data | 11 | @Data |
| 9 | public class AiKnowledgeSegmentUpdateStatusReqVO { | 12 | public class AiKnowledgeSegmentUpdateStatusReqVO { |
| 10 | 13 | ||
| @@ -12,6 +15,8 @@ public class AiKnowledgeSegmentUpdateStatusReqVO { | @@ -12,6 +15,8 @@ public class AiKnowledgeSegmentUpdateStatusReqVO { | ||
| 12 | private Long id; | 15 | private Long id; |
| 13 | 16 | ||
| 14 | @Schema(description = "是否启用", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") | 17 | @Schema(description = "是否启用", requiredMode = Schema.RequiredMode.REQUIRED, example = "1") |
| 18 | + @NotNull(message = "是否启用不能为空") | ||
| 19 | + @InEnum(CommonStatusEnum.class) | ||
| 15 | private Integer status; | 20 | private Integer status; |
| 16 | 21 | ||
| 17 | } | 22 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/dal/dataobject/knowledge/AiKnowledgeSegmentDO.java
| @@ -28,12 +28,13 @@ public class AiKnowledgeSegmentDO extends BaseDO { | @@ -28,12 +28,13 @@ public class AiKnowledgeSegmentDO extends BaseDO { | ||
| 28 | private String vectorId; | 28 | private String vectorId; |
| 29 | /** | 29 | /** |
| 30 | * 知识库编号 | 30 | * 知识库编号 |
| 31 | + * | ||
| 31 | * 关联 {@link AiKnowledgeDO#getId()} | 32 | * 关联 {@link AiKnowledgeDO#getId()} |
| 32 | */ | 33 | */ |
| 33 | private Long knowledgeId; | 34 | private Long knowledgeId; |
| 34 | /** | 35 | /** |
| 35 | * 文档编号 | 36 | * 文档编号 |
| 36 | - * <p> | 37 | + * |
| 37 | * 关联 {@link AiKnowledgeDocumentDO#getId()} | 38 | * 关联 {@link AiKnowledgeDocumentDO#getId()} |
| 38 | */ | 39 | */ |
| 39 | private Long documentId; | 40 | private Long documentId; |
| @@ -51,7 +52,7 @@ public class AiKnowledgeSegmentDO extends BaseDO { | @@ -51,7 +52,7 @@ public class AiKnowledgeSegmentDO extends BaseDO { | ||
| 51 | private Integer tokens; | 52 | private Integer tokens; |
| 52 | /** | 53 | /** |
| 53 | * 状态 | 54 | * 状态 |
| 54 | - * <p> | 55 | + * |
| 55 | * 枚举 {@link CommonStatusEnum} | 56 | * 枚举 {@link CommonStatusEnum} |
| 56 | */ | 57 | */ |
| 57 | private Integer status; | 58 | private Integer status; |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/service/knowledge/AiKnowledgeDocumentServiceImpl.java
| @@ -30,13 +30,12 @@ import org.springframework.stereotype.Service; | @@ -30,13 +30,12 @@ import org.springframework.stereotype.Service; | ||
| 30 | import org.springframework.transaction.annotation.Transactional; | 30 | import org.springframework.transaction.annotation.Transactional; |
| 31 | 31 | ||
| 32 | import java.util.List; | 32 | import java.util.List; |
| 33 | -import java.util.Map; | ||
| 34 | 33 | ||
| 35 | import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; | 34 | import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception; |
| 36 | import static cn.iocoder.yudao.module.ai.enums.ErrorCodeConstants.KNOWLEDGE_DOCUMENT_NOT_EXISTS; | 35 | import static cn.iocoder.yudao.module.ai.enums.ErrorCodeConstants.KNOWLEDGE_DOCUMENT_NOT_EXISTS; |
| 37 | 36 | ||
| 38 | /** | 37 | /** |
| 39 | - * AI 知识库-文档 Service 实现类 | 38 | + * AI 知识库文档 Service 实现类 |
| 40 | * | 39 | * |
| 41 | * @author xiaoxin | 40 | * @author xiaoxin |
| 42 | */ | 41 | */ |
| @@ -61,24 +60,21 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | @@ -61,24 +60,21 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | ||
| 61 | @Resource | 60 | @Resource |
| 62 | private AiChatModelService chatModelService; | 61 | private AiChatModelService chatModelService; |
| 63 | 62 | ||
| 64 | - | ||
| 65 | - // TODO 芋艿:需要 review 下,代码格式; | ||
| 66 | @Override | 63 | @Override |
| 67 | @Transactional(rollbackFor = Exception.class) | 64 | @Transactional(rollbackFor = Exception.class) |
| 68 | public Long createKnowledgeDocument(AiKnowledgeDocumentCreateReqVO createReqVO) { | 65 | public Long createKnowledgeDocument(AiKnowledgeDocumentCreateReqVO createReqVO) { |
| 66 | + // 0. 校验 | ||
| 67 | + AiKnowledgeDO knowledge = knowledgeService.validateKnowledgeExists(createReqVO.getKnowledgeId()); | ||
| 68 | + AiChatModelDO model = chatModelService.validateChatModel(knowledge.getModelId()); | ||
| 69 | + | ||
| 69 | // 1.1 下载文档 | 70 | // 1.1 下载文档 |
| 70 | - String url = createReqVO.getUrl(); | ||
| 71 | - // 1.2 加载文档 | ||
| 72 | - TikaDocumentReader loader = new TikaDocumentReader(downloadFile(url)); | 71 | + TikaDocumentReader loader = new TikaDocumentReader(downloadFile(createReqVO.getUrl())); |
| 73 | List<Document> documents = loader.get(); | 72 | List<Document> documents = loader.get(); |
| 74 | Document document = CollUtil.getFirst(documents); | 73 | Document document = CollUtil.getFirst(documents); |
| 74 | + // 1.2 文档记录入库 | ||
| 75 | String content = document.getContent(); | 75 | String content = document.getContent(); |
| 76 | - Integer tokens = tokenCountEstimator.estimate(content); | ||
| 77 | - Integer wordCount = content.length(); | ||
| 78 | - | ||
| 79 | - // 1.3 文档记录入库 | ||
| 80 | AiKnowledgeDocumentDO documentDO = BeanUtils.toBean(createReqVO, AiKnowledgeDocumentDO.class) | 76 | AiKnowledgeDocumentDO documentDO = BeanUtils.toBean(createReqVO, AiKnowledgeDocumentDO.class) |
| 81 | - .setTokens(tokens).setWordCount(wordCount) | 77 | + .setTokens(tokenCountEstimator.estimate(content)).setWordCount(content.length()) |
| 82 | .setStatus(CommonStatusEnum.ENABLE.getStatus()).setSliceStatus(AiKnowledgeDocumentStatusEnum.SUCCESS.getStatus()); | 78 | .setStatus(CommonStatusEnum.ENABLE.getStatus()).setSliceStatus(AiKnowledgeDocumentStatusEnum.SUCCESS.getStatus()); |
| 83 | documentMapper.insert(documentDO); | 79 | documentMapper.insert(documentDO); |
| 84 | Long documentId = documentDO.getId(); | 80 | Long documentId = documentDO.getId(); |
| @@ -90,22 +86,16 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | @@ -90,22 +86,16 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | ||
| 90 | List<Document> segments = tokenTextSplitter.apply(documents); | 86 | List<Document> segments = tokenTextSplitter.apply(documents); |
| 91 | // 2.2 分段内容入库 | 87 | // 2.2 分段内容入库 |
| 92 | List<AiKnowledgeSegmentDO> segmentDOList = CollectionUtils.convertList(segments, | 88 | List<AiKnowledgeSegmentDO> segmentDOList = CollectionUtils.convertList(segments, |
| 93 | - segment -> new AiKnowledgeSegmentDO().setContent(segment.getContent()).setDocumentId(documentId).setKnowledgeId(createReqVO.getKnowledgeId()).setVectorId(segment.getId()) | 89 | + segment -> new AiKnowledgeSegmentDO().setContent(segment.getContent()).setDocumentId(documentId) |
| 90 | + .setKnowledgeId(createReqVO.getKnowledgeId()).setVectorId(segment.getId()) | ||
| 94 | .setTokens(tokenCountEstimator.estimate(segment.getContent())).setWordCount(segment.getContent().length()) | 91 | .setTokens(tokenCountEstimator.estimate(segment.getContent())).setWordCount(segment.getContent().length()) |
| 95 | .setStatus(CommonStatusEnum.ENABLE.getStatus())); | 92 | .setStatus(CommonStatusEnum.ENABLE.getStatus())); |
| 96 | segmentMapper.insertBatch(segmentDOList); | 93 | segmentMapper.insertBatch(segmentDOList); |
| 97 | 94 | ||
| 98 | - // 3.1 document 补充源数据 | ||
| 99 | - segments.forEach(segment -> { | ||
| 100 | - Map<String, Object> metadata = segment.getMetadata(); | ||
| 101 | - metadata.put(AiKnowledgeSegmentDO.FIELD_KNOWLEDGE_ID, createReqVO.getKnowledgeId()); | ||
| 102 | - }); | ||
| 103 | - | ||
| 104 | - AiKnowledgeDO knowledge = knowledgeService.validateKnowledgeExists(createReqVO.getKnowledgeId()); | ||
| 105 | - AiChatModelDO model = chatModelService.validateChatModel(knowledge.getModelId()); | ||
| 106 | - // 3.2 获取向量存储实例 | 95 | + // 3.1 获取向量存储实例 |
| 107 | VectorStore vectorStore = apiKeyService.getOrCreateVectorStore(model.getKeyId()); | 96 | VectorStore vectorStore = apiKeyService.getOrCreateVectorStore(model.getKeyId()); |
| 108 | - // 3.3 向量化并存储 | 97 | + // 3.2 向量化并存储 |
| 98 | + segments.forEach(segment -> segment.getMetadata().put(AiKnowledgeSegmentDO.FIELD_KNOWLEDGE_ID, createReqVO.getKnowledgeId())); | ||
| 109 | vectorStore.add(segments); | 99 | vectorStore.add(segments); |
| 110 | return documentId; | 100 | return documentId; |
| 111 | } | 101 | } |
| @@ -117,7 +107,9 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | @@ -117,7 +107,9 @@ public class AiKnowledgeDocumentServiceImpl implements AiKnowledgeDocumentServic | ||
| 117 | 107 | ||
| 118 | @Override | 108 | @Override |
| 119 | public void updateKnowledgeDocument(AiKnowledgeDocumentUpdateReqVO reqVO) { | 109 | public void updateKnowledgeDocument(AiKnowledgeDocumentUpdateReqVO reqVO) { |
| 110 | + // 1. 校验文档是否存在 | ||
| 120 | validateKnowledgeDocumentExists(reqVO.getId()); | 111 | validateKnowledgeDocumentExists(reqVO.getId()); |
| 112 | + // 2. 更新文档 | ||
| 121 | AiKnowledgeDocumentDO document = BeanUtils.toBean(reqVO, AiKnowledgeDocumentDO.class); | 113 | AiKnowledgeDocumentDO document = BeanUtils.toBean(reqVO, AiKnowledgeDocumentDO.class); |
| 122 | documentMapper.updateById(document); | 114 | documentMapper.updateById(document); |
| 123 | } | 115 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/service/knowledge/AiKnowledgeSegmentService.java
| @@ -7,7 +7,7 @@ import cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.segment.AiKnowle | @@ -7,7 +7,7 @@ import cn.iocoder.yudao.module.ai.controller.admin.knowledge.vo.segment.AiKnowle | ||
| 7 | import cn.iocoder.yudao.module.ai.dal.dataobject.knowledge.AiKnowledgeSegmentDO; | 7 | import cn.iocoder.yudao.module.ai.dal.dataobject.knowledge.AiKnowledgeSegmentDO; |
| 8 | 8 | ||
| 9 | /** | 9 | /** |
| 10 | - * AI 知识库分片 Service 接口 | 10 | + * AI 知识库段落 Service 接口 |
| 11 | * | 11 | * |
| 12 | * @author xiaoxin | 12 | * @author xiaoxin |
| 13 | */ | 13 | */ |
| @@ -22,16 +22,17 @@ public interface AiKnowledgeSegmentService { | @@ -22,16 +22,17 @@ public interface AiKnowledgeSegmentService { | ||
| 22 | PageResult<AiKnowledgeSegmentDO> getKnowledgeSegmentPage(AiKnowledgeSegmentPageReqVO pageReqVO); | 22 | PageResult<AiKnowledgeSegmentDO> getKnowledgeSegmentPage(AiKnowledgeSegmentPageReqVO pageReqVO); |
| 23 | 23 | ||
| 24 | /** | 24 | /** |
| 25 | - * 更新段落内容 | 25 | + * 更新段落的内容 |
| 26 | * | 26 | * |
| 27 | * @param reqVO 更新内容 | 27 | * @param reqVO 更新内容 |
| 28 | */ | 28 | */ |
| 29 | void updateKnowledgeSegment(AiKnowledgeSegmentUpdateReqVO reqVO); | 29 | void updateKnowledgeSegment(AiKnowledgeSegmentUpdateReqVO reqVO); |
| 30 | 30 | ||
| 31 | /** | 31 | /** |
| 32 | - * 更新状态 | 32 | + * 更新段落的状态 |
| 33 | * | 33 | * |
| 34 | * @param reqVO 更新内容 | 34 | * @param reqVO 更新内容 |
| 35 | */ | 35 | */ |
| 36 | void updateKnowledgeSegmentStatus(AiKnowledgeSegmentUpdateStatusReqVO reqVO); | 36 | void updateKnowledgeSegmentStatus(AiKnowledgeSegmentUpdateStatusReqVO reqVO); |
| 37 | + | ||
| 37 | } | 38 | } |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/service/model/AiApiKeyService.java
| @@ -86,14 +86,6 @@ public interface AiApiKeyService { | @@ -86,14 +86,6 @@ public interface AiApiKeyService { | ||
| 86 | ChatModel getChatModel(Long id); | 86 | ChatModel getChatModel(Long id); |
| 87 | 87 | ||
| 88 | /** | 88 | /** |
| 89 | - * 获得 EmbeddingModel 对象 | ||
| 90 | - * | ||
| 91 | - * @param id 编号 | ||
| 92 | - * @return EmbeddingModel 对象 | ||
| 93 | - */ | ||
| 94 | - EmbeddingModel getEmbeddingModel(Long id); | ||
| 95 | - | ||
| 96 | - /** | ||
| 97 | * 获得 ImageModel 对象 | 89 | * 获得 ImageModel 对象 |
| 98 | * | 90 | * |
| 99 | * TODO 可优化点:目前默认获取 platform 对应的第一个开启的配置用于绘画;后续可以支持配置选择 | 91 | * TODO 可优化点:目前默认获取 platform 对应的第一个开启的配置用于绘画;后续可以支持配置选择 |
| @@ -122,7 +114,15 @@ public interface AiApiKeyService { | @@ -122,7 +114,15 @@ public interface AiApiKeyService { | ||
| 122 | SunoApi getSunoApi(); | 114 | SunoApi getSunoApi(); |
| 123 | 115 | ||
| 124 | /** | 116 | /** |
| 125 | - * 获得 vector 对象 | 117 | + * 获得 EmbeddingModel 对象 |
| 118 | + * | ||
| 119 | + * @param id 编号 | ||
| 120 | + * @return EmbeddingModel 对象 | ||
| 121 | + */ | ||
| 122 | + EmbeddingModel getEmbeddingModel(Long id); | ||
| 123 | + | ||
| 124 | + /** | ||
| 125 | + * 获得 VectorStore 对象 | ||
| 126 | * | 126 | * |
| 127 | * @param id 编号 | 127 | * @param id 编号 |
| 128 | * @return VectorStore 对象 | 128 | * @return VectorStore 对象 |
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/service/model/AiApiKeyServiceImpl.java
| @@ -110,13 +110,6 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | @@ -110,13 +110,6 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | ||
| 110 | } | 110 | } |
| 111 | 111 | ||
| 112 | @Override | 112 | @Override |
| 113 | - public EmbeddingModel getEmbeddingModel(Long id) { | ||
| 114 | - AiApiKeyDO apiKey = validateApiKey(id); | ||
| 115 | - AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); | ||
| 116 | - return modelFactory.getOrCreateEmbeddingModel(platform, apiKey.getApiKey(), apiKey.getUrl()); | ||
| 117 | - } | ||
| 118 | - | ||
| 119 | - @Override | ||
| 120 | public ImageModel getImageModel(AiPlatformEnum platform) { | 113 | public ImageModel getImageModel(AiPlatformEnum platform) { |
| 121 | AiApiKeyDO apiKey = apiKeyMapper.selectFirstByPlatformAndStatus(platform.getPlatform(), CommonStatusEnum.ENABLE.getStatus()); | 114 | AiApiKeyDO apiKey = apiKeyMapper.selectFirstByPlatformAndStatus(platform.getPlatform(), CommonStatusEnum.ENABLE.getStatus()); |
| 122 | if (apiKey == null) { | 115 | if (apiKey == null) { |
| @@ -146,9 +139,17 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | @@ -146,9 +139,17 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | ||
| 146 | } | 139 | } |
| 147 | 140 | ||
| 148 | @Override | 141 | @Override |
| 142 | + public EmbeddingModel getEmbeddingModel(Long id) { | ||
| 143 | + AiApiKeyDO apiKey = validateApiKey(id); | ||
| 144 | + AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); | ||
| 145 | + return modelFactory.getOrCreateEmbeddingModel(platform, apiKey.getApiKey(), apiKey.getUrl()); | ||
| 146 | + } | ||
| 147 | + | ||
| 148 | + @Override | ||
| 149 | public VectorStore getOrCreateVectorStore(Long id) { | 149 | public VectorStore getOrCreateVectorStore(Long id) { |
| 150 | AiApiKeyDO apiKey = validateApiKey(id); | 150 | AiApiKeyDO apiKey = validateApiKey(id); |
| 151 | AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); | 151 | AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); |
| 152 | return vectorFactory.getOrCreateVectorStore(getEmbeddingModel(id), platform, apiKey.getApiKey(), apiKey.getUrl()); | 152 | return vectorFactory.getOrCreateVectorStore(getEmbeddingModel(id), platform, apiKey.getApiKey(), apiKey.getUrl()); |
| 153 | } | 153 | } |
| 154 | + | ||
| 154 | } | 155 | } |
| 155 | \ No newline at end of file | 156 | \ No newline at end of file |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiModelFactory.java
| @@ -27,18 +27,6 @@ public interface AiModelFactory { | @@ -27,18 +27,6 @@ public interface AiModelFactory { | ||
| 27 | ChatModel getOrCreateChatModel(AiPlatformEnum platform, String apiKey, String url); | 27 | ChatModel getOrCreateChatModel(AiPlatformEnum platform, String apiKey, String url); |
| 28 | 28 | ||
| 29 | /** | 29 | /** |
| 30 | - * 基于指定配置,获得 EmbeddingModel 对象 | ||
| 31 | - * <p> | ||
| 32 | - * 如果不存在,则进行创建 | ||
| 33 | - * | ||
| 34 | - * @param platform 平台 | ||
| 35 | - * @param apiKey API KEY | ||
| 36 | - * @param url API URL | ||
| 37 | - * @return ChatModel 对象 | ||
| 38 | - */ | ||
| 39 | - EmbeddingModel getOrCreateEmbeddingModel(AiPlatformEnum platform, String apiKey, String url); | ||
| 40 | - | ||
| 41 | - /** | ||
| 42 | * 基于默认配置,获得 ChatModel 对象 | 30 | * 基于默认配置,获得 ChatModel 对象 |
| 43 | * | 31 | * |
| 44 | * 默认配置,指的是在 application.yaml 配置文件中的 spring.ai 相关的配置 | 32 | * 默认配置,指的是在 application.yaml 配置文件中的 spring.ai 相关的配置 |
| @@ -92,4 +80,16 @@ public interface AiModelFactory { | @@ -92,4 +80,16 @@ public interface AiModelFactory { | ||
| 92 | */ | 80 | */ |
| 93 | SunoApi getOrCreateSunoApi(String apiKey, String url); | 81 | SunoApi getOrCreateSunoApi(String apiKey, String url); |
| 94 | 82 | ||
| 83 | + /** | ||
| 84 | + * 基于指定配置,获得 EmbeddingModel 对象 | ||
| 85 | + * | ||
| 86 | + * 如果不存在,则进行创建 | ||
| 87 | + * | ||
| 88 | + * @param platform 平台 | ||
| 89 | + * @param apiKey API KEY | ||
| 90 | + * @param url API URL | ||
| 91 | + * @return ChatModel 对象 | ||
| 92 | + */ | ||
| 93 | + EmbeddingModel getOrCreateEmbeddingModel(AiPlatformEnum platform, String apiKey, String url); | ||
| 94 | + | ||
| 95 | } | 95 | } |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiModelFactoryImpl.java
| @@ -100,21 +100,6 @@ public class AiModelFactoryImpl implements AiModelFactory { | @@ -100,21 +100,6 @@ public class AiModelFactoryImpl implements AiModelFactory { | ||
| 100 | } | 100 | } |
| 101 | 101 | ||
| 102 | @Override | 102 | @Override |
| 103 | - public EmbeddingModel getOrCreateEmbeddingModel(AiPlatformEnum platform, String apiKey, String url) { | ||
| 104 | - String cacheKey = buildClientCacheKey(EmbeddingModel.class, platform, apiKey, url); | ||
| 105 | - return Singleton.get(cacheKey, (Func0<EmbeddingModel>) () -> { | ||
| 106 | - // TODO @xin 先测试一个 | ||
| 107 | - switch (platform) { | ||
| 108 | - case TONG_YI: | ||
| 109 | - return buildTongYiEmbeddingModel(apiKey); | ||
| 110 | - default: | ||
| 111 | - throw new IllegalArgumentException(StrUtil.format("未知平台({})", platform)); | ||
| 112 | - } | ||
| 113 | - }); | ||
| 114 | - } | ||
| 115 | - | ||
| 116 | - | ||
| 117 | - @Override | ||
| 118 | public ChatModel getDefaultChatModel(AiPlatformEnum platform) { | 103 | public ChatModel getDefaultChatModel(AiPlatformEnum platform) { |
| 119 | //noinspection EnhancedSwitchMigration | 104 | //noinspection EnhancedSwitchMigration |
| 120 | switch (platform) { | 105 | switch (platform) { |
| @@ -192,6 +177,20 @@ public class AiModelFactoryImpl implements AiModelFactory { | @@ -192,6 +177,20 @@ public class AiModelFactoryImpl implements AiModelFactory { | ||
| 192 | return Singleton.get(cacheKey, (Func0<SunoApi>) () -> new SunoApi(url)); | 177 | return Singleton.get(cacheKey, (Func0<SunoApi>) () -> new SunoApi(url)); |
| 193 | } | 178 | } |
| 194 | 179 | ||
| 180 | + @Override | ||
| 181 | + public EmbeddingModel getOrCreateEmbeddingModel(AiPlatformEnum platform, String apiKey, String url) { | ||
| 182 | + String cacheKey = buildClientCacheKey(EmbeddingModel.class, platform, apiKey, url); | ||
| 183 | + return Singleton.get(cacheKey, (Func0<EmbeddingModel>) () -> { | ||
| 184 | + // TODO @xin 先测试一个 | ||
| 185 | + switch (platform) { | ||
| 186 | + case TONG_YI: | ||
| 187 | + return buildTongYiEmbeddingModel(apiKey); | ||
| 188 | + default: | ||
| 189 | + throw new IllegalArgumentException(StrUtil.format("未知平台({})", platform)); | ||
| 190 | + } | ||
| 191 | + }); | ||
| 192 | + } | ||
| 193 | + | ||
| 195 | private static String buildClientCacheKey(Class<?> clazz, Object... params) { | 194 | private static String buildClientCacheKey(Class<?> clazz, Object... params) { |
| 196 | if (ArrayUtil.isEmpty(params)) { | 195 | if (ArrayUtil.isEmpty(params)) { |
| 197 | return clazz.getName(); | 196 | return clazz.getName(); |
| @@ -255,8 +254,7 @@ public class AiModelFactoryImpl implements AiModelFactory { | @@ -255,8 +254,7 @@ public class AiModelFactoryImpl implements AiModelFactory { | ||
| 255 | } | 254 | } |
| 256 | 255 | ||
| 257 | /** | 256 | /** |
| 258 | - * 可参考 {@link ZhiPuAiAutoConfiguration#zhiPuAiChatModel( | ||
| 259 | - *ZhiPuAiConnectionProperties, ZhiPuAiChatProperties, RestClient.Builder, List, FunctionCallbackContext, RetryTemplate, ResponseErrorHandler)} | 257 | + * 可参考 {@link ZhiPuAiAutoConfiguration#zhiPuAiChatModel(ZhiPuAiConnectionProperties, ZhiPuAiChatProperties, RestClient.Builder, List, FunctionCallbackContext, RetryTemplate, ResponseErrorHandler)} |
| 260 | */ | 258 | */ |
| 261 | private ZhiPuAiChatModel buildZhiPuChatModel(String apiKey, String url) { | 259 | private ZhiPuAiChatModel buildZhiPuChatModel(String apiKey, String url) { |
| 262 | url = StrUtil.blankToDefault(url, ZhiPuAiConnectionProperties.DEFAULT_BASE_URL); | 260 | url = StrUtil.blankToDefault(url, ZhiPuAiConnectionProperties.DEFAULT_BASE_URL); |
| @@ -265,8 +263,7 @@ public class AiModelFactoryImpl implements AiModelFactory { | @@ -265,8 +263,7 @@ public class AiModelFactoryImpl implements AiModelFactory { | ||
| 265 | } | 263 | } |
| 266 | 264 | ||
| 267 | /** | 265 | /** |
| 268 | - * 可参考 {@link ZhiPuAiAutoConfiguration#zhiPuAiImageModel( | ||
| 269 | - *ZhiPuAiConnectionProperties, ZhiPuAiImageProperties, RestClient.Builder, RetryTemplate, ResponseErrorHandler)} | 266 | + * 可参考 {@link ZhiPuAiAutoConfiguration#zhiPuAiImageModel(ZhiPuAiConnectionProperties, ZhiPuAiImageProperties, RestClient.Builder, RetryTemplate, ResponseErrorHandler)} |
| 270 | */ | 267 | */ |
| 271 | private ZhiPuAiImageModel buildZhiPuAiImageModel(String apiKey, String url) { | 268 | private ZhiPuAiImageModel buildZhiPuAiImageModel(String apiKey, String url) { |
| 272 | url = StrUtil.blankToDefault(url, ZhiPuAiConnectionProperties.DEFAULT_BASE_URL); | 269 | url = StrUtil.blankToDefault(url, ZhiPuAiConnectionProperties.DEFAULT_BASE_URL); |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiVectorStoreFactory.java
| @@ -4,13 +4,14 @@ import cn.iocoder.yudao.framework.ai.core.enums.AiPlatformEnum; | @@ -4,13 +4,14 @@ import cn.iocoder.yudao.framework.ai.core.enums.AiPlatformEnum; | ||
| 4 | import org.springframework.ai.embedding.EmbeddingModel; | 4 | import org.springframework.ai.embedding.EmbeddingModel; |
| 5 | import org.springframework.ai.vectorstore.VectorStore; | 5 | import org.springframework.ai.vectorstore.VectorStore; |
| 6 | 6 | ||
| 7 | +// TODO @xin:也放到 AiModelFactory 里面好了,后续改成 AiFactory | ||
| 7 | /** | 8 | /** |
| 8 | * AI Vector 模型工厂的接口类 | 9 | * AI Vector 模型工厂的接口类 |
| 10 | + * | ||
| 9 | * @author xiaoxin | 11 | * @author xiaoxin |
| 10 | */ | 12 | */ |
| 11 | public interface AiVectorStoreFactory { | 13 | public interface AiVectorStoreFactory { |
| 12 | 14 | ||
| 13 | - | ||
| 14 | /** | 15 | /** |
| 15 | * 基于指定配置,获得 VectorStore 对象 | 16 | * 基于指定配置,获得 VectorStore 对象 |
| 16 | * <p> | 17 | * <p> |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiVectorStoreFactoryImpl.java
| @@ -26,6 +26,7 @@ public class AiVectorStoreFactoryImpl implements AiVectorStoreFactory { | @@ -26,6 +26,7 @@ public class AiVectorStoreFactoryImpl implements AiVectorStoreFactory { | ||
| 26 | return Singleton.get(cacheKey, (Func0<VectorStore>) () -> { | 26 | return Singleton.get(cacheKey, (Func0<VectorStore>) () -> { |
| 27 | // TODO 芋艿 @xin 这两个配置取哪好呢 | 27 | // TODO 芋艿 @xin 这两个配置取哪好呢 |
| 28 | // TODO 不同模型的向量维度可能会不一样,目前看貌似是以 index 来做区分的,维度不一样存不到一个 index 上 | 28 | // TODO 不同模型的向量维度可能会不一样,目前看貌似是以 index 来做区分的,维度不一样存不到一个 index 上 |
| 29 | + // TODO 回复:好的哈 | ||
| 29 | String index = "default-index"; | 30 | String index = "default-index"; |
| 30 | String prefix = "default:"; | 31 | String prefix = "default:"; |
| 31 | var config = RedisVectorStore.RedisVectorStoreConfig.builder() | 32 | var config = RedisVectorStore.RedisVectorStoreConfig.builder() |
| @@ -41,11 +42,11 @@ public class AiVectorStoreFactoryImpl implements AiVectorStoreFactory { | @@ -41,11 +42,11 @@ public class AiVectorStoreFactoryImpl implements AiVectorStoreFactory { | ||
| 41 | }); | 42 | }); |
| 42 | } | 43 | } |
| 43 | 44 | ||
| 44 | - | ||
| 45 | private static String buildClientCacheKey(Class<?> clazz, Object... params) { | 45 | private static String buildClientCacheKey(Class<?> clazz, Object... params) { |
| 46 | if (ArrayUtil.isEmpty(params)) { | 46 | if (ArrayUtil.isEmpty(params)) { |
| 47 | return clazz.getName(); | 47 | return clazz.getName(); |
| 48 | } | 48 | } |
| 49 | return StrUtil.format("{}#{}", clazz.getName(), ArrayUtil.join(params, "_")); | 49 | return StrUtil.format("{}#{}", clazz.getName(), ArrayUtil.join(params, "_")); |
| 50 | } | 50 | } |
| 51 | + | ||
| 51 | } | 52 | } |