Reputation: 9316
I am trying to write unit tests for a Sequelize model. I have an instance method on the class that call's Sequelize's update
method. Turning update
into a mocked function is no problem. I just can't seem to figure out how to properly do a X = new MyModel()
without some kind of error. It tells me Class constructor model cannot be invoked without 'new'
.
I took a look at https://sequelize-mock.readthedocs.io/en/stable/ but the way it's written makes me think it's better suited for mocking the Models when testing classes that are taking advantage of a model, rather than the model itself.
const BaseUtut = sequelizeInstance.define('utut', {
id: {
type: Sequelize.INTEGER,
primaryKey: true,
autoIncrement: true
},
metadata: {
type: Sequelize.JSON
}
});
class Utut extends BaseUtut {
async updateFromFlat(id, metadata) {
// in reality, i modify metadata, and want to test things around that
modifiedMetadata = methodThatModified(metadata);
// I want to see that update is called with the right output of the modified metadata
return await this.update(
{
id: id,
metadata: modifiedMetadata
},
{
where: {
locale: metadata.locale
}
}
);
}
}
So with the above code sample, if I have an insance of Utut
, I know I can easily mock update
. I just don't know how to initialize the class to then mock things.
The intent of the test I want to write is simply to see that update is called with the right parameters, based on my own code that has nothing to do with Sequelize. I want to make sure my transform on the inputs are set right when going to Sequelize. I am not planning to check that the DB is actually updated. The only problem I am having is actually instantiating the model.
So all I need is for code like this to work:
const instance = new Utut(); // This line doesn't work
instance.update = Jest.fn();
I'm not sure why it says I need to invoke with new
, when that is exactly what I am doing.
Upvotes: 1
Views: 1842
Reputation: 9316
So taking advantage of the Model
being returned from Sequelize.define
causes this issue. Rather than doing class Utut extends BaseUtut {
, I did this:
// Static methods
Object.assign(BaseUtut, {});
// Instance methods
Object.assign(BaseUtut.prototype, {});
Doing that lets me do new
on the model with no issue in my tests
Update
Just saw this was unanswered on 9/23/19. The above answer looks to be for an older version. I now just do
class MyClass extends Sequelize.Model {}
MyClass.init(definition, options);
export default MyClass;
Upvotes: 1