0

I am trying to mock a function named callApi. I use jest.fn(), but I am having the error message:

function callApi(method: string, url: string, path: string, data?: any): Promise> Cannot assign to 'callApi' because it is a read-only property.ts(2540)

I have tried to follow the examples on jest examples

What is wrong with my code? Why am I having the error message.
Part of callApi is import axios from "axios";

export function callApi(
  method: string,
  url: string,
  path: string,
  data?: any
) {
  switch (method) {

The test is as follows:

import {runSaga} from 'redux-saga';
import * as api from '../Utilities/api'
import { getPaymentsError, getPaymentsSuccess, IPaymentsAction } from './actions';
import handleFetch from './sagas'


test('should test fetch payments success',async() =>{
const dispatchedActions = [{}];
const mockedPayments = [{
    details: {
    amount: "10000",
    date: new Date(),
    id: 5
  },
  id: 5,
  month: "Feb 2003",
  userID: 3
}];


 api.callApi = jest.fn(() => Promise.resolve(mockedPayments));<----------error here



const fakeStore = {
    dispatch:(action:IPaymentsAction) =>dispatchedActions.push(action)
}
await runSaga(fakeStore,handleFetch).done;
expect(api.callApi.mock.calls.length).toBe(1);
expect(dispatchedActions).toContainEqual(getPaymentsSuccess(mockedPayments));
})

1 Answer 1

4

Assigning to a jest.fn() doesn't work well with TypeScript typing.

Use jest.spyOn instead:

test('should test fetch payments success', async (done) => {
  const dispatchedActions = [{}];
  const mockedPayments = [{
    details: {
      amount: "10000",
      date: new Date(),
      id: 5
    },
    id: 5,
    month: "Feb 2003",
    userID: 3
  }];

  const spy = jest.spyOn(api, 'callApi');
  spy.mockImplementation(() => Promise.resolve(mockedPayments));

  const fakeStore = {
    dispatch: (action: IPaymentsAction) => dispatchedActions.push(action)
  }
  await runSaga(fakeStore, handleFetch);done();
  expect(spy.mock.calls.length).toBe(1);
  expect(dispatchedActions).toContainEqual(getPaymentsSuccess(mockedPayments));
})
Sign up to request clarification or add additional context in comments.

4 Comments

I am having the error Timeout - Async callback was not invoked within timeout specified by jasmine.DEFAULT_TIMEOUT_INTERVAL. at pTimeout (node_modules/jest-jasmine2/build/queueRunner.js:53:21) at Timeout.callback [as _onTimeout] (node_modules/jsdom/lib/jsdom/browser/Window.js:523:19)
@jupitersailormoon that is a separate issue (sounds like your saga might not be resolving) and should be addressed in a new question if help is needed.
I have added the done function . Thanks to stackoverflow.com/questions/49603939/… and thanks @brian-lives-outdoors
After hours of searching, this answer saved me from slamming my keyboard off my desk. THANK YOU!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.