Как построить отношения «Многие ко многим» в последовательности?

#javascript #node.js #database #orm #sequelize.js

Вопрос:

Вот мои модели: Персонал

 const { DataTypes } = require('sequelize');
const sequelize = require('../sequelize')

const Staff = sequelize.define('Staff', {

name: {
    type: DataTypes.STRING,
    allowNull: false,
},
SSN: {
    type: DataTypes.INTEGER,
},
email:{
    type: DataTypes.STRING,
}
}, {
    timestamps: true
});
Staff.associate = function (models) {
    Staff.belongsToMany(models.Technology, {through: models.StaffTechnology});

};

module.exports = Staff;
 

ТЕХНОЛОГИЯ:

 const { DataTypes } = require('sequelize');
const sequelize = require('../sequelize')


const Technology = sequelize.define('Technology', {
    name: {
        type: DataTypes.STRING,
        allowNull: false,
    },
    description: {
        type: DataTypes.STRING,

    }
}, {
    timestamps: true
});
Technology.associate = function (models) {
    Technology.belongsToMany(models.Staff, { through: models.StaffTechnology});

};
module.exports = Technology;
 

Это будет объединенная таблица:

 const { DataTypes } = require('sequelize');
const sequelize = require('../sequelize')
const Staff = require('../../database/models/staff.model');
const Technology = require('../../database/models/technology.model');


const StaffTechnology = sequelize.define('StaffTechnology', {
    experience: {
        type: DataTypes.INTEGER,
    },
    StaffID: {
        type: DataTypes.INTEGER,
        references: {
            model: Staff, 
            key: 'id'
        }
    },
    TechnologyID: {
        type: DataTypes.INTEGER,
        references: {
            model: Technology,
            key: 'id'
        }
    },
}, {
    timestamps: true
});
StaffTechnology.associate = function (models) {
      //StaffTechnology.hasMany(models.Staff, { foreignKey: 'StaffID' });
      //StaffTechnology.hasMany(models.Technology, { foreignKey: 'TechnologyID' });
};

module.exports = StaffTechnology
 

Прямо сейчас я не могу выполнить Staff.findAll({включить:Технология}), так как он выдает ошибку, в которой говорится, что персонал и технология не связаны, но я видел документацию по секвенированию, и я видел очень похожий пример работы.
Чего я хочу, так это возможности вернуть всех сотрудников с их технологиями, у персонала может быть много технологий, и Технологии могут принадлежать многим сотрудникам, но на самом деле они связаны через объединенную таблицу StaffTechnology.

Ответ №1:

Вам нужно объявить ассоциации внутри вашего index.js (или где вы инициализируете свою БД). Вы можете либо сделать это вручную, объявив ассоциации напрямую, потребовав модели и выполнив

 Model1.association(Model2, {
  through: "JoinTable"
}

Model2.association(Model1, {
  through: "JoinTable"
}
 

Или сделайте это программно (если вы уже используете этот подход для инициализации своей БД):

 'use strict'
 
const fs = require('fs');
const path = require('path');
const Sequelize = require('sequelize');
const basename = path.basename(__filename);
const config = {
  "username": "root",
  "password": "YOUR ROOT PASSWORD HERE",
  "database": "YOUR DATABASE NAME HERE",
  "host": "127.0.0.1",
  "dialect": "mysql"
}
const db = {}
 
let sequelize = new Sequelize(config.database, config.username, config.password, config);
 
fs.readdirSync(__dirname)
  .filter(file => {
    return (file.indexOf('.') !== 0)
    amp;amp; (file !== basename)
    amp;amp; (file.slice(-3) === '.js');
  })
  .forEach(file => {
    const model = require(path.join(__dirname, file))(sequelize, Sequelize.DataTypes);
    db[model.name] = model;
  });
 
Object.keys(db).forEach(modelName => {
  if (db[modelName].associate) {
    db[modelName].associate(db);
  }
});
 
db.sequelize = sequelize;
db.Sequelize = Sequelize;
 
module.exports = db;
 

^ Этот код выполняет как инициализацию, так и ассоциации в одном. Вам необходимо убедиться, что файлы вашей модели и файл инициализации находятся в одной папке.

Комментарии:

1. ЧУВАК, это работает, у меня только что было 2 папки с моделями, спасибо