Модульное тестирование для метода обслуживания Angular с импортированной независимой зависимостью - PullRequest
0 голосов
/ 16 октября 2018

У меня есть служба Angular, которая импортирует стороннюю зависимость.Я вызываю зависимость, чтобы дать мне отпечаток браузера, который затем сохраняется в службе.

Я не уверен, как смоделировать эту зависимость в тесте, чтобы я мог утверждать, что она была вызвана, и проверять возвращаемое значение.

Это услуга:

import { Inject, Injectable } from '@angular/core';
import * as Fingerprint2 from 'fingerprintjs2';

@Injectable()
export class ClientInfoService {
    public fingerprint: string | null = null;

    constructor() {
    }

    createFingerprint(): any {
        return new Fingerprint2();
    }

    setFingerprint(): void {
        let fprint = this.createFingerprint();
        setTimeout(() => fprint.get(hash => this.fingerprint = hash), 500);
    }

    getFingerprint(): string | null {
        return this.fingerprint;
    }

}

Это текущий код теста:

import { TestBed } from '@angular/core/testing';
import { ClientInfoService } from './client-info.service';

describe('Client Info Service', () => {
    const hash = 'a6e5b498951af7c3033d0c7580ec5fc6';
    let service: ClientInfoService;

    beforeEach(() => {
        TestBed.configureTestingModule({
            providers: [ClientInfoService],
        });
        service = TestBed.get(ClientInfoService);
    });

    test('should be defined', () => {
        expect(service).toBeDefined();
    });


    describe('get the fingerprint', () => {

        test('it should be null', () => {
            let fprint = service.getFingerprint();
            expect(fprint).toBeNull();
        });

        test('it should be the hash value', () => {
            service.fingerprint = hash;
            let fprint = service.getFingerprint();
            expect(fprint).toEqual(hash);
        });

    test('it should get the hash value after setting', () => {
        jest.useFakeTimers();
        service.createFingerprint = jest.fn().mockReturnValue(() => {
            return {
                get: function (cb) {
                    return cb(hash);
                }
            };
        });
        spyOn(service, 'createFingerprint');
        service.setFingerprint();
        jest.runAllTimers();
        expect(service.createFingerprint).toHaveBeenCalled();
        expect(service.fingerprint).toEqual(hash);
    });

    });

});

Ответы [ 2 ]

0 голосов
/ 01 ноября 2018

Я бы не стал импортировать третьи стороны напрямую в сервис, так как их сложно тестировать модулем (особенно, если они делают какие-то хитрые вещи, такие как http-вызовы, манипулирование DOM и т. Д ...)

Это может быть хорошей идеейчтобы создать службу Angular, которая работает как фабрика для третьих лиц:

import * as Fingerprint2 from 'fingerprintjs2';

@Injectable()
export class FingerprintFactory {
    create(): any {
        return new Fingerprint2();
    }
}

После этого вы можете внедрить FingerprintFactory в свой ClientInfoService и использовать его метод create для создания Fingerprint2 экземпляра.

Также будет очень легко высмеивать FingerprintFactory в вашем ClientInfoService

0 голосов
/ 18 октября 2018

Мне удалось добиться этого с помощью нижеуказанной спецификации.Я использовал шпионов и возвращенные значения, чтобы издеваться над созданием отпечатка пальца.

import { TestBed } from '@angular/core/testing';
import { ClientInfoService } from './client-info.service';

describe('Client Info Service', () => {
    const hash = 'a6e5b498951af7c3033d0c7580ec5fc6';
    let service: ClientInfoService;

    beforeEach(() => {
        TestBed.configureTestingModule({
            providers: [ClientInfoService],
        });
        service = TestBed.get(ClientInfoService);
    });

    test('should be defined', () => {
        expect(service).toBeDefined();
    });

    test('it should set the fingerprint', () => {
        jest.useFakeTimers()
        let cb = (h) => {return h;};
        spyOn(service, 'createFingerprint').and.returnValue({
            get: (cb) => {
                return cb(hash);
            },
        });
        service.setFingerprint();
        jest.runAllTimers();
        expect(service.createFingerprint).toHaveBeenCalled();
        expect(service.fingerprint).toEqual(hash);
    });

    test('it should get the fingerprint', () => {
        let fprint = service.getFingerprint();
        expect(fprint).toEqual(service.fingerprint);
    });

});
...