Я медленно создаю свои навыки Зенда путем создания некоторых служебных веб-сайтов для моего собственного использования. Я использовал Формы Зенда и проверку Формы и до сих пор был рад, что понимал Зенд способ сделать вещи. Однако я немного перепутан с тем, как использовать Zend_Validate_Db_NoRecordExists () в контексте формы редактирования и поля, которое отображается на столбец базы данных, который должен быть уникальным.
Например, с помощью этой простой таблицы
TABLE Test
(
ID INT AUTO_INCREMENT,
Data INT UNIQUE
);
Если бы я просто добавлял новую строку к Тесту Таблицы, то я мог бы добавить блок проверки допустимости к элементу Формы Зенда для Поля данных как такового:
$data = new Zend_Form_Element_Text('Data');
$data->addValidator( new Zend_Validate_Db_NoRecordExists('Test', 'Data') )
При проверке формы этот блок проверки допустимости проверит, что содержание Элемента данных уже не существует в таблице. Таким образом вставка в Тест может идти вперед, не нарушая Поля данных УНИКАЛЬНЫЙ спецификатор.
Однако ситуация отличается при редактировании существующей строки таблицы Test. В этом случае блок проверки допустимости должен проверить, что значение элемента удовлетворяет одному из двух взаимоисключающих условий условий:
Пользователь изменил значение элемента, и новое значение в настоящее время не существует в таблице.
Пользователь Не изменил значение элемента. Таким образом значение действительно в настоящее время существует в таблице (и это в порядке).
Документы Проверки Зенда говорят о добавлении параметра к NoRecordExists () блок проверки допустимости в целях исключения записей от процесса проверки. Причем идея состоит в том, чтобы "проверить таблицу, ища любые строки соответствия, но проигнорировать любые хиты, где поле имеет это определенное значение". Такой вариант использования - то, что необходимо для проверки элемента при редактировании таблицы. Псевдо код, чтобы сделать это в 1,9 похоже так (на самом деле, я получил это от 1,9 исходных кодов - я думаю, что текущие документы могут быть неправильными):
$data = new Zend_Form_Element_Text('Data');
$data->addValidator( new Zend_Validate_Db_NoRecordExists('Test', 'Data',
array ('field'=>'Data', 'Value'=> $Value) );
Проблема состоит в том, что значение, которое должно быть исключено ($Value), связывается с блоком проверки допустимости в то время, когда это инстанцируют (также, когда форма инстанцируют). Но когда форма редактирует запись, то значение должно быть связано с содержанием поля $data, когда форма была первоначально заполнена с данными - IE Значение данных, первоначально считанное из Тестовой строки таблицы. Но на типичном Пехлеви копирует форму, инстанцирован и заполнен на двух отдельных шагах, который устраняет связывать исключить значение с желаемым значением элемента.
Следующий Зенд psuedo кодирует метки, где я хотел бы, чтобы привязка $Value к NoRecordExists () блок проверки допустимости произошла (и отметить, что это - общий шаблон контроллера Зенда):
$form = new Form()
if (is Post) {
$formData = GetPostData()
if ($form->isValid($formData)) {
Update Table with $formData
Redirect out of here
} else {
$form->populate($formData)
}
} else {
$RowData = Get Data from Table
$form->populate($RowData) <=== This is where I want ('value' => $Value) bound
}
Я мог разделить Zend_Form на подклассы и переопределить заполнение () метод, чтобы сделать одноразовую вставку NoRecordExists () блок проверки допустимости на начальном населении формы, но это походит на огромный взлом мне. Таким образом, я хотел знать то, что думают другие люди и есть ли некоторый шаблон, уже записанный, который решает эту проблему?
Редактирование 04.02.2009
Я думал, что единственное достойное решение этой проблемы состоит в том, чтобы записать нестандартный элемент верификации и забыть о версии Зенда. Моя форма имеет рекордный идентификатор как скрытое поле, так, чтобы, учитывая имена таблиц и имена столбцов я мог обработать некоторый SQL, чтобы протестировать на уникальность и исключить строку с идентификатором такой такого. Конечно, это запустило меня думающий о том, как я буду связывать форму со слоем дБ, который Модель, как предполагается, скрывает!
После изучения подавляющего числа откликов я решил, что буду использовать пользовательский валидатор
Вы можете просто позвонить $ Form-> GetElement («вход») -> Removevalidator ('zend_validator_db_norecordexists');
вместо того, чтобы поставлять исключение.