Frontend
October 15, 2023

Работа с формами в Angular: Reactive Forms, Template-driven Forms

Формы в Angular

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

Разработчики Angular уделили формам особое внимание и предоставили гибкие инструменты для их создания. В Angular есть два основных подхода к разработке форм - Template-driven и Reactive. Далее мы подробно разберем оба подхода, рассмотрим их особенности и отличия.

Template-driven формы

Template-driven формы, как видно из названия, описываются с помощью шаблонов Angular. Их логика заключена непосредственно в разметке компонента.

Рассмотрим пример простой формы поиска:

<form>

  <input type="text" name="search" ngModel>

  <button type="submit">Найти</button>

</form>

Здесь мы используем директиву ngModel для связывания поля ввода с переменной в компоненте. Это позволяет реализовать двустороннее (two-way) привязку: данные автоматически передаются из поля ввода в компонент и обратно.

Кроме того, кнопка имеет атрибут type="submit", который позволяет отправлять данные формы по нажатию на эту кнопку.

Для валидации полей формы в Template-driven подходе используются такие директивы как required, minlength, maxlength и другие. Например:

<input name="username" ngModel required minlength="5">

Это поле будет обязательным для заполнения и должно содержать минимум 5 символов.

Также важный момент - доступ к данным формы из кода компонента. Это можно сделать через ссылку на форму и обращение к ее свойствам и методам.

Например:

@ViewChild('myForm') form: NgForm;

onSubmit() {
  console.log(this.form.value); 
}

Здесь мы получаем значения всех полей формы по нажатию на кнопку отправки.

Таким образом, в Template-driven формах вся логика сосредоточена в шаблоне компонента. Это делает их простыми в использовании, особенно для небольших форм.

Reactive формы

В отличие от предыдущего подхода, в Reactive формах логика выносится из шаблона в код компонента. Для описания формы используются специальные классы FormControl, FormGroup из пакета @angular/forms.

Рассмотрим пример:

// Компонент

searchForm = new FormGroup({
  searchInput: new FormControl('')
});

onSubmit() {
  console.log(this.searchForm.value);
}
<!-- Шаблон -->

<form [formGroup]="searchForm">

  <input formControlName="searchInput">
  
  <button type="submit">Найти</button>

</form>

Здесь мы создаем форму searchForm типа FormGroup, в которую добавляем поле searchInput типа FormControl.

В шаблоне мы указываем привязку [formGroup] к этой форме, а полю ввода назначаем formControlName равный имени поля в форме.

Получается, что все данные формы теперь хранятся в объекте searchForm, до которого легко можно добраться из кода компонента.

Для валидации полей используются методы setValidators или передача валидаторов при создании FormControl:

searchInput: new FormControl('', Validators.required)

Такой подход дает ряд преимуществ:

  • Логика формы отделена от шаблона
  • Легче тестировать код формы
  • Удобнее отслеживать состояние формы и полей
  • Мощные возможности асинхронной валидации

Но Reactive формы также требуют больше кода для реализации, чем Template-driven.

Сравнение подходов

Давайте теперь сравним оба подхода, чтобы понять их различия:

Template-driven формы:

  • Проще и быстрее для создания простых форм
  • Вся логика в шаблоне компонента
  • Используют двустороннее связывание
  • Поддерживают простую валидацию через директивы

Reactive формы:

  • Логика реализуется в коде компонента
  • Лучше для сложных форм и асинхронной валидации
  • Гибкость в настройке и валидации полей
  • Удобные инструменты для слежения за состоянием формы
  • Больше кода для реализации

Как видно из сравнения, оба подхода имеют свои плюсы и минусы.

Template-driven удобны для простых случаев, когда нужно быстро создать форму и не требуется сложная валидация.

Reactive лучше подходят для больших и динамических форм. За счет гибкости настройки они могут обрабатывать сложные сценарии.

Как выбрать подход?

При выборе между Template-driven и Reactive формами стоит учитывать следующее:

  • Сложность формы. Для простых форм удобнее Template-driven.
  • Требования к валидации. Reactive удобнее для асинхронной валидации.
  • Объем кода. Template-driven требуют меньше кода.
  • Тестирование. Reactive проще тестировать благодаря четкому разделению логики.
  • Гибкость. Reactive позволяют динамически менять форму.
  • Опыт разработчика. Новичкам проще начать с Template-driven.

Для небольшой формы регистрации или поиска лучше выбрать Template-driven формы. А вот для многошаговой формы заказа товара удобнее использовать Reactive approach.

При этом, опытные разработчики могут реализовать сложные сценарии и с Template-driven формами. А новички быстрее освоят простые Reactive формы.

Поэтому жестких правил здесь нет - выбирайте подход исходя из конкретных требований и вашего опыта!

Итог

Мы познакомились с двумя основными подходами к созданию форм в Angular:

  • Template-driven формы описывают логику в шаблоне компонента. Они проще для небольших форм.
  • Reactive формы реализуют логику в коде компонента, используя объекты FormControl, FormGroup. Этот подход гибче настраивается.

Также мы рассмотрели конкретные примеры и сравнили оба подхода по разным критериям. Выбор между ними зависит от требований и опыта разработчика.

Рекомендую использовать оба варианта в практических проектах - это поможет глубже разобраться в их возможностях.