NodeJS 对象中包含的存根模型

ogsagwnx  于 2023-06-05  发布在  Node.js
关注(0)|答案(1)|浏览(166)

我有真实的的问题stubbing一个特定的东西使用西农。我有一个简单的功能,我正在测试

const floatAPIModels = require("models/float/floatAPIModels");

const insertFloatData = async (databaseConnection, endpoint, endpointData) => {
  try {
    const floatModel = floatAPIModels(databaseConnection);
    await databaseConnection.sync();

    if (endpoint === "people") {
      endpointData.forEach(async (record) => {
        await floatModel.Person.upsert(record);
      });
    }

    return true;
  } catch (error) {
    console.log("Unable to insert data into the database:", error);
    return error;
  }
};

问题是floatAPIModels是一个返回东西的Object。我的实现如下

const { DataTypes } = require("sequelize");

const floatAPIModels = (sequelize) => {
  const Person = sequelize.define(
    "Person",
    {
      people_id: { type: DataTypes.INTEGER, primaryKey: true },
      job_title: { type: DataTypes.STRING(200), allowNull: true },
      employee_type: { type: DataTypes.BOOLEAN, allowNull: true },
      active: { type: DataTypes.BOOLEAN, allowNull: true },
      start_date: { type: DataTypes.DATE, allowNull: true },
      end_date: { type: DataTypes.DATE, allowNull: true },
      department_name: { type: DataTypes.STRING, allowNull: true },
      default_hourly_rate: { type: DataTypes.FLOAT, allowNull: true },
      created: { type: DataTypes.DATE, allowNull: true },
      modified: { type: DataTypes.DATE, allowNull: true },
    },
    {
      timestamps: true,
      tableName: "Person",
    }
  );

  return {
    Person,
  };
};

module.exports = floatAPIModels;

我删除了一些东西来减少代码。目前我正在做这样的事情

const { expect } = require("chai");
const sinon = require("sinon");
const floatAPIModels = require("src/models/float/floatAPIModels");
const floatService = require("src/services/float/floatService");

describe("insertFloatData", () => {
  let databaseConnection;
  let floatModelMock;

  beforeEach(() => {
    databaseConnection = {};

    floatModelMock = {
      Person: { upsert: sinon.stub().resolves() },
    };

    sinon.stub(floatAPIModels, "Person").returns(floatModelMock.Person);
  });

  afterEach(() => {
    sinon.restore();
  });

  it("should insert endpointData into the 'people' endpoint", async () => {
    const endpoint = "people";
    const endpointData = [{ record: "data" }];

    await floatService.insertFloatData(databaseConnection, endpoint, endpointData);

    expect(floatModelMock.Person.upsert.calledOnce).to.be.true;
    expect(floatModelMock.Person.upsert.firstCall.args[0]).to.deep.equal(endpointData[0]);
  });
});

通过以上内容,我得到

TypeError: Cannot stub non-existent property Person

但我试过违约,还有很多其他方法,但似乎都不起作用。
我如何正确地存根这一点,并得到单元测试工作?
谢谢

holgip5t

holgip5t1#

floatAPIModels是一个返回{ Person }对象的函数。此函数上没有Person属性。这就是为什么你得到了错误。
为了存根floatAPIModels函数,我将使用proxyquire模块来执行此操作。
例如
model.js

const { DataTypes } = require("sequelize");

const floatAPIModels = (sequelize) => {
  const Person = sequelize.define(
    "Person",
    {
      people_id: { type: DataTypes.INTEGER, primaryKey: true },
      // rest fields, don't matter for this test
      // ...
    },
    { timestamps: true, tableName: "Person", }
  );

  return {
    Person,
  };
};

module.exports = floatAPIModels;

service.js

const floatAPIModels = require("./model");

const insertFloatData = async (databaseConnection, endpoint, endpointData) => {
  try {
    const floatModel = floatAPIModels(databaseConnection);
    await databaseConnection.sync();
    if (endpoint === "people") {
      endpointData.forEach(async (record) => {
        await floatModel.Person.upsert(record);
      });
    }
    return true;
  } catch (error) {
    console.log("Unable to insert data into the database:", error);
    return error;
  }
};

module.exports = { insertFloatData }

service.test.js

const sinon = require("sinon");
const proxyquire = require('proxyquire');

describe("insertFloatData", () => {
  let databaseConnection;

  beforeEach(() => {
    databaseConnection = {
      define: sinon.stub(),
      sync: sinon.stub()
    };
  });

  afterEach(() => {
    sinon.restore();
  });

  it("should insert endpointData into the 'people' endpoint", async () => {
    const endpoint = "people";
    const endpointData = [{ record: "data" }];
    const PersonStub = {
      upsert: sinon.stub()
    }
    const floatAPIModelsStub = sinon.stub().returns({ Person: PersonStub })
    const floatService = proxyquire('./service', {
      './model': floatAPIModelsStub
    })

    await floatService.insertFloatData(databaseConnection, endpoint, endpointData);

    sinon.assert.calledOnce(PersonStub.upsert)
    sinon.assert.match(PersonStub.upsert.firstCall.args[0], endpointData[0])
  });
});

测试结果:

insertFloatData
    ✓ should insert endpointData into the 'people' endpoint (4168ms)

  1 passing (4s)

------------|---------|----------|---------|---------|-------------------
File        | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s 
------------|---------|----------|---------|---------|-------------------
All files   |   76.47 |       50 |   66.67 |   76.47 |                   
 model.js   |      60 |      100 |       0 |      60 | 4-24              
 service.js |   83.33 |       50 |     100 |   83.33 | 14-15             
------------|---------|----------|---------|---------|-------------------

相关问题