【问题标题】:Exported object returns undefined导出的对象返回未定义
【发布时间】:2020-07-24 19:03:03
【问题描述】:

我的app.js 代码中有以下单例:

const TodoManager = (function () {
    const allTodos = [];

    return {
        addNewTodo: function (title, color) {
            allTodos.push(new Todo(title, color));
        },
    };
})();

我想将addNewTodo 函数导出到另一个.js 文件,所以我将它附加到app.js 的末尾:

module.exports = TodoManager

然后,在我的dom.js 文件(我想使用addNewTodo 函数的文件)上,我将其导入:

import TodoManager from './app.js';

但是,每次我尝试访问它的任何对象时,它都会返回 undefined。我做错了什么愚蠢的错误吗?

(我使用 Parcel.js 作为打包器)

【问题讨论】:

  • 每次我尝试访问它的任何对象时你能说明你是如何尝试访问它们的吗?
  • @CertainPerformance 是的!所以,在我的dom.js 文件中,如果我附上console.log(TodoManager.addNewTodo()),例如,它指出.addNewTodo() 不是一个函数
  • 你可能有一个循环依赖,导致TodoManager没有在你期望的时候被定义
  • @CertainPerformance mmm 很有趣,所以也许我应该使用异步,对吧?你能告诉我它是怎么做的吗?
  • 不,使用异步函数不能解决问题。很难说不看完整代码,看看循环依赖在哪里

标签: javascript parceljs


【解决方案1】:

你有:

// app.js
require("./dom.js");

const TodoManager = (function () {
  // ...

你也有

// dom.js
import TodoManager from './app.js';

const MenuBar = (function(){
  // ...

这是一个循环依赖。当其中一个文件运行时,它发现需要导入另一个文件,因此控制流切换到另一个。然后,另一个看到它需要导入第一个文件。但是第一个文件已经在创建过程中,所以它不会切换回来。解释器知道您有一个潜在的问题,但它不会抛出错误,它会尝试通过最初将原始文件的导出设置为空对象来尽可能地运行脚本。但这会导致错误。

但是,在您的代码中,app.js 实际上并没有对require("./dom.js"); 做任何事情——app.js 没有必要依赖于dom.js。所以,你真正需要做的就是从app.js 中删除require("./dom.js");

【讨论】:

  • 你就是那个男人!非常感谢,现在我将继续了解有关循环依赖的更多信息。只是一个简单的问题,因为我删除了require("./dom.js"),所以我必须在我的index.html 中添加一个新的<script> 指代dom.js。你知道 Parcel.js 和 Webpack 等打包工具会接受吗?到目前为止,我在捆绑器中看到的所有示例都是只有一个 .js 文件入口点
  • 通常,如果你有一个循环依赖,正确的做法是弄清楚如何构造代码来移除它。有时会有一些黑客可以让你把它留在里面(不管你使用什么捆绑器),但它们是一种代码味道。
猜你喜欢
  • 2017-07-11
  • 1970-01-01
  • 2016-01-30
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多