I've a Sails app, that uses MySQL as the DB (well, MySQL and others, but the problem is with MySQL). My problem is that is creating a record on the DB table, but all the cells are empty, and I don't understand why! Let me share the code and the table definition:
CREATE TABLE `components` (
`id` INT NOT NULL AUTO_INCREMENT,
`column1` VARCHAR(32) NOT NULL,
`column2` VARCHAR(50) NOT NULL,
`group` INT,
`subgroup` INT,
`column3` INT,
PRIMARY KEY (`id`),
FOREIGN KEY (`column1`) REFERENCES `table1`(`recipe_id`),
FOREIGN KEY (`group`) REFERENCES `table_groups`(`id`),
FOREIGN KEY (`subgroup`) REFERENCES `table_groups`(`id`),
FOREIGN KEY (`column3`) REFERENCES `table2`(`id`))
DEFAULT CHARSET=utf8;
Sails model definition:
module.exports = {
connection: 'mysqlDb',
autoCreatedAt: false,
autoUpdatedAt: false,
column1: {
type: 'string',
required: true
},
column2: {
type: 'string',
required: true
},
group: {
type: 'integer',
required: true
},
subgroup: {
type: 'integer',
required: true
},
column3: {
type: 'integer'
}
};
Waterline create query:
const data = {
column1: '383qa8475dd11231aa682y2728172y12',
column2: 'canvas',
groups: 2,
subgroup: 5,
column3: 1
};
Components.create(data).exec((error, results) => {
if(error) console.error(error);
else console.log('Created!');
});
It doesn't break, but the record on MySQL is empty, so why is inserting everything empty??? In the INT columns, is inserting a 0.
What am I missing?
Thanks!
Oh my... I found the problem. I forgot to wrap the column names, in the model, inside attributes key, so the model should be like this:
module.exports = {
connection: 'mysqlDb',
autoCreatedAt: false,
autoUpdatedAt: false,
attributes: {
column1: {
type: 'string',
required: true
},
column2: {
type: 'string',
required: true
},
group: {
type: 'integer',
required: true
},
subgroup: {
type: 'integer',
required: true
},
column3: {
type: 'integer'
}
}
};
Very silly mistake, but it cost me HOURS! Anyway, it is silly, but I will leave my question here, if anyone makes the same mistake.
Related
I'm trying to use Sequelize with express.js and MySQL, but i cant get a one-to-one relation to work.
The API always responses the address_id with the integer informed in the field, but not with the infos in the customers_addresses table. I try to force the eager loading by using { include: { all: true }}, but with no success.
Below is the files involved.
Can someone help ? :)
How the two tables are created:
CREATE TABLE IF NOT EXISTS `customers_addresses`
(`address_id` INTEGER NOT NULL auto_increment , `numero_casa` VARCHAR(255),
`complemento` VARCHAR(255), `rua` VARCHAR(255), `bairro` VARCHAR(255), `cidade`
VARCHAR(255), `estado` VARCHAR(2), `cep` VARCHAR(9), PRIMARY KEY (`address_id`))
CREATE TABLE IF NOT EXISTS `customers` (`customer_id` INTEGER NOT NULL auto_increment ,
`first_name` VARCHAR(25) NOT NULL, `last_name` VARCHAR(50) NOT NULL, `cpf` CHAR(11) NOT NULL,
`rg` VARCHAR(20) NOT NULL, `expedidor_rg` VARCHAR(20) NOT NULL, `inss_number` INTEGER,
`inss_situation` INTEGER, `email` VARCHAR(30), `phone` VARCHAR(20), `gender` VARCHAR(1),
`civil_state` VARCHAR(255), `address_id` INTEGER, PRIMARY KEY (`customer_id`),
FOREIGN KEY (`address_id`) REFERENCES `customers_addresses` (`address_id`))
The init-models.js file:
function initModels(sequelize) {
var customers = _customers(sequelize, DataTypes);
var customers_addresses = _customers_addresses(sequelize, DataTypes);
customers.hasOne(customers_addresses, { foreignKey: "address_id"});
customers_addresses.belongsTo(customers, { foreignKey: "address_id"});
return {
customers,
customers_addresses,
};
}
The customers.js model:
const Sequelize = require('sequelize');
module.exports = function(sequelize, DataTypes) {
return sequelize.define('customers', {
customer_id: {
autoIncrement: true,
type: DataTypes.INTEGER,
allowNull: false,
primaryKey: true
},
first_name: {
type: DataTypes.STRING(25),
allowNull: false
},
last_name: {
type: DataTypes.STRING(50),
allowNull: false
},
cpf: {
type: DataTypes.CHAR(11),
allowNull: false
},
rg: {
type: DataTypes.STRING(20),
allowNull: false
},
expedidor_rg: {
type: DataTypes.STRING(20),
allowNull: false
},
inss_number: {
type: DataTypes.INTEGER,
allowNull: true
},
inss_situation: {
type: DataTypes.INTEGER,
allowNull: true
},
email: {
type: DataTypes.STRING(30),
allowNull: true
},
phone: {
type: DataTypes.STRING(20),
allowNull: true
},
gender: {
type: DataTypes.STRING(1),
allowNull: true
},
civil_state: {
type: DataTypes.STRING(255),
allowNull: true
},
address_id: {
type: DataTypes.INTEGER,
notNull: true,
references: {
model: 'customers_addresses',
key: 'address_id'
}
}
}, {
sequelize,
tableName: 'customers',
timestamps: false
});
};
How the API controller calls it:
customers.findAll({ include: { all: true }})
The query that is finally executed:
Executing (default): SELECT `customer_id`, `first_name`, `last_name`, `cpf`, `rg`, `expedidor_rg`, `inss_number`, `inss_situation`, `email`, `phone`, `gender`, `civil_state`, `address_id` FROM `customers` AS `customers`;
Try this in your API Controller. I think we should call the model name that have associations with the customer table
customers.findAll({include: [{model:customer_addresses}]})
So. I'm creating tables and while migrating i'm facing the error:
Cannot add foreign key constraint
errno: 1215
sqlState: 'HY000',
sqlMessage: 'Cannot add foreign key constraint',
sql: 'CREATE TABLE IF NOT EXISTS users_questionnaire_contact\n' +
" ( user_id int(10) unsigned NOT NULL DEFAULT '0',\n" +
" del int(10) unsigned NOT NULL DEFAULT '0',\n" +
" id_questionnaire int(10) unsigned NOT NULL DEFAULT '0',\n" +
" contact char(1) COLLATE 'utf8_general_ci' NOT NULL DEFAULT '1',\n" +
' createdAt datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,\n' +
' updatedAt datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,\n' +
' CONSTRAINT FK_UQContactUser FOREIGN KEY (user_id) REFERENCES users(id) ON DELETE CASCADE,\n' +
' FOREIGN KEY (id_questionnaire) REFERENCES questionnaires(id),\n' +
' PRIMARY KEY (user_id, id_questionnaire)\n' +
' ) ENGINE=InnoDB DEFAULT CHARSET=utf8;'
},
I'm using sequlize.js orm and sequlize:cli for migrating. Here is my model form where i'm getting an error.
module.exports = function(sequelize, DataTypes) {
return sequelize.define('UserQuestionnaireContact', {
user_id: {
type: DataTypes.INTEGER(10).UNSIGNED,
allowNull: false,
defaultValue: '0',
primaryKey: true
},
id_questionnaire: {
type: DataTypes.INTEGER(10).UNSIGNED,
allowNull: false,
defaultValue: '0',
primaryKey: true
},
contact: {
type: DataTypes.CHAR(1),
allowNull: false,
defaultValue: '1'
}
}, {
tableName: 'users_questionnaire_contact',
defaultScope: { attributes: { exclude: [ 'id'] } }
});
};
My user model:
module.exports = function(sequelize, DataTypes) {
const Model = sequelize.define('User', {
company_id: {
type: DataTypes.INTEGER(10).UNSIGNED,
allowNull: false,
references: {
model: 'Company',
key: 'id'
}
},
first_name: {
type: DataTypes.STRING(512),
allowNull: false
},
last_name: {
type: DataTypes.STRING(250),
allowNull: true
},
career_category_id: {
type: DataTypes.INTEGER(10),
allowNull: true
},
training_course_id: {
type: DataTypes.INTEGER(11),
allowNull: true
},
country_id: {
type: DataTypes.INTEGER(11),
allowNull: true
},
currency_id: {
type: DataTypes.INTEGER(11),
allowNull: true
},
}, {
tableName: 'users'
});
Model.associate = models => {
Model.belongsTo(models.Currency, {foreignKey: 'currency_id', as: 'curr'});
Model.belongsTo(models.Country, {foreignKey: 'country_id', as: 'country'});
Model.belongsTo(models.CareerCategory, {foreignKey: 'career_category_id', as: 'career'});
Model.belongsTo(models.TrainingCourse, {foreignKey: 'training_course_id', as: 'training_course'});
Model.belongsTo(models.Company, {foreignKey: 'company_id', as: 'company'});
Model.hasMany(models.Attempt, {foreignKey: 'user_id', as: 'attempts'});
Model.hasMany(models.UserQuestionnaireContact, {foreignKey: 'user_id', as: 'u_q_contact'});
Model.hasMany(models.UsersQuestionnaireAttemptLimit, {foreignKey: 'user_id', as: 'u_q_limit'});
};
return Model;
};
And my questionaries table which is related to:
const Model = sequelize.define('Questionnaire', {
type: {
type: DataTypes.INTEGER(10).UNSIGNED,
allowNull: true,
defaultValue: '0'
},
}, {
tableName: 'questionnaires'
});
Model.associate = models => {
Model.belongsToMany(models.Company, {
as: 'questCompanies',
foreignKey: 'questionnaire_id',
otherKey: 'company_id',
through: 'company_questionnaire_maps'});
Model.hasMany(models.Attempt, {foreignKey: 'questionnaire_id', as: 'q_attempts'});
Model.hasMany(models.QuestionGroup, {foreignKey: 'questionnaire_id', as: 'q_groups'});
Model.hasMany(models.CompanyQuestionnaireMap, {foreignKey: 'questionnaire_id', as: 'company_questionnaire_maps'});
};
Does somebody have any idea how to fix this ? Thanks in advance.
I am have a sequelize table that does not have a current primary key in it as ID. I currently am not sure why the id primary key is not rendering. I tried forcing the id to primary key and autoincrement.
Does anyone know how i can solve this issue.
this is what my current table looks like:
colabdesk=# \d users;
Table "public.users"
Column | Type | Collation | Nullable | Default
------------+--------------------------+-----------+----------+---------
id | integer | | not null |
username | character varying(255) | | |
password | character varying(255) | | |
email | character varying(255) | | |
first_name | character varying(255) | | |
last_name | character varying(255) | | |
DATE | timestamp with time zone | | not null |
Indexes:
"users_pkey" PRIMARY KEY, btree (id)
"users_email_key" UNIQUE CONSTRAINT, btree (email)
"users_username_key" UNIQUE CONSTRAINT, btree (username)
Referenced by:
TABLE "details" CONSTRAINT "details_userId_fkey" FOREIGN KEY ("userId") REFERENCES users(id) ON UPDATE CASCADE ON DELETE SET NULL
TABLE "profiles" CONSTRAINT "profiles_userId_fkey" FOREIGN KEY ("userId") REFERENCES users(id) ON UPDATE CASCADE ON DELETE SET NULL
colabdesk=#
this is what my sequlize table design looks like:
const seq = require('sequelize');
const { postgres } = require('../index');
const permissions = [['Admin', 'Staff', 'User']];
const User = postgres.define(
"user",
{
username: {type: seq.STRING, unique: true, require: true,
validate: {isAlphanumeric: true, len: [8,16]}
},
password: {type: seq.STRING, require: true,
validate: {len: [8, 18]}
},
email: {type: seq.STRING, unique: true, require: true,
validate: {isEmail: true}
},
first_name: {type: seq.STRING, require: true,
validate: {isAlpha: true}
},
last_name: {type: seq.STRING, require: true,
validate: {isAlpha: true,}
},
permission: {type: seq.STRING, require: true,
validate: {isAlpha: true, isIn: permissions}
},
renter: {type: seq.BOOLEAN, require: true, defaultValue: 0,
validate: {isIn: [['0', '1']], isInt: true}
},
rentee: {type: seq.BOOLEAN, require: true, defaultValue: 0,
validate: {isIn: [['0', '1']], isInt: true}
},
},
{
createdAt: seq.DATE,
updatedAt: seq.DATE,
}
);
postgres.sync()
.then(() => {
console.log("User table is connected and synced")
})
.catch((err) => {
console.log("Error syncing the User table: " + JSON.stringify(err))
})
module.exports.User = User;
does anyone know how to solve this issue
UPDATE
this is what the request looks like:
{
"username": "omarjandali",
"password": "password",
"email": "omar#admin.com",
"first_name": "omar",
"last_name": "jandali",
"permission": "Admin",
"renter": "1",
"rentee": "0"
}
Looks like the table was created as
create table users( id integer, ...) --which would not auto-increment
as opposed to
create table users( id serial, ...) --which would auto-increment.
If there is no data it might be just as easy to drop and recreate the table. You could also try
create sequence users_id_seq
increment 1
minvalue 1
maxvalue 99999999999999999
start 1;
alter table users alter column id set default nextval('users_id_seq'::regclass);
If there is data in the table you will have to adjust the start value for the sequence.
I think you missed to define the primary key in your model :
id: {
type: seq.INTEGER,
primaryKey: true,
autoIncrement: true,
},
It should look like this :
const User = postgres.define(
"user", {
id: {
type: seq.INTEGER,
primaryKey: true,
autoIncrement: true,
},
... // <--- REST OF YOUR FIELDS
}, {
createdAt: seq.DATE,
updatedAt: seq.DATE,
}
);
Working with Sequelize and MySQL database, I was trying to achieve composite primary keys combination in junction table, but unfortunately without result.
I have tables:
They are in relation many to many. In junction table user_has_project I want two primary keys combination: user_id and project_id.
Sequelize models definition:
User:
module.exports = function(sequelize, Sequelize) {
var User = sequelize.define('user', {
id: {
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER(11)
},
name: {
type: Sequelize.STRING(100),
allowNull: false
}
},{
timestamps: false,
freezeTableName: true,
underscored: true
});
User.associate = function (models) {
models.user.belongsToMany(models.project, {
through: 'user_has_project',
foreignKey: 'user_id',
primaryKey: true
});
};
return User;
}
Project:
module.exports = function(sequelize, Sequelize) {
var Project = sequelize.define('project', {
id: {
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER(11)
},
name: {
type: Sequelize.STRING(100),
allowNull: false
}
},{
timestamps: false,
freezeTableName: true,
underscored: true
});
Project.associate = function (models) {
models.project.belongsToMany(models.user, {
through: 'user_has_project',
foreignKey: 'project_id',
primaryKey: true
});
};
return Project;
}
I was trying to 'force' Primary keys definition in user_has_project table using "primaryKey: true" in both models association, but definition above is creating only user_id as PRI and project_id as MUL
What is Sequelize version? I tested Sequelize 4 in sqlite3, the definition above makes a query
CREATE TABLE IF NOT EXISTS `user_has_project` (`created_at` DATETIME NOT NULL, `updated_at` DATETIME NOT NULL, `user_id` INTEGER(11) NOT NULL REFERENCES `user` (`id`) ON DELETE CASCADE ON UPDATE CASCADE, `project_id` INTEGER(11) NOT NULL REFERENCES `project` (`id`) ON DELETE CASCADE ON UPDATE CASCADE, PRIMARY KEY (`user_id`, `project_id`));
Is "PRIMARY KEY (user_id, project_id)" what you want?
I have 2 tables with many to many relationships through an intersection table.
Products --> Orders <-- Outlets
This is what Sequelize generates
CREATE TABLE IF NOT EXISTS `Orders` (`id` INTEGER auto_increment , `amount` INTEGER, `orderDate` DATETIME, `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `OutletId` INTEGER, `ProductId` INTEGER, `UserId` INTEGER, UNIQUE `Orders_ProductId_OutletId_unique` (`OutletId`, `ProductId`), PRIMARY KEY (`id`), FOREIGN KEY (`OutletId`) REFERENCES `Outlets` (`id`) ON DELETE SET NULL ON UPDATE CASCADE, FOREIGN KEY (`ProductId`) REFERENCES `Products` (`id`) ON DELETE SET NULL ON UPDATE CASCADE, FOREIGN KEY (`UserId`) REFERENCES `Users` (`id`) ON DELETE SET NULL ON UPDATE CASCADE) ENGINE=InnoDB;
I know it creates a unique key: UNIQUE Orders_ProductId_OutletId_unique (OutletId, ProductId).
That's why I can't save, them with the same OutletId and ProductId, however, my case, OutletId and ProductId can be the same, but the orderDate must be different.
So I save this is okay,
OrderId, ProductId, OutletId, orderDate
1, 1, 1, '2016-1-1'
2, 2, 1, '2016-1-1'
However, when I save another row:
1, 1, 1, '2016-1-2'
MySql gives me this error:
ERROR 1062: 1062: Duplicate entry '1-1' for key 'Orders_ProductId_OutletId_unique'
Ok, so the question is, how can I create the model that has this validation or constraint?
Here are my models:
Order
'use strict';
module.exports = function(sequelize, DataTypes) {
var Order = sequelize.define('Order', {
id: {
type: DataTypes.INTEGER,
primaryKey: true,
autoIncrement: true
},
amount: DataTypes.INTEGER,
orderDate: DataTypes.DATE
},
{
associate: function(models){
Order.belongsTo(models.Outlet);
Order.belongsTo(models.Product);
Order.belongsTo(models.User);
}
}
);
return Order;
};
Product
'use strict';
module.exports = function(sequelize, DataTypes) {
var Product = sequelize.define('Product', {
inventoryCode: DataTypes.STRING,
name: DataTypes.STRING,
nameKh: DataTypes.STRING,
unitKh: DataTypes.STRING,
unit: DataTypes.STRING,
monthlyCaseTarget: DataTypes.INTEGER,
pieces: DataTypes.INTEGER,
star: DataTypes.BOOLEAN,
price: DataTypes.FLOAT,
active: DataTypes.BOOLEAN
},
{
associate: function(models){
Product.belongsToMany(models.Outlet, {through: models.Order});
Product.belongsTo(models.Category);
// Product.hasMany(models.Order);
}
}
);
return Product;
};
Outlets
'use strict';
module.exports = function(sequelize, DataTypes) {
var Outlet = sequelize.define('Outlet', {
outletCode: DataTypes.STRING,
outletName: DataTypes.STRING,
outletNameKh: DataTypes.STRING,
outletSubtype: DataTypes.STRING,
perfectStoreType: DataTypes.STRING,
address: DataTypes.STRING
},
{
associate: function(models){
Outlet.belongsToMany(models.Product, {through: models.Order});
Outlet.belongsTo(models.Distributor);
// Outlet.hasMany(models.Order);
}
}
);
return Outlet;
};
Since sequelize produces this query:
UNIQUE Orders_ProductId_OutletId_unique (OutletId, ProductId)
so I kinda hack it by adding the composite unique key to the order column.
'use strict';
module.exports = function(sequelize, DataTypes) {
var Order = sequelize.define('Order', {
id: {
type: DataTypes.INTEGER,
primaryKey: true,
autoIncrement: true
},
amount: {
type: DataTypes.INTEGER
},
orderDate: {
type: DataTypes.DATE,
unique: 'Orders_ProductId_OutletId_unique'
}
},
{
associate: function(models){
Order.belongsTo(models.Outlet);
Order.belongsTo(models.Product);
Order.belongsTo(models.User);
}
}
);
return Order;
};