Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

foreign key constraint #154

Open
jagoanmamah opened this issue Dec 26, 2023 · 3 comments
Open

foreign key constraint #154

jagoanmamah opened this issue Dec 26, 2023 · 3 comments

Comments

@jagoanmamah
Copy link

jagoanmamah commented Dec 26, 2023

Screenshot 2023-12-26 at 12 36 29
@jorgebodega
Copy link
Owner

Sorry, I cannot work just with an image without any context.

Please, try to create a reproducible example in a repo, or at least, a decent amount of code.

@viki53
Copy link

viki53 commented Jun 3, 2024

Hi, I'm having a similar error when using subscribers and factories. Here's some stripped-down code to give an idea of how it works.

Basically I have a main entity:

@Entity()
class Ticket extends BaseEntity {
  // [...]
  @OneToMany(() => TicketEvent, (event) => event.ticket)
  events?: TicketEvent[];
  // [...]
}

A matching factory:

export class TicketFactory extends Factory<Ticket> {
  protected entity = Ticket;
  protected dataSource = dataSource;

  protected attrs(): FactorizedAttrs<Ticket> {
    return {
      id: randomUUID(),
      /* Other attributes, not related to sub-entity */
    }
  }
}

A sub-entity (mostly generated entries):

@Entity()
class TicketEvent extends BaseEntity {
  // [...]
  @Index()
  @Column({
    nullable: false,
  })
  ticketId!: Ticket['id'];
  // [...]
}

And I have a subscriber on the main entity that creates the sub-entity after insert:

@EventSubscriber()
export class TicketSubscriber implements EntitySubscriberInterface<Ticket> {
  constructor(
    @InjectDataSource()
    readonly dataSource: DataSource,
  ) {
    dataSource.subscribers.push(this);
  }
  listenTo() {
    return Ticket;
  }

  async afterInsert(event: InsertEvent<Ticket>): Promise<void> {
    const { manager, entity: ticket } = event;

    await manager
      .create(TicketEvent, {
        ticketId: ticket.id,
        /* Other internal attributes */
      })
      .save({
        data: { /* Some internal data */ },
      });
  }
}

And when running my e2e tests it triggers this SQL error:

QueryFailedError: insert or update on table "ticket_event" violates foreign key constraint "FK_xxxxxxxxxxxxxxxxxxxxxx"

The code looks like this:

const ticket = await new TicketFactory().create({
  /* Some entity attributes, possibly including an EagerInstanceAttribute (other relationship to a different parent entity that may) if that's of any incidence */
});` 

It this related to how we use the subscriber (I know it's not the updated way of doing it directly via an attribute on the Entity)? Or maybe the manager isn't awaiting properly between the subscriber and the factory?

Let me know if any more info can be helpful.

@viki53
Copy link

viki53 commented Jun 3, 2024

Nevermind, this was related to my use of the manager in the subscriber:

Replacing manager.create(TicketEvent, {}).save() by manager.save({}) fixed the issue (I guess TypeORM doesn't keep the transaction when returning from create 👌

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants