В предыдущем уроке я показал, как настроить как серверную, так и клиентскую части Discourse для обработки запроса.
Теперь мы рекомендуем вам ознакомиться с документацией по компонентам Ember: Introducing Components - Components - Ember Guides
Старый урок
В этом уроке я создам новый компонент Ember как способ инкапсуляции стороннего JavaScript-кода. Это будет похоже на видео с YouTube, которое я снял некоторое время назад и которое, возможно, окажется полезным. Однако в этот раз речь пойдёт конкретно о Discourse и о том, как мы организуем файлы в нашем проекте.
Зачем нужны компоненты?
Handlebars — довольно простой и привлекательный язык. Это обычный HTML с добавлением динамических частей. Он лёгок в освоении и отлично подходит для повышения продуктивности, но не так хорош для повторного использования кода. Если вы разрабатываете большое приложение, такое как Discourse, вы обнаружите, что хотите многократно использовать одни и те же элементы.
Компоненты — это решение этой проблемы в Ember. Давайте создадим компонент, который будет отображать наш «закуску» более красиво.
Создание нового компонента
Имена компонентов должны содержать дефис. Я выберу fancy-snack в качестве имени для этого компонента. Давайте создадим наш шаблон:
app/assets/javascripts/admin/templates/components/fancy-snack.hbs
<div class="fancy-snack-title">
<h1>{{snack.name}}</h1>
</div>
<div class="fancy-snack-description">
<p>{{snack.description}}</p>
</div>
Теперь, чтобы использовать наш компонент, мы заменяем существующий шаблон admin/snack следующим:
app/assets/javascripts/admin/templates/snack.hbs
{{fancy-snack snack=model}}
Теперь мы можем повторно использовать компонент fancy-snack в любом другом шаблоне, просто передавая модель по мере необходимости.
Добавление пользовательского JavaScript-кода
Помимо возможности повторного использования, компоненты в Ember отлично подходят для безопасного добавления пользовательского JavaScript, jQuery и другого внешнего кода. Они дают вам контроль над тем, когда компонент вставляется на страницу и когда удаляется. Для этого мы определяем Ember.Component с некоторым кодом:
app/assets/javascripts/admin/components/fancy-snack.js
export default Ember.Component.extend({
didInsertElement() {
this._super();
this.$().animate({ backgroundColor: "yellow" }, 2000);
},
willDestroyElement() {
this._super();
this.$().stop();
},
});
Если вы добавите код выше и обновите страницу, вы увидите, что наша «закуска» имеет анимацию плавного появления жёлтого фона.
Давайте объясним, что здесь происходит:
-
Когда компонент отображается на странице, вызывается метод
didInsertElement. -
Первая строка
didInsertElement(иwillDestroyElement) — этоthis._super(), что необходимо, поскольку мы наследуемся от Ember.Component. -
Анимация выполняется с помощью функции jQuery’s animate.
-
Наконец, анимация отменяется в хуке
willDestroyElement, который вызывается, когда компонент удаляется со страницы.
Вы можете спросить, зачем нам вообще нужен willDestroyElement. Причина в том, что в долгоживущем JavaScript-приложении, таком как Discourse, важно очищать за собой, чтобы избежать утечек памяти или оставить работающие процессы. В данном случае мы останавливаем анимацию, что сообщает любым таймерам jQuery, что им больше не нужно срабатывать, так как компонент больше не виден на странице.
Куда двигаться дальше
Финальный урок в этой серии посвящён автоматизированному тестированию.
Этот документ находится под контролем версий — предлагайте изменения на GitHub.