Utilizing Jest to Simulate a Class - Incorporation via Imported Module

I'm having difficulty mocking a constructor of a class from an imported module. Interestingly, it works perfectly when my mock implementation is directly inserted into the jest.mock() factory function, but fails when the implementation is imported from another file.

Successful Implementation:

test.ts:


jest.mock('external-lib', () => {
  const originalModule = jest.requireActual('@external-lib');

  function ClassMock(): any {
    return {
      method1: (val: number): Promise<any> => {
        return Promise.resolve({ a: val });
      },
    };
  }

  return {
    __esModule: true,
    ...originalModule,
    StrategyComputation: jest.fn(ClassMock),
  };
});

Unsuccessful Attempt:

When I extract the function ClassMock into another file mocks.ts and import it in the test file, it stops working:

test.ts:

import { ClassMock } from './mocks'; 

jest.mock('external-lib', () => {
  const originalModule = jest.requireActual('@external-lib');

  return {
    __esModule: true,
    ...originalModule,
    StrategyComputation: jest.fn(ClassMock),
  };
});

mocks.ts:

  export function ClassMock(): any {
    return {
      method1: (val: number): Promise<any> => {
        return Promise.resolve({ a: val });
      },
    };
  }

Unfortunately, it leads to an error:

TypeError: Cannot read property 'ClassMock' of undefined

Answer №1

To maintain the integrity of the mock factory, one approach is to encapsulate the function() {} within it and solely import the implementations of the class methods:

test.ts:

import { MockFunctions } from './mocks';

jest.mock('external-lib', () => {
  const originalModule = jest.requireActual('@external-lib');

  return {
    __esModule: true,
    ...originalModule,
    StrategyComputation: jest.fn(function() {
        return MockFunctions
    }),
  };
});

mocks.ts:

export const MockFunctions = {
    method1: (val: number): Promise<any> => {
      return Promise.resolve({ a: val });
    },
}

Answer №2

For my mock assignment, I followed these steps which made it much simpler.

import Axios, { AxiosRequestConfig } from 'axios';

jest.mock('axios');

describe('MyClass', () => {
  it('test doSomething', async () => {
    const axios = Axios as jest.Mocked<typeof Axios>;
    axios.request.mockResolvedValue({});

    const result = new MyClass().doSomething();

    expect(result).toBeTruthy();
  });
});

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Verify whether a component is a React.ReactElement<any> instance within a child mapping operation

I am facing a challenge with a component that loops through children and wraps them in a div. I want to exclude certain elements from this process, but I am struggling to determine if the child is a ReactElement or not (React.ReactChild can be a string or ...

Having trouble decoding a cookie received from a React.js front-end on an Express server

When using React js for my front end, I decided to set a cookie using the react-cookie package. After confirming that the request cookie is successfully being set, I moved on to configure the Express server with the cookie parser middleware. app.use(cookie ...

Develop a TypeScript class in a distinct file

I currently have ag-grid implemented in an Angular project with a CustomFilter. The problem is that the file containing the code for the CustomFilter function is becoming quite large and difficult to manage. I am now looking to move the CustomFilter to a s ...

Leveraging external type definitions with certain types that are not made available for export

Currently, I am integrating TypeScript into my ReactJs project along with the Leaflet library for displaying world maps. The challenge arose when I needed to provide type definitions for the Leaflet library, but I discovered that they already exist as a no ...

The type '{}' is lacking the 'submitAction' property, which is necessary according to its type requirements

I'm currently diving into the world of redux forms and typescript, but I've encountered an intriguing error that's been challenging for me to resolve. The specific error message reads as follows: Property 'submitAction' is missing ...

How can we define a function using a generic type in this scenario using Typescript?

Here's a challenge that I'm facing. I have this specific type definition: type FuncType<T> = (value: T) => T I want to create a function using this type that follows this structure: const myFunc: FuncType<T> = (value) => valu ...

Express middleware generator function causing a type error

I recently implemented a function that takes a middleware function, wraps it in a try-catch block, and then returns the modified middleware function. tryCatch.ts import { Request, Response, NextFunction } from "express"; export default function ...

React-snap causing trouble with Firebase

I'm having trouble loading items from firebase on my homepage and I keep running into an error. Does anyone have any advice on how to fix this? I've been following the instructions on https://github.com/stereobooster/react-snap and here is how ...

Issue with rendering Base64 image array strings in FlatList component in React Native

In my RN App, I am trying to display a FlatList with Image Items but it seems like I have missed something. I am retrieving blob data from my API, converting it to a String using Buffer, and then adding it to an Array. This Array is used to populate the F ...

typescript undefined subscription to observable

After making an http request to fetch some data, I am facing issues in displaying it as intended. The dropdown select for entriesPerPage, and the left and right cursors for switching page in pagination are working fine. However, upon switching a page, I en ...

What is the procedure for linking the value (<p>John</p>) to the mat form field input so that it displays as "John"?

Can I apply innerHTML to the value received from the backend and connect it to the matInput? Is this a viable option? ...

Using custom properties from the Material-UI theme object with custom props in Emotion styled components: a step-by-step guide

I have implemented a custom object called fTokens into the MUI theme using Module augmentation in TypeScript This is how my theme.d.ts file is structured declare module "@mui/material/styles" { interface FPalette { ... } interface FTokens ...

Is condition checking taken into consideration by Typescript?

I keep encountering this strange TypeScript compile warning that just won't go away, even though I believe it shouldn't be there in the first place... Here are the interfaces I'm working with: interface Props { tasks: TaskType[] } inter ...

Issue with toggling in react js on mobile devices

Currently, I am working on making my design responsive. My approach involves displaying a basket when the div style is set to "block", and hiding it when the user browses on a mobile device by setting the display to "none". The user can then click on a but ...

Selecting ion-tabs causes the margin-top of scroll-content to be destroyed

Check out the Stackblitz Demo I'm encountering a major issue with the Navigation of Tabs. On my main page (without Tabs), there are simple buttons that pass different navparams to pre-select a specific tab. If you take a look at the demo and click t ...

Encountering a problem with the 'string' parameter when using TypeScript

I keep encountering the following error message: Element implicitly has an 'any' type because expression of type 'string' can't be used to index type '{ barkingRoadProject: string[]; }'. No index signature with a paramet ...

Rearrange Material UI styles in a separate file within a React project

Currently, I am developing an application utilizing material-ui, React, and Typescript. The conventional code for <Grid> looks like this: <Grid container direction="row" justifyContent="center" alignItems="center&q ...

Is there a way to transform time into a percentage with the help of the moment

I am looking to convert a specific time range into a percentage, but I'm unsure if moment.js is capable of handling this task. For example: let start = 08:00:00 // until let end = 09:00:00 In theory, this equates to 100%, however, my frontend data ...

Tips for implementing self-managed state in Vue.js data object

My approach in organizing my Vue application involves using classes to encapsulate data, manage their own state (edited, deleted, etc), and synchronize with the back-end system. However, this method seems to conflict with Vue in some respects. To illustra ...

Organized modules within an NPM package

I am looking to develop an NPM package that organizes imports into modules for better organization. Currently, when I integrate my NPM package into other projects, the import statement looks like this: import { myFunction1, myFunction2 } from 'my-pac ...