bower init - difference between amd, es6, globals and node

Just for reference, this is precisely what bower specifies regarding the module types:

The type of module defined in the main JavaScript file. Can be one or an array of the following strings:

  • globals: JavaScript module that adds to global namespace, using window.namespace or this.namespace syntax
  • amd: JavaScript module compatible with AMD, like RequireJS, using define() syntax
  • node: JavaScript module compatible with node and CommonJS using module.exports syntax
  • es6: JavaScript module compatible with ECMAScript 6 modules, using export and import syntax
  • yui: JavaScript module compatible with YUI Modules, using YUI.add() syntax

Relevant link: https://github.com/bower/spec/blob/master/json.md#moduletype


If you don't know, it's quite likely globals is the right answer for you.

Either way, you need to understand:

  • what is and why AMD
  • what is a nodejs module
  • what is ecmascript 6 and especially es6 modules

[UPDATE]

This feature was introduced very recently in bower and is not documented at all yet (AFAIK). It essentially describes the moduleType, which states for what module technology the package is meant to be consumed (see above).

Right now, It doesn't have any effect apart from setting the moduleType property in the bower.json file of the package.

See https://github.com/bower/bower/pull/934 for the original pull-request.

[UPDATE #2]

A few additional points, to answer comments:

  • right now AFAIK there is no validation done on the moduleType property - which means that people are technically allowed to use whatever value they want for it, including angularjs if they feel inclined to do so
  • the bower committee seems to not be keen toward the inclusion of additional non-interoperable/proprietary moduleTypes (think composer, angular, etc) - which is easily understandable, but yet again, nothing really prevents people from using the moduleType value they want
  • an exception to the previous is the (somewhat) recent inclusion of the yui moduleType, so, there are "exceptions" to be made, assuming they are part of a concerted plan

What I would do if I were to author a package for a not-listed package manager and publish it on bower?

I would author an es6 module, and use / patch es6-transpiler to output the package format I need. Then I would either/and:

  • petition the bower guys to include my package technology as a choice (based on the fact it's supported by es6-transpiler as a target)
  • publish my package including both the es6 module version of it and the transpiled XXX version of it, and use es6 as a moduleType

Disclaimer: I don't have real-life experience authoring angularjs modules.


Initial

I'm using bower init for first time too.

The options should refer to the different ways to modularize some JavaScript code:

  • amd: using AMD define, like requirejs.
  • node: using Node.js require.
  • globals: using JavaScript module pattern to expose a global variable (like window.JQuery).
  • es6: using upcoming EcmaScript6 module feature.

In my case I wrote a Node.js module dflow but I'm using browserify to create a dist/dflow.js file that exports a global dflow var: so I selected globals.

Other Updates

The command I used to browserify dflow as a window global object was

browserify -s dflow -e index.js -o dist/dflow.js

I changed it cause I prefer to use require also inside the browser, so now I am using

browserify -r ./index.js:dflow -o dist/dflow.js

and so I changed the bower.moduleType to node in my bower.json file.

The main motivation was that if my module name has a dash, for example my project flow-view, I need to camelize the global name in flowView.

This new approach has two other benefits:

  1. Node and browser interface are the same. Using require on both client side and server side, let me write only once the code examples, and reuse them easily on both contexts.
  2. I use npm scripts and so, I can take advantage of ${npm_package_name} variable and write once the script I use to browserify.

This is another topic, but, it is really worth that you consider how it is useful the latter benefit: let me share the npm.scripts.browserify attribute I use in my package.json

"browserify": "browserify -r ./index.js:${npm_package_name} -o dist/${npm_package_name}.js"