使用 browserify 时未定义 require 错误

Posted

技术标签:

【中文标题】使用 browserify 时未定义 require 错误【英文标题】:require is not defined error with browserify 【发布时间】:2015-04-26 02:50:14 【问题描述】:

我是 browserify 新手并尝试在浏览器中加载 npm 模块,但我收到以下错误:

Uncaught ReferenceError: require is not defined

我正在学习来自http://browserify.org/ 的教程。创建了包含以下内容的 javascript 文件:

var unique = require('uniq');

然后运行

npm install uniq

浏览 main.js -o bundle.js

生成了 bundle.js 文件,我将它包含在我的 html 中,但仍然出现上述错误。任何想法我做错了什么?

这是最终 HTML 文件的内容:

<!DOCTYPE html>
<html>
<head>
    <title></title>

    <script src="bundle.js"></script>
    <script src="script.js"></script>
</head>
<body>

</body>
</html>

这是 bundle.js 的内容:http://pastebin.com/1ECkBceB

这是 script.js:

var unique = require('uniq');

【问题讨论】:

你能发布更多的上下文代码吗? bundle.js 和 script.js 的内容是什么 @sma 刚刚用两个文件的内容更新了问题。 【参考方案1】:

简答:删除 script.js 导入

更长的答案: 您收到错误是因为方法 require 未在浏览器中定义。你不应该包含script.js

Browserify 背后的想法是,您可以使用 CommonJS 模块拆分源代码,并将它们捆绑到一个文件中以在浏览器中使用。 Browserify 将遍历您的所有源并将所有 required 文件连接到包中。

【讨论】:

【参考方案2】:

“require”函数仅在“bundle.js”脚本上下文中可用。 Browserify 将获取所有必要的脚本文件并将它们放入“bundle.js”文件中,因此您只需在 HTML 文件中包含“bundle.js”,而不是“script.js”文件。

【讨论】:

所以我不能要求为此目的捆绑在一起的模块..? 您可以在运行 browserify 之前在您编写的源代码中使用“require”。因此,在您的源 javascript 中,您可以要求任何您需要的模块,然后当您浏览源代码时,它会将所有源代码(包括您需要的模块)打包到您可以在 html 中引用的“bundle.js”文件中。希望有帮助! 我现在明白了——browserify 不会创建你可以从浏览器 require() 的模块——它会打包你的代码并将整个东西包装在一个闭包中——你需要特殊的步骤来创建一个库您可以从浏览器中使用。我会弄清楚这些步骤并将它们添加到这个答案中,因为很多人都会对 OP 和我自己产生同样的误解。【参考方案3】:

我个人更喜欢将我的库代码和应用程​​序代码分开。所以我也创建了bundle.jsscript.js 之类的东西。

有一个简单的解决方法,可以使这项工作。这是我的浏览器文件中的某个地方:

window.require = require;

这会将require 暴露到“全局”命名空间中。然后,您可以从您的script.js 获取您想要的所有内容。

不过,您确实放弃了一个优势:您必须在 browserify 文件中包含所有必需的库。那么,你不会得到它找到所有依赖项的奢侈!

我完全希望人们会喊“肮脏的黑客”或“这不是它的本意”。也许吧。但我希望这些文件分开。只要我不包含任何其他所谓的“要求”,我就可以了,非常感谢。

有时一个全局变量可以发挥重要作用。

【讨论】:

【参考方案4】:

似乎要运行这样的脚本,您必须在捆绑包上使用独立的。

browserify main.js --standalone Bundle > bundle.js

之后,您应该在bundle.js 中有window.Bundle。 因此,此时您应该可以从script.js 访问。

如果你正在使用 grunt

如果您使用的是grunt,请安装grunt-browserify

npm install grunt-browserify --save-dev

然后在grunt.js Gruntfile:

// Add the task
grunt.loadNpmTasks('grunt-browserify');

// Add the configuration:
browserify: 
    dist: 
        options: 
            // uncomment if you use babel
            // transform: [
            //     ["babelify",  "presets": ["env"] ]
            // ],
            browserifyOptions: 
                standalone: 'Bundle'
            
        ,
        files: 
           "bundle.js": ["main.js"]
        
    
,

如果你正在使用 gulp

 // on your build task
 var bundled = browserify('main.js',  standalone: 'Bundle' )
               .bundle()
               .pipe(source('bundle.js'))
               .pipe(gulp.dest(outDir));

有关 Chart.js gulp 文件,请参阅 here。

如果你正在使用 babel

如果您使用的是 babel 和 es6,那么您可能正在导出您的 Bundle 类。

// you should have something like that 

class Bundle 
    ...



export default Bundle;

所以因为 babel 现在要使用 Bundle 你应该使用 Bundle.default 等等:

// in script.js
var bundle = new Bundle.default();

要避免这种语法,您可以用Bundle.default 覆盖Bundle

在 bundle.js 末尾插入:

window.Bundle = window.Bundle.default;

所以现在你将拥有:

// in script.js
var bundle = new Bundle();

来源

Standalone browserify builds

【讨论】:

关于 Babel 和 Bundle.default().. 的结尾部分没有意义。 “所以现在你将拥有:” new Bundle.default() 这与你之前的几段没有什么不同。 tnx @joedotnot 修复。您扣除的覆盖的要点是拥有var bundle = new Bundle();

以上是关于使用 browserify 时未定义 require 错误的主要内容,如果未能解决你的问题,请参考以下文章

使用函数和 Firestore 时未定义字段值

Browserify 中的 require.context() 等效项

browserify 不打包某些文件或者把公共文件提取出来教程

browserify babel gulp 没有编译import的文件

在 Browserify 中将模块公开为全局变量

测试用 browserify 打包的模块?