<commit_before>---
layout: page
title: Node.js notes
---

NPM
===
It is considered a good practice to specify an engines key with your current
version of Node.

By default, npm does not save installed dependencies to package.json, but you
should track your dependencies. For apps, another good idea is to keep track of
exact versions of your dependencies.

Organization
============
Only use lowercase filenames.

Clustering
==========
Deploying a non-clustered node app on a large server is a huge waste of
resources.

A fundamental idea is never to do CPU-intensive operations on the Node.js
instances that the clients talk to.

Invoking callbacks multiple times is a common source of bugs. Avoiding callback
hell (deeply nested callbacks) is also important to maintain code readability.

Anything that should happen after a callback has fired needs to be invoked from
within it.

Throwing errors from inside callbacks is usually a source of bugs. Encompassing
try-catch blocks may be out of scope when the callback is asynchronously
called.

The integer is a lie
====================
Numbers in JavaScript are floating points - **there is no integer data type**.

Free laugh:

    Math.pow(2, 53) + 1 === Math.pow(2, 53)  // evaluates to true.

Solution
--------
If you ever need to deal with large numbers, there are big integer libraries
that implement the important mathematical operations on large precision
numbers, such as `node-bigint`.

Using modules
=============
Node treats each file as an isolated module. A file can export its
functionality by adding properties to the `exports` object:

    exports.validate = ...

When this is done, anyone requiring this file will be given **an object** with
the property function `validate`.

What if we want to export this function directly, and not as the property of
some object? We can **overwrite** `exports` to do this, but we must not treat
it as a global variable then:

    module.exports = ... 

Notice that we are treating `exports` as a property of the module object. The
distinction here between `module.exports` and `exports` is very important, and
is often a cause of frustration among inexperienced developers.

Supervisor programs
===================
A supervisor program can orchestrate your Node.js application. It is a good
practice to fail fast: if an unexpected error occurs, do not try to handle it,
rather let your program crash and have the supervisor restart it.<commit_msg>Added some notes on Performance to Node.js<commit_after>---
layout: page
title: Node.js notes
---

NPM
===
It is considered a good practice to specify an engines key with your current
version of Node.

By default, npm does not save installed dependencies to package.json, but you
should track your dependencies. For apps, another good idea is to keep track of
exact versions of your dependencies.

Organization
============
Only use lowercase filenames.

Clustering
==========
Deploying a non-clustered node app on a large server is a huge waste of
resources.

A fundamental idea is never to do CPU-intensive operations on the Node.js
instances that the clients talk to.

Invoking callbacks multiple times is a common source of bugs. Avoiding callback
hell (deeply nested callbacks) is also important to maintain code readability.

Anything that should happen after a callback has fired needs to be invoked from
within it.

Throwing errors from inside callbacks is usually a source of bugs. Encompassing
try-catch blocks may be out of scope when the callback is asynchronously
called.

The integer is a lie
====================
Numbers in JavaScript are floating points - **there is no integer data type**.

Free laugh:

    Math.pow(2, 53) + 1 === Math.pow(2, 53)  // evaluates to true.

Solution
--------
If you ever need to deal with large numbers, there are big integer libraries
that implement the important mathematical operations on large precision
numbers, such as `node-bigint`.

Using modules
=============
Node treats each file as an isolated module. A file can export its
functionality by adding properties to the `exports` object:

    exports.validate = ...

When this is done, anyone requiring this file will be given **an object** with
the property function `validate`.

What if we want to export this function directly, and not as the property of
some object? We can **overwrite** `exports` to do this, but we must not treat
it as a global variable then:

    module.exports = ... 

Notice that we are treating `exports` as a property of the module object. The
distinction here between `module.exports` and `exports` is very important, and
is often a cause of frustration among inexperienced developers.

Supervisor programs
===================
A supervisor program can orchestrate your Node.js application. It is a good
practice to fail fast: if an unexpected error occurs, do not try to handle it,
rather let your program crash and have the supervisor restart it.

Performance
===========
Why is declaring a variable outside any function's scope in a browser slower
than in Node.js? Within a web browser, the variable's scope makes it global
and therefore binds it as a property of the huge `window` object. Therefore,
declaring this variable in a web browser requires resolving a property within
the heavily populated `window`.

In Node.js, however, declaring any variable outside of any function's scope
binds it only to the module's own scope which therefore makes it much easier
and faster to resolve.
{'fraction_non_alphanumeric': 0.07631915282088735, 'fraction_numerical': 0.0025561438743837866, 'mean_word_length': 4.282545805207329, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3359223', 'n_tokens_mistral': 1370, 'n_tokens_neox': 1292, 'n_words': 818}