Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Nestjs how to test authentication guard

I have hard time testing this simple authentication guard in nestjs framework:

import { ExecutionContext, Injectable } from '@nestjs/common';
import { Reflector } from '@nestjs/core';
import { AuthGuard } from '@nestjs/passport';
import { IS_PUBLIC_ROUTE } from '../public-route.decorator';

@Injectable()
export class JwtAuthGuard extends AuthGuard('custom-jwt') {
  constructor(private reflector: Reflector) {
    super();
  }

  canActivate(context: ExecutionContext) {
    const isPublicRoute = this.reflector.getAllAndOverride<boolean>(
      IS_PUBLIC_ROUTE,
      [context.getHandler(), context.getClass()],
    );
    if (isPublicRoute) {
      return true;
    }
    return super.canActivate(context);
  }
}

IS_PUBLIC_ROUTE property is assigned by decorator on api handler:

import { SetMetadata } from '@nestjs/common';

//Public Route Decorator
export const IS_PUBLIC_ROUTE = 'isPublicRoute';
export const PublicRoute = () => SetMetadata(IS_PUBLIC_ROUTE, true);

So far a I have this:

import { createMock } from '@golevelup/ts-jest';
import { ExecutionContext, UnauthorizedException } from '@nestjs/common';
import { Reflector } from '@nestjs/core';
import { IS_PUBLIC_ROUTE, PublicRoute } from '../public-route.decorator';
import { JwtAuthGuard } from './jwt-auth.guard';

describe('JwtAutthGuad testing...', () => {
  let guard: JwtAuthGuard;

  beforeEach(() => {
    guard = new JwtAuthGuard(new Reflector());
  });

  it('should be defined', () => {
    expect(guard).toBeDefined();
  });

and it is working.

How to set IS_PUBLIC_ROUTE on tests...?

I have tried this with no luck:

const context = createMock<ExecutionContext>();
Reflect.set(context.getClass(), IS_PUBLIC_ROUTE, true);
like image 258
momi Avatar asked Sep 05 '25 03:09

momi


1 Answers

You can mock Reflector's getAllAndOverride call as follow:

describe('JwtAutthGuard', () => {
  let guard: JwtAuthGuard;
  let reflector: Reflector;

  beforeEach(() => {
    reflector = new Reflector();
    guard = new JwtAuthGuard(reflector);
  });

  it('should be defined', () => {
    expect(guard).toBeDefined();
  });

  it('should return true when IS_PUBLIC_ROUTE is true', () => {
    reflect.getAllAndOverride = jest.fn().mockReturnValue(true);
    const context = createMock<ExecutionContext>();
    const canActivate = guard.canActivate(context);

    expect(canActivate).toBe(true); 
  }
like image 177
Nicolas St-Amour Avatar answered Sep 08 '25 00:09

Nicolas St-Amour