Requirejs 出现淘汰错误:无法处理绑定“组件:函数 (){return f}” - 不匹配的匿名 Defined() 模块

问题描述 投票:0回答:3

我在所有浏览器上都会遇到错误。我说“无法处理绑定“组件”......”。我读过很多文章,包括 requirejs 网站。 我已经检查了可能导致错误的原因,但我不知道它们是否适用于我的代码。据我所知,我没有使用 script 标签手动加载任何内容,并且每个模块都使用 requirejs 加载。

我使用 yoman 创建了一个淘汰赛项目:

yo ko
。之后使用
yo ko:component [name of component]
添加组件。大多数情况下页面加载正常,但偶尔会出现以下错误。当我使用两个组件时,频率似乎会增加。我编辑了新组件并删除了对淘汰对象的引用,但错误仍然发生,尽管不那么频繁。

具体错误如下:

Uncaught Error: Unable to process binding "component: function (){return f}"
Message: Mismatched anonymous define() module: function (a){function b(a){return h.raw?a:encodeURIComponent(a)}function c(a){return h.raw?a:decodeURIComponent(a)}function d(a){return b(h.json?JSON.stringify(a):String(a))}function e(a){0===a.indexOf('"')&&(a=a.slice(1,-1).replace(/\\"/g,'"').replace(/\\\\/g,"\\"));try{return a=decodeURIComponent(a.replace(g," ")),h.json?JSON.parse(a):a}catch(b){}}function f(b,c){var d=h.raw?b:e(b);return a.isFunction(c)?c(d):d}var g=/\+/g,h=a.cookie=function(e,g,i){if(void 0!==g&&!a.isFunction(g)){if(i=a.extend({},h.defaults,i),"number"==typeof i.expires){var j=i.expires,k=i.expires=new Date;k.setTime(+k+864e5*j)}return document.cookie=[b(e),"=",d(g),i.expires?"; expires="+i.expires.toUTCString():"",i.path?"; path="+i.path:"",i.domain?"; domain="+i.domain:"",i.secure?"; secure":""].join("")}for(var l=e?void 0:{},m=document.cookie?document.cookie.split("; "):[],n=0,o=m.length;o>n;n++){var p=m[n].split("="),q=c(p.shift()),r=p.join("=");if(e&&e===q){l=f(r,g);break}e||void 0===(r=f(r))||(l[q]=r)}return l};h.defaults={},a.removeCookie=function(b,c){return void 0===a.cookie(b)?!1:(a.cookie(b,"",a.extend({},c,{expires:-1})),!a.cookie(b))}}
http://requirejs.org/docs/errors.html#mismatch 

下面是文件中的一些代码(如果有帮助的话)

index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <title>ko-cai</title>
    <!-- build:css -->
      <link href="bower_modules/semantic/dist/semantic.css" rel="stylesheet">
      <link href="bower_modules/c3/c3.css" rel="stylesheet">
      <link href="css/styles.css" rel="stylesheet">
    <!-- endbuild -->
    <!-- build:js -->
      <script src="app/require.config.js"></script>
      <script data-main="app/startup" src="bower_modules/requirejs/require.js"></script>
    <!-- endbuild -->
  </head>
  <body>
    <div>
      <!--<side-bar></side-bar>
      <page-container></page-container>-->
      <dashboard></dashboard>
      this is a test
    </div>
  </body>
</html>

require.config.js

// require.js looks for the following global when initializing
var require = {
    baseUrl: ".",
    paths: {
        "crossroads":           "bower_modules/crossroads/dist/crossroads.min",
        "hasher":               "bower_modules/hasher/dist/js/hasher.min",
        "jquery":               "bower_modules/jquery/dist/jquery",
        "knockout":             "bower_modules/knockout/dist/knockout",
        "knockout-projections": "bower_modules/knockout-projections/dist/knockout-projections",
        "signals":              "bower_modules/js-signals/dist/signals.min",
        "text":                 "bower_modules/requirejs-text/text",
        "semantic":             "bower_modules/semantic/dist/semantic",
        "lodash":               "bower_modules/lodash/dist/lodash",
        "c3": "bower_modules/c3/c3",
        "d3": "bower_modules/d3/d3",
        "config":               "../../cai/config",
        "observations":         "../../cai/observations"
    },
    shim: {
        "semantic": { deps: ["jquery"] },
        "c3": { deps: ["d3"]},
        "config": { deps: ["knockout"]},
        "observations": { deps: ["knockout","jquery"]}
    }
};

仪表板.html

<h2>dashboard</h2>
<p data-bind='text: message'></p>

仪表板.ts

/// <amd-dependency path="text!./dashboard.html" />
import ko = require("knockout");
export var template: string = require("text!./dashboard.html");
export class viewModel {
    public message = ko.observable("Hello from the dashboard component too!");
    constructor (params: any) {
    }
    public dispose() {
        // This runs when the component is torn down. Put here any logic necessary to clean up,
        // for example cancelling setTimeouts or disposing Knockout subscriptions/computeds.
    }
}

仪表板.js

define(["require", "exports", "knockout", "text!./dashboard.html"], function(require, exports, ko) {
    exports.template = require("text!./dashboard.html");
    var viewModel = (function () {
        function viewModel(params) {
            this.message = ko.observable("Hello from the dashboard component too!");
        }
        viewModel.prototype.dispose = function () {
            // This runs when the component is torn down. Put here any logic necessary to clean up,
            // for example cancelling setTimeouts or disposing Knockout subscriptions/computeds.
        };
        return viewModel;
    })();
    exports.viewModel = viewModel;
});
//# sourceMappingURL=dashboard.js.map
  1. 我做错了什么?
  2. 如何解决这个问题,因为它使测试变得非常困难?
  3. 我可以在哪里检查哪些已知问题适用于我的代码,以便我寻找修复方案。
javascript knockout.js requirejs
3个回答
3
投票

经过更多调查,我找到了解决方案。可能不是最好的,但我还没有看到另一个。该问题与 require.js 有关。看来文件中包含的内容并不重要(我什至尝试使用空白函数并得到不匹配错误)。然而我注意到,当我在错误后执行相同的 require 语句时,它实际上有效。我在knockout中添加了一个组件加载器来获取组件的配置。下面是为我工作的加载程序。希望它对某人有用,直到找到更好的解决方案或我们彻底解决这个问题。

//register a custom loader
ko.components.loaders.unshift({
getConfig: function(name,callback){
    ko.components.defaultLoader.getConfig(name, function(c){
    if (c && c.require){ //do custom loading here. make first attempt to fetch the config
        try{
        require([c.require],function(config){
            callback(config);
        });
        }catch(e){
        //todo: check that this is mismatch error and try again. else throw exception
        require([c.require], function(config){ //make the request again
            callback(config);
        });
        }
    } else {
        callback(c);
    }
    })
}
});

1
投票

您检查过 requirejs 文档吗?更准确地说,是您发布的错误链接后面的列表:

避免错误:

  • 确保加载所有通过 RequireJS API 调用 Define() 的脚本。 不要在 HTML 中手动编写脚本标签来加载具有以下功能的脚本: Define() 在其中调用。
  • 如果您手动编写 HTML 脚本标记,请确保它仅包含 命名模块,并且匿名模块将具有相同的 名称为该文件中的模块之一未加载。
  • 如果问题是使用加载器插件或匿名模块,但是 RequireJS 优化器不用于文件捆绑,请使用 RequireJS 优化器。
  • 如果问题是 var Define lint 方法,请使用 /*global Define */(“全局”之前没有空格)改为注释样式。

http://requirejs.org/docs/errors.html#mismatch


0
投票

我有 Chutzpah、Jasmine 等生成的测试页面,更新后得到了

Error: Error: Mismatched anonymous define() module: function (koExports, amdRequire) {

在 require.js 中找到了这个:

    define.amd = {
        jQuery: true
    };

然后在knockout.js中

(function(factory) {
    // Support three module loading scenarios
    if (typeof define === 'function' && define['amd']) {
        // [1] AMD anonymous module
        define(['exports', 'require'], factory);
    } else if (typeof exports === 'object' && typeof module === 'object') {
        // [2] CommonJS/Node.js
        factory(module['exports'] || exports);  // module.exports is for Node.js
    } else {
        // [3] No module loader (plain <script> tag) - put directly in global namespace
        factory(window['ko'] = {});
    }

这导致

    define = function (name, deps, callback) {
        var node, context;

        //Allow for anonymous modules
        if (typeof name !== 'string') { // receives Array
            //Adjust args appropriately
            callback = deps;
            deps = name;
            name = null; // <= error reason
        }
...
globalDefQueue.push([name, deps, callback]);
// name = null, deps(2) = ['exports', 'require'], callback = f (koExports, amdRequire)

然后在require.js中

    //Make sure any remaining defQueue items get properly processed.
    while (defQueue.length) {
        args = defQueue.shift();
        if (args[0] === null) {
            return onError(makeError('mismatch', 'Mismatched anonymous define() module: ' +
                args[args.length - 1]));

所以问题出在

[1] AMD anonymous module

delete define['amd']
define['amd']= {jQuery: true}
最终出现在
[3]
并且控制台中没有错误:-) require.js 和 knockout.js 都按此顺序位于 SCRIPT 标记中。

在我的情况下,如果块无用或生成提到的错误,这似乎是第一个。

© www.soinside.com 2019 - 2024. All rights reserved.