NodeJS modularizaton & strict mode
Tags: node, javascript, webdev
Published: 2020-12-25 17:50:20

Maybe you know a lot about the `strict mode` in Javascript/ ECMAscript. It is quite a useful stuff and it is strongly recommended to use always to throw error during the development and avoid confusing bugs.

You can read more about strict mode here on the official [Docs](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Strict_mode).

## Strict mode in NodeJs

Maybe when you start developing a NodeJS project or a simple application, it comes to your mind: do I have to put the `"use strict";` boilerplate onto the first line of every *.js* file in my project?

> Depends on your configuration, you have to and also you do not have to.

Keep reading, I will explain this in details.

### Default mode in Node JS

The default NodeJS set up, when you initialize your project first for example with the `npm init` command **does not use strict mode**.

> NodeJS uses [CommonJS](https://nodejs.org/api/modules.html#modules_modules_commonjs_modules) modularization by default.

So if you hang up with this configuration, you end up **not using strict mode** in any of your files.

#### Non strict mode example

For clarity, let me show you some code snippets.

I have an *app.js* file containing the following setup (I import the modules this way to emphasize the different modes)

```
const nonStrictMode = require('./modules/non-strict');
nonStrictMode.preventExtension();
```
And the following *non-strict.js*

```
module.exports = {
    preventExtension: () => {
        console.log('Non strict mode.');
        const fixed = {};
        Object.preventExtensions(fixed);
        fixed.newProperty = 'newProp';
        console.log(fixed.newProperty);
        console.log('Non strict mode finished.');
    }
};
``` 
That is a full valid JavaScript syntax in non strict mode. Although it will not work as the way you expect, you will not get a *compile* time error, and you will be confused maybe.

The console output will be the following:
```
Non strict mode.
*undefined*
Non strict mode finished.
```
Hmm, maybe that is not what you want to achieve. So it would be better if an error will be thrown to inform you about this 'problem'.

> Strict mode for the rescue.

#### Strict mode example

So I have the following configuration in my *app.js* file:

```
const strictMode = require('./modules/strict');
strictMode.preventExtension();
```
And the following code in my *strict.js*:

```
'use strict';

module.exports = {
    preventExtension: () => {
        console.log('Strict mode on.');
        const fixed = {};
        Object.preventExtensions(fixed);
        fixed.newProperty = 'newProp';
        console.log('Strict mode finished.');
    }
};
```

The output will be a nice:
```
Strict mode on.
TypeError: Cannot add property newProperty, object is not extensible.
```

> Wait, wait, is it not possible to add properties to a freezed object?

No it is not, and it is far more better to get a *compile* time error than avoiding this error at all.

As you can see, I used the **'use strict';** at the top of this *.js* file. So maybe you had better to use this configuration as well.

## Modules on ECMAScript

The modularization was announced in the 6th edition of [ECMAScript](https://en.wikipedia.org/wiki/ECMAScript#6th_Edition_%E2%80%93_ECMAScript_2015) (released on 2015), known as ES6.

It is such a big help for complex applications.

> ECMAScript modules uses strict mode by default.

It comes in handy if you want to omit all the boilerplate from the first line of files and enforce some coding restrictions with the *strict* mode.

### Enforcing modularization for NodeJS


If you are initialize a project with the *npm init*, a *package.json* file will be added to your root directory.

In this *package.json* will have to look like something like this:

```
{
  "name": "js",
  "version": "1.0.0",
  "description": "Strict mode compare",
  "main": "app.js",
  "type": "module",
  "author": "You",
  "license": "MIT"
}
```

Note the `'type': 'module'` property. 

> With this property, you can enforce your NodeJS app to use the modularization described in the ECMAScript 6 rules.

#### Modularized example

My *app.js* and the *modularized.js* look like the following:
```
import {modularizedPreventExtension} from 'modularized.js';
modularizedPreventExtension();
```

```
function modularizedPreventExtension() {
    console.log('Modularized mode on.');
    const fixed = {};
    Object.preventExtensions(fixed);
    fixed.newProperty = 'newProp';
    console.log('Modularized mode finished.');
}

export {modularizedPreventExtension};
```

End as you expect, the output will be:

```
Modularized mode on.
TypeError: Cannot add property newProperty, object is not extensible
```


## Additional information

So you are wondering maybe how the app knows whether to use or not to use this type of modularization. It is totally based on your **closest** *package.json*.

I truly recommend not to mix this types, just simply use the modularization provided y ES6.


Hope you enjoyed my article, please add your reviews in the comments below! :) 

References:
[CommonJS modules](https://nodejs.org/api/modules.html#modules_modules_commonjs_modules)
[ECMAScript modules](https://nodejs.org/api/esm.html#esm_modules_ecmascript_modules)