Deno — это современная среда выполнения JavaScript, конкурент Node.js, с планами внедрения таких функций, как безопасный ввод-вывод (secure I/O) и встроенная поддержка TypeScript. Deno построена с помощью языка Rust Райаном Далем — создателем Node.js.
Background
В докладе «
10 things i regret about Node« Райан Даль рассуждает о многих проблемах Node. Один из озвученных вопросов — это неспособность Node использовать веб-стандарты, безопасность, способ компиляции собственных модулей GYP и NPM. Затем анонсировали Deno. Deno был новым проектом, который решал многие из поднятых Райаном проблем, и предлагал дополнительные преимущества, как упомянутая поддержка TypeScript. Изначально Deno проектировалась на языке Go, но позже выбор остановили на Rust.
С тех пор, как Deno был впервые анонсирован, проект добился значительного прогресса. В августе 2020 года была выпущена версия 1.0 и некоторые компании, такие как Slack, приняли его. Также, Deno выпустил собственную
edge serverless платформу
Deno Deploy.
Почему Deno важен
Безопасность
V8 — это движок JavaScript, который изолирует код в песочнице, не позволяя выполнять действия за её пределами. Однако Node.js предоставляет доступ к таким вещам, как сеть и файловая система внутри песочницы, что нивелирует безопасность V8. Даже в случае с надежными программами такой подход нежелателен, так как небезопасный код или вредоносные зависимости могут нанести значительный ущерб или украсть данные.
Deno решает проблемы безопасности с помощью системы
разрешений. Такая система позволяет конкретно и точно определить, что программа может делать за пределами песочницы, например, иметь доступ к файловой системе и переменным среды. Если вы хотите разрешить чтение файлов в локальном каталоге, то вы можете запустить Deno с такой командой:
deno run –allow-read=./assets
Благодаря гарантии, что ваш код не выйдет за пределы обозначенной среды, повышается общая безопасность.
Стандартизированные API
Поскольку Node.js и веб-платформы развивались параллельно, у них много различий. Примеров этому множество, например, система модулей и HTTP запросов.
ECMAScript и CommonJS
Когда появился Node.JS, JavaScript мог использовать другие модели, только встраивая их в теги
script
и используя их из global window scope. Поскольку HTML и window не были доступны на сервере, Node.js требовался модульный формат. Поэтому Node.js перенял концепцию популярного и простого CommonJS. Однако CommonJS не поддерживался браузерами (для это необходимо использовать библиотеку наподобии
Browserify) и между реализациями CommonJS существовали различия.
Годы спустя, в 2016 году, в ES6 была доработана спецификация модуля ECMAScript Modules (ESM). Эта спецификация могла работать в браузере без каких-либо библиотек. Вдобавок к этому, решались многие проблемы, связанные с CommonJS, такие как асинхронная загрузка модулей и tree shaking. Однако Node.js потребовалось некоторое время для внедрения поддержки ESM, и даже после этого степень принятия ESM в Node.js была не слишком высокой, поскольку большинство NPM пакетов по-прежнему включают версии только CommonJS. Кроме того, Node.js не имеет полностью соответствующую стандартам реализацию ESM.
В противоположность Node.js, Deno работает только со стандартизированной ESM. Это значительно упрощает использование Deno как для пользователей, так и для разработчиков библиотек. Исходя из опыта, использование одного формата модуля намного проще, чем ESM и CommonJS. Соответствие стандартам Deno упрощает работу, так как вы точно знаете, что код вашего модуля работает в браузере корректно.
HTTP fetching
Отправка HTTP-запросов — ещё одна проблемная область, которую решает Deno. Node.js позволяет выполнять HTTP запросы с помощью функций стандартной библиотеки http и https. Однако современная практика выполнения HTTP-запросов базируется на функции fetch() API, которая стандартизирована и проще, чем http. Node.js не поддерживает fetch(), поэтому для её использования приходится обращаться к таким пакетам, как
node-fetch или
cross-fetch. Это проблемотично, так как требуется ещё одна зависимость, недоступная без импорта. Deno поддерживает fetch() API по умолчанию.
Децентрализованный хостинг модулей
То, что он децентрализован, не означает, что он использует блокчейн (
хотя и существует услуга хостинга пакетов Deno, поддерживающая блокчейн). Вместо этого децентрализованный хостинг модулей Deno позволяет запрашивать модули по URL-адресу, а не из централизованной базы данных наподобии NPM. Такой подход предоставляет большую свободу при хостинге модулей. Deno действительно предлагает такую услугу, как размещение модулей на
deno.land/x, но это не ограничивает вас. Вы можете ссылаться на любой CDN ESM или что-то другое, обслуживающее файл JavaScript. Многие люди волнуются об удаленном изменении кода, потому что он не обязательно контролируется, но большинство служб хостинга модулей Deno неизменяемы. К тому же Deno кэширует файлы, поэтому он может изменится только в случае, если вы обновили кэш.
Встроенная поддержка TypeScript
Deno позволяет напрямую запускать TypeScript файлы без участия компилятора. Deno оптимизирует этот процесс, кэшируя полученный JavaScript и используя
SWC — быстрый компилятор на основе Rust, если проверка типов не требуется. Встроенная поддержка TypeScript повышает эффективность, поскольку вам не нужно настраивать этап сборки, если вы создаете приложение с помощью TypeScript. Существуют способы автоматической компиляции в Node.js, например, с помощью
ts-node, но они не так функциональны и не устанавливаются по умолчанию.
The State of Deno
Экосистема
В настоящее время это самая большая проблема Deno и, в тоже время, основная причина, почему разработчики Node.js не переходят на Deno. На
deno.land/x размещено 3501 модуль, а на NPM — 1.3 миллиона. Однако, многие люди используют другие услуги хостинга (см. «Децентрализованный хостинг модулей»), и большинство современных веб-пакетов должны работать на Deno. Самыми большими проблемами для совместимости с Node.js являются CommonJS и Node API. Deno обеспечивает
режим совместимости с Node.js, но он экспериментальный.
Развертывание
Deno может быть развернут довольно широко, хотя и не так широко, как Node.js
Контейнеры и виртуальные машины
Deno поддерживает различные контейнерные сервисы, а deno.land предоставляет docker при необходимости. Однако, хотя большинство популярных сервисов и поддерживают Deno, эта поддержка зачастую является неофициальной и не всегда постоянной. Вот перечень инструментов и ресурсов для запуска Deno в контейнерных сервисах:
Бессерверные вычисления
Именно здесь Deno раскрывает себя лучше всего. Основным коммерческим предложением Deno является Deno Deploy — бессерверный модуль пограничных функций. Он концептуально схож с Cloudflare Workers, так как использует изоляцию V8 для сверхбыстрого запуска. Преимущества Deno Deploy заключается в том, что оно включает в себя Deno API и другие фичи, делающие Deno таким полезным. Однако, Deno Deploy находится в бета-тестировании. Вот список инструментов для запуска Deno с помощью поставщиков бессерверных вычислений: