Внедрение зависимостей: параметры покоя и функции по умолчанию для одной и той же функции? - PullRequest
0 голосов
/ 13 декабря 2018

Скажем, у меня есть такой код:

function a(...numbers) {
   return numbers.map(n => b(n)); 
}

function b(n) {
   return n+1; 
}

Я искал способы протестировать подобный код, особенно для проверки функциональности a без фактического вызова b,

Один из вариантов - использовать внедрение зависимостей и передать функцию b в качестве параметра.

т.е.

function a(...numbers, _b=b) {
   return numbers.map(n => _b(n)); 
}

Но, конечно, оператор rest не позволит мне добавить аргумент в конец.

И я не хочу ставить аргумент функции первым - потому что тогда разработчику приходится каждый раз передавать функцию b или что угодно, либо передавать нулевое значение или подобное.

Есть ли способ достичь этой функциональности?

Ответы [ 2 ]

0 голосов
/ 13 декабря 2018

Function.prototype.bind() (вроде) решает это!

//The convention we will use here is that developers shouldn't use the 
// _underscore methods in production. 

export const _a = function(_b, ...numbers) {
 return numbers.map(n => _b(n)); 
}; 

export const b = function(n) {
  return n+1; 
}

export const a = _a.bind(null, b); 

console.log(a(1,2,3)) //[2,3,4]

Это также имеет то преимущество, что вы скрываете введенную функцию от разработчика.

Теперь, как бы вы это проверили?

Вы должны протестировать метод _underscore, так что-то вроде:

import { _a } from "../functions";

describe("_a", () => {

    it("_a(1,2,3) calls _b three times.", () => {
        const mockFn = jest.fn();
        const a = _a.bind(null, mockFn);

        a(1, 2, 3);

        expect(mockFn.mock.calls).toHaveLength(3);
    })

}); 

Если вам интересно - я запустил репозиторий Github с более конкретным примеромэтот подход здесь .

Если у кого-то есть более аккуратный способ сделать это - я весь в ушах.

0 голосов
/ 13 декабря 2018

остальные параметры могут работать только как последний аргумент, принятый функцией, он захватывает все аргументы, которые не были объявлены в параметре функции.Вы можете на самом деле отпустить параметр rest и передать массив

function a(numbers, _b = b) {
   return numbers.map(n => _b(n)); 
}

function b(n) {
   return n+1; 
}

console.log(a([1,2,3,4], f => f * 1));
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...