Node.js Recipes
3.23K subscribers
174 photos
7 videos
1 file
622 links
По буднях нотатки по #Nodejs розробці, по вихідним огляди конференцій та доповідей (с) @galkin_nikita
Download Telegram
​​Как померять время выполнения команды в терминале?
#cli

TL;DR Используйте hyperfine

Стандартный способ померять время исполнения команды посредством time.
Пример: time npm run build.

Если time использовать в связке с curl, то можно узнать время выполнения запроса. Для такой задаче лучше подходит ab. Это сокращение от apache benchmark. Это команда отправляет не один запрос на указанный URL, а несколько. На основание результатов считаются статистики: средние, квартили и тп. Поэтому в название и есть benchmark.
Пример: ab -n 10 http://localhost:3000/

Для оценки cli команд тоже есть benchmark. Называется hyperfine. Он может сравнивать несколько команд, делать прогрев или подготовку.
Пример: hyperfine 'npm run build'.
Его удобно использовать в извечном холиваре #nodejs разработчиков: yarn vs npm. Вот так можно сделать сравнение для вашего проекта:
hyperfine --prepare 'rm -rf node_modules' 'yarn' 'npm install'
​​Что такое .npmrc и почему его стоит добавить?
#cli

У npm как и других #nodejs инструментов есть конфигурация через rc файл. Вы можете разместить .npmrc в папке проекта или в папке $HOME . Используйте npm config list, чтобы увидеть итоговую конфигурацию.

Полный перечень параметров в приведен документации. Рассмотрим те, которые стоит отключить:
➡️ update-notifier – регулярно показывает сообщение, что пора обновиться. Делать этого не стоит.
➡️ fund, выводит xx packages are looking for funding. Поддержите opensource и смело выключайте.
➡️ audit, после каждого npm install показывает сжатый security audit. После добавления npm audit в CI можно смело выключать.

Выключение всех этих параметров уменьшит количество бесполезных логов. Осталось изменить уровень loglevel с notice на error и получим .npmrc, который выводит в CI только важную информацию:
loglevel=error
fund=false
update-notifier=false
audit=false

В yarn-based проектах необходимо использовать .yarnnc. Он не заменяет, а дополняет .npmrc. Посмотреть результат конфигурации yarn config list
👍4
Как определить не используемые зависимости?
#package #cli

На картинке популярный мем про node_modules. Одной из причин раздутия данной папки являются неиспользуемые зависимости. Для облегчения их нахождения существует пакет depcheck. Устанавливать его в приложения не нужно, достаточно запустить npx depcheck . Данная команда покажет неиспользуемые и забытые зависимости. Работает как с javascript, так и с typescript. Верить результатам на 100% не стоит, особенно, если вы используете в коде магию🪄🎩.

Проверьте свой проект. Вдруг в package.json пора навести порядок.
👍1
Как автоматизировать работу с git?
#cli #git

У git есть малодокументированная возможность – external commands, то есть команды определенные пользователем. Упрощено говоря, git somename это алиас для команды git-somename.

Использовать можно так:
1️⃣ Смотрим зарегистрированные пути echo $PATH.
2️⃣ Выбираем папку из 1️⃣, где мы будем создавать команду.
3️⃣ Делаем файл с нашей команда git-done и таким контентом:
#!/usr/bin/env bash
DEFAULT_BRANCH=master
CURRENT_BRANCH=$(git branch | grep \* | cut -d ' ' -f2)
git checkout ${DEFAULT_BRANCH}
git pull
git branch -D ${CURRENT_BRANCH}
4️⃣ Делаем файл исполняемым chmod +x git-done

Так мы создали команду git done, которая удаляет активную ветку и переключает на master. У меня это команда еще передвигает текущую задачу в следующую колонку в Jira.

Обратите внимание на первую строчку #!/usr/bin/env bash, после #! (shebang) идет интепритатор. Для написания скрипта на #nodejs используется конструкция #!/usr/bin/env node

Можно установить один из готовых скриптов: npm install -g git-open. Он будет открывать текущую ветку в вашем репозитории. Подробности

Так же для проектов с GitHub рекомендую посмотреть cli.github.com
На что влияет environment variable EDITOR?
#cli

Переменная окружения EDITOR определяет, какой текстовый редактор использовать при многострочном пользовательском вводе или редактирование файла. По умолчанию в Unix системах это vim, в Windows – notepad.exe.
Я предпочитаю его переопределять на Visual Code.
export EDITOR='code'
В зависимости от того, какой shell вы используете это строчку необходимо внести в ~/.profile, ~/.bashrc, ~.zshrc, то есть в конфигурационный файл вашего shell.

Примеры, когда будет вызван редактор:
➡️ npm config edit
➡️ git commit
➡️ при клике по строчке ошибки в браузере вашего React приложения.

Есть быть более точным, то многое программное обеспечение использует EDITOR, если не задан SOMETHING_EDITOR. Например, можно использовать REACT_EDITOR и GIT_EDITOR, но не NPM_EDITOR. Читайте документацию или исходный код конкретного ПО.
Как обнаружить синхронные операции в Node.js коде?
#nodejs_api

Каждый #nodejs разработчик знает, что блокировать Event Loop-а плохо. Блокировка может быть по двум причинам:
– cpu intensive операции, т.е. с большим количеством вычислений. Примеры: трансформация JSON объекта на 2 мегабайта, обход большого массива, подсчеты хешей.
– синхронные операции, т.е. операции которые до своего завершения блокируют Event Loop, читай дальнейшее выполнение JavaScript. Пример – все синхронные файловые операции.

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

У Node.js есть специальный флаг --trace-sync-io. При его использование в консоль будут выводить trace для первого вызова любого синхронного вызова. Запускаем с этим флагом или c переменной окружения NODE_OPTIONS=--trace-sync-io и анализируем результаты. На своем проекте я так обнаружил, что пора выкинуть module-alias и переконфигурировать pino.

Рецепты по теме:
- Как запускать Node.js с доп. аргументами?
Что нужно знать об Error stack trace?
#nodejs_api

В JavaScript есть встроенный объект Error, который сохраняет stack trace (на русском трассировка стека). Так называется список методов, которые были вызваны до момента, когда в приложении произошло ошибка. Он доступен как error.stack и выглядит так:
Error: Things keep happening!
at /home/user/file.js:525:2
at Frobnicator.refrobulate (/home/user/business-logic.js:424:21)
at Actor.<anonymous> (/home/user/actors.js:400:8)
at increaseSynergy (/home/user/actors.js:701:6)

Плохой практикой является использование throw c литералами или объектами не наследниками Error. У них не будет stack trace.

По умолчанию длина стэка ограничена 10 методами. Параметр можно изменить на уровне кода через Error.stackTraceLimit. На уровне v8 существует флаг --stack-trace-limit. Его можно передать как аргумент или через переменную окружения NODE_OPTIONS=--stack-trace-limit=10

Начиная с 12-ой версии Node.js у нас есть поддержка Async Stack Traces. Пример stack trace:
Error: Oops
at bar (/workspace/test.js:11:9)
at async run (/workspace/test.js:5:3)
Для поддержки этих stack trace рекомендуется делать await перед return. Подробней в nodebestpractices.

Если код скомпилирован с помощью babel или typescript, то правильным будет показывать stack trace для исходного кода, а не скомпилированного. Для этого использовался пакет source-map-support. Под капотом идет использование Error.prepareStackTrace. Однако сейчас Node.js умеет это делать из коробки с помощью флага --enable-source-maps
👍3
Как запустить JavaScript код из буфера обмена?
#cli

TL;DR Используйте pbpaste | node

Сразу скажу, что сегодняшний рецепт для unix пользователей, т.е. MacOS и Linux. Под Windows я не проверял.

В unix есть оператор pipe, который выглядит так |. С его помощью можно делать цепочки команд передавая результат выполнения из одной в другую. Вот примеры использования:
ps -ax | grep node
history | grep kubectl

Еще в unix есть две команды pbcopy и pbpaste. С их помощью можно записывать или читать из буфера обмена. Попробуйте:
pbcopy < package.json
pbpaste

Собственно на этом объяснение магии сегодняшнего рецепта окончено. Скопируйте в буфере JS код, который вы хотите запустить и выполните в терминале pbpaste | node
Как и что настроить в git?
#git #cli

1️⃣Указать имя и емейл
Зачем? Чтобы комиты были залинкованы с вашей учеткой в github/gitlab.
git config --global user.name "Your Name"
git config --global user.email you@example.com
Можно настроить для каждого репозитория отдельно. Важно, если вы overemployed.
2️⃣Подключить ssh ключ
Зачем? Чтобы не вводить логин и пароль каждый раз
1. Generating a new SSH key
2. Add your SSH key to the ssh-agent
3. Adding a new SSH key to your GitHub account
или полная документация
3️⃣Изменить текстовый редактор
Зачем? Чтобы использовать привычный редактор, а не vim.
git config --global core.editor "code --wait"
Данный пример установить visual code как git редактор. Проверить можно git commit без флага -m.
4️⃣Автогенерация .gitignore
Зачем? Чтобы экономить время во время старта нового репозитория
1. Откройте gitignore.io.
2. Выберите node, операционку, IDE и т.д.
3. Сохраните в .gitignore вашего репозитория
4. Добавляйте специфичные для вашего проекта файлы, а не для тех. стэка.
5️⃣Использование глобального .gitignore
Зачем? Чтобы не закинуть в git вещи специфичные для вашего окружения.
Сохраните вещи из 4️⃣ в ~/.gitignore_global
git config --global core.excludesfile ~/.gitignore_global
Хорошая практика держать там .env файл

Из комментариев:
Начинающему техлиду стоит использовать .gitattributes для выставления конца строки на уровне репозитория с помощью core.autocrlf. Тогда джуны сидящие на Windows не буду страдать.
👍1
Как просто улучшить работу с git?
#git #cli
TL;DR установите git-extras

Я предпочитаю работать с git через командную строку, а не в IDE. Одна из причин прокачка git с помощью external commands, о которых я уже писал. Лучшим набором таких команд является git-extras.

Мои наиболее часто используемые команды:
git undo – отмена последнего коммита
git undo N  – отмена последних N коммитов
git abort – отмена текущего rebase, merge или cherry-pick.
git browse – аналог вышеназванного git open. Откроет в браузере страницу репозитория (github, gitlab).
git effort --above 5 – узнать какие файлы менялись больше чем в 5 коммитах. Удобно при анализе нового проекта

Начать использовать можно тут.

Рецепты по теме:
- Как автоматизировать работу с git?
- На что влияет environment variable EDITOR?
- Как и что настроить в git?
👍32
Тонкости работы с npm scripts
#cli #npm

1️⃣ pre- post- scripts
Для ежедневной работы JS часто использует автоматизацию с помощью npm scripts. У них есть pre- post- scripts, т.е. скрипты автоматически вызваны до или после скрипта. Например, так можно перекомпилить тайпскрипт перед запуском: "prestart": "npm run build". На канале уже был рецепт об postinstall идет в связки с пакетом patch-package.

Для выключения работы этих скриптов необходимо установить флаг ignore-scripts в .npmrc или командой:
npm config set ignore-scripts true

2️⃣ Использование --
Для добавления аргументов в npm script используется --. Например, в проекте есть команда "test": "jest". Команда npm run test -- -t="Example" запустит jest -t="Example", то есть только тесты с названием Example. Это работает только основной команды, но не для pre-/post-.

3️⃣ Работа с PATH
В npm скриптах не нужно прописывать путь к исполняемым файлам, хранимых в ./node_modules/.bin. Npm в момент запуска скрипта расширяет переменную PATH. Это идею можно расширить и в другую сторону, то есть сделать:
export PATH="$PATH:./node_modules/.bin"
После чего можно запускать установленный npm пакеты как из скриптов. Удобно для редких команд, которые не имеет смысла тащить в npm scripts.

Рецепты по теме:
​​Что такое .npmrc и почему его стоит добавить?
Как исправить код в node_modules?
👍15😱1
Что такое npm overrides?
#cli #npm

Делая обзор Nodejs 16.14.0, я не рассказал об обновление версии npm с 8.1.2 до 8.3.1. Основной фичей обновления является overrides, т.е. переопределение версий пакетов в зависимостях второго+ уровня. Это аналог resolutions в yarn. Чаще всего это нужно, чтобы заменить версию зависимости с известной проблемой безопасности. Реже, чтобы везде использовать одна и ту же версия пакета. Теперь npm догнал yarn не только по скорости, но и по необходимым фичам.

Подробней в ссылках:
🔗 npm overrides
🔗 yarn resolutions
👍24🎉3
Як прискорити eslint?
#cli #tooling
Чи довго працює eslint залежить від вашого проєкту та налаштувань eslint (включаючи правила, що використовуються).

1. Перевірте, чи eslint перевіряє лише потрібні файли. Раптом ви настроїли перевіряти node_modules? Щоб вивести всі файли, включаючи ті, де немає помилок, додайте в команду --format tap.

2. Перевірте чи не іде eslint вище по ієрархії і не мерджит конфіги з інших директорій, які ви не очікуєте.
Якщо забути поставити "root": true, можна довго дебажити що ж те так з конфігом

3. Налаштуйте, замініть або вимкніть довгі правила. Для їх знаходження запустіть змінну оточення TIMING=1. Приклад TIMING=1 npm run eslint. Докладніше в документації

4. Якщо все вище написане не допомагає, то час включати cache. Для цього додайте --cache. Ви можете зіткнутися з типовою проблемою кешування – коли скинути кеш або чому він порожній. Тому треба додати --cache скрізь, інакше eslint затиратиме кеш. Докладніше у документації

Update: Додав пункт 2. Дякую Євгену за коментар.
🔥23👍7
Що таке .nvmrc?
#cli
Для локальної розробки я рекомендую встановлювати Node.js через nvm. Це дозволяє легко перемикатися між версіями Node.js.

Після встановлення nvm необхідно налаштувати ваш shell, щоб nvm use автоматично викликався при заході в папку де є .nvmrc. Як це зробити описано тут.

Залишилося створити .nvmrc:
node -v > .nvmrc
git commit -am 'Add nvmrc'

PS Не плутайте .npmrc та .nvmrc
👍43🔥11
Що таке glob шаблони (або globbing)?
#cli #npm

JavaScript розробники нерідко роблять помилку у glob шаблонах. Ми їх використовуємо, щоб задати маску для файлів. Приклад:
eslint --fix 'src/*.js'.

Ці glob шаблони (або globbing) йдуть з Unix та нагадують RegExp. У JavaScript екосистемі є пакет minimatch який конвертую glob шаблон у RegExp. Звичайно ж, є і пакет glob від того самого автора, який є обгорткой до minimatch. Тому зустрічається термін minimatch syntax (приклад у eslint). Але правильний термін – glob/globbing.

Покажу, як виглядає типова помилка у використанні:
prettier --write 'src/*.js'
Очікування: будуть переформатовані всі файли у src.
Реальність: будуть переформатовані лише файли на першому рівні вкладеності.

Треба мати на увазі, що */?/etc працюють лише у path segments, тобто у іменах файлів/директорії. Для рекурсивного пошуку необхідно використовувати **. Тому правильна команда:
prettier --write 'src/**/*.js'

👉 Інструмент для перевірки/тренування тут.
👍42👌21
Як перевірити локальне середовище?
#list #cli

Сьогодні розповім як провести troubleshooting локального середовища.

1️⃣ Контролюйте змінні оточення за допомогою команди env. Нагадаю, що dotenv за замовчуванням має override false. Змінна PATH визначає, у яких папках OS буде шукати виконувані файли.
2️⃣ Використовуйте команду which, щоб перевірити що використовується правильний виконуваний файл. Приклад: which yarn
Якщо ви використовуєте nvm, то результат буде таким:
/Users/{{username}}/.nvm/versions/node/v18.12.1/bin/yarn
3️⃣ Перевіряйте версії використовуючи --version. Приклад: npm --version. Пам'ятаємо про Dev/prod parity. До речі версію npm краще використовувати яка йде у Node.js.
4️⃣ Використовуйте npm doctor, щоб перевірити права.
5️⃣ Перевіряйте конфігурацію:
git config --list --global
npm config list
👍201🔥1
Чому розробнику необхідно використати термінал?
#cli
Під час інтерв'ю чи сесії парного програмування я часто даю зворотний зв'язок використовувати термінал замість click-based інструментів. Термінал, на відміну візуальних інструментів, веде історію. Вона доступна за командою history і при локальній розробці, і при віддаленому налагодженні Docker або EC2. З її допомогою можна зрозуміти як система прийшла до поточного стану. У разі використання візуальних click-based інструментів у нас такої можливості немає.

Розробникам-початківцям освоєння терміналу для повсякденного використання найкраще почати з cli версії git. Там є чудова команда git reflog, яка неодноразово допомагала повернути втрачені коміти.

Чи зміниться ця відповідь на це запитання через кілька років, коли додатковим інструментом розробника до пари миша/клавіатура додасться голос, я не знаю. Тому що цю нотатку я набираю для вас саме голосом.
25👍16😁4❤‍🔥3
Як перевірити конфігурацію інструментарію?
#cli

Типовий набір інструментів у Web/Node.js проекті включає у себе п'ять та більше інструментів. Кожен з інструментів має свою конфігурацію, яка може наслідуватися з встановленого пакета або глобального конфігу, перевизначатися змінною оточення або на рівні вкладеної папки. Більшість інструментів вміють показувати використовуваний конфіг у явному вигляді або завдяки підвищенню рівня логування до дебагу.

Ось приклади команд для найпопулярніших інструментів:
npm config list --long
prettier --log-level=debug --check '{src,tests}/**/*.ts'
eslint --print-config '{src,tests}/**/*.ts'
tsc --project tsconfig.json --showConfig
jest --debug --config jest.config.ts

Використовувати перевірку конфігурації варто не тільки для налагодження чи налаштування інструментів, але й під час оновлення версій пакетів. Для цього зручно виводити конфігурацію у файл за допомогою перенаправленням виводу (символ >). Приклад: eslint --print-config '{src,tests}/**/*.ts' > eslint.v1.json Після оновлення версії пакета або його конфігурації можна порівняти два файли.

Наприкінці хочу наголосити: уникайте глобальних установок та налаштувань інструментів. У протилежному випадку ваше локальне середовище може давати інші результати, ніж середовища ваших колег чи CI/CD. Що призведе на витрату часу на пошук причин таких розбіжностей.
👍431