TypeORM不支持PostgreSQL向量类型,NestJS无法访问向量列求助
解决NestJS+TypeORM中无法访问手动添加的PostgreSQL向量列问题
以下是几种可行的解决方法:
方法1:在Product实体中显式定义embedding字段
TypeORM虽然原生不支持PostgreSQL的vector类型,但可以直接指定字段类型为vector,让TypeORM直接映射数据库已存在的列。修改你的Product实体:
import { Entity, Column, PrimaryGeneratedColumn } from 'typeorm'; @Entity('products') export class Product { @PrimaryGeneratedColumn() id: number; // 其他已有的字段示例 @Column() name: string; // 添加embedding字段定义 @Column({ type: 'vector', nullable: true, length: 512 // 对应你手动创建的向量维度 }) embedding?: number[]; }
修改后,TypeORM会自动将数据库中的embedding列映射到实体的embedding属性,你就能在服务中直接访问product.embedding了。由于你已经手动创建了该列,无需生成新的迁移文件,重启服务即可生效。
方法2:使用QueryBuilder查询并获取原始结果
如果不想修改实体类,可以通过TypeORM的QueryBuilder直接指定查询embedding字段,再通过getRawOne()或getRawMany()获取包含该字段的原始结果:
// 在ProductService中的示例方法 async getProductWithEmbedding(id: number) { const rawProduct = await this.productRepository .createQueryBuilder('p') .select(['p.id', 'p.name', 'p.embedding']) .where('p.id = :id', { id }) .getRawOne(); // TypeScript类型断言,避免类型报错 return rawProduct as { id: number; name: string; embedding: number[] }; }
这种方式无需修改实体,适合临时或局部需要访问该字段的场景,仅需处理TypeScript的类型断言即可。
方法3:扩展实体类型(可选)
如果需要在多个地方访问embedding字段但不想修改原实体,可以创建扩展类型:
// 定义扩展类型 type ProductWithEmbedding = Product & { embedding: number[] }; // 在服务中使用 async getProduct(id: number): Promise<ProductWithEmbedding> { const product = await this.productRepository.findOne({ where: { id } }); // 单独查询embedding字段并赋值 const { p_embedding: embedding } = await this.productRepository .createQueryBuilder('p') .select('p.embedding') .where('p.id = :id', { id }) .getRawOne(); return { ...product, embedding } as ProductWithEmbedding; }
这种方式适合需要保持原实体纯净,但又要在多个场景使用带embedding的产品对象的需求。
内容的提问来源于stack exchange,提问作者FARHAN JAVAID
相关产品推荐
相关产品推荐

