Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Sequelize - Update FOREIGN KEY constraint win ONDELETE CASCADE

I'm using Postgres with Sequelize and I need to update an existing ForeignKey Constraint with onDelete = Cascade.

I have updated my model, but the migration file comes up as a skeleton. I haven't found a way to update this constraint.

My model file:

export const Property = sequelize.define<PropertyModel, PropertyAttribute>('property', {
  id: {
    type: Sequelize.UUID,
    primaryKey: true,
    defaultValue: Sequelize.UUIDV4,
    allowNull: false
  },
  name: Sequelize.STRING,
  status: {
    type: Sequelize.BOOLEAN,
    defaultValue: true
  },
  publishedAt: Sequelize.DATE
});

Property.associate = models => {
  Property.belongsTo(models.User, {
    foreignKey: { allowNull: false },
    allowNull: false
  });
  Property.hasMany(
    models.PropertyService, {onDelete: "cascade"});

  Property.hasMany(
    models.Visitor, {onDelete: "cascade"});
};

My migration file:

module.exports = {
  up: (queryInterface, Sequelize) => {
      // How can I update a FK constraint??
  },

  down: (queryInterface, Sequelize) => {
      // How can I undo an FK update constraint??
  }
};

Any ideas on how to make this migration?

like image 816
danielrvt Avatar asked Aug 20 '18 16:08

danielrvt


People also ask

How do I change my foreign key in Sequelize?

Sequelize association methods also accept an options object that you can use to configure the details of the association. For example, you can change the foreign key name on the table by adding the foreignKey property: User. hasOne(Invoice, { foreignKey: "invoice_creator", // UserId -> invoice_creator });

How do you define a foreign key in Sequelize?

As shown above, the foreignKey option accepts a string or an object. When receiving an object, this object will be used as the definition for the column just like it would do in a standard sequelize.define call. Therefore, specifying options such as type , allowNull , defaultValue , etc, just work.

What are constraints in sequelize?

Constraints are the rules that we define on the level of SQL. For example, if one attribute is supposed to be unique then this will be handled on the level of SQL. If a constraint check fails then Sequelize will forward the error message sent by the database.


1 Answers

I found it simplest to first remove the existing constraint and then add it back with onDelete. Sequelize has queryInterface.removeConstraint and queryInterface.addConstraint methods for this.

Here is a contrived example:

'use strict';

module.exports = {
  up: async (queryInterface, Sequelize) => {
    const transaction = await queryInterface.sequelize.transaction();
    try {
      await queryInterface.removeConstraint(
        'users',
        'users_address_id_fkey',
        { transaction }
      );
      await queryInterface.addConstraint('users', ['address_id'], {
        type: 'foreign key',
        name: 'users_address_id_fkey',
        references: {
          table: 'addresses',
          field: 'id',
        },
        onDelete: 'CASCADE',
        transaction
      });
      return transaction.commit();
    } catch (error) {
      await transaction.rollback();
      throw error;
    }
  },

  down: async (queryInterface, Sequelize) => {
    const transaction = await queryInterface.sequelize.transaction();
    try {
      await queryInterface.removeConstraint(
        'users',
        'users_address_id_fkey',
        { transaction }
      );
      await queryInterface.addConstraint('users', ['address_id'], {
        type: 'foreign key',
        name: 'users_address_id_fkey',
        references: {
          table: 'addresses',
          field: 'id',
        },
        transaction
      });
      return transaction.commit();
    } catch (error) {
      await transaction.rollback();
      throw error;
    }
  },
};
like image 189
Stone Avatar answered Nov 15 '22 04:11

Stone