Чего вы ожидали?
Я ожидал, что смогу заглушить стрелочную функцию в классе.
Что на самом деле происходит
Я не могу заглушить функцию стрелки, но могу заглушить функцию прототипа класса.
FAILED TESTS:
ExampleClass tests
× should stub thisDoesntWork arrow function
Chrome 52.0.2743 (Windows 10 0.0.0)
TypeError: Attempted to wrap undefined property thisDoesntWork as function
at wrapMethod (webpack:///~/sinon/pkg/sinon.js:3138:0 <- test-bundler.js:7377:21)
at Object.stub (webpack:///~/sinon/pkg/sinon.js:2472:0 <- test-bundler.js:6711:12)
at Context.<anonymous> (webpack:///src/stores/sinon.test.ts:22:51 <- test-bundler.js:96197:72)
Как воспроизвести
export class ExampleClass {
thisWorks() {
return 0;
}
thisDoesntWork = () => {
return 0;
}
}
describe("ExampleClass tests", () => {
it("should stub thisWorks function", () => {
let stubFunctionA = sinon.stub(ExampleClass.prototype, "thisWorks");
});
it("should stub thisDoesntWork arrow function", () => {
let stubFunctionB = sinon.stub(ExampleClass, "thisDoesntWork");
});
});
Это пища для предстоящего нового сайта документации, где мы надеемся опубликовать еще несколько статей, ориентированных на обучение, по заглушкам, шпионажу и т. Д. В контексте ES2015.
Обычно, когда вы сталкиваетесь с подобными проблемами, очень полезно помнить один простой факт: ES2015 часто является просто синтаксическим сахаром поверх простых конструкций ES5. Это означает, что если вы не понимаете, почему что-то происходит (или не происходит), попробуйте деконструировать код до его эквивалента в ES5. Самый простой способ (это то, что я только что сделал) - просто вставить пример кода на площадку Babel и посмотреть, во что компилируется код ES2015 / ES6:
Транспортированный код из Вавилона
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
var ExampleClass = exports.ExampleClass = function () {
function ExampleClass() {
_classCallCheck(this, ExampleClass);
this.thisDoesntWork = function () {
return 0;
};
}
_createClass(ExampleClass, [{
key: "thisWorks",
value: function thisWorks() {
return 0;
}
}]);
return ExampleClass;
}();
Первое, что я заметил, это то, что стрелочные функции - это просто _instance методы_. Это означает несколько вещей:
Зная все это, просто изменить свой неудачный тест на это:
it("should stub thisDoesntWork arrow function", () => {
var example = new ExampleClass();
let stubFunctionB = sinon.stub(example, "thisDoesntWork", () => "actually it does work" );
});
Удачи.
Самый полезный комментарий
Это пища для предстоящего нового сайта документации, где мы надеемся опубликовать еще несколько статей, ориентированных на обучение, по заглушкам, шпионажу и т. Д. В контексте ES2015.
Обычно, когда вы сталкиваетесь с подобными проблемами, очень полезно помнить один простой факт: ES2015 часто является просто синтаксическим сахаром поверх простых конструкций ES5. Это означает, что если вы не понимаете, почему что-то происходит (или не происходит), попробуйте деконструировать код до его эквивалента в ES5. Самый простой способ (это то, что я только что сделал) - просто вставить пример кода на площадку Babel и посмотреть, во что компилируется код ES2015 / ES6:
Транспортированный код из Вавилона
Первое, что я заметил, это то, что стрелочные функции - это просто _instance методы_. Это означает несколько вещей:
Зная все это, просто изменить свой неудачный тест на это:
Удачи.