javascript - 打包具有依赖项的浏览器/服务器 CommonJS 模块

标签 javascript node.js module browserify commonjs

假设我正在用 JavaScript 编写一个模块,它可以在浏览器和服务器(使用 Node)上使用。让我们称之为模块。假设 Module 将受益于另一个名为 Dependancy 的模块中的方法。这两个模块都被编写为供浏览器和服务器使用,就像 CommonJS 风格:

module.js

if (typeof module !== 'undefined' && module.exports)
  module.exports = Module; /* server */
else
  this.Module = Module; /* browser */

dependancy.js

if (typeof module !== 'undefined' && module.exports)
  module.exports = Dependancy; /* server */
else
  this.Dependancy = Dependancy; /* browser */

显然,Dependancy 可以直接在浏览器中使用。但是如果 Module 包含一个 var dependancy = require('dependency');指令,“维护”模块变得更加麻烦。

我知道我可以对 Module 中的Dependancy 进行全局检查,如下所示:

var dependancy = this.Dependancy || require('dependancy');

但这意味着我的模块有两个额外的浏览器安装要求:

  • 用户必须将 dependency.js 文件包含在 <script> 中在他们的文档中
  • 并且用户必须确保在 module.js
  • 之前加载此脚本

添加这两个要求引发了像 CommonJS 这样易于使用的模块化框架的想法。

我的另一个选择是在我的 Module 包中包含第二个编译脚本,其中包含 dependency.js使用 browserify 捆绑.然后我指示在浏览器中使用脚本的用户包含此脚本,而服务器端用户使用 package.json 中概述的未捆绑的入口脚本。 .这比第一种方式更可取,但它需要一个预编译过程,我每次更改库时都必须运行这个过程(例如,在上传到 GitHub 之前)。

还有什么我没有想到的其他方法吗?

最佳答案

当前给出的两个答案都非常有用,并且帮助我得出了当前的解决方案。但是,根据我的评论,它们并不能完全满足我对可移植性和易用性的特殊要求(对于客户和模块维护者)。

我最后发现的是 browserify 中的一个特定标志。可以捆绑模块并将它们公开为全局变量并在 RequireJS 中使用(如果需要)的命令行界面。 Browserify(和其他人)称之为通用模块定义(UMD)。关于那个的更多信息here .

通过在 browserify 命令中传递 --standalone 标志,我可以轻松地为 UMD 设置我的模块。

所以...

这是模块package.js:

{
  "name": "module",
  "version": "0.0.1",
  "description": "My module that requires another module (dependancy)",
  "main": "index.js",
  "scripts": {
    "bundle": "browserify --standalone module index.js > module.js"
  },
  "author": "shennan",
  "devDependencies": {
    "dependancy": "*",
    "browserify": "*"
  }
}

因此,当处于我的模块的根目录时,我可以在命令行中运行它:

$ npm run-script bundle

它将依赖项捆绑到一个文件中,并按照 UMD 方法公开它们。这意味着我可以通过三种不同的方式引导模块:

NodeJS

var Module = require('module');
/* use Module */

浏览器 Vanilla

<script src="module.js"></script>
<script>
  var Module = module;
  /* use Module */
</script>

带有 RequireJS 的浏览器

<script src="require.js"></script>
<script>
  requirejs(['module.js'], function (Module) {
    /* use Module */
  });
</script>

再次感谢大家的意见。所有答案都是有效的,我鼓励大家尝试所有答案,因为不同的用例需要不同的解决方案。

关于javascript - 打包具有依赖项的浏览器/服务器 CommonJS 模块,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36454785/

相关文章:

module - OCaml 模块和性能

javascript - 无法更改从 localStorage 检索的对象的属性

javascript - GTM数据层如何推送到GTM门户?

android - Cordova 在设置 Android 项目时找不到 Android 19 SDK

javascript - REST API 与 Postgresql - 如何制作最简单的前端界面

php - 找不到 Prestashop 1.7 模块目录数据

ruby-on-rails-3 - 如何使用 Ruby on Rails 3 创建和使用模块?

javascript - 使用 Node 和 AngularJS 验证用户身份的最佳方法是什么?

javascript - Facebook js sdk iPhone登录

javascript - 设置cookie并重定向,不带express