在严格模式下使用this.inherited(arguments)时出现DOJO错误

时间:2015-10-19 07:34:50

标签: javascript dojo

我为Dijit Custom小部件声明了一个基础“Class”。

'strict mode'例程中this.inherited(arguments);正在调用,我收到此错误:

  

未捕获的TypeError:'caller','callee'和'arguments'属性可能   不能在严格模式函数或参数对象上访问   打电话给他们

我需要保持使用'严格模式'。

知道怎么解决吗?

define([
    'dojo/_base/declare',
    'dojo/topic',
    'dojo/_base/lang'
], function (
    declare,
    topic,
    lang
    ) {
    'use strict';
    var attachTo = 'myPanels';
    return declare(null, {
        id: null,
        title: null,
        postCreate: function () {
            // ERROR HERE
            this.inherited(arguments);
            this.placeAt(attachTo);
        },
        constructor: function () {
        },
    });
});

注意:删除'strict mode'可以解决问题,但在我的情况下不是一个选项,因为我需要使用'strict mode'

2 个答案:

答案 0 :(得分:1)

这是已知问题,Dojo使用arguments.callee进行内省并确定继承(更确切地说是下一个)方法。要解决此问题,您需要创建自己的arguments对象,然后指定arguments.callee属性并将其传递给Dojo以进行内省。唯一的问题是将函数传递给它自己,但它可以很容易地解决,例如使用这个帮助器,将它放在一个模块中,例如override.js

"use strict";
define([], function () {
    var slice = Array.prototype.slice;
    return function (method) {
        var proxy;

        /** @this target object */
        proxy = function () {
            var me = this;
            var inherited = (this.getInherited && this.getInherited({
                // emulating empty arguments
                callee: proxy,
                length: 0
            })) || function () {};

            return method.apply(me, [function () {
                return inherited.apply(me, arguments);
            }].concat(slice.apply(arguments)));
        };

        proxy.method = method;
        proxy.overrides = true;

        return proxy;
    };
});

现在您可以使用它来调用继承的方法

define([
    'dojo/_base/declare',
    'dojo/topic',
    'dojo/_base/lang',
    './override'
], function (
    declare,
    topic,
    lang,
    override
    ) {
    'use strict';
    var attachTo = 'myPanels';
    return declare(null, {
        id: null,
        title: null,
        postCreate: override(function (inherited) {
            inherited(); // the inherited method 
            this.placeAt(attachTo);
        }),
        methodWithArgs : override(function(inherited, arg1, arg2)) {
            inherited(arg1, arg2);
            // pass all arguments to the inherited method
            // inherited.apply(null,Array.prototype.slice.call(arguments, 1));
        }),
        constructor: function () {
        },
    });
});

答案 1 :(得分:0)

从v1.13.0开始,此问题已在Dojo框架中解决。

假设您使用的是Dojo 1.13.0或更高版本,要从严格模式文件中调用this.inherited,只需将引用传递给调用函数(使用命名函数表达式或NFE),如下所示:第一个论点。

所以上面的代码如下:

define([
    'dojo/_base/declare',
    'dojo/topic',
    'dojo/_base/lang'
], function (
    declare,
    topic,
    lang
    ) {
    'use strict';
    var attachTo = 'myPanels';
    return declare(null, {
        id: null,
        title: null,
        postCreate: function postCreate() { //(1) add function name
            //(2) pass function reference as the first argument
            this.inherited(postCreate, arguments);
            this.placeAt(attachTo);
        },
        constructor: function () {
        },
    });
});

请注意,命名函数表达式(NFE)在IE8和更早的版本中存在很多错误,因此,如果您支持这些浏览器,请不要使用它。