Существует две проблемы.
Во-первых, мы не можем сказать, когда завершено выполнение метода Index.get()
(он не принимает обратный вызов, не возвращает обещание, не помеченное как асинхронное и т. Д.).
get(uri) { ... }
Использование такого метода критически неудобно.Например: если мы хотим сначала выполнить Index.get()
, а затем выполнить какое-либо действие сразу после того, как мы не сможем.
Чтобы исправить это, мы можем просто добавить обратный вызов в качестве последнего параметраIndex.get
.
Вторая проблема заключается в том, как заглушается метод http.get
:
httpSpy = stub(http, 'get')
Эта строка в основном означает: замените http.get
пустой функцией.Эта фиктивная функция не сработает, если вы передадите обратный вызов внутри , но не вызовет ее.
Именно поэтому http.get
вызывается только один раз.Он просто игнорирует переданный обратный вызов, где http.get
должен быть вызван во второй раз.
Чтобы исправить это, мы можем использовать метод stub.yields()
, чтобы заставить sinon знать, что последний параметр, переданный заглушке, является обратным вызовом (иСинон должен это назвать).Вы можете найти метод в документах .
Вот рабочий пример, пожалуйста, смотрите мои комментарии:
class Index {
// Added a callback here
get(uri, callback) {
http.get(uri, () => {
http.get('/', () => {
// Pass any data you want to return here
callback(null, {});
})
})
}
}
let httpSpy;
beforeEach(() => {
a = new Index()
// Now sinon will expect a callback as a last parameter and will call it
httpSpy = stub(http, 'get').yields();
})
describe('When the get method is invoked', () => {
const uri = 'http://www.google.co.uk';
// Now we are waiting for the execution to end before any assertions
beforeEach(done => {
a.get(uri, done);
});
it('should make a call to the http service with passed in uri', () => {
assert.calledTwice(httpSpy);
assert.match(httpSpy.getCall(0).args[0], uri);
assert.match(httpSpy.getCall(1).args[0], '/');
});
})