UniqueEntity в нескольких полях не отображает сообщение об ошибке

Я добавил к своей сущности следующее ограничение:

 * @ORM\Table(name="link", uniqueConstraints={@ORM\UniqueConstraint(name="unique_link_idx", columns={"first_form_id", "first_question_id","last_form_id","last_question_id"})})
 * @UniqueEntity(fields={"firstForm", "firstQuestion","lastForm","lastQuestion"}, message="Cette liaison existe déjà !")
 * @ORM\Entity(repositoryClass="Ineat\LinkQuestionBundle\Entity\LinkRepository")

Ограничение UniqueEntity работает хорошо, потому что перед его добавлением при попытке вставить ту же самую сущность в БД у меня было ограничение целостности DBALException abount. С тех пор у меня больше не было этого исключения, форма не проверяется, но {{ form_errors(form) }} не выводит никаких сообщений.

После проверки контроллер $form->getErrors() возвращает пустой массив, а $form->getErrorsAsString() содержит ограничение UniqueENtity.

Как я могу отобразить сообщение об ошибке ограничения UniqueEntity


person DevAntoine    schedule 25.06.2013    source источник
comment
getErrorsAsString() обращается к тому же свойству, что и getErrors(), а именно к this->errors в Symfony / Component / Form / Form, поэтому $form->getErrors() возврат пустого массива невозможен. Взгляните на github.com/ symfony / symfony / blob / master / src / Symfony / Component /   -  person Nicolai Fröhlich    schedule 25.06.2013
comment
Нет, он обращается только к $ this- ›children, тогда как getErrors обращается только к ошибкам.   -  person DevAntoine    schedule 25.06.2013
comment
ну, тогда ограничение uniqueEntity исходит от одной из ваших дочерних форм ... вы должны были это сказать.   -  person Nicolai Fröhlich    schedule 25.06.2013


Ответы (2)


Поскольку проверка UniqueEntity, похоже, не работает в одной из ваших дочерних форм ...

(поскольку сообщение об ошибке присутствует только в getErrorsAsString, а не в getErrors)

... чтобы ошибки дочерней формы были доступны в вашей родительской форме, используйте всплытие ошибок:

$formBuilder->add('child-form','child-form-type', array(
       'error_bubbling' => true,
   )
)

... или внутри вашей дочерней формы:

public function setDefaultOptions(OptionsResolverInterface $resolver)
{
    $resolver->setDefaults(array(
        'error_bubbling' => true,
    ));
}
person Nicolai Fröhlich    schedule 25.06.2013
comment
error_bubling в моей глобальной форме не работает, мне пришлось добавить его в каждую дочернюю форму, почему? - person DevAntoine; 25.06.2013
comment
используя ->add() или используя setDefaultOptions()? setDefaultOptions в дочерней форме, конечно, - отредактировал ответ, чтобы сделать его более понятным. всплытие ошибок информирует родительские формы об ошибках - person Nicolai Fröhlich; 25.06.2013
comment
Спасибо. На мой взгляд, error_bubbling по умолчанию должен иметь значение true. - person DevAntoine; 25.06.2013

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

# src/Ineat/LinkQuestionBundle/Resources/config/validation.yml
Ineat\LinkQuestionBundle\Entity\LinkRepository:
    constraints:
        - Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity:
            fields: [firstForm, firstQuestion, lastForm, lastQuestion]
            errorPath: lastQuestion
            message: 'This port is already in use on that host.'

Дополнительная информация здесь: Symfony - UniqueEntity

Также хорошей практикой является размещение текстовых строк в файлах «перевода» (даже если вы используете / имеете только один язык). У вас не будет фрагментов текста, лежащих в вашем views / entities / forms / controllers .... Все они будут в вашей папке переводов в одном месте. При необходимости повторяющиеся строки также можно изменить сразу. Это выглядело бы так:

# src/Ineat/LinkQuestionBundle/Resources/config/validation.yml
Ineat\LinkQuestionBundle\Entity\LinkRepository:
    constraints:
        - Symfony\Bridge\Doctrine\Validator\Constraints\UniqueEntity:
            fields: [firstForm, firstQuestion, lastForm, lastQuestion]
            errorPath: lastQuestion
            message: 'linkquestion.form.errors.unique'

# src/Ineat/LinkQuestionBundle/Resources/translations/validators.fr.yml
linkquestion:
  form:
    errors:
      unique: "This port is already in use on that host."
# Or which ever structure you choose.

Тогда просто сообщите своему приложению, что оно всегда будет на французском языке.

person Sparkup    schedule 29.01.2015