Massimiliano Oreto
Massimiliano Oreto

Reputation: 67

TypeOrm update Entity not updating related one

I have this entity:

export class User {
  @PrimaryGeneratedColumn()
  id: number;

  @Column()
  email: string;

  @Column()
  password: string;

  @Column({ default: false })
  activated: boolean;

  @OneToOne(() => UserAnag, (userAnag) => userAnag.user)
  useranag: UserAnag;
}

and this related entity

@Entity()
export class UserAnag {
@PrimaryGeneratedColumn()
  id: number;
  @Column()
  name: string;
  @Column()
  surname: string;

   @OneToOne(() => User, (user) => user.useranag, {
    onUpdate: 'CASCADE',
    onDelete: 'CASCADE',
  })
  @JoinColumn()
  user: User;

and this is my update function:

async update(id: number, attrs: Partial<UpdateUserDto>) {
    const user = await this.findById(id);
    if (!user) {
      throw new NotFoundException('User not found');
    }
    if (attrs.useranag) {
      const useranag = Object.assign(user.useranag, attrs.useranag);
      Object.assign(user, attrs);
      user.useranag = useranag;
    } else {
      Object.assign(user, attrs);
    }
    return this.repo.save(user);
  }

my findById function

    if (!id) {
      return null;
    }
    const user = await this.repo.find({
      where: { id: id },
      relations: { useranag: true },
    });
    return user[0];
  }

If i debug this, i can see that the userEntity is correctly updated and also the return have the correct object updated but on database, only User entity is correctly updated, not Useranag entity. I try alo setting eager on Useranag but have the same problem. Database is updated only in User not in Useranag

Additional info: I'm logging the query and before update , select only id and userId on useranag entity that are obviously equal to the original and no update query was launched

Upvotes: 1

Views: 962

Answers (2)

Massimiliano Oreto
Massimiliano Oreto

Reputation: 67

I have solved the problem. I made confusion between onUpdate e cascade: ['update']

The correct way that i find to update my related entity is to set cascade: ['update'] in the entity i will update, not in the related entity.

So the correct code is:

@Entity()
export class User {
  @PrimaryGeneratedColumn()
  id: number;

  @Column()
  email: string;

  @Column()
  password: string;

  @Column({ default: false })
  activated: boolean;

  @OneToOne(() => UserAnag, (userAnag) => userAnag.user, {
    cascade: ['update'],
  })
  useranag: UserAnag;
}

and

@Entity()
export class UserAnag {
  @PrimaryGeneratedColumn()
  id: number;
  @Column()
  name: string;
  @Column()
  surname: string;
  @Column()
  psn: string;
  @Column()
  discord: string;
  @Column()
  drivernumber: number;

  @OneToOne(() => User, (user) => user.useranag, {
    onDelete: 'CASCADE',
  })
  @JoinColumn()
  user: User;
}

Upvotes: 0

shoaib30
shoaib30

Reputation: 975

The cascade syntax is different. You can either set it as cascade: true or a list of operations to cascade

 @OneToOne(() => User, (user) => user.useranag, {cascade: true})
  @JoinColumn()
  user: User;
 @OneToOne(() => User, (user) => user.useranag, {cascade: ['update', 'delete']})
  @JoinColumn()
  user: User;

Source: https://orkhan.gitbook.io/typeorm/docs/relations#cascades

Upvotes: 2

Related Questions