I'm testing Sequelize and I'm liking it so far. Now I've come across a problem that I could not solve and not find any answer from the web.
So I've these three tables which are created through migrations
Users:
'use strict';
module.exports = {
up: (queryInterface, Sequelize) => {
return queryInterface.createTable('Users', {
id: {
allowNull: false,
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER
},
.
. // All user data here
.
});
},
down: (queryInterface, Sequelize) => {
return queryInterface.dropTable('Users');
}
};
Property:
'use strict';
module.exports = {
up: (queryInterface, Sequelize) => {
return queryInterface.createTable('Properties', {
id: {
allowNull: false,
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER
},
.
. // All property data here
.
});
},
down: (queryInterface, Sequelize) => {
return queryInterface.dropTable('Properties');
}
};
And PropertyUser:
'use strict';
module.exports = {
up: (queryInterface, Sequelize) => {
return queryInterface.createTable('PropertyUsers', {
property_id: {
type: Sequelize.INTEGER,
allowNull: false,
primaryKey: true,
references: {
model: 'Properties',
key: 'id'
}
},
user_id: {
type: Sequelize.INTEGER,
allowNull: false,
primaryKey: true,
references: {
model: 'Users',
key: 'id'
}
},
role: {
type: Sequelize.ENUM('admin', 'basic', 'read'),
allowNull: false,
defaultValue: 'read'
},
createdAt: {
allowNull: false,
type: Sequelize.DATE
},
updatedAt: {
allowNull: false,
type: Sequelize.DATE
}
});
},
down: (queryInterface, Sequelize) => {
return queryInterface.dropTable('PropertyUsers');
}
};
So we have Users and Property tables that are connected through PropertyUser table and PropertyUser table hold the information about which role user has in property (Admin, basic, read).
I've also created these models
User:
'use strict';
module.exports = (sequelize, DataTypes) => {
const User = sequelize.define('User', {
firstname: DataTypes.STRING,
.
.
.
}, {});
User.associate = function(models) {
// associations can be defined here
User.belongsToMany(models.Property, {through: 'PropertyUsers', foreignKey: 'user_id', as: 'properties'})
};
return User;
};
Property:
'use strict';
module.exports = (sequelize, DataTypes) => {
const Property = sequelize.define('Property', {
.
.
.
}, {});
Property.associate = function(models) {
// associations can be defined here
Property.belongsToMany(models.User, {through: 'PropertyUsers', foreignKey: 'property_id', as: 'users'})
};
return Property;
};
PropertyUser:
'use strict';
module.exports = (sequelize, DataTypes) => {
const PropertyUser = sequelize.define('PropertyUser', {
property_id: DataTypes.INTEGER,
user_id: DataTypes.INTEGER,
role: DataTypes.ENUM('admin', 'basic', 'read'),
}, {});
PropertyUser.associate = function(models) {
// associations can be defined here
PropertyUser.belongsTo(models.Property, {foreignKey: 'property_id'});
PropertyUser.belongsTo(models.User, {foreignKey: 'user_id'});
};
PropertyUser.removeAttribute('id');
return PropertyUser;
};
Now when I try to fetch Property with ID and include users that belong to the property it does return the join table data with every user but the join table data only includes user_id, property_id, createdAt and updatedAt and not the role.
Here is the code I use to fetch the data.
return new Promise(async(resolve, reject) => {
try {
const result = await models.Property.findOne({
where: {
id: propertyId
},
include: [{
model: models.User,
as: 'users',
}]
});
resolve(result);
} catch (e) {
reject(e);
}
});
What I'm I doing wrong? Thanks for the help already!
Edit: It seems that when Sequelize constructs the SQL statement it does not add the role to the statement. Here is a the part of the statement that gets the data from PropertyUser table
`users->PropertyUsers`.`createdAt` AS `users.PropertyUsers.createdAt`, `users->PropertyUsers`.`updatedAt` AS `users.PropertyUsers.updatedAt`, `users->PropertyUsers`.`property_id` AS `users.PropertyUsers.property_id`, `users->PropertyUsers`.`user_id` AS `users.PropertyUsers.user_id`
