javascript

npm link на стероидах

  • четверг, 20 июля 2017 г. в 03:12:02
https://habrahabr.ru/company/mailru/blog/333580/
  • Разработка веб-сайтов
  • Node.JS
  • JavaScript
  • Блог компании Mail.Ru Group


npm link + steroids = npmy


Думаю многие из вас уже сталкивались с локальной разработкой npm-пакетов. Обычно никаких трудностей это не вызывает: создаём папку, запускаем npm init, пишем тесты, дальше используем npm link (либо просто симлинк) и «шлифуем» api до полной готовности.


Звучит просто… только если вы не используете Babel, Rollup, Webpack и т.п. Иными словами, всё хорошо, пока проект не нужно собрать перед публикацией, да ещё с модификацией исходного кода. Кроме того, одновременно разрабатываемых пакетов может быть больше чем один, что в разы усложняет «жизнь». Чтобы исправить эту ситуацию, пришлось сделать маленькую утилиту npmy, под катом небольшая статья с описанием тех. процесса работы и пример использования.


Итак, как я уже говорил, основная проблема локальной разработки — это использование scripts/хуков (prepublish, prepublishOnly и т.д.), именно по этой причине npm link не подходит, ведь по сути — это банальный симлинк, да ещё по завершению разработки нужно не забывать про npm unlink.


Поэтому я принялся за свое решение, которое:


  1. Имеет простую настройку.
  2. Эмулирует полный цикл публикации.
  3. Создает симлинк на псевдо-опубликованную версию (далее ПОВ).
  4. Следит за изменениями и обновляет ПОВ.


Настройка проекта


Первой мыслью было добавить правила прямо в package.json, но это неправильно, ведь это именно локальная разработка, поэтому правила было решено размещать в .npmyrc, который без труда можно добавить в .gitignore.


Сам файл — ни что иное, как простой JSON-объект, у которого:


  • key — название зависимости из package.json;
  • value — локальный путь до разрабатываемого пакета (относительный или абсолютный).

Всё, на этом конфигурация закончена.



Запуск


Заходим в папку с .npmyrc и запускаем npmy, который:


  1. Читает .npmyrc.
  2. Фильтруем список зависимостей на два списка для:
    • установки из NPM;
    • локальной установки.
  3. Установка зависимостей из NPM.
  4. Псевдо-публикация пакетов из .npmyrc.
  5. Создание симлинка на ПОВ.
  6. Запуск отслеживания изменений (watch).


Процесс псевдо-публикации


Это самое интересное, ради чего всё и затевалось. Для начала вспомним, как это работает в оригинальном npm.


npm install && npm publish


Как видите, тут нас ждет сюрприз, prepublish и prepare выполняются как на npm publish, так и на npm install (без аргументов). Поэтому если вам нужна сборка проекта перед публикацией, используйте prepublishOnly, но только начиная с 5 версии. Хоть этот хук и добавили в 4, работает он неправильно, и вместо собранного пакета уедет не пойми что, увы.


В моём процессе перед запуском всех хуков есть ещё одно звено, а именно создание копии проекта (вместе с node_modules):


  1. Копия создается через rsync в темповую папку.
  2. Модифицируется package.json, из которого убирается npm test, чтобы не тормозить процесс псевдо-публикации.
  3. Затем для копии запускаются все хуки соответствующие процессу публикации.
  4. И в финальный штрих: удаление всего, что не соответствует секции files.
  5. Profit.

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


Кроме этого, npmy не забывает про секцию bin в package.json и корректно создаёт симлинки на объявленные там скрипты.



Итого


  • npm install -g npmy
  • Создаем .npmyrc в проекте
  • Запускаем npmy

Спасибо за внимание, надеюсь утилита будет полезна не только мне. :]



P.S. Инструмент новый, так что не стесняйтесь писать о проблемах.