ModelState.IsValid == falso, ¿por qué?

120

¿Dónde puedo encontrar la lista de errores que invalidan ModelState? No vi ninguna propiedad de errores en el objeto ModelState.

Omu
fuente

Respuestas:

45

Acerca de "puede ser que 0 errores e IsValid == false": aquí está el código fuente MVC de https://github.com/Microsoft/referencesource/blob/master/System.Web/ModelBinding/ModelStateDictionary.cs#L37-L41

public bool IsValid {
    get {
        return Values.All(modelState => modelState.Errors.Count == 0);
    }
}

Ahora, parece que no puede ser. Bueno, eso es para ASP.NET MVC v1.

queen3
fuente
Me parece que no debería, ¿hay algo mal en Values.All (modelState => modelState.Errors.Count == 0)?
Omu
Tenga en cuenta que el error puede ser Mensaje o Excepción; por ejemplo, Html.ValidationSummary no muestra excepciones (por razones de seguridad, supongo); tal vez por eso no ves errores? ¿Cómo verifica que no haya errores?
queen3
1
ModelState.IsValid da falso
Omu
Ja, ja, eso es obvio ... ¿cómo se comprueba si los valores tienen 0 errores?
queen3
258

Como probablemente esté programando en Visual Studio, será mejor que aproveche la posibilidad de usar puntos de interrupción para pasos de depuración tan sencillos (para hacerse una idea de cuál es el problema como en su caso). Simplemente colóquelos justo en frente / en el lugar donde marca ModelState.isValid y coloque el cursor sobre ModelState. Ahora puede navegar fácilmente a través de todos los valores dentro y ver qué error causa el retorno falso de isvalid.

modelstate

bastijn
fuente
3
¿Podría ser posible que todos los valores tengan 0 errores y el estado del modelo aún no sea válido?
Omu
como se dijo anteriormente, no, esto no es posible :). ¡En algún lugar debe haber un recuento de errores! = 0.
Bastijn
2
Como complemento, si ErrorMessage es ambiguo para usted, puede ir a las claves y le mostrará a qué variable se refiere.
Luminoso
1
en su Vista, haga: @ Html.HiddenFor (model => model.Username) resolverá el problema.
Umit Kaya
1
var asdf = ModelState.Values.Where(v => v.Errors.Count > 0);te puede ayudar
Cirelli94
37

Pegue el siguiente código en ActionResult de su controlador y coloque el depurador en este punto.

var errors = ModelState
    .Where(x => x.Value.Errors.Count > 0)
    .Select(x => new { x.Key, x.Value.Errors })
    .ToArray();
Krishna
fuente
3
La mejor respuesta aquí, debería tener una calificación más alta. ¿Por qué dedicar mi tiempo a explorar 5 capas del objeto ModelState en el depurador cuando puedo eliminar los errores? Estaría allí toda la mañana si siguiera la respuesta mejor calificada
Sean T
2
este es el mejor
juguete de
23
bool hasErrors =  ViewData.ModelState.Values.Any(x => x.Errors.Count > 1);

o iterar con

    foreach (ModelState state in ViewData.ModelState.Values.Where(x => x.Errors.Count > 0))
    {

    }
Michael G
fuente
¿Podría ser posible que todos los valores tengan 0 errores y el estado del modelo aún no sea válido?
Omu
1
El estado del modelo tendrá una "Propiedad" clave y un error asociado en el diccionario. el mensaje de error puede estar en blanco, pero el recuento de errores reflejará el recuento de propiedades que no son válidas. Debido a que el método ModelStateDictionary.AddModelError toma una clave y una excepción o cadena de error; es necesario agregar un error de modelo.
Michael G
13

A veces, un archivador arroja una excepción sin mensaje de error. Puede recuperar la excepción con el siguiente fragmento para averiguar cuál es el problema:

(A menudo, si el archivador intenta convertir cadenas en tipos complejos, etc.)

 if (!ModelState.IsValid)
            {
var errors = ModelState.SelectMany(x => x.Value.Errors.Select(z => z.Exception));

// Breakpoint, Log or examine the list with Exceptions.

  }
Jonas Stensved
fuente
1
Este código fue muy útil para mí, pero iterar los errores (Excepciones) para obtener cada .Message resultó en "referencia de objeto no establecida en una instancia de un objeto". Cuando cambié z.Exception a z.ErrorMessage, pude mostrar los mensajes de error.
StackOverflowUser
Esta fue la solución para mí, cambiar a z.ErrorMessage, aunque no obtuve un error con z.Exception, solo valores nulos. Probablemente valga la pena actualizar la respuesta original.
esp
5

Si quita la comprobación de ModelsState.IsValid y deja que se produzca un error, si copia esta línea ((System.Data.Entity.Validation.DbEntityValidationException)$exception).EntityValidationErrorsy la pega en la sección de observación en Visual Studio, le dará exactamente cuál es el error. Ahorra mucho tiempo comprobando dónde está el error.

Tom McDonough
fuente
1
Consejo realmente útil.
Ash
Este es el mejor consejo de este hilo. El problema que tuve fue un estúpido "." (punto) en UserName
mangia
3

La propiedad ModelState del controlador es en realidad un objeto ModelStateDictionary. Puede iterar a través de las claves en el diccionario y usar el método IsValidField para verificar si ese campo en particular es válido.

tvanfosson
fuente
3

Como me acaba de pasar, esto también puede suceder cuando agrega una propiedad requerida a su modelo sin actualizar su formulario. En este caso, ValidationSummary no mostrará el mensaje de error.

AndyP9
fuente
1
Esto me pasó a mí. ¡Gracias por la propina!
Lewis86