繁体   English   中英

如何使用Jasmine和TypeScript监视构造函数

[英]How to spy on constructor using Jasmine and TypeScript

有没有办法使用Jasmine和Typescript监视构造函数?

有争议的建议解决方案使用Jasmine监视构造函数无效,因为TypeScript不会在window上公开全局声明

这是我的用例:

// higher-order function returns validation function with max length
const maxLengthValidator = maxLength => value => value.length > maxLength;

class Book {
  // will be a different function instance each time the Book object is
  // created causing the following test to fail
  nameValidator = maxLengthValidator(42);
  name = null;
  constructor (name) { this.name = name; }
}

class Library {
  persons = [];
  storeBook (book) { this.persons.push(book); }
  createBook (name) { this.storeBook(new Book(name)); }
}

测试失败:

it('createBook passes new book with provided name to storeBook', () => {
  const lib = new Library();
  spyOn(lib, 'storeBook');
  lib.createBook('Start with Why');
  expect(lib.storeBook).toHaveBeenCalledWith(new Book('Start with Why'));
  // Result: Expected spy storeBook to have been called with
  // [ Book({ name: 'Start with Why', nameValidator: Function }) ]
  // but actual calls were
  // [ Book({ name: 'Start with Why', nameValidator: Function }) ]
});

在测试中,我不太在意构造函数的作用。 我只需要验证是否已使用正确的参数调用了它。 这甚至听起来像是模拟的正确用例。

可以使用它们的toString值比较两个函数。 您可以添加自定义相等性测试器或添加新的匹配器。

添加自定义相等测试器

function replacer(k, v) {
    if (typeof v === 'function') {
        v = v.toString();
    }
    return v;
}

function stringifyEquality(a, b) {
    try {
        return JSON.stringify(a, replacer) === JSON.stringify(b, replacer) ? true : undefined;
    } catch (e) {
        return undefined
    }
}

beforeAll(() => {
    jasmine.addCustomEqualityTester(stringifyEquality);
});

it('createBook passes new book with provided name to storeBook', () => {
    const lib = new Library();
    spyOn(lib, 'storeBook');
    lib.createBook('Start with Why');
    expect(lib.storeBook.calls.mostRecent().args).toEqual([new Book('Start with Why')]);
});

添加自定义匹配器

function replacer(k, v) {
    if (typeof v === 'function') {
        v = v.toString();
    }
    return v;
}

beforeEach(() => {
    jasmine.addMatchers({
        toBeJsonEqual: function(expected){
            var one = JSON.stringify(this.actual, replacer).replace(/(\\t|\\n)/g,''),
                two = JSON.stringify(expected, replacer).replace(/(\\t|\\n)/g,'');

                return one === two;
            }
    });
});

expect(obj).toBeJsonEqual(obj2);

链接: 问题14541287(警察的回答)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM