Практический опыт работы с MarkoJS

автор vadim


Инновации в полнофункциональных средах JavaScript для рендеринга на стороне сервера продолжаются быстрыми темпами. Marko разработан под эгидой eBay, который использует его на своем сайте электронной коммерции. Marko задуман как простой в освоении и высокопроизводительный фреймворк.

Райан Карниато, создатель SolidJS, принимал участие в разработке Marko. Он описывает его как «созданный специально для удовлетворения высоких требований к производительности платформы eBay». Учитывая, что eBay ежемесячно привлекает 307 миллионов пользователей, Марко почти наверняка справится с вашим вариантом использования.

Компоненты Марко

Давайте начнем исследование Марко с его системы компонентов. У Марко есть одна из самых простых систем определения и обнаружения компонентов, когда-либо созданных. Здесь вы можете увидеть простое определение компонента — палитру цветов. Обратите внимание, что в основном файле index.marko есть элемент HTML с именем <color-picker>, а также свойство, содержащее массив шестнадцатеричных цветов. Как Марко находит color-picker компонент?

Ответ заключается в том, что Марко начинает с каталога, в котором обнаружено использование компонента, а затем, начиная с родственных каталогов, движется вверх в поисках каталога /comComponent, содержащего требуемое определение компонента. Если в коде приложения такой компонент не найден, Марко обратится к установленным зависимостям и также просканирует их.

Обратите внимание, что Марко ищет вверх, чтобы каталоги в отдельных ветках не знали друг о друге. Это обеспечивает своего рода область видимости компонентов.

В нашем случае Марко не придется далеко ходить, потому что есть файл /comComponents/color-picker/index.marko. (Марко также будет загружать компоненты из файла с именем компонента в каталоге компонентов или файла внутри каталога компонента с именем компонента в виде папки и файла.)

Если вы посмотрите файл /comComponents/color-picker/index.marko, вы увидите определение компонента выбора цвета, показанное в листинге 1.

Листинг 1. color-picker.marko

import getDefaultColors from '../../util/getDefaultColors.js'

class {
  onInput(input) {
    var colors = input.colors || getDefaultColors();

    this.state = {
      selectedColor: colors[0],
      colors
    };
  }

  handleColorSelected(color) {
    this.state.selectedColor = color;
  }
}

<div>
  <color-picker-header color=state.selectedColor/>
  <color-picker-footer colors=state.colors on-color-selected("handleColorSelected")/>
</div>

Листинг 1 содержит основные элементы компонента. Он начинается с импорта другого файла JS с помощью оператора импорта (простая функция JavaScript, которая будет использоваться, если цвета не передаются). Далее он определяет необходимые структуры JavaScript; в данном случае это класс и функция. Последним является фактическая разметка шаблона, которая в основном включает в себя два других компонента: верхний и нижний колонтитул.

Давайте подробнее рассмотрим определение этого класса. Он определяет два метода.

Ввод свойства

Первый метод onInput(). Это метод жизненного цикла, который получает входной аргумент и позволяет изменять состояние компонента (подробнее о состоянии ниже).

Обратите внимание на входную переменную. Это зарезервированный идентификатор в Marko, который разрешается в свойства, переданные от родительского элемента выше. Помните, что основной компонент содержит свойство элемента. colors это указывало на жестко запрограммированный список шестнадцатеричных цветов. Теперь доступ к ним осуществляется дочерним компонентом через input.colors свойство. Свойства полностью реактивны, то есть система обеспечит обновление всего, что зависит от реквизитов.

Обработка событий

Второй метод класса: handleColorSelected, который является пользовательским обработчиком событий. Вы можете увидеть используемый обработчик в листинге 1, где расположен нижний колонтитул:

<color-picker-footer colors=state.colors on-color-selected("handleColorSelected")/>

Перевод: Когда on-color-selected событие сработало, вызовите handleColorSelected метод, передавая любые имеющиеся аргументы.

Штат в Марко

Состояние в Marko похоже на React в том смысле, что оно должно быть неизменным, а это означает, что необходимо назначить новое состояние для обновления одного свойства. Марко предоставляет способ принудительного запуска обновления состояния:

this.setStateDirty(property);

Как и в других реактивных средах, состояние в Marko моделирует внутреннее состояние компонента. Реактивная система отвечает за обновление пользовательского интерфейса и других значений, зависящих от этого состояния.

Итерация и вызов событий в Marko

Теперь давайте посмотрим, как компонент нижнего колонтитула делает две вещи: перебирает цветовые реквизиты и запускает их. on-color-selected событие.

Код color-picker-footer/index.marko показан в листинге 2.

Листинг 2. color-picker-footer

  <div.color-picker-footer>
  <div.color-picker-selection-container>
    <for|color| of=input.colors>
      <div>
        <color-picker-selection
          color=color
          on-color-selected("handleColorSelected", color)/>
      </div>
    </for>
    <input key="hexInput" placeholder="Hex value" on-input("handleHexInput")/>
  </div>
</div>

Вы можете видеть, что итерационная работа выполняется с помощью <for> ярлык. <for> тег может указать свою переменную-итератор с именем внутри | символы. В этом случае итератору присваивается имя color. Коллекция, по которой необходимо выполнить итерацию, идентифицируется с помощью of имущество, в данном случае имеется в виду input.colors перешло от родителя.

Каждый член input.colors переменная будет выведена как div с доступом к color переменная. По синтаксису он похож на другие фреймворки, такие как React.

Генерация событий в Марко

Большую часть работы по выбору цвета с помощью щелчка мыши выполняет color-picker-selection компонент, который выводится внутри for итератор вместе с color свойство и обработчик для on-color-selected.

В листинге 3 показано color-picker-selection компонент.

Листинг 3. Компонент выбора цвета

class {
  handleColorSelected() {
    this.emit("color-selected");
  }
}

style {
  .color-picker-selection {
    width: 25px;
    height: 25px;
    border-radius: 5px 5px 5px 5px;
    display: flex;
    flex-direction: column;
    margin: 5px 0px 0px 5px;
    float: left;
  }
}

<div.color-picker-selection
  on-click("handleColorSelected")
  on-touchstart("handleColorSelected")
  style={
    backgroundColor: input.color
  }/>

Большинство color-picker-selection посвящен определению макета (т. е. маленьких цветных квадратов, позволяющих выбирать цвет). Здесь вы видите CSS как часть структуры компонента в блоке стилей, который определяет небольшой закругленный квадрат. Обратите внимание, что вы также можете определить CSS в отдельном файле .css с именем style.css. Вы можете увидеть этот последний подход в каталоге /color-picker-selection.

В разметке шаблона обратите внимание на встроенный стиль, который используется для установки цвета фона в шестнадцатеричный цвет, заданный для input.color.

Также обратите внимание на то, как on-click и on-touchstart события используются для фиксации взаимодействия пользователя с цветным квадратом. Мероприятие передается handleColorSelected, который определен в заголовке файла. Оно использует this.emit("color-selected") выстрелить custom color-selected событие.

Напомним, что color-picker-footer часы для индивидуальных мероприятий с on-color-selected("handleColorSelected", color). Обратите внимание, что обработчик вызывает handleColorSelected и прохождение color переменная. Но где определена эта функция?

Гибкость определения компонентов

Ответ: он определен в отдельном файле компонент.js в том же каталоге, подобно отдельному файлу style.css, который вы видели ранее. Возможность поместить отдельные части компонента в один файл или в отдельные файлы (или в комбинацию того и другого) обеспечивает хорошую гибкость в определении компонентов по мере их роста от простого к сложному.

Ожидайте тега в Марко

Марко также включает в себя <await> тег для обработки асинхронного рендеринга. <await> позволяет вам передать обещание, а фреймворк будет ждать его результата и отображать его только тогда, когда он станет доступен. (Это аналог одноименного компонента в Svelte.)

<await> тег упрощает работу с асинхронным выводом.

Простая и неожиданная структура

Марко оправдывает свое обещание быть простым в обучении. Во-первых, он содержит лишь небольшое количество основных тегов, которые необходимо изучить. С другой стороны, эти теги довольно просты и работают в соответствии с принципом наименьшего неожиданности. Marko — это полнофункциональная платформа, поэтому вы также получаете готовый рендеринг на стороне сервера с интеграцией для таких серверов, как Express.

В сочетании с интуитивно понятной системой определения компонентов, сборщиками для Webpack и Rollup и высочайшей производительностью Marko дает веские основания считать, что он станет вашим следующим фреймворком JavaScript.

Related Posts

Оставить комментарий