我正在用React构建一个基本的博客应用程序.我正在使用Jasmine和Karma来进行我的前端测试.我开始运行第一个测试并通过Chrome(Chromium)和Firefox,但是当它在PhantomJS中运行时,我收到以下错误:
PhantomJS 1.9.8 (Linux 0.0.0) ERROR TypeError: 'undefined' is not a function (evaluating 'ReactElementValidator.createElement.bind( null,type )') at /home/michael/repository/short-stories/test/karma_tests/story_test.js:1742
我的测试文件如下所示:
var React = require('react/addons'); var Story = require('../../app/js/components/story.jsx'); var TestUtils = React.addons.TestUtils; var testUtilsAdditions = require('react-testutils-additions'); describe('Story component',function () { var component; beforeEach(function () { component = TestUtils.renderIntoDocument(React.createElement('story')); component.props.storyTitle = 'front end test title'; component.props.author = 'front end author'; component.props.storyText = 'front end story text'; }); it('should display a story',function () { expect(component.props).toBeDefined(); expect(component.props.storyTitle).toBeDefined(); expect(component.props.storyTitle).toBe('front end test title'); expect(component.props.author).toBe('front end author'); expect(component.props.storyText).toBe('front end story text') }); });
我尝试删除我的node_modules,npm缓存清除和npm安装,但它没有修复它.我不确定我的测试如何在Firefox和Chrome中传递,但不能在PhantomJS中传递.您可以在此处查看完整项目:https://github.com/mrbgit/short-stories.如果有更多信息可以提供帮助,请告诉我.任何帮助表示赞赏.谢谢!
解决方法
PhantomJS使用了一个相当旧版本的Qt-Webkit,它不提供
Function.prototype.bind
.这对很多库来说都是一个问题,因此可以使用
polyfill NPM module called ‘phantomjs-polyfill’.
如果您不想使用NPM模块(如果您正在测试未与browserify / webpack捆绑在一起的浏览器站点),则在MDN页面上提供以下用于绑定的polyfill,您可以自己附加它:
if (!Function.prototype.bind) { Function.prototype.bind = function(oThis) { if (typeof this !== 'function') { // closest thing possible to the ECMAScript 5 // internal IsCallable function throw new TypeError('Function.prototype.bind - what is trying to be bound is not callable'); } var aArgs = Array.prototype.slice.call(arguments,1),fToBind = this,fNOP = function() {},fBound = function() { return fToBind.apply(this instanceof fNOP ? this : oThis,aArgs.concat(Array.prototype.slice.call(arguments))); }; fNOP.prototype = this.prototype; fBound.prototype = new fNOP(); return fBound; }; }