Injecter les erreurs sous une forme déjà validée?

97

Après avoir form.Formvalidé les valeurs d'entrée de l'utilisateur, je les transmets à un processus (externe) distinct pour un traitement ultérieur. Ce processus externe peut potentiellement trouver d'autres erreurs dans les valeurs.

Existe-t-il un moyen d'injecter ces erreurs dans le formulaire déjà validé afin qu'elles puissent être affichées via les méthodes habituelles d'affichage des erreurs de formulaire (ou existe-t-il de meilleures approches alternatives)?

L'une des suggestions était d'inclure le traitement externe dans la validation du formulaire, ce qui n'est pas idéal car le processus externe fait beaucoup plus que simplement valider.

Parand
la source

Réponses:

92

Form._errorspeut être traité comme un dictionnaire standard. Il est considéré comme une bonne forme d'utiliser la ErrorListclasse et d'ajouter des erreurs à la liste existante:

from django.forms.utils import ErrorList
errors = form._errors.setdefault("myfield", ErrorList())
errors.append(u"My error here")

Et si vous souhaitez ajouter des erreurs hors champ, utilisez django.forms.forms.NON_FIELD_ERRORS(par défaut "__all__") au lieu de "myfield".

John Millikin
la source
2
Cela semble un peu désagréable, car le nom "_errors" suggère qu'il est censé être interne à la classe de formulaire. Est-ce la manière standard de faire cela dans Django? Je suis dans une situation similaire à l'OP: j'ai un formulaire dans lequel les utilisateurs fournissent un nouveau nom qui doit être unique dans la base de données. S'il y a une collision, j'aimerais renvoyer le formulaire avec une erreur, mais je ne le saurai pas avant d'essayer de faire l'insertion de la base de données. (En théorie, le validateur pourrait vérifier la base de données, mais cela sent et est propice à la course.)
Weeble
1
@scompt: merci, corrigé. @Weeble: _errorsfait partie de l'API de forme publique, malgré son nom; voir la réponse d'insin pour un lien vers les documents.
John Millikin
18
C'est incroyablement non pythonique. Quelle a été la difficulté d'implémenter form.errors ['myfield']. Append (my_error) ou form.add_error ('myfield', my_error)? Trop de place pour l'erreur (sans jeu de mots) dans la mise en œuvre actuelle.
Michael
2
Surtout complet. Une note supplémentaire est que si is_valid () n'a pas été appelé, vous devrez définir form._errors = ErrorDict ()
jacob
12
@Michael - on dirait qu'ils ont suivi votre conseil ... Django Dev - Form.add_error (champ, erreur)
Clayton
14

Vous pouvez ajouter des détails d'erreur supplémentaires à l' _errorsattribut du formulaire directement:

https://docs.djangoproject.com/en/1.5/ref/forms/validation/#described-later https://docs.djangoproject.com/en/1.6/ref/forms/validation/#modifying-field-errors

Jonny Buchanan
la source
6
Et apparemment dans la version de développement post 1.6, ils ajoutent une add_errorfonction: docs.djangoproject.com/en/dev/ref/forms/api
...
Et maintenant Django 1.7 a une fonction add_error officielle: docs.djangoproject.com/en/1.7/ref/forms/api/…
Danilo Cabello
0

Ajouter une erreur à un champ spécifique:

form.add_error('fieldName', 'error description')

** Ajouter une erreur aux non-champs **

form.add_error(None, 'error description')
#Only pass None instead of field name
Muhammad Faizan Fareed
la source