Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I mock an exported typescript function in a jasmine test?

I'm trying to mock a function exported from a typescript file in a Jasmine test. I expect the following to mock the imported foo and return the value 1 in the spec for bar.

The mock appears to be uncalled, so I'm clearly missing something. How can I fix this example?

demo.ts:

export function foo(input: any): any {
  return 2;
}

export function bar(input: any): any {
  return foo(input) + 2;
}

demo.ts.spec:

import * as demo from './demo';

describe('foo:', () => {
  it('returns 2', () => {
    const actual = demo.foo(1);
    expect(actual).toEqual(2);
  });
});

describe('bar:', () => {
  // let fooSpy;
  beforeEach(() => {
    spyOn(demo, 'foo' as any).and.returnValue(1); // 'as any' prevents compiler warning
  });

  it('verifies that foo was called', () => {
    const actual = demo.bar(1);
    expect(actual).toEqual(3); // mocked 1 + actual 2
    expect(demo.foo).toHaveBeenCalled();
  });
});

Failures:

  • Expected 4 to equal 3.
  • Expected spy foo to have been called.
like image 465
Sevenless Avatar asked Mar 28 '18 15:03

Sevenless


1 Answers

Jeffery's answer helped get me on the right track.

To attach the spy is attached to the right reference for foo the product code needs to have a small change. foo() should be called as this.foo()

The below pattern works for testing (and is a lot cleaner than the convoluted work around I was using previously).

demo.ts:

export function foo(input: any): any {
  return 2;
}

export function bar(input: any): any {
  return this.foo(input) + 2;
}

demo.ts.spec:

import * as demo from './demo';

describe('foo:', () => {
  it('returns 2', () => {
    const actual = demo.foo(1);
    expect(actual).toEqual(2);
  });
});

describe('bar:', () => {
  // let fooSpy;
  beforeEach(() => {
    spyOn(demo, 'foo' as any).and.returnValue(1);
  });

  it('verifies that foo was called', () => {
    const actual = demo.bar(1);
    expect(actual).toEqual(3);
    expect(demo.foo).toHaveBeenCalled();
  });
});
like image 161
Sevenless Avatar answered Nov 15 '22 05:11

Sevenless