Головна / Статті / Що насправді робить npm install: реєстр, package.json та файли Lockfile

Що насправді робить npm install: реєстр, package.json та файли Lockfile

Практичний огляд npm: реєстр та CLI, як npm install завантажує пакети, що записується у file package.json та package-lock.json, та як публікувати пакети.

1605 слів

Майже кожний проект на JavaScript, незалежно від того, чи працює він на Node.js, React чи Next.js, починається з однакової команди, і багато розробників виконують її щодня, не розуміючи точно, що вона робить. Знання того, звідки беруться пакети, як npm вирішує, що інсталювати, та для чого саме призначені файли package.json, package-lock.json та node_modules, допомагає легше відловлювати проблеми під час інсталяції. Цей посібник охоплює кожен етап — від першої інсталяції до публікації власного пакету.

Команди, які вводить кожен

Найпоширенішим способом є інсталяція всього, що вже оголошено у проекті:

npm install

Не менш поширеним є додавання бібліотеки за назвою, наприклад веб-фреймворку Express:

npm install express

або HTTP-клієнта Axios:

npm install axios

За цими однорядковими командами криється кілька запитань. Звідки завантажується код? Як npm дізнається, від чого залежить проект? Для чого існує package.json? І чому папка node_modules стає такою великою?

Що таке npm

npm — це стандартний менеджер пакетів для Node.js, який постачається разом із ним. Він дає вам доступ до величезного каталогу повторно використовуваних пакетів, опублікованих іншими розробниками, що дозволяє використовувати перевірений код у вашому проекті замість того, щоб писати його самостійно.

Уявіть собі це як публічну бібліотеку коду. Припустимо, що бекенд на Node.js потребує HTTP-сервера. Замість того, щоб створювати маршрутизацію та проміжні компоненти з нуля, ви додаєте Express:

npm install express

Потрібно викликати інші API? Додайте HTTP-клієнта:

npm install axios

Перевірку надходящих даних за схемою здійснює Zod:

npm install zod

А bcrypt займається хешируванням паролів:

npm install bcrypt

Це найбільша перевага екосистеми: коли існує добре протестоване рішення, рідко буває причина писати власне. З іншого боку, кожен встановлений пакет — це код, якому ви довіряєте, тож краще використовувати підтримувані, широко поширені бібліотеки та тримати список мінімальним. Дізнайтеся як працюють атаки на ланцюг постачання npm, щоб зрозуміти, чому це важливо.

Екосистема, а не просто команда

Початківці часто сприймають npm як просто слово, введене в термінал. Насправді ця назва охоплює кілька взаємодіючих компонентів:

  • Реєстр npm: публічна служба, де пакети публікуються та завантажуються.
  • CLI npm: інструмент командного рядка, який взаємодіє з реєстром та керує залежностями.
  • Пакети: самі багаторазово використовувані одиниці коду.
  • package.json: маніфест, який описує ваш проект та залежності від нього.
  • Публічні пакети є безкоштовними: ви можете встановити будь-який публічний пакет без облікового запису. Ця низька бар’єрна стінка допомогла JavaScript з відкритим кодом поширитися по всьому світу. Обліковий запис потрібен лише для публікації.

    Що відбувається, коли ви запускаєте npm install

    Візьмемо проект, який додає Express:

    npm install express
    

    На високому рівні:

    1. npm шукає пакет у реєстрі та обирає версію, яка відповідає запитаному діапазону (найновішу, якщо жоден не вказаний).
    2. Він розв’язує залежності самого пакета та його залежностей, утворюючи повну ієрархію.
    3. Він завантажує все, що ще не зберігається в кеші, та розміщує його у node_modules.
  • Він фіксує залежності у package.json та точну структуру, яка була вирішена, у package-lock.json.
  • Саме так один короткий командний запит дозволяє отримати цілу структуру функціональностей.

    package.json: маніфест проекту

    У центрі кожного проекту Node.js знаходиться один файл:

    package.json
    

    Він виконує роль посвідчення особи та конфігурації проекту в одному, містячи назву, версію, опис, скрипти, залежності для роботи та розробки, а також дані автора. Мінімальний приклад вказує файл-вхід у main, один скрипт та одну залежність:

    {
      "name": "my-project",
      "version": "1.0.0",
      "description": "My Node.js application",
      "main": "index.js",
      "scripts": {
        "start": "node index.js"
      },
      "dependencies": {
        "express": "^5.1.0"
      }
    }
    

    name

    name ідентифікує проект чи пакет. Якщо ви його публікуєте, саме цей текст люди вводять для його встановлення, тому він має бути унікальним у реєстрі.

    "name": "my-project"
    

    version

    version містить поточну версію пакета.

    "version": "1.0.0"
    

    Це має найбільше значення під час публікації. npm використовує семантичне версіонування (MAJOR.MINOR.PATCH): кардинальні зміни підвищують номер мажорної версії, сумісні функції — номер мінорної, а виправлення — номер патч-версії.

    Опис

    description — це однорядковий огляд того, що робить проект, який відображається у результатах пошуку в реєстрі.

    "description": "My Node.js application"
    

    Скрипти

    scripts визначає іменовані скорочення для часто використовуваних команд. Тут start запускає основний файл:

    "scripts": {
      "start": "node index.js"
    }
    

    Без нього доводилося б вводити повну команду:

    node index.js
    

    З ним це робить те саме:

    npm start
    

    Ключова риса — це послідовність: кожен учасник та кожна робота CI виконують однакову іменовану команду. Власні назви, такі як build, виконуються за допомогою npm run build.

    Залежності: від чого залежить ваш проект

    Уявіть собі платформу для доставки їжі. Її бекенд може використовувати:

    • Express для API
    • Zod для перевірки даних
    • bcrypt для хеширування паролів
    • бібліотеку JSON Web Token для автентифікації
    • Mongoose для роботи з MongoDB

    Кожен з цих елементів є залежністю. Коли ви встановлюєте одну з них:

    npm install express
    

    npm додає запис до package.json:

    "dependencies": {
      "express": "^5.1.0"
    }
    

    Знак „^“ у ^5.1.0 позначає діапазон: приймаються всі наступні версії 5.x, але не 6.0.0. Цей запис повідомляє всім, хто читає проект, що для його роботи потрібен Express. Инструменти, необхідні лише під час розробки, такі як тест-запускачі, додаються до devDependencies за допомогою команди npm install --save-dev.

    Чому одна команда може працювати для цілої команди

    Припустимо, ви приєднуєтесь до команди та клонуєте її репозиторій. Ніхто не очікує, що ви вручну завантажите п’ятдесят бібліотек. Ви виконуєте:

    npm install
    

    npm читає вказані залежності та встановлює їх усі. Саме завдяки можливості відтворення робочого середовища на основі опису менеджери пакетів є незамінними.

    node_modules: де знаходиться встановлений код

    Після встановлення з’являється нова папка:

    node_modules/
    

    У ній знаходяться пакети, які ви запитали, а також усе, від чого вони залежать, через що ця папка стає великою. Типова структура:

    my-project/
    │
    ├── node_modules/
    ├── package.json
    ├── package-lock.json
    └── index.js
    

    Не керуйте node_modules у Git. Він є великим, може містити версії коду для конкретних платформ, і його завжди можна відтворити. Додайте його до .gitignore та керуйте цими файлами замість нього:

    package.json
    package-lock.json
    

    Інші користувачі можуть потім запустити:

    npm install
    

    та отримати ті самі залежності.

    package-lock.json: точний запис

    Поруч із основним файлом знаходиться ще один файл:

    package-lock.json
    

    Чому обидва? Коротка версія:

    • package.json вказує, що потрібно проекту, зазвичай у вигляді діапазонів.
    • package-lock.json фіксує саме те, що було встановлено: кожну версію пакета в усій структурі, а також хеші цілісності.

    npm ci у системах CI, який встановлює програми строго згідно з файлом lockfile.

    Команди npm, які варто знати

    Додати пакет:

    npm install express
    

    Встановити все, що оголошено у проекті:

    npm install
    

    Видалити пакет з node_modules та package.json:

    npm uninstall express
    

    Оновити пакети до найновіших версій, дозволених діапазонами (це не призведе до переходу на нову мажорну версію):

    npm update
    

    Виведіть версію npm:

    npm -v
    

    Виведіть версію Node.js:

    node -v
    

    Покажіть обліковий запис npm, під яким ви увійшли:

    npm whoami
    

    Ви також можете внести вклад у створення пакетів. Опублікуйте корисну бібліотеку, і інші зможуть встановити її як будь-яку іншу:

    npm install your-package
    

    Цей цикл підтримує життя відкритого коду: ви будуєте на роботі інших, створюєте власні рішення та ділитеся ними.

    Кроки публікації

    Вам потрібен обліковий запис npm. Увійдіть через термінал:

    npm login
    

    Підтвердіть, який обліковий запис є активним:

    npm whoami
    

    Перейдіть у проект:

    cd myproject
    

    Переконайтеся, що в ньому є дійсний маніфест із унікальним name та version:

    package.json
    

    Потім опублікуйте:

    npm publish
    

    Тепер цей пакет доступний усім. Два поради: спочатку виконайте npm pack --dry-run, щоб побачити, які файли будуть включені, та завжди збільшуйте version після кожного випуску, адже опублікована версія не може бути використана знову. Ознайомтесь із поточною документацією npm щодо вимог до безпеки облікових записів, таких як двофакторна автентифікація.

    Як усе взаємопов’язано

    Весь процес виглядає так:

    Developer
        ↓
    npm install
        ↓
    npm Registry
        ↓
    Package + Dependencies
        ↓
    node_modules
        ↓
    package.json
        ↓
    Your Application
    

    Ви виконуєте команду, CLI отримує пакети з реєстру, код потрапляє до node_modules, маніфест та файл lockfile фіксують це, а ваше застосунок імпортує його. Саме ця ланцюгова структура дозволяє розробникам ефективно використовувати, керувати, ділитися та публікувати код.

    Основні висновки

    NPM може здаватися набором команд терміналу, але як тільки ви зрозумієте, що відбувається за кожною з них:

    npm install
    

    Система стає простою для розуміння. JavaScript забезпечує мову, Node.js — середовище виконання, а npm — екосистему для обміну кодом. На практиці:

    • package.json описує наміри; package-lock.json фіксує факти. Зберігайте обидва файли.
    • Ніколи не зберігайте node_modules.
    • Діапазон кершнів дозволяє виконувати незначні та коригувальні оновлення, причому npm update залишається в межах цього діапазону.
    • Для автоматизованих встановлень використовуйте npm ci.
    • Додавайте залежності усвідомлено; кожна з них — це код, якому ви довіряєте.

    Тож наступного разу, коли ви будете писати:

    npm install
    

    пам’ятайте, що ви підключаєте свій проект до екосистеми, створеної розробниками з усього світу.

    Пов’язана література