CMS.Fields

Модуль CMS.Fields был создан для упрощения процесса создания, отрисовки, процессинга и валидации форм. Данный механизм основан на том, что всякая форма представляет собой набор полей, каждое из которых имеет строго определенный тип и обладает неким набором дополнительных параметров. Если описать этот набор полей, то на основании данного списка можно автоматически создать форму, отрисовать ее, принять данные, произвести валидацию, записать данные в объект и т.п.

В системе зарегистрирован некий список типов полей, который можно расширять своими типами полей. В данном случае тип поля - это объект, который описывает поведение поля: как оно представлено в объекте формы, как отображается на странице редактирования, как валидируется и пр.

Исходные данные для формы

Исходные данные представляются в виде ассоциативного массива, ключами которого являются имена полей. Элемент этого массива - массив с описанием параметров поля.

Пример:

$fields = array(

  'title' => array(
    'type' => 'input',
    'caption' => 'Наименование',
  ),

  'chapter' => array(
    'type' => 'select',
    'items' => array(
       1 => 'Лопаты',
       2 => 'Молотки',
       3 => 'Микроскопы',
    ),
    'caption' => 'Раздел',
  ),

  'description' => array(
    'type' => 'textarea',
    'caption' => 'Описание',
  ),

);

Создание формы

Core::load('CMS.Fields');

// Создаем форму обычным способом
$form = Forms::Form($name)->action($url);

// Добавляем поля
CMS_Fields::form_fields($form,$fields);

// Добавляем еще один блок полей
CMS_Fields::form_fields($form,$fields_extra);

В описанном примере будет создана форма с валидаторами (которые описываются в параметрах полей).

Присвоение значений из объекта

CMS_Fields::assign_from_object($form,$object,$fields);

Отрисовка формы

Механизм CMS.Fields выводит только HTML-код набора полей и ничего более. Заголовок/футер формы предлагается выводить обычным способом.

Будем считать, что сверстанная форма представляет собой двухколоночную структуру, в левой стороне которой отображены наименования полей, а в правой - сами поля. Бывает, конечно, и сложнее, но мы этот вариант рассматривать не будем, т.к. это во-первых, редко, а во-вторых, никто не мешает сверстать вручную обычным способом.

Полученный HTML-код может быть разным. По крайней мере, есть два варианта: блочный и табличный. Блочный вариант, конечно, православнее, однако при его использовании крайне желательно задавать ширины двух вышеупомянутых колонок, и это обстоятельство не добавляет такой верстке универсальности. Представьте себе, к примеру, админку. Там бывают случаи, когда программист заранее не может сказать про форму вообще ничего: ни набора полей, ни их наименований (да еще их многоязычных версий), ни ширины экрана. Как задавать ширину - непонятно.

Табличная верстка в этом плане гораздо гибче.

Для решения этой проблемы введено понятие обрамления (layout). Сейчас существует два варианта вывода набора полей: блочный по умолчанию и табличный - 'table'.

Вывод формы в блочном варианте:

 <?= $this->forms->begin_form($form,array('class' => 'registration validable')); ?>
 <div id="mycoolform">
    <?= $this->fields->draw($fields) ?>
 </div>
 <?= $this->forms->end_form($form) ?>

Ширины колонок и прочее оформление здесь можно задать в CSS-свойствах объекта mycoolform и его вложенных объектов.

Вывод формы в табличном варианте:

 <?= $this->forms->begin_form($form,array('class' => 'registration validable')); ?>
 <table id="mycoolform">
    <?= $this->fields->draw($fields,'table') ?>
 </table>
 <?= $this->forms->end_form($form) ?>

Процессинг формы и запись полей в объект

Для процессинга существует функция CMS_Fields::process_form, которая не сильно отличается от стандартного метода $form->process. Для простоты она всегда возвращает массив строк - сообщений об ошибках. Если массив пуст, то процессинг прошел удачно. При желании можно использовать обычный способ.

Запись полей в объект осуществляется функцией CMS_Fields::assign_to_object.

  $errors = CMS_Fields::process_form($form,$this->env->request);
  if (count($errors)==0) {
    CMS_Fields::assign_to_object($form,$object,$fields);
    self::db()->mytable->update($object);
    return $this->redirect_to('/');
  }
  else {
    // Отрисуем форму с сообщениями об ошибках
  }

Валидация

Сам процесс валидации происходит автоматически как на стороне клиента (JS), так и на стороне сервера (PHP). Как производить валидацию введенного значения - задача каждого конкретного типа поля, который должен при создании формы создать для этого и валидационные тесты, основываясь на информации из массива, описывающего набор полей формы. Подробно это будет описано в отдельных статьях, посвященных конкретным типам полей.

Можно кратко остановиться на валидации текстовых полей:

  $fields = array(
    'name' => array(
      'caption' => 'Имя',
      'validate_presence' => 'Введите имя!',
    ),
    'email' => array(
      'caption' => 'E-Mail',
      'validate_presence' => 'Введите E-Mail!',
      'validate_email' => 'E-Mail некорректный!',
    ),
    'phone' => array(
      'caption' => 'Телефон',
      'validate_match' => '{^[0-9-]*$}',
      'validate_match_message' => 'Телефон некорректный!',
    ),
    'password' => array(
      'caption' => 'Пароль',
      'type' => 'password',
      'validate_presence' => 'Пароль не может быть пустым!',
    ),
    'password2' => array(
      'caption' => 'Еще раз пароль',
      'type' => 'password',
      'validate_confirmation' => 'password',
      'validate_confirmation_message' => 'Пароль и его копия не совпадают!',
    ),
  );

Думаю, вышеописанное понятно и без объяснений.

Что дальше:

Метки: CMS
14.07.2014
Все статьи