Node Introduction
Intro
This is the first in a series of tutorials on Node.js.
The code for the whole series is available on GitHub at github.com/LearnByCheating/nodejs-tutorial.
There is a separate folder for each tutorial.
Node has two main components.
The first is a JavaScript engine to execute standard JavaScript code. Node uses the same engine that the Chrome and Edge web browsers use. It's called V8.
The second component consists of JavaScript libraries.
Web browsers have a large number of built-in APIs, collectively called Web APIs, that relate to the browser environment. The most commonly used built-in browser API is for using JavaScript to manipulate elements of a web page through the Document Object Model (DOM). But there are many others.
Node operates on the server or personal computer side. It does not have access to the Browser APIs. Instead it has a number of its own built-in libraries, including ones with APIs to interact with the computer's file system, and for hosting websites on the internet or other networks, and many other functions. These are Node's core modules.
These include Google's open sourced V8 engine, used in the Chromium-based Chrome and Edge browsers, and in Node.js.
There's also Mozilla's SpiderMonkey used in the Firefox browser.
And Apple's JavaScriptCore which is part of Webkit used in the Safari browser.
The runtime environment is the hardware and software environment in which a program or application is executed.
The code for the whole series is available on GitHub at github.com/LearnByCheating/nodejs-tutorial.
There is a separate folder for each tutorial.
Read it, watch it, do it, review it:
- There are both a written and accompanying video version of this tutorial. There are timestamps under the headings that align with the video version of the topic.
- Read it: For each topic heading, first read the topic.
- Watch it: Then watch the associated section of the video.
- Do it: Then follow the instructions to replicate the steps on your computer.
- The Node.js CheatSheet has a major category that aligns with this tutorial.
- Review it: When you are done with the whole tutorial, open the CheatSheet and review the Node category from this tutorial. Make sure you understand everything, and can refer back to the CheatSheet when you are working on your own projects in the future.
Definitions and concepts:
[0:00 Video timestamp]
What is Node.js
Node.js (aka Node) is environment for running JavaScript code on a server or personal computer instead of in a web browser. In the world of JavaScript, the release of Node.js in 2009 was a groundbreaking event. In the context of the web, this allows JavaScript to be used both on the client side in the browser environment, and on the server side in the Node environment.Node has two main components.
The first is a JavaScript engine to execute standard JavaScript code. Node uses the same engine that the Chrome and Edge web browsers use. It's called V8.
The second component consists of JavaScript libraries.
Web browsers have a large number of built-in APIs, collectively called Web APIs, that relate to the browser environment. The most commonly used built-in browser API is for using JavaScript to manipulate elements of a web page through the Document Object Model (DOM). But there are many others.
Node operates on the server or personal computer side. It does not have access to the Browser APIs. Instead it has a number of its own built-in libraries, including ones with APIs to interact with the computer's file system, and for hosting websites on the internet or other networks, and many other functions. These are Node's core modules.
Node Package Manager (npm)
Node also has a package manager called npm for incorporating 3rd party libraries or packages into your applications. These can be for a broad array of purposes, such as the Express web framework for hosting web servers, and the Sequelize and Mongoose packages for working with databases.JavaScript Engine
A JavaScript Engine is a computer program that parses JavaScript code, translates it into machine code, then executes it. The major ones are developed by the browser vendors.These include Google's open sourced V8 engine, used in the Chromium-based Chrome and Edge browsers, and in Node.js.
There's also Mozilla's SpiderMonkey used in the Firefox browser.
And Apple's JavaScriptCore which is part of Webkit used in the Safari browser.
Runtime Environment
Runtime is the period of time when a program is running. It begins when a program is opened (or is executed). And ends when the program is closed or finishes.The runtime environment is the hardware and software environment in which a program or application is executed.
JavaScript's runtime environment used to be the browser only. The browser's JavaScript runtime environment includes the JavaScript engine plus all the Web APIs that the JavaScript code can access.
Since 2009 we also have the Node environment. That includes the V8 JavaScript engine, and instead of the Web APIs it has the built-in Node modules plus 3rd party packages that can be installed in a project with npm.
Since 2009 we also have the Node environment. That includes the V8 JavaScript engine, and instead of the Web APIs it has the built-in Node modules plus 3rd party packages that can be installed in a project with npm.
Install or Update Node
Check if Node is installed
[3:07 Video timestamp]
Node does not come preinstalled. To see if your computer already has Node installed you can run:
node --version which returns the version number of Node if it's installed.
Or run:
which node which returns the location of the Node program on your computer, if it's installed.
Even if it is installed, it may be an outdated version that you want to update.
To install or update Node, go to the nodejs.org website. It will list the latest version available.
The LTS or Long Term Support version is recommended for most users.
Just follow the installation wizard. Go with the defaults unless you have a specific reason to use something else.
Node's package manager, npm, is automatically installed when you install Node.
New versions fix issues and may add features. They may also remove deprecated features.
When functionality is changed or removed, the changes are called breaking changes because the update may cause major or minor problems in apps designed to run on an older version. Breaking changes will be listed in the release notes.
If you have numerous Node projects, every time you update to a newer major version of Node (e.g., from 16 to 18) you will need to make sure all your projects still work as expected.
An alternative is to install a version manager such as NVM (Node Version Manager) that allows you to install multiple versions of Node. That way you can run older projects on older versions of Node.
We aren't covering NVM in this tutorial, but be aware that it is available.
Open your computer's command line interface program. On a Mac it will be the Terminal app.
Terminal opens a Unix shell program starting from your home directory.
You can use the Unix cd command to change directories into your Desktop folder (or any other location you prefer):
cd Desktop or if that doesn't work try cd ~/Desktop
Use the Unix mkdir command to make a directory called nodejs-tutorial to hold our practice files throughout this tutorial series. Node has its own similar command that we'll see shortly:
mkdir nodejs-tutorial
Then change directories into the new nodejs-tutorial directory:
cd nodejs-tutorial
To launch Node's REPL from the terminal just enter: node
let x = 7;
x + 5;
Prints: 12
Enter the following statements, one by one. An REPL performs its loop on one command or line of code at a time.
const fs = require('fs');
Now enter:
fs.mkdirSync('1-node');
Enter:
const data = "console.log('Hello from nodefile');";
Enter:
fs.writeFileSync('1-node/nodefile.js', data);
Now that you've created the directory and file, exit the Node shell by pressing Control+D
We just created a file named nodefile.js.
We can execute the code in the file by calling the node program and passing in the file path as the argument.
node 1-node/nodefile.js
By default, Node assumes an extension of .js if none is provided. So including .js in the filename is optional.
node 1-node/nodefile
The file contained a single statement that logs "Hello from nodefile" to the console, which you should see in the Terminal.
There is an npm package called nodemon that we can use to run Node programs with hot reloading.
Hot reloading means if you save changes to any of the JavaScript or JSON files in the project, it will relaunch the program automatically.
Let's install it globally on your computer. We'll cover npm packages in the next section.
npm install nodemon --global
If you get a permissions error, try running the command as the superuser by prepending sudo to the command:
sudo npm install nodemon --global
With that installed, you can start node projects using the nodemon command instead of node, like:
nodemon 1-node/nodefile
To exit nodemon press Control+C
In this section, we will cover importing and exporting modules.
In Node.js, each file is treated as a separate module.
There are two syntaxes for exporting/importing modules:
CommonJS and the ES6 Export and Import statements.
When Node was created in 2009, official JavaScript did not have any module constructs. Since Node is built around modules it needed to look elsewhere. There was an independent JavaScript project called CommonJS that addressed just this issue. Node adopted it as its standard for exporting and importing modules.
Open the nodejs-tutorial project in your text editor.
Create a new file in the 1-node folder called calculator.js. Populate it with:
The file contains a single object called calculator, with two methods:
Create another file in the 1-node folder called app.js and populate it with the below code:
Let's run the app.js file to see the result logged to the console.
If you are using Visual Studio Code you can open a Terminal window right in your text editor.
In VS Code, click the Terminal menu and select New Terminal.
You should now have a Terminal session open at the bottom of the screen.
At the prompt, enter node then the path to the file we want to execute:
node 1-node/app
The .js extension is assumed.
This should execute the app.js file, which imports the calculator module, calls the double and triple methods, passing in an argument of 10 on each of them, and logs the result to the console: 20 and 30.
That means instead of exporting a single function or object, we will export multiple functions, objects, or variables from the module.
Create another file named app2 populated with the below. Instead of importing one overall calculator module, we are using object destructuring, making each property into its own function. One for double. One for triple. We don't use the calculator namespace when calling them.
In the Terminal, enter:
node 1-node/app2
And it should log 20 and 30 to the console.
Official JavaScript (technically known as ECMAScript) added module export and import statements in 2015 with the release of ES6. But Node did not recognize those statements until LTS version 14 in 2020, so it's only relatively recently that export/import statements could be used.
Currently you can either use CommonJS or Export/Import statements.
There are also some popular transpiling programs like Babel that let you use the latest JavaScript syntax, then they transpile your JavaScript code into ES5 syntax. ES5 was released in 2009.
Let's repeat the calculator and app files using export and import statements.
To use export/import statements we need to indicate that the files are modules. One way to do that is to use mjs extensions on your files instead of js. M is for module.
Create two files called calculator.mjs and app.mjs.
Then populate them with the below JavaScript code that use the export and import statements.
In the Terminal, execute the app.mjs file by entering the below, including the .mjs extension:
node 1-node/app.mjs
And it should log 20 and 30 to the console.
export:
import:
Create two files named calculator2.msj and app2.mjs.
Populate them with the below:
In the Terminal, enter the below, including the .mjs extension:
node 1-node/app2.mjs
And it should log 20 and 30 to the console.
It is an object available anywhere in your JavaScript code.
It holds the JavaScript global objects (String, Number, Array, etc.) and all the Web APIs.
And you can assign your own properties directly to the window object.
And call it in your scripts:
Window is implied so you can leave it out:
Some Node modules are attached to the global object such as timers, console.logs the process module, the url module, and others.
Global scoped modules are loaded with the global object so there's no need to import them before using them.
For example, you can open the Node REPL and use globally scoped node modules, such as Console, without importing them first.
console.log('Console is a globally scoped node module');
The global object name is implied.
We could call console log on global explicitly, and it works:
global.console.log('Console is a globally scoped node module');
But it's not necessary.
You can assign variables to the global object:
greeting = "Hello";
greeting;
prints "Hello"
It is generally not advised to assign variables directly to the global object however.
And that wraps up this section on Node introduction.
Node does not come preinstalled. To see if your computer already has Node installed you can run:
node --version which returns the version number of Node if it's installed.
Or run:
which node which returns the location of the Node program on your computer, if it's installed.
Even if it is installed, it may be an outdated version that you want to update.
Installation
[3:35 Video timestamp]To install or update Node, go to the nodejs.org website. It will list the latest version available.
The LTS or Long Term Support version is recommended for most users.
Just follow the installation wizard. Go with the defaults unless you have a specific reason to use something else.
Node's package manager, npm, is automatically installed when you install Node.
Breaking Changes and NVM
When you install an updated version of Node directly from their website, the new version will be used by all your projects.New versions fix issues and may add features. They may also remove deprecated features.
When functionality is changed or removed, the changes are called breaking changes because the update may cause major or minor problems in apps designed to run on an older version. Breaking changes will be listed in the release notes.
If you have numerous Node projects, every time you update to a newer major version of Node (e.g., from 16 to 18) you will need to make sure all your projects still work as expected.
An alternative is to install a version manager such as NVM (Node Version Manager) that allows you to install multiple versions of Node. That way you can run older projects on older versions of Node.
We aren't covering NVM in this tutorial, but be aware that it is available.
Run Node
[5:22 Video timestamp]
Generally you will use Node to build a project containing multiple files.
A web server built using Node and the Express web framework package is an example of a Node project.
Generally you will use Node to build a project containing multiple files.
A web server built using Node and the Express web framework package is an example of a Node project.
Node REPL/Shell - Run Node in the terminal
Node comes with a shell program that lets you run JavaScript and use Node modules from the command line. The shell is called a Read Eval Print Loop program or REPL. When you type in a command and press the return key, the REPL will:- Read the command,
- Evaluate it (i.e., parse and execute the command or code),
- Then print a result back to the Terminal.
- It then returns a prompt waiting for the next command, thus making a full loop.
Create a nodejs-tutorial directory
Before we use it, let's make a directory to hold our Node files using the command line.Open your computer's command line interface program. On a Mac it will be the Terminal app.
Terminal opens a Unix shell program starting from your home directory.
You can use the Unix cd command to change directories into your Desktop folder (or any other location you prefer):
cd Desktop or if that doesn't work try cd ~/Desktop
Use the Unix mkdir command to make a directory called nodejs-tutorial to hold our practice files throughout this tutorial series. Node has its own similar command that we'll see shortly:
mkdir nodejs-tutorial
Then change directories into the new nodejs-tutorial directory:
cd nodejs-tutorial
Launch the Node REPL
As mentioned, the terminal opens to a Unix shell program. To launch a program, like Node, from the Unix shell, you just enter the name of the program.To launch Node's REPL from the terminal just enter: node
Execute JavaScript code from the command line
Now you are in the Node runtime environment. You can execute JavaScript right in the shell.let x = 7;
x + 5;
Prints: 12
Use Node modules in the REPL
You can also use the Node APIs to interact with the file system.Enter the following statements, one by one. An REPL performs its loop on one command or line of code at a time.
const fs = require('fs');
- Here we are importing Node's file system module. This statement does not return a value so when you enter it in the command line it will return
undefined
. The module code is now in memory and can be used until you exit the Node REPL session.
Now enter:
fs.mkdirSync('1-node');
- We will cover how the fs module works in a separate tutorial, but for now just note that we created a directory named 1-node inside our nodejs-tutorial project directory. This will hold the files we work with for the rest of this tutorial.
Enter:
const data = "console.log('Hello from nodefile');";
- This is a variable we will use in the next line.
Enter:
fs.writeFileSync('1-node/nodefile.js', data);
- This statement uses a file system module method to create a file named nodefile.js and populate it with the content from the data variable. That is a single line that logs "Hello from nodefile".
Now that you've created the directory and file, exit the Node shell by pressing Control+D
Run Node.js script from a file
Typically, you will run Node from files, not by typing it into the REPL program. To do that enter the node command and pass in the path to the file as the argument.We just created a file named nodefile.js.
We can execute the code in the file by calling the node program and passing in the file path as the argument.
node 1-node/nodefile.js
By default, Node assumes an extension of .js if none is provided. So including .js in the filename is optional.
node 1-node/nodefile
The file contained a single statement that logs "Hello from nodefile" to the console, which you should see in the Terminal.
Nodemon
[8:39 Video timestamp]There is an npm package called nodemon that we can use to run Node programs with hot reloading.
Hot reloading means if you save changes to any of the JavaScript or JSON files in the project, it will relaunch the program automatically.
Let's install it globally on your computer. We'll cover npm packages in the next section.
npm install nodemon --global
If you get a permissions error, try running the command as the superuser by prepending sudo to the command:
sudo npm install nodemon --global
With that installed, you can start node projects using the nodemon command instead of node, like:
nodemon 1-node/nodefile
To exit nodemon press Control+C
Node Modules
[9:32 Video timestamp]In this section, we will cover importing and exporting modules.
In Node.js, each file is treated as a separate module.
There are three main sources of modules:
- Built-in Node modules. These are installed when you install Node.js.
- Third Party packages available on the npmjs.com registry for installation. You can get 3rd party packages from other sources like GitHub as well.
- User created files for the project. Each file is treated as a module.
Import/Export modules
Except for global built-in modules, modules must be exported from their source files and imported before being used.There are two syntaxes for exporting/importing modules:
CommonJS and the ES6 Export and Import statements.
CommonJS Syntax:
[11:44 Video timestamp]When Node was created in 2009, official JavaScript did not have any module constructs. Since Node is built around modules it needed to look elsewhere. There was an independent JavaScript project called CommonJS that addressed just this issue. Node adopted it as its standard for exporting and importing modules.
CommonJS with a single construct:
Single Construct: Some modules consist of a single construct like an object, function or class:- Export the single construct at the bottom of the file using this format:
module.exports = main_construct;
- Import the module in files that use that construct using the require function and assign it to a variable for use in the file:
const moduleName = require('filename');
CommonJS example with a single construct:
Let's see this in action. We'll create and use a calculator module.Open the nodejs-tutorial project in your text editor.
Create a new file in the 1-node folder called calculator.js. Populate it with:
1-node/calculator.js
const calculator = {
double: (x) => x * 2,
triple: (x) => x * 3
};
module.exports = calculator;
The file contains a single object called calculator, with two methods:
- One called double that will double the number passed to it.
- The other called triple will triple the number passed to it.
Create another file in the 1-node folder called app.js and populate it with the below code:
1-node/app.js
const calculator = require('./calculator');
console.log(calculator.double(10));
console.log(calculator.triple(10));
- At the top we import the calculator module using the require function passing in the file path as the argument.
- You can use an absolute or a relative path. Here we are using the relative path
require('./calculator')
. - The path
./
just means it's in the current directory so you could leave that out:require('calculator')
. - Assign a variable name for the module. Calculator in this case.
- Then you can chain the double and triple methods to the calculator object, passing in a number argument. In app.js we are calling the calculator methods, passing in an argument of 10, then logging the result to the console.
Let's run the app.js file to see the result logged to the console.
If you are using Visual Studio Code you can open a Terminal window right in your text editor.
In VS Code, click the Terminal menu and select New Terminal.
You should now have a Terminal session open at the bottom of the screen.
At the prompt, enter node then the path to the file we want to execute:
node 1-node/app
The .js extension is assumed.
This should execute the app.js file, which imports the calculator module, calls the double and triple methods, passing in an argument of 10 on each of them, and logs the result to the console: 20 and 30.
CommonJS with multiple constructs:
Now let's export/import multiple constructs:That means instead of exporting a single function or object, we will export multiple functions, objects, or variables from the module.
- Export the constructs in an object at the bottom of the file:
module.exports = { construct1[, construct2, ...] };
- Import the module in any files that use it, with the require function. Use destructuring to get the constructs you want to use:
const { construct1[, construct2, ...] } = require('filename');
CommonJS example with multiple constructs:
Create another file called calculator2.js and populate it with the below. Instead of exporting one calculator object, we define separate double and triple functions and export them as a module object. Each function is a separate property.1-node/calculator2.js
const double = (x) => x * 2;
const triple = (x) => x * 3;
module.exports = { double, triple };
Create another file named app2 populated with the below. Instead of importing one overall calculator module, we are using object destructuring, making each property into its own function. One for double. One for triple. We don't use the calculator namespace when calling them.
1-node/app2.js
const { double, triple } = require('./calculator2');
console.log(double(10));
console.log(triple(10));
In the Terminal, enter:
node 1-node/app2
And it should log 20 and 30 to the console.
ES6 export/import statements:
[14:34 Video timestamp]Official JavaScript (technically known as ECMAScript) added module export and import statements in 2015 with the release of ES6. But Node did not recognize those statements until LTS version 14 in 2020, so it's only relatively recently that export/import statements could be used.
Currently you can either use CommonJS or Export/Import statements.
There are also some popular transpiling programs like Babel that let you use the latest JavaScript syntax, then they transpile your JavaScript code into ES5 syntax. ES5 was released in 2009.
ES6 export/import statements with a single construct:
Single Construct: For a module that contains a single construct like a single object or function:- Export the module: Export it at the bottom of the file with:
export default main_construct;
- Import the module: Then in any files that use that construct, import it, assigning it a variable name:
import moduleName = from 'filename';
Let's repeat the calculator and app files using export and import statements.
To use export/import statements we need to indicate that the files are modules. One way to do that is to use mjs extensions on your files instead of js. M is for module.
Create two files called calculator.mjs and app.mjs.
Then populate them with the below JavaScript code that use the export and import statements.
1-node/calculator.mjs
const calculator = {
double: (x) => x * 2,
triple: (x) => x * 3
};
export default calculator;
1-node/app.mjs
import calculator from './calculator.mjs';
console.log(calculator.double(10));
console.log(calculator.triple(10));
In the Terminal, execute the app.mjs file by entering the below, including the .mjs extension:
node 1-node/app.mjs
And it should log 20 and 30 to the console.
ES6 export/import statements with multiple constructs:
Use the below format:export:
export { construct1[, construct2, ...] };
import:
import { construct1[, construct2, ...] } from 'filename';
Create two files named calculator2.msj and app2.mjs.
Populate them with the below:
1-node/calculator2.mjs
const double = (x) => x * 2; const triple = (x) => x * 3; export { double, triple };
1-node/app2.mjs
import { double, triple } from './calculator2.mjs'; console.log(double(10)); // logs 20 console.log(triple(10)); // logs 30
In the Terminal, enter the below, including the .mjs extension:
node 1-node/app2.mjs
And it should log 20 and 30 to the console.
Global Object
[17:00 Video timestamp]
The last topic we will cover in this section is the global object.
The last topic we will cover in this section is the global object.
Global object in the browser is window
When you run JavaScript in the browser, the global object is window.It is an object available anywhere in your JavaScript code.
It holds the JavaScript global objects (String, Number, Array, etc.) and all the Web APIs.
And you can assign your own properties directly to the window object.
window.greeting = "Hello";
And call it in your scripts:
window.greeting;
// returns "Hello"Window is implied so you can leave it out:
greeting = "Hello";
Global object in Node.js is global
In Node.js the global object is called global.Some Node modules are attached to the global object such as timers, console.logs the process module, the url module, and others.
Global scoped modules are loaded with the global object so there's no need to import them before using them.
For example, you can open the Node REPL and use globally scoped node modules, such as Console, without importing them first.
console.log('Console is a globally scoped node module');
The global object name is implied.
We could call console log on global explicitly, and it works:
global.console.log('Console is a globally scoped node module');
But it's not necessary.
You can assign variables to the global object:
greeting = "Hello";
greeting;
prints "Hello"
It is generally not advised to assign variables directly to the global object however.
And that wraps up this section on Node introduction.