Разработка и использование мобильных приложений
Npm (node package manager) — это менеджер пакетов Node.js. В первой части этого материала мы уже упоминали о том, что сейчас в npm имеется более полумиллиона пакетов, что делает его самым большим в мире репозиторием кода, написанного на одном языке. Это позволяет говорить о том, что в npm можно найти пакеты, предназначенные для решения практически любых задач.
Изначально npm создавался как система управления пакетами для Node.js, но в наши дни он используется и при разработке фронтенд-проектов на JavaScript. Для взаимодействия с реестром npm используется одноимённая команда, которая даёт разработчику огромное количество возможностей.
▍Загрузка пакетов
С помощью команды npm можно загружать пакеты из реестра. Ниже мы рассмотрим примеры её использования.
▍Установка всех зависимостей проекта
Если в проекте имеется файл package.json , то установить все зависимости этого проекта можно такой командой:
npm install
Эта команда загрузит всё, что нужно проекту, и поместит эти материалы в папку node_modules , создав её в том случае, если она не существует в директории проекта.
▍Установка отдельного пакета
Отдельный можно установить следующей командой:
npm install
Часто можно видеть, как эту команду используют не в таком вот простом виде, а с некоторыми флагами. Рассмотрим их:
- Флаг —save позволяет установить пакет и добавить запись о нём в раздел dependencies файла package.json , который описывает зависимости проекта. Эти зависимости используются проектом для реализации его основного функционала, они устанавливаются в ходе его развёртывания на сервере (после выхода npm 5 записи об устанавливаемых пакетах в разделе зависимостей делаются автоматически, и без использования этого флага).
- Флаг —save-dev позволяет установить пакет и добавить запись о нём в раздел, содержащий перечень зависимостей разработки (то есть — пакетов, которые нужны в ходе разработки проекта, вроде библиотек для тестирования, но не требуются для его работы) файла package.json , который называется devDependencies .
▍Обновление пакетов
Для обновления пакетов служит следующая команда:
npm update
Получив эту команду, npm проверит все пакеты на наличие их новых версий, и, если найдёт их новые версии, соответствующие ограничениям на версии пакетов, заданным в package.json , установит их.
Обновить можно и отдельный пакет:
npm update
▍Загрузка пакетов определённых версий
В дополнение к стандартной загрузке пакетов, npm поддерживает и загрузку их определённых версий. В частности, можно заметить, что некоторые библиотеки совместимы лишь с некими крупными релизами других библиотек, то есть, если бы зависимости таких библиотек устанавливались бы без учёта версий, это могло бы нарушить их работу. Возможность установить определённую версию некоего пакета полезна и в ситуациях, когда, например, вам вполне подходит самый свежий релиз этого пакета, но оказывается, что в нём имеется ошибка. Ожидая выхода исправленной версии пакета, можно воспользоваться и его более старым но стабильным релизом.
Возможность задавать конкретные версии необходимых проекту библиотек полезна в командной разработке, когда все члены команды пользуются в точности одними и теми же библиотеками. Переход на их новые версии так же осуществляется централизованно, путём внесения изменений в файл проекта package.json .
Во всех этих случаях возможность указания версий пакетов, необходимых проекту, чрезвычайно полезна. Npm следует стандарту семантического версионирования (semver).
▍Запуск скриптов
Файл package.json поддерживает возможность описания команд (скриптов), запускать которые можно с помощью такой конструкции:
Например, вот как выглядят перечень скриптов, имеющийся в соответствующем разделе файла:
Весьма распространено использование этой возможности для запуска Webpack:
Такой подход даёт возможность заменить ввод длинных команд, чреватый ошибками, следующими простыми конструкциями:
$ npm watch $ npm dev $ npm prod
▍Куда npm устанавливает пакеты?
При установке пакетов с использованием npm (или yarn) доступны два варианта установки: локальная и глобальная.
По умолчанию, когда для установки пакета используют команду наподобие npm install lodash , пакет оказывается в папке node_modules , расположенной в папке проекта. Кроме того, если была выполнена вышеописанная команда, npm также добавит запись о библиотеке lodash в раздел dependencies файла package.json , который имеется в текущей директории.
Глобальная установка пакетов выполняется с использованием флага -g :
npm install -g lodash
Выполняя такую команду, npm не устанавливает пакет в локальную папку проекта. Вместо этого он копирует файлы пакета в некое глобальное расположение. Куда именно попадают эти файлы?
Для того чтобы это узнать, воспользуйтесь следующей командой:
npm root -g
В macOS или Linux файлы пакетов могут оказаться в директории /usr/local/lib/node_modules . В Windows это может быть нечто вроде C:\Users\YOU\AppData\Roaming\npm\node_modules .
Однако если вы используете для управления версиями Node.js nvm, путь к папке с глобальными пакетами может измениться.
Я, например, использую nvm, и вышеописанная команда сообщает мне о том, что глобальные пакеты устанавливаются по такому адресу: /Users/flavio/.nvm/versions/node/v8.9.0/lib/node_modules .
▍Использование и выполнение пакетов, установленных с помощью npm
Как использовать модули, установленные с помощью npm, локально или глобально, попадающие в папки node_modules ? Предположим, вы установили популярную библиотеку lodash , содержащую множество вспомогательных функций, используемых в JavaScript-разработке:
npm install lodash
Такая команда установит библиотеку в локальную папку проекта node_modules .
Для того чтобы использовать её в своём коде, достаточно импортировать её с применением команды require :
const _ = require('lodash')
Как быть, если пакет представляет собой исполняемый файл?
В таком случае исполняемый файл попадёт в папку node_modules/.bin/ folder .
Посмотреть на то, как выглядит работа этого механизма можно, установив пакет cowsay. Он представляет собой шуточную программу, написанную для командной строки. Если передать этому пакету какой-нибудь текст, в консоли, в стиле ASCII-арта, будет выведено изображение коровы, которая «произносит» соответствующий текст. «Озвучивать» текст могут и другие существа.
Итак, после установки пакета с использованием команды npm install cowsay , он, вместе со своими зависимостями, попадёт в node_modules . А в скрытую папку .bin будут записаны символические ссылки на бинарные файлы cowsay.
Как их выполнять?
Конечно, можно, для вызова программы, ввести в терминале нечто вроде ./node_modules/.bin/cowsay , это рабочий подход, но гораздо лучше воспользоваться npx, средством для запуска исполняемых файлов npm-пакетов, включаемым в npm начиная с версии 5.2. А именно, в нашем случае понадобится такая команда:
npx cowsay
Путь к пакету npx найдёт автоматически.
Файл package.json
Файл package.json является важнейшим элементов множества проектов, основанных на экосистеме Node.js. Если вы программировали на JavaScript, была ли это серверная или клиентская разработка, то вы, наверняка, уже встречались с этим файлом. Зачем он нужен? Что вам следует о нём знать и какие возможности он вам даёт?
Package.json представляет собой нечто вроде файла-манифеста для проекта. Он даёт в распоряжение разработчика множество разноплановых возможностей. Например, он представляет собой центральный репозиторий настроек для инструментальных средств, используемых в проекте. Кроме того, он является тем местом, куда npm и yarn записывают сведения об именах и версиях установленных пакетов.
▍Структура файла
Вот пример простейшего файла package.json :
Как видите, он пуст. Нет жёстких требований, касающихся того, что должно присутствовать в подобном файле для некоего приложения. Единственное требование к структуре файла заключается в том, что она должна следовать правилам формата JSON. В противном случае этот файл не сможет быть прочитан программами, которые попытаются получить доступ к его содержимому.
Если вы создаёте Node.js-пакет, который собираетесь распространять через npm, то всё радикальным образом меняется, и в вашем package.json должен быть набор свойств, которые помогут другим людям пользоваться пакетом. Подробнее мы поговорим об этом позже.
Вот ещё один пример package.json :
В нём задано свойство name , значением которого является имя приложения или пакета, материалы которого содержатся в той же папке, где находится этот файл.
Вот пример посложнее, который я взял из приложения-примера, написанного с использованием Vue.js:
< "name": "test-project", "version": "1.0.0", "description": "A Vue.js project", "main": "src/main.js", "private": true, "scripts": < "dev": "webpack-dev-server --inline --progress --config build/webpack.dev.conf.js", "start": "npm run dev", "unit": "jest --config test/unit/jest.conf.js --coverage", "test": "npm run unit", "lint": "eslint --ext .js,.vue src test/unit", "build": "node build/build.js" >, "dependencies": < "vue": "^2.5.2" >, "devDependencies": < "autoprefixer": "^7.1.2", "babel-core": "^6.22.1", "babel-eslint": "^8.2.1", "babel-helper-vue-jsx-merge-props": "^2.0.3", "babel-jest": "^21.0.2", "babel-loader": "^7.1.1", "babel-plugin-dynamic-import-node": "^1.2.0", "babel-plugin-syntax-jsx": "^6.18.0", "babel-plugin-transform-es2015-modules-commonjs": "^6.26.0", "babel-plugin-transform-runtime": "^6.22.0", "babel-plugin-transform-vue-jsx": "^3.5.0", "babel-preset-env": "^1.3.2", "babel-preset-stage-2": "^6.22.0", "chalk": "^2.0.1", "copy-webpack-plugin": "^4.0.1", "css-loader": "^0.28.0", "eslint": "^4.15.0", "eslint-config-airbnb-base": "^11.3.0", "eslint-friendly-formatter": "^3.0.0", "eslint-import-resolver-webpack": "^0.8.3", "eslint-loader": "^1.7.1", "eslint-plugin-import": "^2.7.0", "eslint-plugin-vue": "^4.0.0", "extract-text-webpack-plugin": "^3.0.0", "file-loader": "^1.1.4", "friendly-errors-webpack-plugin": "^1.6.1", "html-webpack-plugin": "^2.30.1", "jest": "^22.0.4", "jest-serializer-vue": "^0.3.0", "node-notifier": "^5.1.2", "optimize-css-assets-webpack-plugin": "^3.2.0", "ora": "^1.2.0", "portfinder": "^1.0.13", "postcss-import": "^11.0.0", "postcss-loader": "^2.0.8", "postcss-url": "^7.2.1", "rimraf": "^2.6.0", "semver": "^5.3.0", "shelljs": "^0.7.6", "uglifyjs-webpack-plugin": "^1.1.1", "url-loader": "^0.5.8", "vue-jest": "^1.0.2", "vue-loader": "^13.3.0", "vue-style-loader": "^3.0.1", "vue-template-compiler": "^2.5.2", "webpack": "^3.6.0", "webpack-bundle-analyzer": "^2.9.0", "webpack-dev-server": "^2.9.1", "webpack-merge": "^4.1.0" >, "engines": < "node": ">= 6.0.0", "npm": ">= 3.0.0" >, "browserslist": [ "> 1%", "last 2 versions", "not ie
Как видите, тут прямо-таки немеряно всего интересного. А именно, здесь можно выделить следующие свойства:
- name — задаёт имя приложения (пакета).
- version — содержит сведения о текущей версии приложения.
- description — краткое описание приложения.
- main — задаёт точку входа в приложение.
- private — если данное свойство установлено в true , это позволяет предотвратить случайную публикацию пакета в npm.
- scripts — задаёт набор Node.js-скриптов, которые можно запускать.
- dependencies — содержит список npm-пакетов, от которых зависит приложение.
- devDependencies — содержит список npm-пакетов, используемых при разработке проекта, но не при его реальной работе.
- engines — задаёт список версий Node.js, на которых работает приложение.
- browserlist — используется для хранения списка браузеров (и их версий), которые должно поддерживать приложение.
▍Свойства, используемые в package.json
Поговорим о свойствах, которые можно использовать в package.json . Здесь мы будем использовать термин «пакет», но всё, что сказано о пакетах, справедливо и для локальных приложений, которые не планируется использовать в роли пакетов.
Большинство свойств, которые мы опишем, используются лишь для нужд репозитория npm, некоторые используются программами, которые взаимодействуют с кодом, вроде того же npm.
Свойство name
Свойство name задаёт имя пакета:
"name": "test-project"
Имя должно быть короче 214 символов, не должно включать в себя пробелы, должно состоять только из прописных букв, дефисов ( — ) и символов подчёркивания ( _ ).
Подобные ограничения существуют из-за того, что когда пакет публикуется в npm, его имя используется для формирования URL страницы пакета.
Если вы публиковали код пакета на GitHub, в общем доступе, то хорошим вариантом имени пакета является имя соответствующего GitHub-репозитория.
Свойство author
Свойство author содержит сведения об авторе пакета:
< "author": "Flavio Copes (https://flaviocopes.com)" >
Оно может быть представлено и в таком формате:
Свойство contributors
Свойство contributors содержит массив со сведениями о людях, внёсших вклад в проект:
< "contributors": [ "Flavio Copes (https://flaviocopes.com)" ] >
Это свойство может выглядеть и так:
Свойство bugs
В свойстве bugs содержится ссылка на баг-трекер проекта, весьма вероятно то, что такая ссылка будет вести на страницу системы отслеживания ошибок GitHub:
Свойство homepage
Свойство homepage позволяет задать домашнюю страницу пакета:
Свойство version
Свойство version содержит сведения о текущей версии пакета:
"version": "1.0.0"
При формировании значения этого свойства нужно следовать правилам семантического версионирования. Это означает, в частности, что номер версии всегда представлен тремя цифрами: x.x.x.
Первое число — это мажорная версия пакета, второе — минорная версия, третье — патч-версия.
Изменение этих чисел несёт в себе определённый смысл. Так, релиз пакета, в котором лишь исправляются ошибки, приводит к увеличению значения патч-версии. Если выходит релиз пакета, изменения, внесённые в который, отличаются обратной совместимостью с предыдущим релизом — то меняется минорная версия. В мажорных версиях пакетов могут присутствовать изменения, которые делают эти пакеты несовместимыми с пакетами предыдущих мажорных версий.
Свойство license
Свойство license содержит сведения о лицензии пакета:
"license": "MIT"
Свойство keywords
Свойство keywords содержит массив ключевых слов, имеющих отношение к функционалу пакета:
"keywords": [ "email", "machine learning", "ai" ]
Правильный подбор ключевых слов помогает людям находить то, что им нужно, при поиске пакетов для решения неких задач, позволяет группировать пакеты и быстро оценивать их возможный функционал при просмотре сайта npm.
Свойство description
Свойство description содержит краткое описание пакета:
"description": "A package to work with strings"
Это свойство особенно важно в том случае, если вы планируете публиковать пакет в npm, так как оно позволяет пользователям сайта npm понять предназначение пакета.
Свойство repository
Свойство repository указывает на то, где находится репозиторий пакета:
"repository": "github:flaviocopes/testing",
Обратите внимание, что у значения этого свойства имеется префикс github . Npm поддерживает префиксы и для некоторых других популярных сервисов подобного рода:
"repository": "gitlab:flaviocopes/testing", "repository": "bitbucket:flaviocopes/testing",
Используемую при разработке пакета систему контроля версий можно задать и в явном виде:
"repository": < "type": "git", "url": "https://github.com/flaviocopes/testing.git" >
Один и тот же пакет может использовать разные системы контроля версий:
"repository":
Свойство main
Свойство main задаёт точку входа в пакет:
"main": "src/main.js"
Когда пакет импортируют в приложение, именно здесь будет осуществляться поиск того, что экспортирует соответствующий модуль.
Свойство private
Свойство private , установленное в true , позволяет предотвратить случайную публикацию пакета в npm:
"private": true
Свойство scripts
Свойство scripts задаёт список скриптов или утилит, которые можно запускать средствами npm:
"scripts": < "dev": "webpack-dev-server --inline --progress --config build/webpack.dev.conf.js", "start": "npm run dev", "unit": "jest --config test/unit/jest.conf.js --coverage", "test": "npm run unit", "lint": "eslint --ext .js,.vue src test/unit", "build": "node build/build.js" >
Эти скрипты являются приложениями командной строки. Запускать их можно с помощью npm или yarn, выполняя, соответственно, команды вида npm run XXXX или yarn XXXX , где XXXX — имя скрипта. Например, выглядеть это может так:
npm run dev
Скрипты можно называть так, как вам хочется, делать они могут практически всё, чего может пожелать разработчик.
Свойство dependencies
Свойство dependencies содержит список npm-пакетов, установленных в виде зависимостей пакета:
"dependencies":
При установке пакета с использованиеме npm или yarn используются команды такого вида:
npm install yarn add
Эти пакеты автоматически добавляются в список зависимостей разрабатываемого пакета.
Свойство devDependencies
Свойство devDependencies содержит список npm-пакетов, установленных как зависимости разработки:
"devDependencies":
Этот список отличается от того, который хранится в свойстве dependencies , так как имеющиеся в нём пакеты устанавливаются лишь в системе разработчика пакета, при практическом использовании пакета они не применяются.
Пакеты попадают в этот список при их установке с помощью npm или yarn, выполняемой следующим образом:
npm install --dev yarn add --dev
Свойство engines
Свойство engines указывает, какие версии Node.js и других программных продуктов используются для обеспечения работы пакета:
"engines": < "node": ">= 6.0.0", "npm": ">= 3.0.0", "yarn": "^0.13.0" >
Свойство browserlist
Свойство browserlist позволяет сообщить о том, какие браузеры (и их версии) собирается поддерживать разработчик пакета:
"browserslist": [ "> 1%", "last 2 versions", "not ie
Этим свойством пользуются Babel, Autoprefixer и другие инструменты. Анализ этого списка позволяет им добавлять в пакет только те полифиллы и вспомогательные механизмы, которые нужны для перечисленных браузеров.
Показанное здесь в качестве примера значение свойства browserlist означает, что вы хотите поддерживать как минимум 2 мажорные версии всех браузеров с как минимум 1% использования (эти данные берутся с ресурса CanIUse.com), за исключением IE 8 и более старых версий этого браузера (подробнее об этом можно узнать на странице пакета browserlists).
▍Хранение в package.json настроек для различных программных инструментов
В package.json можно хранить настройки для различных вспомогательных инструментов вроде Babel или ESLint.
Каждому из таких инструментов соответствует особое свойство, наподобие eslintConfig или babel . Подробности об использовании подобных свойств можно найти в документации соответствующих проектов.
▍О версиях пакетов и семантическом версионировании
В вышеприведённых примерах вы могли видеть, что номера версий пакетов задаются не только в виде обычных чисел, разделённых точками, но и с использованием неких специальных символов. Например, в виде ~3.0.0 или ^0.13.0 . Здесь использованы так называемые спецификаторы версий, которые определяют диапазон версий пакетов, подходящих для использования в нашем пакете.
Учитывая то, что при использовании семантического версионирования все номера версий пакетов состоят из последовательностей, представляющих собой три числа, о смысле которых мы говорили выше, опишем следующие правила использования спецификаторов версий:
- ~ : если вы задаёте версию в виде ~0.13.0 это означает, что вас интересуют лишь патч-релизы пакета. То есть, пакет 0.13.1 вам подойдёт, а 0.14.0 — нет.
- ^ : если номер версии задан в виде ^0.13.0 , это означает, что вам подходят новые патч-версии и минорные версии пакета. То есть, вас устроят версии пакета 0.13.1 , 0.14.0 , и так далее.
- * : воспользовавшись этим символом, вы сообщаете системе, что вас устроят любые свежие версии пакета, в том числе — его новые мажорные релизы.
- > : подходят любые версии пакета, которые больше заданной.
- >= : подходят любые версии пакета, которые равны или больше заданной.
- < : вас интересуют пакеты, версии которых меньше заданной.
- = : вам нужна только заданная версия пакета.
- - : используется для указания диапазона подходящих версий, например — 2.1.0 - 2.6.2 .
- || : позволяет комбинировать наборы условий, касающихся пакетов. Например это может выглядеть как < 2.1 || >2.6 .
- отсутствие дополнительных символов: если используется номер версии пакета без дополнительных символов, это значит, что вашему пакету нужна только заданная версия пакета-зависимости и никакая другая.
- latest : указывает на то, что вам требуется самая свежая версия некоего пакета.
Файл package-lock.json
Файл package-lock.json используется с момента появления npm версии 5. Он создаётся автоматически при установке Node.js-пакетов. Что это за файл? Возможно, вы не знакомы с ним даже если знали о package.json , который существует гораздо дольше него.
Цель этого файла заключается в отслеживании точных версий установленных пакетов, что позволяет сделать разрабатываемый продукт стопроцентно воспроизводимым в его исходном виде даже в случае, если те, кто занимается поддержкой пакетов, их обновили.
Этот файл решает весьма специфическую проблему, которая не решается средствами package.json . В package.json можно указать, какие обновления некоего пакета вам подходят (патч-версии или минорные версии) с использованием вышеописанных спецификаторов версий.
В Git не коммитят папку node_modules , так как обычно она имеет огромные размеры. Когда вы пытаетесь воссоздать проект на другом компьютере, то использование команды npm install приведёт к тому, что, если, при использовании спецификатора ~ в применении к версии некоего пакета, вышел его патч-релиз, установлен будет не тот пакет, который использовался при разработке, а именно этот патч-релиз.
То же самое касается и спецификатора ^ . Если же при указании версии пакета спецификаторы не использовались, то будет установлена именно его указанная версия и проблема, о которой идёт речь, окажется в такой ситуации неактуальной.
Итак, кто-то пытается инициализировать проект, пользуясь командой npm install . При выходе новых версий пакетов окажется, что этот проект отличается от исходного. Даже если, следуя правилам семантического версионирования, минорные релизы и патч-релизы не должны содержать в себе изменений, препятствующих обратной совместимости, все мы знаем, что ошибки способны проникать (и проникают) куда угодно.
Файл package-lock.json хранит в неизменном виде сведения о версии каждого установленного пакета и npm будет использовать именно эти версии пакетов при выполнении команды npm install .
Эта концепция не нова, менеджеры пакетов, применяемые в других языках программирования (вроде менеджера Composer в PHP) используют похожую систему многие годы.
Файл package-lock.json нужно отправить в Git-репозиторий, что позволит другим людям скачать его в том случае, если проект является общедоступным, или тогда, когда его разработкой занимается команда программистов, или если вы используете Git для развёртывания проекта.
Версии зависимостей будут обновлены в package-lock.json после выполнения команды npm update .
▍Пример файла package-lock.json
В этом примере продемонстрирована структура файла package-lock.json , который входит в состав пакет cowsay, устанавливаемого в пустой папке командой npm install cowsay :
Зачем нужен package-lock.json
Лукас Ф. Коста — автор библиотеки Chai.js — написал статью про package-lock.json — "Why does package-lock.json exist, and how does it work?".
При повторной установке пакетов с зафиксированными версиями результирующий node_modules может отличаться, так как могут быть обновлены зависимости зависимостей. Чтобы добиться детерминированной установки в npm используется файл package-lock.json, в котором явно описываются все версии всех зависимостей.
При запуске команды npm i установщик получает список зависимостей проекта из package.json и во время их установки обновляет package-lock.json, записывая туда полное дерево зависимостей с необходимой метаинформацей. Для установки пакетов из package-lock.json нужно использовать другую команду — npm ci . Эта команда устанавливает все зависимости, создавая идентичное дерево зависимостей на момент последнего выполнения npm i . Кроме детерминированности npm ci даёт очень хороший буст в скорости установки пакетов, поэтому чаще всего её используют в CI-системах.
В общем, полезная статья. Рекомендую почитать, если хочется разобраться в этой теме подробнее.
package-lock.json
package-lock.json is automatically generated for any operations where npm modifies either the node_modules tree, or package.json . It describes the exact tree that was generated, such that subsequent installs are able to generate identical trees, regardless of intermediate dependency updates.
This file is intended to be committed into source repositories, and serves various purposes:
- Describe a single representation of a dependency tree such that teammates, deployments, and continuous integration are guaranteed to install exactly the same dependencies.
- Provide a facility for users to "time-travel" to previous states of node_modules without having to commit the directory itself.
- Facilitate greater visibility of tree changes through readable source control diffs.
- Optimize the installation process by allowing npm to skip repeated metadata resolutions for previously-installed packages.
- As of npm v7, lockfiles include enough information to gain a complete picture of the package tree, reducing the need to read package.json files, and allowing for significant performance improvements.
package-lock.json vs npm-shrinkwrap.json
Both of these files have the same format, and perform similar functions in the root of a project.
The difference is that package-lock.json cannot be published, and it will be ignored if found in any place other than the root project.
In contrast, npm-shrinkwrap.json allows publication, and defines the dependency tree from the point encountered. This is not recommended unless deploying a CLI tool or otherwise using the publication process for producing production packages.
If both package-lock.json and npm-shrinkwrap.json are present in the root of a project, npm-shrinkwrap.json will take precedence and package-lock.json will be ignored.
Hidden Lockfiles
In order to avoid processing the node_modules folder repeatedly, npm as of v7 uses a "hidden" lockfile present in node_modules/.package-lock.json . This contains information about the tree, and is used in lieu of reading the entire node_modules hierarchy provided that the following conditions are met:
- All package folders it references exist in the node_modules hierarchy.
- No package folders exist in the node_modules hierarchy that are not listed in the lockfile.
- The modified time of the file is at least as recent as all of the package folders it references.
That is, the hidden lockfile will only be relevant if it was created as part of the most recent update to the package tree. If another CLI mutates the tree in any way, this will be detected, and the hidden lockfile will be ignored.
Note that it is possible to manually change the contents of a package in such a way that the modified time of the package folder is unaffected. For example, if you add a file to node_modules/foo/lib/bar.js , then the modified time on node_modules/foo will not reflect this change. If you are manually editing files in node_modules , it is generally best to delete the file at node_modules/.package-lock.json .
As the hidden lockfile is ignored by older npm versions, it does not contain the backwards compatibility affordances present in "normal" lockfiles. That is, it is lockfileVersion: 3 , rather than lockfileVersion: 2 .
Handling Old Lockfiles
When npm detects a lockfile from npm v6 or before during the package installation process, it is automatically updated to fetch missing information from either the node_modules tree or (in the case of empty node_modules trees or very old lockfile formats) the npm registry.
File Format
name
The name of the package this is a package-lock for. This will match what's in package.json .
version
The version of the package this is a package-lock for. This will match what's in package.json .
lockfileVersion
An integer version, starting at 1 with the version number of this document whose semantics were used when generating this package-lock.json .
Note that the file format changed significantly in npm v7 to track information that would have otherwise required looking in node_modules or the npm registry. Lockfiles generated by npm v7 will contain lockfileVersion: 2 .
- No version provided: an "ancient" shrinkwrap file from a version of npm prior to npm v5.
- 1 : The lockfile version used by npm v5 and v6.
- 2 : The lockfile version used by npm v7 and v8. Backwards compatible to v1 lockfiles.
- 3 : The lockfile version used by npm v9 and above. Backwards compatible to npm v7.
npm will always attempt to get whatever data it can out of a lockfile, even if it is not a version that it was designed to support.
packages
This is an object that maps package locations to an object containing the information about that package.
The root project is typically listed with a key of "" , and all other packages are listed with their relative paths from the root project folder.
Package descriptors have the following fields:
- version: The version found in package.json
- resolved: The place where the package was actually resolved from. In the case of packages fetched from the registry, this will be a url to a tarball. In the case of git dependencies, this will be the full git url with commit sha. In the case of link dependencies, this will be the location of the link target. registry.npmjs.org is a magic value meaning "the currently configured registry".
- integrity: A sha512 or sha1 Standard Subresource Integrity string for the artifact that was unpacked in this location.
- link: A flag to indicate that this is a symbolic link. If this is present, no other fields are specified, since the link target will also be included in the lockfile.
- dev, optional, devOptional: If the package is strictly part of the devDependencies tree, then dev will be true. If it is strictly part of the optionalDependencies tree, then optional will be set. If it is both a dev dependency and an optional dependency of a non-dev dependency, then devOptional will be set. (An optional dependency of a dev dependency will have both dev and optional set.)
- inBundle: A flag to indicate that the package is a bundled dependency.
- hasInstallScript: A flag to indicate that the package has a preinstall , install , or postinstall script.
- hasShrinkwrap: A flag to indicate that the package has an npm-shrinkwrap.json file.
- bin, license, engines, dependencies, optionalDependencies: fields from package.json
dependencies
Legacy data for supporting versions of npm that use lockfileVersion: 1 . This is a mapping of package names to dependency objects. Because the object structure is strictly hierarchical, symbolic link dependencies are somewhat challenging to represent in some cases.
npm v7 ignores this section entirely if a packages section is present, but does keep it up to date in order to support switching between npm v6 and npm v7.
Dependency objects have the following fields:
- version: a specifier that varies depending on the nature of the package, and is usable in fetching a new copy of it.
- bundled dependencies: Regardless of source, this is a version number that is purely for informational purposes.
- registry sources: This is a version number. (eg, 1.2.3 )
- git sources: This is a git specifier with resolved committish. (eg, git+https://example.com/foo/bar#115311855adb0789a0466714ed48a1499ffea97e )
- http tarball sources: This is the URL of the tarball. (eg, https://example.com/example-1.3.0.tgz )
- local tarball sources: This is the file URL of the tarball. (eg file:///opt/storage/example-1.3.0.tgz )
- local link sources: This is the file URL of the link. (eg file:libs/our-module )
See also
- npm shrinkwrap
- npm-shrinkwrap.json
- package.json
- npm install
Что за файлы: package.json, package-lock.json, .stylelintrc.json в новых темах WordPress?
Всем привет! Подскажите если кто знает, что за файлы стали появляться в современных стандартных дефолтных темах типа twentytwenty в 2020 г. от создателей WordPress ? (package.json, package-lock.json, .stylelintrc.json). Это как-то связано с пакетным менеджером npm в Node.js, это нужно чтобы устанавливать тему через пакетный менеджер? Заранее всем спасибо за ответы!
- eTarget 2011:Панельная дискуссия «Стратегия и планирование рекламной кампании в интернете»
- eTarget 2011: Круглый стол «Реклама в онлайн-видео»
- Могут ли «плохие» входящие ссылки привести к ухудшению ранжирования?
На сайте с 12.04.2015
10 июля 2020, 11:57
Dmitriy_2014 :
package.jsonpackage.json - информация по пакету, как правило там список зависимостей
package-lock.json - тут конкретно установленные версии этих библиотек, обычно не распространяется если не нужно четкое соответствеи версий
stylelintrc.json - настройка линтера для автопроверки стиля написания кода (в данном случае css стилей)
Разработка проектов на Symfony, Laravel, 1C-Bitrix, UMI.CMS, OctoberCMS
На сайте с 29.03.2012
10 июля 2020, 20:58
Aisamiery #:package.json - информация по пакету, как правило там список зависимостей
package-lock.json - тут конкретно установленные версии этих библиотек, обычно не распространяется если не нужно четкое соответствеи версий
stylelintrc.json - настройка линтера для автопроверки стиля написания кода (в данном случае css стилей)
Вот зачем ты выполняешь работу местных гуру вп, ) но вообще имхо ответ неполный имхо. Я бы добавил что это значит что в теме используются нпм или препроцессоры для стилизации?
На сайте с 12.04.2015
10 июля 2020, 21:11
Sly32 #:Вот зачем ты выполняешь работу местных гуру вп, ) но вообще имхо ответ неполный имхо. Я бы добавил что это значит что в теме используются нпм или препроцессоры для стилизации?
Я сомневаюсь что гуру вп вообще знают что это, на хостингах ноду не ставят как правило, а истинные джедаи вп локально не разрабатывают.
то что npm используется это 100%, тут как бы и уточнять нет смысла, а насчет пре/пост процессоров не факт, чисто потому, что тогда был бы еще файл сборщика, а его здесь не указали, в том же package.json может быть единственная зависимость - сам линтер
- 2020.06.17
- www.npmjs.com
A mighty, modern linter that helps you avoid errors and enforce conventions in your styles. Features It's mighty as it: understands the latest CSS syntax including custom properties and level 4 selectors extracts embedded styles from HTML, markdown and CSS-in-JS object & template literals parses CSS-like syntaxes like SCSS, Sass, Less and.