【问题标题】:Why do I not have the reference ID of the entity?为什么我没有实体的参考 ID?
【发布时间】:2020-04-23 12:34:12
【问题描述】:

我在 TypeORM 中有两个带有 One To One 连接的简单实体。如果我提出POST 请求,我会得到表格,但引用ID 仍然是null。这是为什么呢?

主要用户实体:

@Entity({ name: "user" })
export class User extends BaseEntity {
  @PrimaryGeneratedColumn()
  id: number;

  @Column({ unique: true })
  username: string;

  @Column()
  password: string;

  @OneToOne(
    (type) => Personal,
    (personal) => personal.user,
    { cascade: true }
  )
  @JoinColumn()
  personalId: personal;
}

个人实体:

@Entity({ name: "personal" })
export class Personal {
  @PrimaryGeneratedColumn()
  id: number;

  @Column({ nullable: true })
  familyName: string;

  @Column({ nullable: true })
  additionalName: string;

  @OneToOne(
    (type) => User,
    (user) => user.personalId
  )
  user: User;
}

更新:

我尝试设置eager: true,但没有任何改变。 我曾尝试设置 nullable: false 并删除了现有的数据库,但是当我尝试 POST 时没有任何反应。

【问题讨论】:

    标签: javascript node.js typescript orm typeorm


    【解决方案1】:

    您在 OneToOne 装饰器中指定了cascade: true,这意味着当您使用给定人员保存用户时,该人也将被保存。 加载用户时,需要指定人员的数据需要加入。否则person实体会被持久化,获取用户时不会被加载。在您的情况下,这可以通过将 eager 设置为 true 来完成:

      @OneToOne(
        (type) => Personal,
        (personal) => personal.user,
        { cascade: true, eager: true }
      )
      @JoinColumn()
      personalId: personal;
    

    如果您想使用查询构建器,这将起作用:

    const queryBuilder = entityManager.createQueryBuilder(User, 'user');
    queryBuilder.leftJoinAndSelect('user.person', 'person');
    return queryBuilder.getMany();
    

    【讨论】:

    • 不幸的是,它没有用。我尝试在关系的两边都使用它,但在这两种情况下,我的 ID 也都为 null,当我尝试 GET regquest 时,我没有得到 Personal 的数据。
    • 好的,那么保存个人数据时可能会出现问题。您是否确认个人数据已成功存储在数据库中?您可以发布更多代码,例如您如何保存以及如何查询数据?
    • 我已经用控制器和服务文件(发布和保存方法)更新了问题。
    • 好的,这应该可以。最后一次尝试:您能否发布有关如何获取数据的代码?有很多不同的方法可以实现这一点,也许缺少一些东西。你能验证当你登录'await this.userRepositroy.save(user);'时会发生什么吗?因此 user.person.id 应该存在。然后我们知道 save 方法有效。
    • 我在 POST 请求后再次使用控制台日志更新了问题。 (你可以看到我在真实项目中有更多的专栏)
    【解决方案2】:

    如果您想加载 ID,或单独使用 ID(即设置关系而不加载目标实体),只需声明关系 id 列如下:

      @OneToOne(
        (type) => Personal,
        (personal) => personal.user,
        { cascade: true, eager: true }
      )
      personal!: Personal;
    
      @Column('int')
      personalId!: personal;
    

    如果您需要它可以为空,只需使用@Column('int', { nullable: true })

    TypeORM 将识别列,因为它具有相同的名称并且不会重复架构命令,而您可以直接使用关系 ID。

    【讨论】:

    • 当我尝试这样做时,数据甚至不会进入数据库,因为 ID 想要为空,但它不允许它为空。我不知道为什么它仍然为空......我实际上尝试了一切。
    • 也许你也应该添加@JoinColumn,但不应出现null问题,因为TypeORM会自动插入值,因为列等价
    • 我对我的理解不好感到抱歉,但我只是想确定一下:你有没有像@JoinColumn() @Column('int') personalId: number;一样同时尝试过这两种方法?
    • 好的,我建议同时使用两者
    • 抱歉造成误会。我也试过了......没有成功:(
    猜你喜欢
    • 1970-01-01
    • 2013-07-27
    • 2015-05-23
    • 2014-04-29
    • 1970-01-01
    • 1970-01-01
    • 2010-12-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多