作者 lixiang

框架修改

  1 +package org.jeecg.modules.airag.app.config;
  2 +
  3 +import org.springframework.boot.context.properties.ConfigurationProperties;
  4 +import org.springframework.boot.jdbc.DataSourceBuilder;
  5 +import org.springframework.context.annotation.Bean;
  6 +import org.springframework.context.annotation.Configuration;
  7 +import org.springframework.context.annotation.Primary;
  8 +
  9 +import javax.sql.DataSource;
  10 +
  11 +@Configuration
  12 +public class DataSourceConfig {
  13 +
  14 +// @Bean(name = "mysqlDataSource")
  15 +// @Primary
  16 +// @ConfigurationProperties(prefix = "spring.datasource.mysql")
  17 +// public DataSource mysqlDataSource() {
  18 +// return DataSourceBuilder.create().build();
  19 +// }
  20 +//
  21 +// @Bean(name = "postgresDataSource")
  22 +// @ConfigurationProperties(prefix = "spring.datasource.postgres")
  23 +// public DataSource postgresDataSource() {
  24 +// return DataSourceBuilder.create().build();
  25 +// }
  26 +}
  1 +package org.jeecg.modules.airag.app.controller;
  2 +
  3 +import java.lang.reflect.Field;
  4 +import java.util.Arrays;
  5 +import java.util.List;
  6 +import javax.servlet.http.HttpServletRequest;
  7 +import javax.servlet.http.HttpServletResponse;
  8 +import javax.sql.DataSource;
  9 +import java.sql.Connection; // PostgreSQL JDBC 连接
  10 +import java.sql.PreparedStatement;
  11 +import java.sql.ResultSet;
  12 +import java.sql.ResultSetMetaData;
  13 +import java.sql.SQLException;
  14 +import java.util.ArrayList;
  15 +import java.util.HashMap;
  16 +import java.util.List;
  17 +import java.util.Map;
  18 +
  19 +import dev.langchain4j.store.embedding.EmbeddingStore; // LangChain4j 的 EmbeddingStore 接口
  20 +import dev.langchain4j.store.embedding.pgvector.PgVectorEmbeddingStore;
  21 +import dev.langchain4j.data.embedding.Embedding;
  22 +import dev.langchain4j.data.segment.TextSegment;
  23 +import dev.langchain4j.model.embedding.EmbeddingModel;
  24 +import dev.langchain4j.model.output.Response;
  25 +import dev.langchain4j.store.embedding.EmbeddingMatch;
  26 +import dev.langchain4j.store.embedding.EmbeddingSearchRequest;
  27 +import dev.langchain4j.store.embedding.EmbeddingSearchResult;
  28 +import dev.langchain4j.store.embedding.EmbeddingStore;
  29 +import dev.langchain4j.store.embedding.pgvector.PgVectorEmbeddingStore;
  30 +import org.jeecg.common.api.vo.Result;
  31 +import org.jeecg.common.system.query.QueryGenerator;
  32 +
  33 +import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
  34 +import com.baomidou.mybatisplus.core.metadata.IPage;
  35 +import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
  36 +import lombok.extern.slf4j.Slf4j;
  37 +
  38 +//import org.jeecg.modules.airag.app.config.PostgreEmbeddingStore;
  39 +import org.jeecg.modules.airag.app.entity.Embeddings;
  40 +import org.jeecg.modules.airag.app.entity.Embeddings;
  41 +import org.jeecg.modules.airag.app.service.IEmbeddingsService;
  42 +import org.jeecg.common.system.base.controller.JeecgController;
  43 +import org.jeecg.modules.airag.app.utils.AiModelUtils;
  44 +import org.jeecg.modules.airag.llm.entity.AiragModel;
  45 +import org.springframework.beans.factory.annotation.Autowired;
  46 +import org.springframework.beans.factory.annotation.Qualifier;
  47 +import org.springframework.boot.jdbc.DataSourceBuilder;
  48 +import org.springframework.web.bind.annotation.*;
  49 +import org.springframework.web.servlet.ModelAndView;
  50 +import io.swagger.v3.oas.annotations.tags.Tag;
  51 +import io.swagger.v3.oas.annotations.Operation;
  52 +import org.jeecg.common.aspect.annotation.AutoLog;
  53 +import org.apache.shiro.authz.annotation.RequiresPermissions;
  54 +
  55 + /**
  56 + * @Description: Embeddings
  57 + * @Author: jeecg-boot
  58 + * @Date: 2025-05-26
  59 + * @Version: V1.0
  60 + */
  61 +@Tag(name="Embeddings")
  62 +@RestController
  63 +@RequestMapping("/embeddings/embeddings")
  64 +@Slf4j
  65 +public class EmbeddingsController {
  66 + @Autowired
  67 + private IEmbeddingsService embeddingsService;
  68 +
  69 + @Autowired
  70 + private AiModelUtils aiModelUtils;
  71 +
  72 +
  73 + /**
  74 + * 分页列表查询
  75 + *
  76 + * @param Embeddings
  77 + * @param pageNo
  78 + * @param pageSize
  79 + * @param req
  80 + * @return
  81 + */
  82 + //@AutoLog(value = "Embeddings-分页列表查询")
  83 + @Operation(summary="Embeddings-分页列表查询")
  84 + @GetMapping(value = "/list")
  85 + public Result<IPage<Embeddings>> queryPageList(Embeddings Embeddings,
  86 + @RequestParam(name="pageNo", defaultValue="1") Integer pageNo,
  87 + @RequestParam(name="pageSize", defaultValue="10") Integer pageSize,
  88 + HttpServletRequest req) throws NoSuchFieldException, IllegalAccessException, SQLException {
  89 + Response<Embedding> embedding = aiModelUtils.getEmbedding("1925730210204721154", "33333");
  90 +
  91 + List<Embeddings> records = embeddingsService.findAll();
  92 + for (Embeddings record : records) {
  93 + System.out.println("record = " + record);
  94 + }
  95 + Page<Embeddings> page = new Page<Embeddings>(pageNo, pageSize);
  96 + page.setRecords(records);
  97 + return Result.OK(page);
  98 + }
  99 +
  100 + /**
  101 + * 添加
  102 + *
  103 + * @param Embeddings
  104 + * @return
  105 + */
  106 + @AutoLog(value = "Embeddings-添加")
  107 + @Operation(summary="Embeddings-添加")
  108 + @RequiresPermissions("Embeddings:Embeddings:add")
  109 + @PostMapping(value = "/add")
  110 + public Result<String> add(@RequestBody Embeddings Embeddings) {
  111 +// embeddingsService.save(Embeddings);
  112 + return Result.OK("添加成功!");
  113 + }
  114 +
  115 + /**
  116 + * 编辑
  117 + *
  118 + * @param Embeddings
  119 + * @return
  120 + */
  121 + @AutoLog(value = "Embeddings-编辑")
  122 + @Operation(summary="Embeddings-编辑")
  123 + @RequiresPermissions("Embeddings:Embeddings:edit")
  124 + @RequestMapping(value = "/edit", method = {RequestMethod.PUT,RequestMethod.POST})
  125 + public Result<String> edit(@RequestBody Embeddings Embeddings) {
  126 +// embeddingsService.updateById(Embeddings);
  127 + return Result.OK("编辑成功!");
  128 + }
  129 +
  130 + /**
  131 + * 通过id删除
  132 + *
  133 + * @param id
  134 + * @return
  135 + */
  136 + @AutoLog(value = "Embeddings-通过id删除")
  137 + @Operation(summary="Embeddings-通过id删除")
  138 + @RequiresPermissions("Embeddings:Embeddings:delete")
  139 + @DeleteMapping(value = "/delete")
  140 + public Result<String> delete(@RequestParam(name="id",required=true) String id) {
  141 +// embeddingsService.removeById(id);
  142 + return Result.OK("删除成功!");
  143 + }
  144 +
  145 + /**
  146 + * 批量删除
  147 + *
  148 + * @param ids
  149 + * @return
  150 + */
  151 + @AutoLog(value = "Embeddings-批量删除")
  152 + @Operation(summary="Embeddings-批量删除")
  153 + @RequiresPermissions("Embeddings:Embeddings:deleteBatch")
  154 + @DeleteMapping(value = "/deleteBatch")
  155 + public Result<String> deleteBatch(@RequestParam(name="ids",required=true) String ids) {
  156 +// this.embeddingsService.removeByIds(Arrays.asList(ids.split(",")));
  157 + return Result.OK("批量删除成功!");
  158 + }
  159 +
  160 + /**
  161 + * 通过id查询
  162 + *
  163 + * @param id
  164 + * @return
  165 + */
  166 + //@AutoLog(value = "Embeddings-通过id查询")
  167 + @Operation(summary="Embeddings-通过id查询")
  168 + @GetMapping(value = "/queryById")
  169 + public Result<Embeddings> queryById(@RequestParam(name="id",required=true) String id) {
  170 +// Embeddings Embeddings = embeddingsService.getById(id);
  171 +// if(Embeddings==null) {
  172 +// return Result.error("未找到对应数据");
  173 +// }
  174 + return Result.OK();
  175 + }
  176 +
  177 + /**
  178 + * 导出excel
  179 + *
  180 + * @param request
  181 + * @param Embeddings
  182 + */
  183 + @RequiresPermissions("Embeddings:Embeddings:exportXls")
  184 + @RequestMapping(value = "/exportXls")
  185 + public ModelAndView exportXls(HttpServletRequest request, Embeddings Embeddings) {
  186 + return null;
  187 + }
  188 +
  189 + /**
  190 + * 通过excel导入数据
  191 + *
  192 + * @param request
  193 + * @param response
  194 + * @return
  195 + */
  196 + @RequiresPermissions("Embeddings:Embeddings:importExcel")
  197 + @RequestMapping(value = "/importExcel", method = RequestMethod.POST)
  198 + public Result<?> importExcel(HttpServletRequest request, HttpServletResponse response) {
  199 + return null;
  200 + }
  201 +
  202 +}
  1 +package org.jeecg.modules.airag.app.entity;
  2 +
  3 +import lombok.AllArgsConstructor;
  4 +import lombok.Data;
  5 +import lombok.NoArgsConstructor;
  6 +
  7 +import java.util.Map;
  8 +
  9 +@Data
  10 +@AllArgsConstructor
  11 +@NoArgsConstructor
  12 +public class Embeddings {
  13 + private String id;
  14 +
  15 + private String text;
  16 +
  17 + private float[] embedding;
  18 +
  19 + private Map<String, Object> metadata;
  20 +
  21 + private Double similarity;
  22 +}
  1 +package org.jeecg.modules.airag.app.entity;
  2 +
  3 +import java.io.Serializable;
  4 +import java.io.UnsupportedEncodingException;
  5 +import java.util.Date;
  6 +import java.math.BigDecimal;
  7 +import com.baomidou.mybatisplus.annotation.IdType;
  8 +import com.baomidou.mybatisplus.annotation.TableId;
  9 +import com.baomidou.mybatisplus.annotation.TableName;
  10 +import com.baomidou.mybatisplus.annotation.TableLogic;
  11 +import org.jeecg.common.constant.ProvinceCityArea;
  12 +import org.jeecg.common.util.SpringContextUtils;
  13 +import lombok.Data;
  14 +import com.fasterxml.jackson.annotation.JsonFormat;
  15 +import org.springframework.format.annotation.DateTimeFormat;
  16 +import org.jeecgframework.poi.excel.annotation.Excel;
  17 +import org.jeecg.common.aspect.annotation.Dict;
  18 +import io.swagger.v3.oas.annotations.media.Schema;
  19 +import lombok.EqualsAndHashCode;
  20 +import lombok.experimental.Accessors;
  21 +
  22 +/**
  23 + * @Description: test
  24 + * @Author: jeecg-boot
  25 + * @Date: 2025-05-26
  26 + * @Version: V1.0
  27 + */
  28 +@Data
  29 +@TableName("test")
  30 +@Accessors(chain = true)
  31 +@EqualsAndHashCode(callSuper = false)
  32 +@Schema(description="test")
  33 +public class Test implements Serializable {
  34 + private static final long serialVersionUID = 1L;
  35 +
  36 + /**id*/
  37 + @TableId(type = IdType.ASSIGN_ID)
  38 + @Schema(description = "id")
  39 + private Integer id;
  40 + /**name*/
  41 + @Excel(name = "name", width = 15)
  42 + @Schema(description = "name")
  43 + private String name;
  44 +}
  1 +package org.jeecg.modules.airag.app.mapper;
  2 +
  3 +import java.util.List;
  4 +
  5 +import org.apache.ibatis.annotations.Param;
  6 +import com.baomidou.mybatisplus.core.mapper.BaseMapper;
  7 +import org.jeecg.modules.airag.app.entity.Embeddings;
  8 +import org.jeecg.modules.airag.app.entity.Test;
  9 +
  10 +/**
  11 + * @Description: test
  12 + * @Author: jeecg-boot
  13 + * @Date: 2025-05-26
  14 + * @Version: V1.0
  15 + */
  16 +public interface EmbeddingsMapper {
  17 +
  18 +}
  1 +package org.jeecg.modules.airag.app.mapper;
  2 +
  3 +import com.fasterxml.jackson.core.JsonProcessingException;
  4 +import com.fasterxml.jackson.core.type.TypeReference;
  5 +import com.fasterxml.jackson.databind.ObjectMapper;
  6 +import com.pgvector.PGvector;
  7 +import lombok.extern.slf4j.Slf4j;
  8 +import org.apache.commons.lang3.StringUtils;
  9 +import org.apache.shiro.dao.DataAccessException;
  10 +import org.jeecg.modules.airag.app.entity.Embeddings;
  11 +import org.springframework.stereotype.Component;
  12 +
  13 +import java.sql.*;
  14 +import java.util.ArrayList;
  15 +import java.util.Collections;
  16 +import java.util.List;
  17 +import java.util.Map;
  18 +
  19 +@Component
  20 +@Slf4j
  21 +public class PgVectorMapper {
  22 +
  23 + // PostgreSQL连接参数(实际项目中应从配置读取)
  24 + private static final String URL = "jdbc:postgresql://192.168.100.103:5432/postgres";
  25 + private static final String USER = "postgres";
  26 + private static final String PASSWORD = "postgres";
  27 +
  28 + // 获取数据库连接
  29 + private Connection getConnection() throws SQLException {
  30 + return DriverManager.getConnection(URL, USER, PASSWORD);
  31 + }
  32 +
  33 + // 查询所有向量记录
  34 + public List<Embeddings> findAll() {
  35 + List<Embeddings> results = new ArrayList<>();
  36 + String sql = "SELECT * FROM embeddings";
  37 +
  38 + try (Connection conn = getConnection();
  39 + PreparedStatement stmt = conn.prepareStatement(sql);
  40 + ResultSet rs = stmt.executeQuery()) {
  41 +
  42 + while (rs.next()) {
  43 + results.add(mapRowToEmbeddings(rs));
  44 + }
  45 + } catch (SQLException e) {
  46 + log.error("查询所有向量记录失败", e);
  47 + throw new RuntimeException("查询向量数据时发生数据库错误", e);
  48 + }
  49 + return results;
  50 + }
  51 +
  52 + // 根据ID查询单个向量记录
  53 + public Embeddings findById(Long id) {
  54 + String sql = "SELECT * FROM embeddings WHERE id = ?";
  55 +
  56 + try (Connection conn = getConnection();
  57 + PreparedStatement stmt = conn.prepareStatement(sql)) {
  58 +
  59 + stmt.setLong(1, id);
  60 + try (ResultSet rs = stmt.executeQuery()) {
  61 + if (rs.next()) {
  62 + return mapRowToEmbeddings(rs);
  63 + }
  64 + }
  65 + } catch (SQLException e) {
  66 + log.error("根据ID查询向量记录失败, ID: {}", id, e);
  67 + throw new RuntimeException("根据ID查询向量时发生数据库错误", e);
  68 + }
  69 + return null;
  70 + }
  71 +
  72 + // 插入新向量记录
  73 + public int insert(Embeddings record) {
  74 + String sql = "INSERT INTO embeddings (id, embedding, metadata) VALUES (?, ?, ?::jsonb)";
  75 +
  76 + try (Connection conn = getConnection();
  77 + PreparedStatement stmt = conn.prepareStatement(sql)) {
  78 +
  79 + stmt.setString(1, record.getId());
  80 + stmt.setObject(2, new PGvector(record.getEmbedding()));
  81 + stmt.setString(3, toJson(record.getMetadata()));
  82 +
  83 + return stmt.executeUpdate();
  84 + } catch (SQLException e) {
  85 + log.error("插入向量记录失败: {}", record, e);
  86 + throw new RuntimeException("插入向量数据时发生数据库错误", e);
  87 + }
  88 + }
  89 +
  90 + // 更新向量记录
  91 + public int update(Embeddings record) {
  92 + String sql = "UPDATE embeddings SET embedding = ?, metadata = ?::jsonb WHERE id = ?";
  93 +
  94 + try (Connection conn = getConnection();
  95 + PreparedStatement stmt = conn.prepareStatement(sql)) {
  96 +
  97 + stmt.setObject(1, new PGvector(record.getEmbedding()));
  98 + stmt.setString(2, toJson(record.getMetadata()));
  99 + stmt.setString(3, record.getId());
  100 +
  101 + return stmt.executeUpdate();
  102 + } catch (SQLException e) {
  103 + log.error("更新向量记录失败: {}", record, e);
  104 + throw new RuntimeException("更新向量数据时发生数据库错误", e);
  105 + }
  106 + }
  107 +
  108 + // 根据ID删除向量记录
  109 + public int deleteById(Long id) {
  110 + String sql = "DELETE FROM embeddings WHERE id = ?";
  111 +
  112 + try (Connection conn = getConnection();
  113 + PreparedStatement stmt = conn.prepareStatement(sql)) {
  114 +
  115 + stmt.setLong(1, id);
  116 + return stmt.executeUpdate();
  117 + } catch (SQLException e) {
  118 + log.error("删除向量记录失败, ID: {}", id, e);
  119 + throw new RuntimeException("删除向量数据时发生数据库错误", e);
  120 + }
  121 + }
  122 +
  123 + // 向量相似度搜索
  124 + public List<Embeddings> similaritySearch(float[] vector, int limit) {
  125 + String sql = "SELECT * FROM embeddings ORDER BY embedding <-> ? LIMIT ?";
  126 + List<Embeddings> results = new ArrayList<>();
  127 +
  128 + try (Connection conn = getConnection();
  129 + PreparedStatement stmt = conn.prepareStatement(sql)) {
  130 +
  131 + stmt.setObject(1, new PGvector(vector));
  132 + stmt.setInt(2, limit);
  133 +
  134 + try (ResultSet rs = stmt.executeQuery()) {
  135 + while (rs.next()) {
  136 + results.add(mapRowToEmbeddings(rs));
  137 + }
  138 + }
  139 + } catch (SQLException e) {
  140 + log.error("向量相似度搜索失败", e);
  141 + throw new RuntimeException("执行向量相似度搜索时发生数据库错误", e);
  142 + }
  143 + return results;
  144 + }
  145 +
  146 + // 将ResultSet行映射为VectorRecord对象
  147 + private Embeddings mapRowToEmbeddings(ResultSet rs) throws SQLException {
  148 + Embeddings record = new Embeddings();
  149 + record.setId(rs.getString("embedding_id"));
  150 + record.setText(rs.getString("text"));
  151 +
  152 + String metadataJson = rs.getString("metadata");
  153 + if (StringUtils.isNotBlank(metadataJson)) {
  154 + record.setMetadata(fromJson(metadataJson));
  155 + }
  156 +
  157 + return record;
  158 + }
  159 +
  160 + // 将Map转换为JSON字符串
  161 + private String toJson(Map<String, Object> map) {
  162 + try {
  163 + return new ObjectMapper().writeValueAsString(map);
  164 + } catch (JsonProcessingException e) {
  165 + log.error("元数据转换为JSON失败", e);
  166 + return "{}";
  167 + }
  168 + }
  169 +
  170 + // 将JSON字符串转换为Map
  171 + private Map<String, Object> fromJson(String json) {
  172 + try {
  173 + return new ObjectMapper().readValue(json, new TypeReference<Map<String, Object>>() {});
  174 + } catch (JsonProcessingException e) {
  175 + log.error("JSON转换为元数据失败", e);
  176 + return Collections.emptyMap();
  177 + }
  178 + }
  179 +}
  1 +package org.jeecg.modules.airag.app.service;
  2 +
  3 +//import org.jeecg.modules.demo.test.entity.Test;
  4 +import org.jeecg.modules.airag.app.entity.Test;
  5 +
  6 +import com.baomidou.mybatisplus.extension.service.IService;
  7 +import org.jeecg.modules.airag.app.entity.Embeddings;
  8 +
  9 +import java.util.List;
  10 +
  11 +/**
  12 + * @Description: test
  13 + * @Author: jeecg-boot
  14 + * @Date: 2025-05-26
  15 + * @Version: V1.0
  16 + */
  17 +public interface IEmbeddingsService {
  18 +
  19 + List<Embeddings> findAll();
  20 +}
  1 +package org.jeecg.modules.airag.app.service.impl;
  2 +
  3 +import org.jeecg.modules.airag.app.entity.Test;
  4 +import org.jeecg.modules.airag.app.entity.Embeddings;
  5 +import org.jeecg.modules.airag.app.mapper.EmbeddingsMapper;
  6 +import org.jeecg.modules.airag.app.mapper.PgVectorMapper;
  7 +import org.jeecg.modules.airag.app.service.IEmbeddingsService;
  8 +import org.springframework.beans.factory.annotation.Autowired;
  9 +import org.springframework.stereotype.Service;
  10 +
  11 +import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
  12 +
  13 +import java.util.List;
  14 +
  15 +/**
  16 + * @Description: test
  17 + * @Author: jeecg-boot
  18 + * @Date: 2025-05-26
  19 + * @Version: V1.0
  20 + */
  21 +@Service
  22 +public class IEmbeddingsServiceImpl implements IEmbeddingsService {
  23 + @Autowired
  24 + private PgVectorMapper pgVectorMapper;
  25 + @Override
  26 + public List<Embeddings> findAll() {
  27 + return pgVectorMapper.findAll();
  28 + }
  29 +}
  1 +package org.jeecg.modules.airag.app.utils;
  2 +
  3 +import dev.langchain4j.data.embedding.Embedding;
  4 +import dev.langchain4j.model.embedding.EmbeddingModel;
  5 +import dev.langchain4j.model.output.Response;
  6 +import org.jeecg.ai.factory.AiModelFactory;
  7 +import org.jeecg.ai.factory.AiModelOptions;
  8 +import org.jeecg.common.util.AssertUtils;
  9 +import org.jeecg.modules.airag.llm.consts.LLMConsts;
  10 +import org.jeecg.modules.airag.llm.entity.AiragModel;
  11 +import org.jeecg.modules.airag.llm.service.IAiragModelService;
  12 +import org.springframework.beans.factory.annotation.Autowired;
  13 +import org.springframework.context.annotation.Lazy;
  14 +import org.springframework.stereotype.Component;
  15 +
  16 +import static org.jeecg.modules.airag.llm.handler.EmbeddingHandler.buildModelOptions;
  17 +
  18 +@Component
  19 +public class AiModelUtils {
  20 +
  21 + @Autowired
  22 + @Lazy
  23 + private IAiragModelService airagModelService;
  24 +
  25 + private AiragModel getEmbedModelData(String modelId) {
  26 + AssertUtils.assertNotEmpty("向量模型不能为空", modelId);
  27 + AiragModel model = airagModelService.getById(modelId);
  28 + AssertUtils.assertNotEmpty("向量模型不存在", model);
  29 + AssertUtils.assertEquals("仅支持向量模型", LLMConsts.MODEL_TYPE_EMBED, model.getModelType());
  30 + return model;
  31 + }
  32 +
  33 + /**
  34 + * 获取向量模型
  35 + * @param modelId 模型id
  36 + * @return 向量模型
  37 + */
  38 + public EmbeddingModel getEmbeddingModel(String modelId) {
  39 + AiModelOptions modelOp = buildModelOptions(getEmbedModelData(modelId));
  40 + return AiModelFactory.createEmbeddingModel(modelOp);
  41 + }
  42 +
  43 + /**
  44 + * 根据模型id选择向量模型,将文本向量化
  45 + * @param modelId 模型id
  46 + * text 文本
  47 + * @return Embedding
  48 + */
  49 + public Response<Embedding> getEmbedding(String modelId, String text) {
  50 + return getEmbeddingModel(modelId).embed(text);
  51 + }
  52 +
  53 +
  54 +
  55 +
  56 +}
  1 +package org.jeecg.modules.airag.app.utils;
  2 +
  3 +import java.sql.*;
  4 +import java.util.ArrayList;
  5 +import java.util.HashMap;
  6 +import java.util.List;
  7 +import java.util.Map;
  8 +
  9 +public class PureJdbcVectorQuery {
  10 +
  11 + // PostgreSQL连接参数
  12 + private static final String URL = "jdbc:postgresql://192.168.100.103:5432/postgres";
  13 + private static final String USER = "postgres";
  14 + private static final String PASSWORD = "postgres";
  15 +
  16 + public static List<Map<String, Object>> queryVectors() {
  17 + List<Map<String, Object>> results = new ArrayList<>();
  18 +
  19 + try (Connection conn = DriverManager.getConnection(URL, USER, PASSWORD);
  20 + PreparedStatement stmt = conn.prepareStatement("SELECT * FROM embeddings");
  21 + ResultSet rs = stmt.executeQuery()) {
  22 +
  23 + ResultSetMetaData metaData = rs.getMetaData();
  24 + int columnCount = metaData.getColumnCount();
  25 +
  26 + while (rs.next()) {
  27 + Map<String, Object> row = new HashMap<>();
  28 + for (int i = 1; i <= columnCount; i++) {
  29 + String columnName = metaData.getColumnName(i);
  30 + Object value = "embedding".equals(columnName)
  31 + ? rs.getBytes(i) // 向量字段特殊处理
  32 + : rs.getObject(i);
  33 + row.put(columnName, value);
  34 + }
  35 + results.add(row);
  36 + }
  37 + } catch (SQLException e) {
  38 + e.printStackTrace();
  39 + }
  40 + return results;
  41 + }
  42 +
  43 +
  44 + public static void main(String[] args) {
  45 + List<Map<String, Object>> maps = queryVectors();
  46 + for (Map<String, Object> map : maps) {
  47 + System.out.println(map);
  48 + }
  49 + }
  50 +}
@@ -6,6 +6,7 @@ import org.flywaydb.core.Flyway; @@ -6,6 +6,7 @@ import org.flywaydb.core.Flyway;
6 import org.flywaydb.core.api.FlywayException; 6 import org.flywaydb.core.api.FlywayException;
7 import org.springframework.beans.factory.annotation.Autowired; 7 import org.springframework.beans.factory.annotation.Autowired;
8 8
  9 +import org.springframework.beans.factory.annotation.Qualifier;
9 import org.springframework.beans.factory.annotation.Value; 10 import org.springframework.beans.factory.annotation.Value;
10 import org.springframework.context.annotation.Bean; 11 import org.springframework.context.annotation.Bean;
11 import org.springframework.context.annotation.Configuration; 12 import org.springframework.context.annotation.Configuration;
@@ -26,6 +27,7 @@ import java.util.Map; @@ -26,6 +27,7 @@ import java.util.Map;
26 public class FlywayConfig { 27 public class FlywayConfig {
27 28
28 @Autowired 29 @Autowired
  30 +// @Qualifier("mysqlDataSource")
29 private DataSource dataSource; 31 private DataSource dataSource;
30 32
31 @Autowired 33 @Autowired
@@ -26,7 +26,7 @@ management: @@ -26,7 +26,7 @@ management:
26 spring: 26 spring:
27 flyway: 27 flyway:
28 # 是否启用flyway 28 # 是否启用flyway
29 - enabled: true 29 + enabled: false
30 # 是否关闭要清除已有库下的表功能,生产环境必须为true,否则会删库,非常重要!!! 30 # 是否关闭要清除已有库下的表功能,生产环境必须为true,否则会删库,非常重要!!!
31 clean-disabled: true 31 clean-disabled: true
32 servlet: 32 servlet:
@@ -50,6 +50,8 @@ spring: @@ -50,6 +50,8 @@ spring:
50 quartz: 50 quartz:
51 job-store-type: jdbc 51 job-store-type: jdbc
52 initialize-schema: embedded 52 initialize-schema: embedded
  53 + jdbc:
  54 + initialize-schema: always
53 #定时任务启动开关,true-开 false-关 55 #定时任务启动开关,true-开 false-关
54 auto-startup: true 56 auto-startup: true
55 #延迟1秒启动定时任务 57 #延迟1秒启动定时任务
@@ -119,6 +121,7 @@ spring: @@ -119,6 +121,7 @@ spring:
119 web-stat-filter: 121 web-stat-filter:
120 enabled: true 122 enabled: true
121 dynamic: 123 dynamic:
  124 + primary: master
122 druid: # 全局druid参数,绝大部分值和默认保持一致。(现已支持的参数如下,不清楚含义不要乱设置) 125 druid: # 全局druid参数,绝大部分值和默认保持一致。(现已支持的参数如下,不清楚含义不要乱设置)
123 # 连接池的配置信息 126 # 连接池的配置信息
124 # 初始化大小,最小,最大 127 # 初始化大小,最小,最大
@@ -154,11 +157,11 @@ spring: @@ -154,11 +157,11 @@ spring:
154 password: 1234 157 password: 1234
155 driver-class-name: com.mysql.cj.jdbc.Driver 158 driver-class-name: com.mysql.cj.jdbc.Driver
156 # 多数据源配置 159 # 多数据源配置
157 - #multi-datasource1:  
158 - #url: jdbc:mysql://localhost:3306/jeecg-boot2?useUnicode=true&characterEncoding=utf8&autoReconnect=true&zeroDateTimeBehavior=convertToNull&transformedBitIsBoolean=true&allowPublicKeyRetrieval=true&serverTimezone=Asia/Shanghai  
159 - #username: root  
160 - #password: root  
161 - #driver-class-name: com.mysql.cj.jdbc.Driver 160 +# pgvector:
  161 +# jdbc-url: jdbc:postgresql://192.168.100.103:5432/postgres
  162 +# username: postgres
  163 +# password: postgres
  164 +# driver-class-name: org.postgresql.Driver
162 #redis 配置 165 #redis 配置
163 redis: 166 redis:
164 database: 0 167 database: 0
@@ -253,7 +256,7 @@ jeecg: @@ -253,7 +256,7 @@ jeecg:
253 #大屏报表参数设置 256 #大屏报表参数设置
254 jmreport: 257 jmreport:
255 #多租户模式,默认值为空(created:按照创建人隔离、tenant:按照租户隔离) (v1.6.2+ 新增) 258 #多租户模式,默认值为空(created:按照创建人隔离、tenant:按照租户隔离) (v1.6.2+ 新增)
256 - saasMode: 259 + saasMode:
257 # 平台上线安全配置(v1.6.2+ 新增) 260 # 平台上线安全配置(v1.6.2+ 新增)
258 firewall: 261 firewall:
259 # 数据源安全 (开启后,不允许使用平台数据源、SQL解析加签并且不允许查询数据库) 262 # 数据源安全 (开启后,不允许使用平台数据源、SQL解析加签并且不允许查询数据库)
@@ -432,6 +432,12 @@ @@ -432,6 +432,12 @@
432 </exclusion> 432 </exclusion>
433 </exclusions> 433 </exclusions>
434 </dependency> 434 </dependency>
  435 + <!-- HikariCP连接池 -->
  436 +<!-- <dependency>-->
  437 +<!-- <groupId>com.zaxxer</groupId>-->
  438 +<!-- <artifactId>HikariCP</artifactId>-->
  439 +<!-- <version>5.0.1</version>-->
  440 +<!-- </dependency>-->
435 <dependency> 441 <dependency>
436 <groupId>org.jeecgframework.jimureport</groupId> 442 <groupId>org.jeecgframework.jimureport</groupId>
437 <artifactId>jimureport-nosql-starter</artifactId> 443 <artifactId>jimureport-nosql-starter</artifactId>