Writing Jest Test Cases for a NestJS Service Function with TypeORM Dependencies

24 Views Asked by At

I am relatively new to Jest testing in NestJS and currently working on writing test cases for a service function that retrieves the count of approved leaves for a specific date. The service function uses TypeORM and has a dependency injected as follows:

constructor(private readonly dataServices: TypeOrmDataServices) {}

Here's the function I need to test:

  async getApprovedLeavesCount(date: Date, employee: Employee) {
    const currentDate = new Date(date);
    currentDate.setUTCHours(0, 0, 0, 0);

    const endDate = new Date();
    endDate.setUTCHours(23, 59, 59, 999);

    const queryBuilder = await this.dataServices.requests.repository
      .createQueryBuilder('request')
      .where('request.organizationId = :organizationId', {
        organizationId: employee.organization.id,
      })
      .where('request.status = :status', { status: RequestStatus.APPROVED })
      .andWhere('request.start >= :currentDate', {
        currentDate: currentDate.toISOString(),
      })
      .andWhere('request.end <= :endDate', { endDate: endDate.toISOString() });
    const leaveCount = await queryBuilder.getCount();
    return leaveCount;
  }

this is how my function look like and now I want to write a test cases of this also one dependencies I am using this service file is

  constructor(private readonly dataServices: TypeOrmDataServices) {}

I'm seeking guidance on how to write Jest test cases for this function. Specifically, I'm unsure about how to mock the TypeORM query builder and handle dependencies like the TypeOrmDataServices instance.

I've attempted to create a test file, and here is what I have so far:

import { Test, TestingModule } from '@nestjs/testing';
import { DashboardService } from './dashboard.service'; // Adjust the path based on your actual structure
import { RequestStatus } from '../data-services/entities/request.entity';
import * as moment from 'moment';

class MockTypeOrmDataServices {
  requests = {
    repository: {
      createQueryBuilder: jest.fn(() => ({
        where: () => jest.fn(),
        andWhere: () => jest.fn(),
      })),
    },
  };
}
describe('EmployeeService', () => {
  let employeeService: DashboardService;
  let mockTypeOrmDataServices: MockTypeOrmDataServices;

  beforeEach(async () => {
    const module: TestingModule = await Test.createTestingModule({
      providers: [
        DashboardService,
        {
          provide: 'TypeOrmDataServices',
          useClass: MockTypeOrmDataServices,
        },
      ],
    }).compile();

    employeeService = module.get<DashboardService>(DashboardService);
  });

  it('should get approved leaves count', async () => {
    const date = new Date('2024-03-04');
    const employee = {
      organization: { id: 1 },
    };

    const mockQueryBuilder = {
      where: jest.fn().mockReturnThis(),
      andWhere: jest.fn().mockReturnThis(),
      getMany: jest.fn(() => [
        {
          selectedDays: {
            '2024-03-04': true,
            '2024-03-05': false,
          },
        },
      ]),
    };

    const mockDataServices = {
      requests: {
        repository: {
          createQueryBuilder: jest.fn(() => mockQueryBuilder),
        },
      },
    };

    jest.spyOn(employeeService, 'getApprovedLeavesCount').mockImplementation(
      async () =>
        await employeeService.getApprovedLeavesCount({
          date,
          employee: employee as any, // Cast to any if necessary
        }),
    );

    const result = await employeeService.getApprovedLeavesCount({
      date,
      employee: employee as any, // Cast to any if necessary
    });

    expect(result).toBe(1); // Adjust based on your mock data
    expect(
      mockDataServices.requests.repository.createQueryBuilder,
    ).toHaveBeenCalled();
    expect(mockQueryBuilder.where).toHaveBeenCalledWith(
      'request.organizationId = :organizationId',
      {
        organizationId: 1, // Replace with actual organization ID
      },
    );
    expect(mockQueryBuilder.andWhere).toHaveBeenCalledWith(
      'request.status = :status',
      {
        status: RequestStatus.APPROVED,
      },
    );
  });
});

I'm looking for insights on:

How to properly mock the TypeORM query builder for the given function. Guidance on mocking the TypeOrmDataServices dependency and handling its injection. Suggestions for improving the existing test structure. Additionally, any reference materials or examples demonstrating Jest testing in a NestJS service with TypeORM dependencies would be highly appreciated.

0

There are 0 best solutions below