TypeORM 级联:true 标志不会删除相关实体

问题描述 投票:0回答:5

我无法弄清楚是否是我,

cascade: true
选项在删除父实体时不会删除子实体?

@Entity()
export class Folder {
  @PrimaryGeneratedColumn()
  public readonly id: number;

  @OneToMany(() => Segment, (segment) => segment.folder, {
    cascade: true,
  })
  public segments: Segment[];
}


@Entity()
export class Segment {
  @PrimaryGeneratedColumn()
  public readonly id: number;

  @ManyToOne(() => Folder, (folder) => folder.segments)
  @JoinColumn()
  public folder: Folder;
}

然后我就这么做了

await getRepository(Folder).delete(id);

这给了我一个错误:

update or delete on table "folder" violates foreign key constraint "FK_12606f83d18e5ae0c7e5693f3fb" on table
"segment"

也尝试过做

const folder = await this.repository.findOneOrFail(id);
repository.remove(folder)
//or 
folder.segments = null;
await this.repository.save(folder);

仍然错误...

我不想循环遍历所有子实体并手动删除它们。我认为

cascade: true
应该处理它以及保存或更新。 也许语法应该不同?

谢谢!

typescript typeorm
5个回答
12
投票

Cascade仅描述如何处理相关实体,当实体本身被删除时它没有效果。如果要在删除文件夹时删除所有段,则需要使用onDelete(这是数据库功能,否则则级联,这是在TypeORM内实现的。这意味着添加onDelete时需要生成并执行迁移)。所以这应该对你有用:

@Entity()
export class Segment {
  @PrimaryGeneratedColumn()
  public readonly id: number;

  @ManyToOne(() => Folder, (folder) => folder.segments, { onDelete: 'CASCADE' })
  @JoinColumn()
  public folder: Folder;
}

5
投票

父实体 => 设置

cascade to "remove"

// Parent Entity
@OneToMany(type => Comment, comment => comment.parent,{ cascade: ["remove"] })
replies: Comment[];

子实体 => 设置

onDelete to CASCADE
orphanedRowAction to delete

// Child Entity
@ManyToOne(type => Comment, comment => comment.replies, {
    onDelete: "CASCADE", orphanedRowAction: 'delete'
})
parent: Comment;

注意

当您想要删除父级及其子级时,您必须执行以下操作:

await ParentRepository.delete(parentId)
    

2
投票

- 父实体

@OneToMany(type => Comment, comment => comment.parent, { cascade: ["remove"] }) replies: Comment[];

@OneToMany 关系中创建 cascade 选项。
@OneToMany 不需要关系 onDelete 选项。

{ cascade: ["remove"] }


- 子实体

@ManyToOne(type => Comment, comment => comment.replies, { onDelete: "CASCADE" }) parent: Comment;

@ManyToOne 关系中创建 onDelete 选项。
@ManyToOne 不需要关系级联选项。

{ onDelete: "CASCADE" }
    

1
投票
这是 typeorm 代码中的一个“错误”(不确定这是否是所需的行为),我通过使用

https://www.npmjs.com/package/patch-package 修复了此问题,因为我需要此修复尽快

您需要使用此代码修补

node_modules/typeorm/persistence/subject-builder/OneToManySubjectBuilder.js

处的文件(- 是您需要删除的内容,+ 是您需要添加的内容):

var removedRelatedEntitySubject = new Subject_1.Subject({ metadata: relation.inverseEntityMetadata, parentSubject: subject, - canBeUpdated: true, + canBeUpdated: !relation.isNullable, + mustBeRemoved: relation.isNullable,
    

0
投票
级联删除所有相关实体的步骤如下。我的情况是,当我删除信号时,它的 signalDetail、signalClassificationJoins、signalPostJoin 和帖子都应该被删除。

这是信号实体

@OneToMany( () => SignalClassificationJoin, (SignalClassificationJoin) => SignalClassificationJoin.signal, { cascade: true, lazy: false, } ) classificationDetails: SignalClassificationJoin[]; @OneToOne(() => SignalDetail, (SignalDetail) => SignalDetail.signal, { cascade: true, lazy: false, }) signalDetail: SignalDetail; @OneToMany(() => SignalPostJoin, (SignalPostJoin) => SignalPostJoin.signal, { cascade: true, lazy: false, }) signalPostJoin?: SignalPostJoin[];
当您定义逆关系时,与相关实体一起做

@ManyToOne(() => Signal, (Signal) => Signal.classificationDetails, { onDelete: "CASCADE", }) @JoinColumn({ name: "signal_id" }) signal: Signal;
最后,删除具有相关实体的信号,如下所示,包括要删除的所有嵌套关系

const signal = await this.signalRepository.findOne({ where: { id }, relations: { classificationDetails: true, signalDetail: true, signalPostJoin: { posts: true }, }, }); const deletedSignal = await this.signalRepository.remove(signal);
    
© www.soinside.com 2019 - 2024. All rights reserved.