Register to get access to 15+ free programming courses with interactive exercises

Dependencies JS: Setting up environment

JavaScript, like any other language, contains many ready-made functions and modules that facilitate development. Together, they make up the standard language library. In Node.js, for example, there are modules for cryptography (encryption), HTTP, file systems, and more. In browsers, this set is much smaller, but still present.

// Example of a built-in function
Math.round(5.34); // 5

// Node.js built-in module for working with files
import fs from "fs";

// Reads the contents of the file
const data = fs.readFileSync("path/to/file");

No matter how good a standard library is, it cannot cover all the issues that arise during development. Of course, you can implement all the missing components yourself, but then the development of any project will turn into an endless marathon. There are too many typical tasks to solve in any non-trivial project.

Commercial projects use millions of lines of third-party code written by programmers around the world. Such code is stored in libraries, which you can plug into your project. In the JavaScript world, they are commonly referred to as packages.

What issues do such packages solve? All sorts. From small useful functions for working with strings or dates to frameworks and software systems that shape code architecture. For example, the lodash library is incredibly popular in JavaScript. It provides about a hundred useful functions that solve typical issues with arrays, strings, and other data types. A couple of examples:

// By convention, lodash is imported as _ character
import _ from "lodash";

// Array Intersection
_.intersection([2, 1], [2, 3]); // => [2]

// capitalize makes the first letter capital
_.capitalize("hello"); // Hello

Each of these functions individually may look small. However, the larger the project, the more such features are required, and all together they become quite a large codebase. And it would also be nice to have good documentation.

Note how code is imported from external libraries. In this case, the package name is specified without the ./ path. This way, JavaScript understands that it's a package you're looking for, and does not need to look for a file named lodash.js.

// This will search for the file lodash.js in the current directory
import _ from "./lodash";

// This is how the code from the package is imported
import _ from "lodash";


If you just import lodash вin the code and then run it, the program will crash with an error: "lodash not found". In order to use a third-party package, it must be added to the project as a dependency. There is an installation command in the npm for this purpose:

# Must be executed at the project root
# only then will lodash be in the right place
npm install lodash

This command performs three actions. First, it downloads a package into the node_modules directory at the root of the project. If this directory didn't exist before, it is automatically created. Then it adds an entry in package.json that the lodash package has become a dependency. Finally, it creates or updates the package-lock.json file.

tree -L 1
├── node_modules
├── package.json
├── package-lock.json
└── index.js

Dependencies are added to package.json under the dependencies key. All packages used in the project and not included in the standard library are listed here.

"dependencies": {
  "lodash": "^4.17.15"

The name of the package in the dependencies is specified as a key. This is the name used when importing the package. The value is the last available version at the time of download.

Now, when Node.js meets this kind of import:

import React from "react";

It makes an attempt to import a module from node_modules/react/...

All that's left is to deal with the package-lock.json file. Its purpose is rather complicated for beginners. So, here we won't go into detail, we'll just describe the general concept. The rest is better to learn in practice when working with real projects.

Briefly, the dependencies of our project have their own dependencies, and they, in turn, have their own dependencies (dependencies of dependencies are called transitive dependencies). Such a chain can be quite long, and the same packages can appear in different parts of it, but with different versions. package-lock.json contains a description of all the packages that will be installed, including all their dependencies and specific versions. This makes it possible to guarantee you have all the same versions of dependencies for all project developers. This file is created by the npm install command and then used when installing dependencies. If there is a package-lock.json in the project, it is recommended to install the dependencies with the command npm ci

# If we want exactly the same versions of all the packages
# that the other developers on this project had
npm ci

Linking to git

Programmers don't often do projects from scratch. More often than not, they work with ready-made projects. Projects, in turn, are stored in git repositories. What needs to be stored in the repository and what doesn't when we talk about dependencies?

The code of the dependencies themselves is not part of the source code. It's always added to .gitignore. But the package.json and package-lock.json files are part of the source code and it's through them that Node.js learns which packages to put on the system.

Imagine that you clone a finished project from GitHub to your computer and immediately try to run it. It'll fail and show an error because the code of the dependencies themselves in node_modules (as well as the directory itself) is missing. To make it appear there, you have to run the command to install the already added dependencies:

# Executed at the project root
# Installing all the required dependencies
npm ci

This command does not change anything in the project. It only downloads dependencies into the node_modules directory, based on the contents of package.json and versions from package-lock.json.


During the installation of the dependencies, npm displays many different messages. Among them are the following:

npm WARN deprecated minimatch@2.0.10: Please update to minimatch 3.0.2 or higher to avoid a RegExp DoS issue

Most of these messages do not affect the operation of the application. All they say is that some versions are out of date or the package is no longer in use.

Do it yourself

  1. Install the lodash in the hexlet-js project
  2. Add to the index.js file the import functions from the lodash package, as in the examples above
  3. Write console.log(_.last(['one', 'two'])); to the index.js file
  4. Run the code, make sure that "two" is the output
  5. Add the changes to GitHub. Make sure that node_modules is ignored
  6. Examine the structure of the node_modules directory
  7. Find the source code of the lodash package on GitHub and compare it with the contents of node_modules

Recommended materials

  1. Search packages here
  2. The difference between npm ci and npm install

Аватары экспертов Хекслета

Are there any more questions? Ask them in the Discussion section.

The Hexlet support team or other students will answer you.

For full access to the course you need a professional subscription.

A professional subscription will give you full access to all Hexlet courses, projects and lifetime access to the theory of lessons learned. You can cancel your subscription at any time.

Get access
hours of theory

Sign up

Programming courses for beginners and experienced developers. Start training for free

  • 130 courses, 2000+ hours of theory
  • 1000 practical tasks in a browser
  • 360 000 students
By sending the form, you agree to Personal Policy and Service Conditions

Our graduates work in companies:

<span class="translation_missing" title="translation missing:">Bookmate</span>
<span class="translation_missing" title="translation missing:">Healthsamurai</span>
<span class="translation_missing" title="translation missing:">Dualboot</span>
<span class="translation_missing" title="translation missing:">Abbyy</span>
Suggested learning programs

From zero to a developer. Refunds in case you won't get a job

Frontend Developer icon
Development of front-end components for web applications
start anytime 10 months

Use Hexlet to the fullest extent!

  • Ask questions about the lesson
  • Test your knowledge in quizzes
  • Practice in your browser
  • Track your progress

Sign up or sign in

By sending the form, you agree to Personal Policy and Service Conditions

Toto Image

Ask questions if you want to discuss a theory or an exercise. Hexlet Support Team and experienced community members can help find answers and solve a problem.