Comment obtenir la collection d'erreurs dans une vue?
Je ne souhaite pas utiliser le résumé ou le message de validation de l'assistant d'aide HTML. Au lieu de cela, je veux vérifier les erreurs et, le cas échéant, les afficher dans un format spécifique. Également sur les contrôles d'entrée, je souhaite vérifier une erreur de propriété spécifique et ajouter une classe à l'entrée.
P.S. J'utilise le moteur de visualisation Spark), mais l'idée devrait être la même.
Alors j'ai pensé que je pourrais faire quelque chose comme ...
<if condition="${ModelState.Errors.Count > 0}">
DispalyErrorSummary()
</if>
....and also...
<input type="text" value="${Model.Name}"
class="?{ModelState.Errors["Name"] != string.empty} error" />
....
Ou quelque chose comme ça.
MISE À JOUR
Ma solution finale ressemblait à ceci:
<input type="text" value="${ViewData.Model.Name}"
class="text error?{!ViewData.ModelState.IsValid &&
ViewData.ModelState["Name"].Errors.Count() > 0}"
id="Name" name="Name" />
Cela n’ajoute la classe css d’erreur que si cette propriété a une erreur.
<% ViewData.ModelState.IsValid %>
ou
<% ViewData.ModelState.Values.Any(x => x.Errors.Count >= 1) %>
et pour une propriété spécifique ...
<% ViewData.ModelState["Property"].Errors %> // Note this returns a collection
Pour obtenir uniquement les erreurs du ModelState, utilisez ce Linq:
var modelStateErrors = this.ModelState.Keys.SelectMany(key => this.ModelState[key].Errors);
Version condensée de réponse de ChrisMcKenzie :
var modelStateErrors = this.ModelState.Values.SelectMany(m => m.Errors);
Cela vous donnera une chaîne avec toutes les erreurs avec séparateur de virgule
string validationErrors = string.Join(",",
ModelState.Values.Where(E => E.Errors.Count > 0)
.SelectMany(E => E.Errors)
.Select(E => E.ErrorMessage)
.ToArray());
Merci Tchad! Pour afficher toutes les erreurs associées à la clé, voici ce que j'ai proposé. Pour une raison quelconque, l’assistant de base Html.ValidationMessage n’affiche que la première erreur associée à la clé.
<%= Html.ShowAllErrors(mykey) %>
HtmlHelper:
public static String ShowAllErrors(this HtmlHelper helper, String key) {
StringBuilder sb = new StringBuilder();
if (helper.ViewData.ModelState[key] != null) {
foreach (var e in helper.ViewData.ModelState[key].Errors) {
TagBuilder div = new TagBuilder("div");
div.MergeAttribute("class", "field-validation-error");
div.SetInnerText(e.ErrorMessage);
sb.Append(div.ToString());
}
}
return sb.ToString();
}
En rassemblant plusieurs réponses venant d’en haut, c’est ce que j’ai utilisé:
var validationErrors = ModelState.Values.Where(E => E.Errors.Count > 0)
.SelectMany(E => E.Errors)
.Select(E => E.ErrorMessage)
.ToList();
validationErrors
finit par être un List<string>
qui contient chaque message d'erreur. À partir de là, il est facile de faire ce que vous voulez avec cette liste.
Voici le VB.
Dim validationErrors As String = String.Join(",", ModelState.Values.Where(Function(E) E.Errors.Count > 0).SelectMany(Function(E) E.Errors).[Select](Function(E) E.ErrorMessage).ToArray())
Si vous ne savez pas quelle propriété a causé l'erreur, vous pouvez, en utilisant la réflexion, boucler sur toutes les propriétés:
public static String ShowAllErrors<T>(this HtmlHelper helper) {
StringBuilder sb = new StringBuilder();
Type myType = typeof(T);
PropertyInfo[] propInfo = myType.GetProperties();
foreach (PropertyInfo prop in propInfo) {
foreach (var e in helper.ViewData.ModelState[prop.Name].Errors) {
TagBuilder div = new TagBuilder("div");
div.MergeAttribute("class", "field-validation-error");
div.SetInnerText(e.ErrorMessage);
sb.Append(div.ToString());
}
}
return sb.ToString();
}
Où T est le type de votre "ViewModel".