Эволюция технологий
Начнем с небольшого экскурса, как комьюнити пришло к Bun.js.
С момента появления JavaScript серверная разработка на JS была практически невозможна, пока в 2009 году Райан Даль, разработчик из Южной Америки, не зарелизил первую версию Node.js. Ему не нравились технологии, которые были на тот момент, — он хотел создать что-то свое. Так Райан пришел к модели, которая сейчас лежит в основе Node.js, — асинхронности и event loop.
Событие стало громким для индустрии, и Node.js быстро начал обрастать своей экосистемой. В 2010 году появился пакетный менеджер, в 2011 году он был импортирован под Windows. Разработчикам понравился Node, и вокруг него начало складываться комьюнити.
Но со временем темпы развития Node.js перестали устраивать разработчиков: новые версии появлялись долго и редко, новых фич практически не было, всё концентрировалось на баг-фиксах. Так в 2014 году появился форк io.js, который развивался только силами комьюнити. Кстати, только благодаря io.js сейчас мы можем пользоваться промисами и async/await.
Разработчиков Node.js это немного отрезвило — они поняли, что нужно что-то менять. В 2015-м они объединяются с io.js, становятся открытой компанией Node Foundation и продолжают разработку в ускоренном темпе. С этого момента модель выпуска версий Node.js меняется, появляется больше новых фич.
Но проблемы всё же остаются — появляется известное выражение «Покажи мне самый большой объект во вселенной, и я покажу тебе свою папку node_modules».
К тому моменту Райан Даль уже отошел от разработки Node.js и долгое время работал над своими проектами. В 2018 году он выступил с докладом «10 вещей, о которых я жалею в Node.js». В конце он представил Deno — духовного наследника Node.js, который должен был закрыть все его недостатки.
Deno был написан на Rust, ориентирован на повышенную безопасность и представлялся как более удобный для разработчиков инструмент. Он поставлялся со своим менеджером пакетов и своим компилятором TypeScript.
В 2021 году начинается разработка героя нашей статьи — Bun. Он быстро прошел стадии альфы и беты, и в 2023 году случился его релиз. Это стало довольно громким событием в комьюнити JavaScript — Bun мгновенно нашел своих поклонников.
Забавный факт: название компании-разработчика — Oven — переводится с английского как «духовка». Соответственно, Bun — это «булочка, испеченная в духовке».
Что умеет Bun?
Рантайм прежде всего ориентирован на быстродействие — возможность встраиваться в ресурсоемкие системы, обрабатывать больше запросов и совершать больше операций в секунду. На этой философии основана вся экосистема Bun, а она, к слову, уже сейчас довольно внушительная. Если уже Deno позиционировался как мультитул со своим компилятором и пакетным менеджером, то Bun получилась еще совершеннее.
Вот основные преимущества Bun.js:
- Почти полная совместимость с Node.js/Deno.
- В десятки раз быстрее Node.js и Deno.
- Нативная поддержка JavaScript.
- Богатый набор встроенных Web API.
- Самый эффективный менеджер пакетов.
- Встроенный dev-сервер.
- Встроенный раннер тестов.
- Встроенный бандлер.
- Возможность почти моментального перехода с Node на Bun.
Откуда такая скорость? В первую очередь это современные технологии и тонны большого труда при профилировке и оптимизации.
За счет чего достигается эффект Blazingly Fast, которым так известен Bun.js сегодня?
- Bun написан на языке Zig. Это альтернатива C++ и Rust. Zig предоставляет низкоуровневые возможности для ручной работы с памятью, за счет чего появляется возможность оптимизировать вообще все элементы платформы. К слову, это и было сделано: более 80% составных частей Bun, которые так или иначе уже были реализованы в Node, были переписаны на Zig с максимальной оптимизацией обращений к памяти.
- Bun использует движок JSCore. Конечно, напрямую на производительность это не влияет, поскольку многие бенчмарки вам скажут, что JSC почти идентичен по скорости V8. Однако в данном случае дело вовсе не в производительности. JSCore предоставляет более открытую и удобную платформу для выполнения JS-кода, в отличие от V8, который изолирует этот процесс, поэтому накладные расходы на многие процессы снижаются.
Посмотрим на практике
Для начала устанавливаем пакет bloater — это занимает всего 27 секунд. Он не несет какой-либо смысловой нагрузки для проекта — это, по сути, бенчмаркинговый тул, с помощью которого можно протестировать нагрузку и сравнить, как ведет себя пакетный менеджер npm и менеджер Bun.
Открываем две папки для npm и для Bun.
Теперь делаем то же самое для Bun.
Различия незначительны, но уже здесь мы видим, что Bun требует куда меньшее количество шагов при инициализации проекта, что не может не радовать.
Начинаем наше тестирование. Запускаем сначала процесс для npm.
А перед тем как запустить Bun, я сделаю небольшой пруф его производительности. Мы очистим кеш Bun полностью.
В основе работы npm и пакетного менеджера Bun лежит кеширование. Мы же не будем каждый раз, переустанавливая веб-модули, тянуть из интернета все тонны гигабайтов пакетов, превращая нашу node_modules в черную дыру. Применяются разные техники кеширования, и в основе Bun лежит большое количество этих подходов — наиболее оптимизированные способы копирования.
Единственная проблема, которая может поставить менеджеры npm и Bun рядом друг с другом, — это скорость интернета. Вместо традиционных package-lock Bun использует свои веб-файлы, которые хранятся в бинарном виде и используют большое количество оптимизаций, битовые массивы и так далее. Таким образом, чтение данных происходит быстрее. В нашем случае процесс занял 70 секунд.
Тем временем npm всё еще в этом состоянии.
Чтобы удостовериться, что там действительно закачалось такое большое количество данных, вы можете посмотреть на объем папки node_modules — полтора гигабайта.
Теперь сделаем следующее. Мы удаляем нашу папку node_modules и устанавливаем пакеты заново.
Как видите, кеширование сделало свое дело: 6 секунд против 70 в первый раз. На протяжении всего этого времени (более 76 секунд) ситуация в npm не менялась.
Недостатки Bun.js
Самый известный минус этого рантайма — Bun нет на Windows. На мой взгляд, сейчас это не такой серьезный недостаток. Хотя и на Linux Bun не всегда доступен. Но в целом это не проблема, даже для тех, кто предпочитает разрабатывать на Windows, — ведь у нас есть WSL. К тому же процесс разработки не стоит на месте, и команда Oven уже смогла адаптировать сигналы консольного ввода к Bun.
Следующий недостаток — отсутствие менеджера версий. Сейчас это не такая серьезная проблема, но через пару лет может стать более ощутимой. Разработчикам необходима обратная совместимость, а без нее Bun может стать крайне неудобным решением.
Bun еще молодой — большое количество edge-кейсов еще не покрыто. Многие вещи, удачные на первый взгляд, на определенном наборе данных или на каком-то типе процесса могут обернуться для Bun неприятными последствиями. Поэтому мы пока и не слышим о том, что крупные компании стараются писать на Bun свои приложения. Но у этого есть и обратная сторона. Своим выходом Bun спровоцировал определенные изменения, которые коснулись не только сообщества в целом, но и конкретных разработчиков Deno и Node. Например, в 21-й версии Node, которая вышла относительно недавно, появились предпосылки того, что он также начинает наращивать свою производительность во времени. Как мне кажется, это сыграет на руку всем.
Заключение
В том виде, в котором Bun.js есть сейчас, он отлично подойдет разработчикам, которые исследуют различные среды. Даже тем, кто никогда не писал на Node, кто находится на начальной точке старта и хочет погрузиться в разработку, — в Bun всё для этого есть.
Bun.js отлично подойдет стартапам, небольшим компаниям, которые хотят развивать технологии. А вот большим компаниям, которые пишут высокопроизводительные приложения с высокой стабильностью, использование Bun может выйти боком. Дело в том, что Bun.js как платформа развивается очень быстро, и многие изменения в нем могут сказаться на процессе разработки, а для больших вендоров это неприемлемо.
Есть и промежуточная категория, кому Bun.js в теории может подойти, — это компании или пользователи, у которых уже есть приложения на Node, и они хотят повысить их производительность.
Сейчас мы наблюдаем рост конкуренции между Bun, Node и Deno, а конкуренция — это всегда стимул для развития всех игроков рынка. Так что ждем еще большего роста производительности у всех этих продуктов.