• Eager 和 Lazy 关系
    • Eager 关系
    • Lazy 关系

    Eager 和 Lazy 关系

    Eager 关系

    每次从数据库加载实体时,都会自动加载 Eager 关系。例如:

    1. import { Entity, PrimaryGeneratedColumn, Column, ManyToMany } from "typeorm";
    2. import { Question } from "./Question";
    3. @Entity()
    4. export class Category {
    5. @PrimaryGeneratedColumn()
    6. id: number;
    7. @Column()
    8. name: string;
    9. @ManyToMany(type => Question, question => question.categories)
    10. questions: Question[];
    11. }
    1. import { Entity, PrimaryGeneratedColumn, Column, ManyToMany, JoinTable } from "typeorm";
    2. import { Category } from "./Category";
    3. @Entity()
    4. export class Question {
    5. @PrimaryGeneratedColumn()
    6. id: number;
    7. @Column()
    8. title: string;
    9. @Column()
    10. text: string;
    11. @ManyToMany(type => Category, category => category.questions, {
    12. eager: true
    13. })
    14. @JoinTable()
    15. categories: Category[];
    16. }

    现在当你加载 questions 时,不需要加入或指定要加载的关系。它们将自动加载:

    1. const questionRepository = connection.getRepository(Question);
    2. // questions 将加载其类别 categories
    3. const questions = await questionRepository.find();

    Eager 关系只有在使用find *方法时才有效。如果你使用QueryBuilder,则禁用 eager 关系,并且必须使用leftJoinAndSelect来加载。Eager 的关系只能用于关系的一方,在关系的两边使用eager:true是不允许的。

    Lazy 关系

    当你访问的时候会加载 Lazy 关系中的实体。这种关系必须有Promise作为类型 ,并且将值存储在一个 promise 中,当你加载它们时,也会返回 promise。 例如:

    1. import { Entity, PrimaryGeneratedColumn, Column, ManyToMany } from "typeorm";
    2. import { Question } from "./Question";
    3. @Entity()
    4. export class Category {
    5. @PrimaryGeneratedColumn()
    6. id: number;
    7. @Column()
    8. name: string;
    9. @ManyToMany(type => Question, question => question.categories)
    10. questions: Promise<Question[]>;
    11. }
    1. import { Entity, PrimaryGeneratedColumn, Column, ManyToMany, JoinTable } from "typeorm";
    2. import { Category } from "./Category";
    3. @Entity()
    4. export class Question {
    5. @PrimaryGeneratedColumn()
    6. id: number;
    7. @Column()
    8. title: string;
    9. @Column()
    10. text: string;
    11. @ManyToMany(type => Category, category => category.questions)
    12. @JoinTable()
    13. categories: Promise<Category[]>;
    14. }

    categories 是一个 Promise. 这意味着它是 lazy 的,它只能存储一个带有值的 promise。

    例如:

    保存这种关系:

    1. const category1 = new Category();
    2. category1.name = "animals";
    3. await connection.manager.save(category1);
    4. const category2 = new Category();
    5. category2.name = "zoo";
    6. await connection.manager.save(category2);
    7. const question = new Question();
    8. question.categories = Promise.resolve([category1, category2]);
    9. await connection.manager.save(question);

    如何在 Lazy 关系中加载对象:

    1. const question = await connection.getRepository(Question).findOne(1);
    2. const categories = await question.categories;
    3. // you'll have all question's categories inside "categories" variable now

    注意:如果你来自其他语言(Java,PHP 等)并且习惯于在任何地方使用 lazy 关系,请小心使用。这些语言不是异步的,延迟加载是以不同的方式实现的,这就是为什么不能使用 promises 的原因。在 JavaScript 和 Node.JS 中,如果你想拥有延迟加载的关系,你必须使用 promises。但是这是非标准技术,而且在 TypeORM 中被认为是实验性的。