gpt4 book ai didi

postgresql - TypeORM postgresql 急切加载关系定义为惰性

转载 作者:行者123 更新时间:2023-12-03 13:42:00 25 4
gpt4 key购买 nike

我正在尝试找出解决 Nestjs TypeORM postgresql 应用程序中惰性关系的最佳方法(或最佳实践方法)。

我已经将实体中的一些 OneToMany 和 ManyToOne 关系定义为惰性关系,并且在查询这些实体之一的数组时,到目前为止我发现的最佳解决方案是一大堆 promise rosolving。

我的 Customer实体(customer.entity.ts):

import { Column, CreateDateColumn, Entity, Index, PrimaryGeneratedColumn, UpdateDateColumn, ManyToOne, OneToMany } from 'typeorm';
import { IsEmail } from 'class-validator';
import { ReservationDate } from '../reservation_date/reservation_date.entity';

@Entity()
export class Customer {
@PrimaryGeneratedColumn('uuid')
id: string;

@Index()
@Column()
@IsEmail()
email: string;

@Column()
firstName: string;

@Column()
lastName: string;

@CreateDateColumn()
createDate: Date;

@UpdateDateColumn()
updateDate: Date;

@OneToMany(type => ReservationDate, reservationDate => reservationDate.customer)
reservationDates: Promise<ReservationDate[]>;
}

和我的 ReservationDate实体(reservation_date.entity.ts):
import { Column, CreateDateColumn, Entity, PrimaryGeneratedColumn, UpdateDateColumn, ManyToOne } from 'typeorm';
import { Customer } from '../customer/customer.entity';

@Entity()
export class ReservationDate {
@PrimaryGeneratedColumn('uuid')
id: string;

@Column()
date: Date;

@CreateDateColumn()
createDate: Date;

@UpdateDateColumn()
updateDate: Date;

@ManyToOne(type => Customer, customer => customer.reservationDates, { onDelete: 'CASCADE' })
customer: Promise<Customer>;
}

我需要检索 ReservationDate 的数组s,并将其发送到某个地方,但我需要它来解决 customer字段(例如,预先加载该关系)。这就是“工作”:
const reservationDates: ReservationDate[] = await this.reservationDateRepository
.createQueryBuilder('reservationDate')
.leftJoinAndSelect('reservationDate.customer', 'customer')
.getMany();

// Same result as query builder above
// const reservationDates: ReservationDate[] = await this.reservationDateRepository
// .find({
// relations: ['customer'],
// take: 5
// });

console.log(reservationDates[0].car); // => Promise { <pending> }
console.log(reservationDates[0].__car__); // => Car { id: string, owner... }

// this is where it gets ugly
const reservationDatesWithResolvedRelationships = await Promise.all(
reservationDates.map(async (resDate: ReservationDate) => {
const withResolved: ReservationDateRepoObject = { ...resDate };

withResolved.customer = await resDate.customer;

return withResolved;
})
);

console.log(reservationDatesWithResolvedRelationships[0].car); // => Car { id: string, owner... }

// send off the JSON-like object here

我觉得应该有一种方法来进行连接并强制加载,但查询构建器或 repository.find 都没有。方法似乎按照我设置的方式执行此操作。

我也试过添加 { lazy: true }{ eager: true }实体中的关系,但没有任何改变。

编辑:

仍然没有多少运气,但是我能够一起破解一个伪解决方案。
private parseRaw = name => raw => {
const parsed = new ReservationDate();
Object.entries(raw).forEach(([typeKey, value]) => {
const [type, key] = typeKey.split('_');
if (type === name) {
parsed[key] = value;
} else {
parsed[type] = parsed[type] || {};
parsed[type][key] = value;
}
});
return parsed;
};

let reservationDates: ReservationDate[] = (await this.reservationDateRepository
.createQueryBuilder('reservationDate')
.leftJoinAndSelect('reservationDate.customer', 'customer')
.limit(5)
.getRawMany()).map(this.parseRaw('reservationDate'));

super 丑陋的 hack,但它会转换原始数据, snake_case db 结果到 camelCase我需要发送的json对象...

最佳答案

您需要使用 find()为了实现急切加载,

Eager relations only work when you use find* methods. If you use QueryBuilder eager relations are disabled and have to use leftJoinAndSelect to load the relation. Eager relations can only be used on one side of the relationship, using eager: true on both sides of relationship is disallowed.


Docs here

关于postgresql - TypeORM postgresql 急切加载关系定义为惰性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52333277/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com