npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

do-webp

v2.0.0

Published

Convert images to WebP via npx do-webp

Readme

do-webp

Утилита командной строки для конвертации изображений в формат WebP с сохранением исходной структуры папок или размещением результатов рядом с оригиналами.

!!! AI POWERED

Всё было проверено только на шиндоус.

Возможности

  • Конвертация отдельных файлов или целых папок (рекурсивно по умолчанию)
  • Поддержка форматов: .jpg, .jpeg, .png, .tiff, .bmp, .svg
  • Настраиваемое качество WebP (1–100) и режим без потерь
  • Изменение размера результата: в пикселях (--width/--height) или в процентах (--scale)
  • Два режима работы:
    • без параметра -d – WebP-файлы создаются рядом с исходными (в тех же папках)
    • с параметром -d – все результаты сохраняются в указанную выходную папку с сохранением вложенной структуры
  • Возможность отключить рекурсивный обход подпапок (--no-recursive)

Требования и зависимости

  • Node.js 22.12 или новее
  • Пакеты sharp и commander ставятся автоматически

Установка

Глобальная установка из NPM

npm install -g do-webp

Локальная установка

git clone https://github.com/Manshooo/do-webp
cd do-webp
npm install
npm run build
npm link

Вызов без установки

npx do-webp -s ./images -d ./webp

или

do-webp -s ./images

Использование

do-webp -s <путь> [options]

Параметры

| Параметр | Описание | |------------------------------|---------------------------------------------------------------------------| | -s, --source <path> | Исходный файл или папка (обязательный) | | -d, --dist <path> | Выходная папка. Если не указана, WebP-файлы создаются рядом с оригиналами | | -q, --quality <number> | Качество сжатия от 1 до 100 (по умолчанию 80) | | -w, --width <px> | Ширина результата в пикселях | | --height <px> | Высота результата в пикселях | | --scale <percent> | Масштаб в процентах от исходного размера: 50 или 150% | | --fit <mode> | Как вписывать в заданные размеры (по умолчанию inside) | | --lossless | Сжатие без потерь: файл крупнее, но без артефактов | | --no-recursive | Отключить рекурсивную обработку подпапок (по умолчанию рекурсия включена) | | -c, --concurrency <number> | Количество параллельных потоков (по умолчанию 4) | | -V, --version | Показать версию | | -h, --help | Показать справку |

Размер результата

Размер задаётся одним из двух способов, вместе они не работают:

  • В пикселях--width и/или --height. Если указать только одну сторону, вторая считается сама по пропорциям.
  • В процентах--scale. Считается от исходного размера файла, поэтому в папке с разными картинками каждая масштабируется от своего размера.
# фиксированная ширина, высота по пропорциям
do-webp -s logo.svg --width 512

# уменьшить вдвое
do-webp -s photo.jpg --scale 50

# увеличить в полтора раза (проценты можно писать со знаком)
do-webp -s photo.jpg --scale 150%

Режимы --fit

Нужны только когда заданы обе стороны сразу. Значения те же, что у sharp:

| Режим | Что делает | |-----------|--------------------------------------------------------------------------| | inside | Вписывает целиком, пропорции сохраняются, результат может быть меньше заданного (по умолчанию) | | cover | Заполняет прямоугольник целиком и обрезает лишнее | | contain | Вписывает целиком и дополняет до нужного размера полями | | fill | Растягивает до точного размера, пропорции нарушаются | | outside | Вписывает так, чтобы покрыть прямоугольник, без обрезки |

# впишется в 200x200, реальный размер, например, 200x133
do-webp -s photo.jpg --width 200 --height 200

# ровно 200x200 с обрезкой по краям
do-webp -s photo.jpg --width 200 --height 200 --fit cover

Про SVG

SVG растеризуется в размер, записанный в самом файле — в атрибутах width и height, а если их нет, то в размер из viewBox. Именно поэтому иконка с viewBox="0 0 64 64" без width/height превращается в WebP 64×64 и выглядит пиксельной, сколько ни поднимай -q.

Лечится указанием размера — тогда картинка перерисовывается из вектора сразу в нужное разрешение, а не растягивается после отрисовки:

do-webp -s favicon.svg --width 512

Для иконок и логотипов с плоскими заливками имеет смысл добавить --lossless: файл получится крупнее, но без «грязи» вокруг контуров и текста.

do-webp -s favicon.svg --width 512 --lossless

Примеры

  1. Конвертация всех изображений в папке photos с сохранением результатов в той же папке (структура сохраняется):

    do-webp -s ./photos
  2. Конвертация папки photos с сохранением всех WebP-файлов в папку webp (структура вложенных папок сохраняется):

    do-webp -s ./photos -d ./webp
  3. Конвертация одного файла:

    do-webp -s avatar.png

    Результат: avatar.webp рядом с avatar.png.

  4. Конвертация с качеством 90 и отключением рекурсии (обрабатываются только файлы в корне photos):

    do-webp -s ./photos -q 90 --no-recursive
  5. Конвертация файла в указанную выходную папку:

    do-webp -s image.jpg -d ./converted
  6. Превью для галереи: всё в папке уменьшается до ширины 400 пикселей и складывается отдельно:

    do-webp -s ./photos -d ./thumbs --width 400

Что стоит знать

  • Ориентация фотографий. Поворот из EXIF применяется к картинке при конвертации, потому что WebP этот тег не хранит. Снятые вертикально фотографии не ложатся набок.
  • Совпадение имён. logo.png и logo.svg в одной папке дают один и тот же logo.webp. Второй файл пропускается с предупреждением, а не затирает первый молча — переименуйте исходник или разложите файлы по разным папкам.
  • Код возврата. 0, если сконвертировались все файлы. 1, если хоть один файл не удалось обработать или пришлось пропустить из-за совпадения имён — так ошибку видно в скриптах и CI.
  • Прогресс. Первые три файла печатаются построчно, дальше идёт счётчик. При выводе в файл или пайп счётчик не печатается, чтобы не засорять лог.

Что изменилось в 2.0

Ломающие изменения:

  • Node.js 22.12 или новее вместо 14. Подтянулось за sharp 0.35 и commander 15.
  • sharp обновлён с 0.33 до 0.35 — в 0.33 остались незакрытые уязвимости libvips.
  • -q 0 больше не принимается, минимум 1: нуля WebP всё равно не понимает.
  • Ненулевой код возврата при ошибках конвертации и пропущенных файлах. Раньше всегда возвращался 0, даже когда не сконвертировалось ничего.
  • Совпадение имён не приводит к перезаписи — лишний файл пропускается.
  • Точка входа переехала с bin/do-webp.js на dist/cli.js. Через do-webp и npx разницы нет, но прямой запуск файла из node_modules придётся поправить.

Остальное:

  • Исходники переписаны на TypeScript, в пакет уезжает собранный JavaScript.
  • Появились --width, --height, --scale, --fit и --lossless.
  • Исправлен разбор -q и -c: раньше любое значение превращалось в NaN.
  • photo.PNG больше не даёт photo.PNG.webp.

Разработка

npm install
npm test          # проверка типов + сборка + тесты
npm run build     # только сборка в dist/
npm run typecheck # только проверка типов, включая тесты

Структура:

| Файл | За что отвечает | |---------------------|-------------------------------------------------------| | src/cli.ts | Разбор аргументов, оркестрация, вывод итогов | | src/options.ts | Типы опций, парсеры значений, проверка сочетаний | | src/files.ts | Обход дерева, имена результатов, совпадения имён | | src/convert.ts | Расчёт размера и конвейер sharp | | src/pool.ts | Ограничение параллелизма | | src/logger.ts | Вывод в консоль и строка прогресса |

Исходники написаны так, чтобы node мог запускать .ts напрямую своей вырезкой типов — без сборки, когда нужно быстро проверить правку:

node src/cli.ts -s ./photos --width 400

Тесты в test/ делятся на два вида: юнит-тесты берут функции прямо из src/, а cli.test.ts запускает собранный dist/cli.js отдельным процессом и проверяет настоящие файлы на диске.

Выпуск версии

Версия поднимается только через workflow Release, руками её править не нужно:

  1. Actions → ReleaseRun workflow
  2. Выбрать, что сделать с версией
  3. Run workflow

Дальше всё делается само: прогоняются тесты, версия записывается в package.json, пакет уезжает в npm, появляются коммит, тег и релиз на GitHub. Разойтись тег и package.json не могут — их ставит один и тот же шаг.

Значения поля «Что сделать с версией»:

| Значение | Что делает | |-------------------------|-------------------------------------------------------------------| | none (по умолчанию) | Выпускает версию, которая уже записана в package.json | | patch minor major | Поднимает соответствующую часть версии перед публикацией |

Ниже есть поле для точной версии — если его заполнить, выбор выше игнорируется.

По умолчанию стоит none, чтобы случайный запуск не поднял версию молча: такой прогон просто упрётся в проверку «эта версия уже в npm» и остановится.

Если релиз упал

Смотря на каком шаге. Всё до публикации — тесты, расчёт версии, проверки — происходит внутри раннера и в репозиторий не попадает: ни лишнего тега, ни поднятой версии не остаётся, можно просто запустить workflow заново с теми же параметрами.

Публикация в npm — точка невозврата. Если она прошла, а коммит с тегом запушить не удалось (например, из-за защиты ветки), версия в npm уже есть. Тогда остаётся поправить причину и проставить коммит с тегом руками — повторный запуск не поможет, он упрётся в проверку «уже опубликовано».

Настройка публикации в npm (делается один раз)

Публикация идёт по OIDC через доверенного издателя, без токенов в секретах. Пока издатель не настроен, npm publish падает с ENEEDAUTH — прав id-token: write в workflow для этого недостаточно, npm должен со своей стороны знать, какому репозиторию доверять.

  1. Зайти на npmjs.com под владельцем пакета
  2. Открыть страницу пакета do-webpSettings
  3. Найти раздел Trusted publisher и выбрать GitHub Actions
  4. Заполнить:
    • Organization or user: Manshooo
    • Repository: do-webp
    • Workflow filename: release.yml
    • Environment: оставить пустым
  5. Сохранить

Значения должны совпадать с репозиторием буква в букву, включая регистр. Если позже переименовать файл workflow, издателя нужно будет поправить.

Запасной вариант, если доверенный издатель по каким-то причинам не подходит: создать в npm гранулярный токен с правом публикации, положить его в секреты репозитория как NPM_TOKEN и добавить в шаг setup-node параметр registry-url: "https://registry.npmjs.org", а в шаг публикации — env: NODE_AUTH_TOKEN: ${{ secrets.NPM_TOKEN }}. Такие токены живут максимум 90 дней, так что менять их придётся регулярно.

Лицензия

MIT