javascript - Mock exported const arrow functions with Jest - Stack Overflow

Given the following example with a basic test, I'd expect bar to be returned when sendMessage.mess

Given the following example with a basic test, I'd expect bar to be returned when sendMessage.message is mocked with Jest. Instead, when called, it returns the original value of "Hello World".

serviceBus.js

export const message = () => {
  return "Hello world";
};

export const foo = () => {
  return message();
};

mockDemo.test.js

import * as sendMessage from "../src/services/serviceBus";

describe("sendMessage", () => {
  sendMessage.message = jest.fn(() => {
    return "bar";
  });

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

And the results as follows:

$ ./node_modules/.bin/jest ./__tests__/mockDemo.test.js
 FAIL  __tests__/mockDemo.test.js
  MessageReceiver Router
    ✕ message should return bar (9ms)

  ● MessageReceiver Router › message should return bar

    expect(received).toBe(expected) // Object.is equality

    Expected: "bar"
    Received: "Hello world"

       9 |   it(`message should return bar`, async () => {
      10 |     expect(sendMessage.message()).toBe("bar");
    > 11 |     expect(sendMessage.foo()).toBe("bar");
         |                               ^
      12 |   });
      13 | });
      14 |

      at Object.<anonymous> (__tests__/mockDemo.test.js:11:31)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 total

It looks as if sendMessage.foo is calling the bound function once imported of message, which by default returns Hello World.

How would one mock message in this context?

Update

Using jest.fn().mockImplementation(() => "bar"); results in the same behaviour:

describe("MessageReceiver Router", () => {
  //   sendMessage.message.mockImplementation = jest.fn(() => {
  //     return "bar";
  //   });

  sendMessage.message = jest.fn().mockImplementation(() => "bar");

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

Results:

$ ./node_modules/.bin/jest ./__tests__/mockDemo.test.js
 FAIL  __tests__/mockDemo.test.js
  MessageReceiver Router
    ✕ message should return bar (10ms)

  ● MessageReceiver Router › message should return bar

    expect(received).toBe(expected) // Object.is equality

    Expected: "bar"
    Received: "Hello world"

      11 |   it(`message should return bar`, async () => {
      12 |     expect(sendMessage.message()).toBe("bar");
    > 13 |     expect(sendMessage.foo()).toBe("bar");
         |                               ^
      14 |   });
      15 | });
      16 |

      at Object.<anonymous> (__tests__/mockDemo.test.js:13:31)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 total
Snapshots:   0 total
Time:        2.175s

Given the following example with a basic test, I'd expect bar to be returned when sendMessage.message is mocked with Jest. Instead, when called, it returns the original value of "Hello World".

serviceBus.js

export const message = () => {
  return "Hello world";
};

export const foo = () => {
  return message();
};

mockDemo.test.js

import * as sendMessage from "../src/services/serviceBus";

describe("sendMessage", () => {
  sendMessage.message = jest.fn(() => {
    return "bar";
  });

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

And the results as follows:

$ ./node_modules/.bin/jest ./__tests__/mockDemo.test.js
 FAIL  __tests__/mockDemo.test.js
  MessageReceiver Router
    ✕ message should return bar (9ms)

  ● MessageReceiver Router › message should return bar

    expect(received).toBe(expected) // Object.is equality

    Expected: "bar"
    Received: "Hello world"

       9 |   it(`message should return bar`, async () => {
      10 |     expect(sendMessage.message()).toBe("bar");
    > 11 |     expect(sendMessage.foo()).toBe("bar");
         |                               ^
      12 |   });
      13 | });
      14 |

      at Object.<anonymous> (__tests__/mockDemo.test.js:11:31)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 total

It looks as if sendMessage.foo is calling the bound function once imported of message, which by default returns Hello World.

How would one mock message in this context?

Update

Using jest.fn().mockImplementation(() => "bar"); results in the same behaviour:

describe("MessageReceiver Router", () => {
  //   sendMessage.message.mockImplementation = jest.fn(() => {
  //     return "bar";
  //   });

  sendMessage.message = jest.fn().mockImplementation(() => "bar");

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

Results:

$ ./node_modules/.bin/jest ./__tests__/mockDemo.test.js
 FAIL  __tests__/mockDemo.test.js
  MessageReceiver Router
    ✕ message should return bar (10ms)

  ● MessageReceiver Router › message should return bar

    expect(received).toBe(expected) // Object.is equality

    Expected: "bar"
    Received: "Hello world"

      11 |   it(`message should return bar`, async () => {
      12 |     expect(sendMessage.message()).toBe("bar");
    > 13 |     expect(sendMessage.foo()).toBe("bar");
         |                               ^
      14 |   });
      15 | });
      16 |

      at Object.<anonymous> (__tests__/mockDemo.test.js:13:31)

Test Suites: 1 failed, 1 total
Tests:       1 failed, 1 total
Snapshots:   0 total
Time:        2.175s
Share Improve this question edited Feb 18, 2020 at 16:01 steadweb asked Feb 18, 2020 at 15:56 steadwebsteadweb 16.7k3 gold badges38 silver badges53 bronze badges 3
  • sendMessage.message.mockImplementation? – evolutionxbox Commented Feb 18, 2020 at 15:56
  • Doesn't work unfortunately :/ – steadweb Commented Feb 18, 2020 at 15:58
  • Ah. It has been closed over. So you may not be able to. – evolutionxbox Commented Feb 18, 2020 at 15:59
Add a ment  | 

2 Answers 2

Reset to default 3

So internal functions called cannot be mocked or spyed on. To fix this, you need to create an object of services, and export that instead.

serviceBus.js

const message = () => {
  return "Hello world";
};

const foo = () => {
  return services.message();
};

const services = {
  message,
  foo
};

export default services;

mockDemo.test.js

import sendMessage from "../src/services/serviceBus";

describe("MessageReceiver Router", () => {
  sendMessage.message = jest.fn(() => {
    return "bar";
  });

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

You should use spyOn method to mock the sendMessage.message method.

import * as sendMessage from "../src/services/serviceBus";

describe("sendMessage", () => {
   jest.spyOn(sendMessage, 'message').mockReturnValue("bar")

  it(`message should return bar`, async () => {
    expect(sendMessage.message()).toBe("bar");
    expect(sendMessage.foo()).toBe("bar");
  });
});

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1744730826a4590455.html

相关推荐

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信