Приятно видеть, что узел 8 сейчас входит в LTS. Участники узла проделали огромную работу привнося в узел новейшие функции ES, расширяя возможности разработчиков и повышая их производительность. Это заставляет меня думать:

Что, если мы сможем написать код с новейшими функциями ES, но по-прежнему иметь обратную совместимость для более старых узлов?

Команда babel уже проделала для нас много работы. Конечно, мы можем скомпилировать наш код в наиболее совместимую форму: ES3. Но зачем тратить время на перекомпилированный код, когда мы работаем на платформе, которая поддерживает генератор, асинхронные функции… и многое другое? Это приводит нас к экспериментальному babel-preset-env. Это позволяет нам указать платформу, которую мы хотели бы поддерживать, и настроить babeloptions так, чтобы обеспечить минимальную транспиляцию вашего кода.

Все это звучит для нас здорово. Но можем ли мы сделать лучше? Допустим, вы пишете асинхронную функцию, которая становится стабильной после node ≥ 7.6.0. Но у нас уже есть генераторы для узла ≥ 4.8.5. Что, если мы хотим поддерживать все версии для узла ≥ 0.12? У нас будет три кейса:

  1. узел ≥ 7.6.0: не переносить, использовать нативный
  2. узел ≥ 4.8.5, но узел ‹7.6.0: перенос на генераторы с regenerator-runtime
  3. узел ‹4.8.5: преобразовать в функции, имитирующие генераторы с переключателями, и запустить с regenerator-runtime

Это означает, что для одного исходного файла нам нужно будет сгенерировать три файла для разных версий. Это невозможно, учитывая, что текущее babel CLI взаимно-однозначное сопоставление. Итак, я создаю инструмент CLI:

Бабель-мульти-окр

Он сгенерирует набор файлов на основе желаемых поддерживаемых версий node.js. Каждый исходный файл станет серией случаев переключения на выходе:

var gte = require("semver").gte;
var version = process.version;

if (gte(version, "8.0.0")) {
  module.exports = require("./index__8.0.0__.js");
} else if (gte(version, "6.0.0")) {
  module.exports = require("./index__6.0.0__.js");
} else if (gte(version, "4.0.0")) {
  module.exports = require("./index__4.0.0__.js");
} else if (gte(version, "0.12.0")) {
  module.exports = require("./index__0.12.0__.js");
} else {
  module.exports = require("./index__0.10.0__.js");
}

Таким образом, теперь у нас есть транспилированные файлы, работающие с их последними наборами функций. Даёт нам:

  1. Лучшая производительность: меньше накладных расходов на транспиляцию
  2. Улучшенный опыт отладки: собственные асинхронные функции похожи на легкий ветерок

Хотите попробовать сразу? Перейдите на страницу GitHub и узнайте больше:



Рад слышать ваши мысли / отзывы!