使用 typeorm 并尝试找出如何查询多对多关系,我有两个表:
产品(id,名称...等)<---many-to-many--->stash(id,名称...等)
连接表有两个附加列:expirationDate 和数量
我已经确定了关系 :
@Entity('stash')
export class Stash {
@PrimaryGeneratedColumn()
id?: number;
@Column("text")
name!: string;
@OneToMany(type => productStash, ps => ps.stash)
public productStashes?: Relation<ProductStash[]>;
}
@Entity('product')
export class Product {
@PrimaryGeneratedColumn()
id?: number;
@Column("text")
name!: string;
@OneToMany(type => productStash, ps => ps.prudct)
public productStashes?: Relation<ProductStash[]>;
}
加入表:
@Entity('product_stash')
export class ProductStash {
@Column("integer")
@PrimaryColumn({ name: 'ingredientId' })
ingredientId?: number;
@Column("integer")
@PrimaryColumn({ name: 'stashId' })
stashId?: number;
@Column("integer", { default: 1 })
quantity?: number;
@Column("text")
expirationDate!: Date;
@ManyToOne(type => Product, p => p.productStashes)
product?: Relation<Product>
@ManyToOne(type => Stash, s => s.productStashes)
stash?: Relation<Stash>;
}
现在,当我尝试查询藏品及其所有产品时,我得到:
repository.createQueryBuilder("s")
.innerJoinAndSelect("s.productStashes", "sp")
.innerJoinAndSelect("sp.product", "p")
.where("s.id = :id", { id: stashId })
.getOne();
我明白了:
{
"id":1,
"name":"stash_1",
"productStashes":[
{
"quantity":1,
"expirationDate":"2023-07-11",
"product":{
"id":1,
"name":"Computer"
}
},
{
"quantity":1,
"expirationDate":"2023-07-11 19:06:58.861",
"product":{
"id":2,
"name":"Mouse"
}
}
]
}
但我想要的是连接表中的额外列(过期日期、数量)位于产品对象中,或者可能只是展平产品对象以获得类似的内容:
{
"id":1,
"name":"stash_1",
"productStashes":[
{
"quantity":1,
"expirationDate":"2023-07-11",
"id":1,
"name":"Computer"
},
{
"quantity":1,
"expirationDate":"2023-07-11 19:06:58.861",
"id":2,
"name":"Mouse"
}
]
}
知道我该怎么做吗?
要实现连接表中的额外列(
expirationDate
和 quantity
)包含在 Product
对象中或 Product
对象在 Stash
对象中展平的预期结果,您可以修改相应的查询和实体定义。具体方法如下:
修改您的
Stash
实体以将 productStashes
的属性包含为同时包含 Product
属性和连接表属性的对象数组。
@Entity('藏匿') 导出类存储{ @PrimaryGenerateColumn() id?:号码;
@Column("text")
name!: string;
@OneToMany(type => ProductStash, ps => ps.stash, { eager: true })
productStashes?: ProductStash[]; // Use eager loading to load related entities
}
修改查询以从联接表和产品中获取所需的列,然后根据需要格式化结果:
const stash =等待repository.createQueryBuilder(“s”) .leftJoin("s.productStashes", "ps") // 使用左连接包含所有存储,即使是那些没有产品存储的 .leftJoin("ps.product", "p") .where("s.id = :id", { id: stashId }) .getOne();
// 根据需要格式化结果 常量格式化Stash = { id: 存储.id, 名称: 存储名称, 产品Stashes: stash.productStashes.map(ps => ({ 数量:ps.数量, 过期日期: ps.expirationDate, ...ps.product, // 传播 Product 属性 })), };
console.log(formattedStash);
此代码将从连接表中检索存储及其关联的产品存储,包括额外的列(
expirationDate
和 quantity
),然后按照您指定的方式格式化结果。