<commit_before>
## API

 Modul8's API is in its basic form extremely simple, all we need to do is `add()` domains to `domains()`,
 an entry point for the first domain to modul8 itself, and the target JavaScript file to write

    var modul8 = require('modul8');
    var dir = __dirname;

    modul8('app.js')
      .domains()
        .add('app', dir+'/app/client/')
        .add('shared', dir+'/app/shared/')
      .compile('./out.js');


 You can add any number of domains to be scanned, but the first domain `add()`ed must be the location of the entry point ('app.js').
 Files on these domains can be `require()`d specifically with `require('domain::filename')`.
 Both the domain and file extension can be omitted if there are no conflicts (if there are the main domain will be scanned first).

 The following are equivalent from the file: 'helper.js' on the 'shared' domain.

    1. require('shared::validation.js') //3. => can remove extension
    2. require('./helpers.js') //relative require searches only this domain
    3. require('./helpers') //.js extension always gets searched before .coffee

 Additionally, `require('helpers')` will resolve to the same file if there are no helpers.js in the root of any other domains.
 More information on `require` is available in Readme.md

### Adding Libraries

 Not every JavaScript library is CommonJS compatible, and you also just want to keep exporting jQuery to window since it is so heavily intwined with
 your application code. Modul8 makes this easy by simply concatenating in the libraries you need first - in the order you specify.

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .libraries()
        .list(['jQuery.js','history.js'])
        .path(dir+'/app/client/libs/')
        .target('out-libs.js')
      .compile('./out.js');

 Libraries tend to update with a very different frequency to the main client code. Thus, it can be useful to separate these from your main application code.
 This can be done like the above example by calling `target()` on `libraries()`.

 Note that for huge libraries like jQuery, you may benefit (bandwidth wise) by using the [Google CDN](http://code.google.com/apis/libraries/devguide.html#jquery).
 In general, offsourcing static components to load from a CDN is a good first step to scale your website.
 There is also evidence to suggest that splitting up your files may help the browser finish loading your page faster (the browser can download scripts in parallel),
 just don't overdo it - HTTP requests are still expensive. Two or three JavaScript files for your site should be plenty using HTTP.

### Adding Data

 At some point during development it is natural to feel that this data should be available on the client as well. There are two fundamental ways of doing this with modul8.

 - Have an explicit file on a shared domain, exporting the objects you need
 - Export the object directly onto the data domain

 The first is good if you have static data like definitions, because they are perhaps useful to the server as well,
 but suppose you want to export more ephemeral data that the server has no need for, like templates or template versions.
 To export these to the server, you will have to obtain the data somehow - your job - and allow modul8 to pull it into the script.

 The data API simply consists of `add()`ing data keys and functions to `data()`

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .data()
        .add('versions', myVersionParser)
        .add('templates', myTemplateCompiler)
      .compile('./out.js');

 Under the covers, Modul8 attaches the output of the myX functions to an internal _data domain_ (so this domain is reserved).
 The end result is that you can require this data as if it were exported from a file (named versions|templates) on a domain named data.
 The second argument to add must be a function returning a string. Its result is attached verbatim to Modul8's require tree.

### Middleware

 Middleware come in two forms: pre-processing and post-processing.
 - Pre-processing is middleware that is applied before analysing dependencies as well as before compiling.
 - Post-processing is middleware that is only applied to the output right before it gets written.

 Modul8 comes bundled with one of each of these:

 - modul8.minifier - post-processing middleware that minifies using UglifyJS
 - modul8.testcutter - pre-processing middleware that cuts out the end of a file (after require.main is referenced) to avoid pulling in test dependencies.

 To use these they must be chained on `modul8()` via `before()` or `after()` depending on what type of middleware it is.

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .before(modul8.testcutter)
      .after(modul8.minifier)
      .compile('./out.js');

### Settings

 Below are the settings available:

   - `domloader` A function that safety wraps code with a DOMContentLoaded barrier
   - `namespace`  The namespace modul8 uses in your browser, defaulting to `M8`

 **You have to** set `domloader` if you do not use jQuery. If you are familiar with the DOM or any other library this should be fairly trivial.
 The default jQuery implementation is as follows:

     domloader_fn = function(code){
      return "jQuery(function(){"+code+"});"
    }
 You should never have to set namespace unless you go digging in the source and the M8 references offend you.

 Options can be set by chaining them on `modul8()` using the `set(option, value)` method. For example:

    modul8('app.js')
      .set('namespace', 'BOOM')
      .set('domloader', domloader_fn)
      .domains().add('app', dir+'/app/client/')
      .compile('./out.js');

### Code Analysis

 To dynamically resolve dependencies from a single entry point, modul8 does a recursive analysis of the `require()`d code.
 To avoid getting stuck in an infinite loop, modul8 enforces the **no circular dependencies rule**. Granted, this is possible
 with sufficient fiddling, but it brings one major disadvantages to the table:

 A circularly dependent set of modules are tightly coupled; they are really no longer a set of moudles, but more of a library.
 There are numerous sources talking about (why is tight coupling is bad)[www.google.com/search?q=tight+coupling+bad] so this
 will not be covered here. Ignore this warnig at your own risk (regardless of whether or not you end up using modul8).

 Additionally, the dependency diagram cannot be easily visualized as it has gone from being a tree, to a tree with cycles.<commit_msg>fix link markup<commit_after>
## API

 Modul8's API is in its basic form extremely simple, all we need to do is `add()` domains to `domains()`,
 an entry point for the first domain to modul8 itself, and the target JavaScript file to write

    var modul8 = require('modul8');
    var dir = __dirname;

    modul8('app.js')
      .domains()
        .add('app', dir+'/app/client/')
        .add('shared', dir+'/app/shared/')
      .compile('./out.js');


 You can add any number of domains to be scanned, but the first domain `add()`ed must be the location of the entry point ('app.js').
 Files on these domains can be `require()`d specifically with `require('domain::filename')`.
 Both the domain and file extension can be omitted if there are no conflicts (if there are the main domain will be scanned first).

 The following are equivalent from the file: 'helper.js' on the 'shared' domain.

    1. require('shared::validation.js') //3. => can remove extension
    2. require('./helpers.js') //relative require searches only this domain
    3. require('./helpers') //.js extension always gets searched before .coffee

 Additionally, `require('helpers')` will resolve to the same file if there are no helpers.js in the root of any other domains.
 More information on `require` is available in Readme.md

### Adding Libraries

 Not every JavaScript library is CommonJS compatible, and you also just want to keep exporting jQuery to window since it is so heavily intwined with
 your application code. Modul8 makes this easy by simply concatenating in the libraries you need first - in the order you specify.

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .libraries()
        .list(['jQuery.js','history.js'])
        .path(dir+'/app/client/libs/')
        .target('out-libs.js')
      .compile('./out.js');

 Libraries tend to update with a very different frequency to the main client code. Thus, it can be useful to separate these from your main application code.
 This can be done like the above example by calling `target()` on `libraries()`.

 Note that for huge libraries like jQuery, you may benefit (bandwidth wise) by using the [Google CDN](http://code.google.com/apis/libraries/devguide.html#jquery).
 In general, offsourcing static components to load from a CDN is a good first step to scale your website.
 There is also evidence to suggest that splitting up your files may help the browser finish loading your page faster (the browser can download scripts in parallel),
 just don't overdo it - HTTP requests are still expensive. Two or three JavaScript files for your site should be plenty using HTTP.

### Adding Data

 At some point during development it is natural to feel that this data should be available on the client as well. There are two fundamental ways of doing this with modul8.

 - Have an explicit file on a shared domain, exporting the objects you need
 - Export the object directly onto the data domain

 The first is good if you have static data like definitions, because they are perhaps useful to the server as well,
 but suppose you want to export more ephemeral data that the server has no need for, like templates or template versions.
 To export these to the server, you will have to obtain the data somehow - your job - and allow modul8 to pull it into the script.

 The data API simply consists of `add()`ing data keys and functions to `data()`

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .data()
        .add('versions', myVersionParser)
        .add('templates', myTemplateCompiler)
      .compile('./out.js');

 Under the covers, Modul8 attaches the output of the myX functions to an internal _data domain_ (so this domain is reserved).
 The end result is that you can require this data as if it were exported from a file (named versions|templates) on a domain named data.
 The second argument to add must be a function returning a string. Its result is attached verbatim to Modul8's require tree.

### Middleware

 Middleware come in two forms: pre-processing and post-processing.
 - Pre-processing is middleware that is applied before analysing dependencies as well as before compiling.
 - Post-processing is middleware that is only applied to the output right before it gets written.

 Modul8 comes bundled with one of each of these:

 - modul8.minifier - post-processing middleware that minifies using UglifyJS
 - modul8.testcutter - pre-processing middleware that cuts out the end of a file (after require.main is referenced) to avoid pulling in test dependencies.

 To use these they must be chained on `modul8()` via `before()` or `after()` depending on what type of middleware it is.

    modul8('app.js')
      .domains().add('app', dir+'/app/client/')
      .before(modul8.testcutter)
      .after(modul8.minifier)
      .compile('./out.js');

### Settings

 Below are the settings available:

   - `domloader` A function that safety wraps code with a DOMContentLoaded barrier
   - `namespace`  The namespace modul8 uses in your browser, defaulting to `M8`

 **You have to** set `domloader` if you do not use jQuery. If you are familiar with the DOM or any other library this should be fairly trivial.
 The default jQuery implementation is as follows:

     domloader_fn = function(code){
      return "jQuery(function(){"+code+"});"
    }
 You should never have to set namespace unless you go digging in the source and the M8 references offend you.

 Options can be set by chaining them on `modul8()` using the `set(option, value)` method. For example:

    modul8('app.js')
      .set('namespace', 'BOOM')
      .set('domloader', domloader_fn)
      .domains().add('app', dir+'/app/client/')
      .compile('./out.js');

### Code Analysis

 To dynamically resolve dependencies from a single entry point, modul8 does a recursive analysis of the `require()`d code.
 To avoid getting stuck in an infinite loop, modul8 enforces the **no circular dependencies rule**. Granted, this is possible
 with sufficient fiddling, but it brings one major disadvantages to the table:

 A circularly dependent set of modules are tightly coupled; they are really no longer a set of moudles, but more of a library.
 There are numerous sources talking about [why is tight coupling is bad](http://www.google.com/search?q=tight+coupling+bad) so this
 will not be covered here. Ignore this warnig at your own risk (regardless of whether or not you end up using modul8).

 Additionally, the dependency diagram cannot be easily visualized as it has gone from being a tree, to a tree with cycles.
{'fraction_non_alphanumeric': 0.08263017863930065, 'fraction_numerical': 0.0047130368681109844, 'mean_word_length': 3.7103472968134623, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 2, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3973910', 'n_tokens_mistral': 3467, 'n_tokens_neox': 3289, 'n_words': 1815}