Как npm хранит и обрабатывает ваши пакеты

Пакеты есть повсюду в экосистеме js. Каждый пакет зависит от других пакетов, и эти пакеты используют некоторые другие, и это продолжается и продолжается.

Зависимости определяются в определенном типе нотации, называемом семантическим управлением версиями. Теперь, чтобы справиться со всем этим беспорядком, приходит npm и создает дерево всех этих зависимостей. Таким образом, мы можем решить любой пакет.

Терминология

прежде чем мы начнем, мы должны познакомиться с несколькими терминологиями, чтобы действительно понять, что происходит под капотом

Узловые модули

Все эти зависимости находятся в папке модулей вашего узла. У каждого пакета здесь своя папка. Теперь размещение пакета всего на один уровень ниже позволяет вам получить к нему доступ извне, а также через пакеты вашего брата (пакеты также внутри папки node_modules)

Первичные и вторичные зависимости

Таким образом, все пакеты, установленные внутри папки node_modules, являются либо первичными, либо вторичными зависимостями.

Первичные зависимости - это те, которые находятся в package.json и должны использоваться в проекте.

Вторичные зависимости - это те, которые требуются для этих первичных зависимостей. Опять же, любые требуемые им зависимости также являются вторичными зависимостями для контекста проекта.

Плоское и вложенное разрешение

Таким образом, все эти пакеты либо устанавливаются плоскими, либо вложенными.

Плоские пакеты являются прямыми потомками node_modules. В то время как вложенные пакеты находятся внутри node_modules любого из этих пакетов Flat. Давайте посмотрим на диаграмму, чтобы лучше понять это

стили chalk и ansi - это плоские, тогда как supports-color вложены внутрь chalk.

Обработка первичных зависимостей

Итак, в основном мы хотим, чтобы пользователи разрешили импортировать любые основные пакеты, и единственный способ сделать это - сохранить их в единой форме.

Таким образом, каждый пакет, упомянутый в вашем package.json, устанавливается в плоском виде. Вот и все

Но подождите, а как насчет вторичных зависимостей?

Обработка вторичных зависимостей

Чтобы избежать каких-либо проблем, мы можем разместить вторичные зависимости вложенными, например, предположим, что пакет A зависит от X и Y, а пакет B зависит от X и Z. Мы устанавливаем X и Y внутри A, а X и Z внутри B.

Глубокие деревья и избыточность

Так что подход к установке этих пакетов рекурсивный.

Это приводит к длинным вложенным папкам node_modules → package → node_modules → package → node_modules…, которые мы называем этими глубокими деревьями.

Теперь посмотрите, что у нас есть избыточность, у нас есть две копии X, одна внутри A и одна внутри B

Теперь в крупных проектах эта избыточность может быстро увеличиваться.

Вот почему наш прекрасный npm сделал поворот и оптимизацию.

Оптимизация в npm

Не все плоские зависимости являются первичными. Да, возможно, вы думали, что первичный = плоский, а вторичный = вложенный. Так было до npm 2.

npm 3 пришлось разрушить эти простые отношения, разрешив установку вторичных пакетов без изменений. Мы делаем это, чтобы оптимизировать наше глубокое дерево и уменьшить избыточность. Допустим, у всех 7 основных пакетов есть какой-то пакет X в качестве зависимости, тогда, если мы установим его в плоском виде, а не во вложенном, у нас будет только 1 копия X вместо 7. если пакет был 12 КБ, мы просто сохранили 72 КБ !. Но учтите, это не всегда возможно

X здесь плоская, но не основная зависимость

Заключение

Подводя итог, получается, что все ваши первичные зависимости хранятся в плоском виде, и для оптимизации и уменьшения размера вашей папки node_modules мы стараемся устанавливать вторичные пакеты, когда это возможно.

Теперь вам может быть интересно, как он решает, какие вторичные пакеты устанавливать в обычном режиме. Что ж, это интересная история, вы можете прочитать об этом во второй части.

Если вам понравилась эта история, нажмите кнопку 👏 и поделитесь ею, чтобы помочь другим найти ее! Не стесняйтесь, чтобы оставить комментарий ниже.

Groww Engineering публикует технические материалы, новейшие технологии и лучшие способы решения общих проблем программирования. Вы можете подписаться, чтобы получать их здесь.