1

In my controller I have imported the secure util file when I call that util with path as parameter it returns unique Id. but how to call this function in test file using proxyquire and stub.

controller.ts

import { getSecret } from './util/secrect-util'

export function getId(req: Request, res: Response) {
    const path='test/path'
    const uniueID = getSecret(path);
    console.log(uniueID) // prints testUser01
    const url=`https://mytest.com?userid=${uniueID}`;
    res.redirect(302,url);
}

test.ts

import { Request, Response } from "express";
import * as sinon from 'sinon';
import * as proxyquire from 'proxyquire';

describe('should redirect', () => {
    const validurl:string="https://mytest.com?userid=testUser01";
    let res:any;
    let req:any

    beforeEach(() => {
        res = {
            redirect:sinon.stub()
       }
   });

   it('should get error with invalid path', () => {
       const secPath = sinon.stub().returns('/test/invalidPath');
       const urlctl = proxyquire('./controller', {
           getSecret: { path: secPath },
       });
      urlctl.getId(req, res);
      sinon.assert.calledWithExactly(
          res.redirect,
          400,
          'inValidpath',
      )
  });
});

getting error while run the test cases. Please assist.

Lin Du
  • 88,126
  • 95
  • 281
  • 483
rrUI0026
  • 21
  • 4

1 Answers1

1

From the doc:

proxyquire({string} request, {Object} stubs)

  • request: path to the module to be tested e.g., ../lib/foo
  • stubs: key/value pairs of the form { modulePath: stub, ... } module paths are relative to the tested module not the test file therefore specify it exactly as in the require statement inside the tested file values themselves are key/value pairs of functions/properties and the appropriate override

E.g.

controller.ts:

import { getSecret } from './util/secrect-util';
import { Request, Response } from 'express';

export function getId(req: Request, res: Response) {
  const path = 'test/path';
  const uniueID = getSecret(path);
  console.log(uniueID);
  const url = `https://mytest.com?userid=${uniueID}`;
  res.redirect(302, url);
}

util/secrect-util.ts:

export function getSecret(path) {
  return 'real implementation';
}

controller.test.ts:

import sinon from 'sinon';
import proxyquire from 'proxyquire';

describe('70666283', () => {
  it('should pass', () => {
    const getSecretStub = sinon.stub().returns('123');
    const urlctl = proxyquire('./controller', {
      './util/secrect-util': {
        getSecret: getSecretStub,
      },
    });
    const req = {};
    const res = { redirect: sinon.stub() };
    urlctl.getId(req, res);
    sinon.assert.calledWithExactly(getSecretStub, 'test/path');
    sinon.assert.calledWithExactly(res.redirect, 302, 'https://mytest.com?userid=123');
  });
});

Test result:

  70666283
123
    ✓ should pass (1743ms)


  1 passing (2s)

------------------|---------|----------|---------|---------|-------------------
File              | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s 
------------------|---------|----------|---------|---------|-------------------
All files         |   88.89 |      100 |      50 |   88.89 |                   
 70666283         |     100 |      100 |     100 |     100 |                   
  controller.ts   |     100 |      100 |     100 |     100 |                   
 70666283/util    |      50 |      100 |       0 |      50 |                   
  secrect-util.ts |      50 |      100 |       0 |      50 | 2                 
------------------|---------|----------|---------|---------|-------------------
Lin Du
  • 88,126
  • 95
  • 281
  • 483
  • How to handle multiple variables with same function like below `export function getId(req: Request, res: Response) { const path = 'test/path'; const path1 = 'test/path1'; const uniueID = getSecret(path); const uniueID1 = getSecret(path1); console.log(uniueID); const url = `https://mytest.com?userid=${uniueID}?userid1=${uniueID1}`; res.redirect(302, url); }` – rrUI0026 Jan 24 '22 at 10:09