Управление состоянием в Alpine.js с использованием Spruce
Если вы использовали фреймворки JavaScript, такие как React и Vue.js, то, возможно, вы уже знакомы с концепцией управления состоянием, которая создает способ взаимодействия и обмена данными между компонентами.
В идеале пользователям требуется управление состоянием, когда их приложение имеет два или более компонента, которые должны обмениваться данными и обмениваться данными без необходимости объявлять данные в области действия каждого компонента и вручную передавать их. Как правило, у пользователей есть какое-то хранилище, которое служит единым источником истины для состояния / данных приложения.
Alpine.js, относительно новые JavaScript фреймворк, который заимствует понятия из React и Vue.js, а также имеет свою собственную реализацию управления состоянием через библиотеку под названием Spruce. Spruce - это легкая библиотека управления состоянием для Alpine.js и как и Alpine.js, Spruce проста и занимает мало места.
Что мы строим
В этой статье мы создадим простое приложение для выполнения задач, которое состоит из двух компонентов: ввода для добавления новых задач и таблицы, отображающей список задач. Это даст нам возможность получить доступ к состоянию из глобального хранилища внутри двух независимых компонентов.
Начало работы с Spruce
Для начала создадим новый каталог проекта, который мы назовем: alpine-spruce-todo
mkdir alpine-spruce-todo
Затем создайте файл index.html
в каталоге проекта.
cd alpine-spruce-todo
touch index.html
Как и Alpine.js, Spruce можно установить либо из CDN, либо с помощью npm или Yarn. В этом руководстве мы будем использовать CDN. Добавьте внутрь index.html
следующий код:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<meta http-equiv="X-UA-Compatible" content="ie=edge">
<title>Todo</title>
<link
rel="stylesheet"
href="https://cdn.jsdelivr.net/npm/bulma@0.9.0/css/bulma.min.css"
/>
<script src="https://cdn.jsdelivr.net/npm/@ryangjchandler/spruce@1.1.0/dist/spruce.umd.js"></script>
<script src="https://cdn.jsdelivr.net/npm/alpinejs@2.6.0/dist/alpine.min.js"></script>
</head>
<body>
<section class="section">
<div class="container">
<div class="columns">
<div class="column is-three-fifths is-offset-one-fifth">
Поскольку мы используем CDN, нам нужно загрузить Spruce перед Alpine.js. Для стилизации воспользуемся Bulma CSS, который мы также извлечем из CDN.
Создание глобального стора
Чтобы начать использовать Spruce, нам нужно определить глобальное хранилище, которое будет служить единым источником истины для всех компонентов нашего приложения. Создадим глобальный стор нашего приложения.
Добавьте следующий фрагмент непосредственно перед закрывающим тегом body:
<script>
Spruce.store('todo', {
todos: [],
})
</script>
Мы используем сборку CDN, что означает, что Spruce доступен в области окна. Используя переменную Spruce
, мы вызываем метод store
для создания хранилища.
Метод принимает два аргумента: имя хранилища и состояние (данные) хранилища. Поскольку мы создаем приложение todo, имеет смысл назвать наше хранилище todo
. В хранилище есть только одно состояние (todos
), которое представляет собой массив задач, который мы сделаем пустым по умолчанию.
Доступ к состоянию
Имея глобальное хранилище, нам теперь нужно определить, как получить доступ к хранилищу из наших компонентов. К счастью для нас, Spruce делает это бесшовным, демонстрируя волшебное свойство $store
.
Замените текст «component goes here» следующим кодом:
<div x-data="{}">
<template x-if="$store.todo.todos.length">
<div class="box mt-5">
<table class="table is-fullwidth">
<tbody>
<template
x-for="(todo, index) in $store.todo.todos"
:key="index"
>
<tr>
<td x-text="todo.title"></td>
</tr>
</template>
</tbody>
</table>
</div>
</template>
</div>
Это типичный компонент Alpine.js, но вы заметите, что мы не объявляли область действия для этого компонента. Это потому, что мы хотим использовать данные из нашего глобального хранилища, чтобы мы могли получить доступ к хранилищу todo
, используя $store.todo
, а затем и свойствам хранилища.
Сначала мы проверим, содержит ли массив todos
несколько задач. Затем мы отобразим задачи в таблице путем итерации по массиву todos
.
Изменение состояния магазина
Мы видели, как получить доступ к состоянию в хранилище. Что, если мы хотим изменить состояние? Для этого мы выполняем шаги, аналогичные тому, что уже сделали. Чтобы изменить состояние, мы просто переназначим ему новое значение. Но поскольку мы работаем с массивом как с нашим состоянием, нам придется помещать в массив новые элементы.
Добавьте следующий код перед предыдущим компонентом:
<div x-data="todoInput()">
<div class="field">
<div class="control">
<input
type="text"
class="input"
x-model="newTodo"
placeholder="What needs to be done?"
@keyup.enter="addTodo"
/>
</div>
</div>
</div>
Это типичный компонент Alpine.js, но на этот раз компонент имеет некоторую собственную область действия, которую мы извлекаем в отдельную функцию под названием todoInput()
. Входные данные привязываются к новым данным Todo
, и как только клавиша enter
нажата, мы вызываем метод addTodo
.
Создадим функцию. Добавьте приведенный ниже фрагмент после кода для определения хранилища Spruce:
function todoInput() {
return {
newTodo: '',
addTodo() {
if (!this.newTodo) {
return
}
this.$store.todo.todos.push({
title: this.newTodo,
})
this.newTodo = ''
}
}
}
Поскольку мы получаем доступ к хранилищу из функции, нам нужно использовать this
. Мы просто добавляем новую задачу в массив todos
.
Вывод
В этом руководстве мы рассмотрели определение управления состоянием, а также почему и когда его использовать. Мы также узнали, как применять управление состоянием в Alpine.js с помощью Spruce, и увидели, как получить доступ к состоянию хранилища и изменить его.