Comment puis-je désactiver la validation du modèle pour une seule action dans un contrôleur? Ou puis-je le faire par modèle en enregistrant le type de modèle au démarrage quelque part? P>
Je veux que la modélisation se lie au modèle, mais elle ne doit pas effectuer la validation du modèle. P>
La raison pour laquelle je ne veux pas que je ne veux pas que la validation soit parce que j'essaie de déplacer la logique des contrôleurs à une couche de service qui sera responsable de la validation des modèles car je ne peux pas supposer que les modèles passés à un service contiennent des données valides. . P>
Si je comprends bien, c'est l'approche de recommandation (pour ne pas avoir la logique dans les contrôleurs), donc je le trouve un peu étrange que je ne peux pas sembler trouver quelque chose sur la manière dont la validation du modèle peut être désactivée (par action ou par type de modèle ). p>
Veuillez noter que je ne veux pas désactiver la validation du modèle pour l'ensemble du webapplication (en supprimant les fournisseurs de validation), et je ne veux pas désactiver la validation d'entrée qui vérifie que le code malveillant est affiché. P>
J'utilise .NET 4.0 et MVC 3 Aperçu 1 P>
7 Réponses :
J'utilise [ValidateInput (FALSE)] P>
Je ne sais pas si cela empêche la validation du modèle ou uniquement la validation de l'IIS. P>
Il n'empêche pas le modèle d'être validé. Autant que je sache, il est utilisé pour désactiver la vérification de l'entrée malveillante (comme des balises HTML ou JavaScript, etc.)
Je vous recommanderais d'effectuer une validation dans les deux lieux em> plutôt que d'essayer de désactiver la validation dans l'interface utilisateur. Je comprends votre argument que le service ne peut supposer que cela est passé des données valides - c'est une préoccupation valable et c'est la raison pour laquelle votre service devrait avoir la validation. Mais vous devriez aussi em> avoir une validation dans votre interface utilisateur. Ceci est également agréable car vous pouvez avoir une validation côté client pour empêcher les erreurs de l'utilisateur et vous donner aux utilisateurs une meilleure expérience. P>
Merci pour votre réponse. J'ai la validation de l'UI Clientside. J'utilise les attributs dans l'espace de noms de basenotation pour mes modèles. Ma couche de service ajoute les erreurs de validation à la modélisation (si dans un contexte Web). Il n'y a aucune raison d'effectuer la même validation deux fois. :)
Fondamentalement, ma couche de service suit cette approche ASP.net/ MVC / Tutoriels / Validation-avec-A-Service-Couche - CS Cela fonctionne bien, mais l'exemple n'utilise pas les attributs de basenotation pour la validation, qui sont automatiquement validés dans MVC (et ce que j'essaie d'empêcher) .
Ce lien n'a pas de date à ce qu'il a été écrit mais je suppose que c'est assez vieux. Lorsque MVC a été publié pour la première fois, il y avait une certaine confusion autour de où i> la logique de validation devrait aller (contrôleur, etc.). Mais cette histoire a été solidifiée au cours de la dernière année environ avec les meilleures pratiques recommandées étant généralement que la validation de l'interface utilisateur devrait se produire dans le classeur de modèle, c'est pourquoi c'est maintenant la valeur par défaut dans MVC 2.
Si vous êtes prêt à le faire de cette façon, cela pourrait être accompli en hérité de la base de donnéesAnnotationModelbinder, puis remplacez la méthode Onmodelupdated () et à l'intérieur de ModelState.clear (). Je ne dis pas que je le ferais cependant. :)
Je suppose que vous parlez du défautModelbinder (car il n'y a pas de dataannotationsModelbinder - il existe un dataannotationsModelvalidator). Faire un modèle de modèle.Clear () à l'intérieur de la modélisation affectera l'ensemble de l'application Web que je ne veux pas, je veux qu'il continue à fonctionner de manière traditionnelle, mais être capable de désactiver la validation du modèle par action ou par type de modèle. Je pouvais bien sûr faire un gros commutateur ou si la clause et ajouter chaque type de modèle que je ne veux pas valider - mais ce serait assez moche, je suppose - mais c'est peut-être la meilleure option! :)
Je peux voir que la méthode Onmodelupdated obtient un contrôleContext et un modèleBindingContext. La meilleure option serait si elle est possible de déterminer quelle action est appelée, puis vérifiez s'il dispose d'un attribut personnalisé (validateModel, etc.) qui lui est attaché pour éviter de valider le modèle. Une autre option consiste à enregistrer un modèle de modèle qui ne fait pas la validation et enregistrez chaque type - quelque chose comme ModelBinders.binders [typeof (myModelType)] = nouveau non évalidanteModelbinder (); Merci d'avoir répondu. Il y a quelques options que je peux essayer de travailler. :)
Oui, je voulais dire "DefaultModelbinder". J'utiliserais votre deuxième approche: ModelBinders.binders [typeof (myModelType)] = nouveau non évalidantmodelbinder (); De cette façon, cela n'affecte pas votre application au niveau mondial.
Juste pour donner une petite mise à jour (si elle vous intéresse), il est possible de joindre des attributs aux paramètres (comme le Bindattribute), il doit donc être facile de vérifier si le paramètre / modèle comporte un attribut attaché dans l'ondulupdated et juste désactiver la validation si elle a. Donc, quand je n'ai pas besoin de validation modèle, je peux simplement le désactiver en faisant quelque chose comme une action publiqueReSresult ActionMethodName ([DisabloDelValidation] MyModelType Model) {...} :)
En tant que spécialiste de la convivialité, je suis en désaccord. Les utilisateurs détestent de ne pas avoir toutes les validations à la fois. Sauf si vous les dupliquez tous tous les diviser, c'est une mauvaise forme.
Malheureusement, il semble y avoir un moyen facile de désactiver la validation du modèle qui se produit dans la modélisation, à l'exception de l'enregistrement de chaque type de modèle que vous ne souhaitez pas valider (y compris des types complexes imbriqués) avec un jeu de modèles spécifique. Cela peut être fait avec le code suivant: p>
Création d'un SkipValidationAbute qui peut être attaché aux méthodes d'action ou aux paramètres de la méthode d'action ne semble pas possible car il devrait être mis en œuvre dans le contrôleurInvoker, mais il n'ya aucun moyen de laisser le modèle de modélisation savoir qu'il devrait faire toute validation dans le setProperty () et des méthodes onModelupdated lors de l'appel de BinModel () dans la méthode GetParameValue (). P>
Modelbinders.binders [typeof (mymodeltype)] = nouveau non évalidanteModelBinder ();
code> p>
J'ai fait le travail d'approche "SkipValidationAttribute", en créant ma propre implémentation de contrôleurInvoker qui reçoit l'attribut du paramètre de méthode et s'il est déclaré, il ajoute une touche à la modélisation injectée dans la méthode ModelBinder (méthode BinModel) et retirez-la lorsque Le modèle est lié. Ensuite, je peux vérifier dans la modélisation si la modélisation contient la clé et si elle saute la validation, sinon effectue une validation comme elle le ferait normalement.
@Kugel: Même si la voie de la fin, non évalidanteModelbinder Vous devez vous mettre en œuvre.
Je n'aime pas vraiment cet ajout dans la version 2.0, car, comme vous l'avez dit dans votre question, la validation a plus de sens dans la couche de service. De cette façon, vous pouvez la réutiliser dans d'autres applications non-web et le tester plus facilement sans avoir à se moquer du mécanisme de validation automatique.
Validation dans la couche de contrôleur est inutile car dans cette partie, vous ne pouvez définir que les données du modèle et non Règles commerciales. Par exemple, pensez à un service responsable de l'ajout de nouveaux commentaires et un utilisateur qui souhaite poster une nouvelle, les données dans le commentaire qu'il / elle affiche peut être valide, mais que se passe-t-il si l'utilisateur est interdit de commenter à cause de la mauvaise conduite autrefois? Vous devriez faire une certaine validation dans la couche de service pour vous assurer que cela ne se produit pas, et si cela fait, jetant une exception. En bref, la validation doit être effectuée dans la couche de service. P>
J'utilise Xval comme cadre de validation car il est compatible avec le daNaNanNotationModel, me permet de passer une validation où que je souhaite et effectue une validation côté client sans extra- effort, même à distance du côté de la clientèle. C'est ainsi que je l'utilise au début de chacun de mes services, par exemple un service de connexion: p> simple, indépendant Web et facile ... alors, dans Le contrôleur: p>
Retirez simplement les éléments que vous n'avez pas besoin avant de vérifier si le modèle est valide
ModelState.Remove("Email"); if (ModelState.IsValid) { // your logic }
Celui-ci est plus plus rapide et facile!
Ceci est court, propre et aide.
J'ai résolu ce problème avec ce code:
public ActionResult Totals(MyModel model) { ModelState.Clear(); return View(model); }
Les données d'état modèle font plus que la validation de la validation. En nettoyant l'état modèle, vous perdrez également d'autres fonctionnalités.
Je sais que cela a déjà été répondu, mais ce que vous aviez vraiment besoin était d'étendre le Puis, alors, au démarrage, vous le feriez Supprimer le Inutile de dire, si vous ne voulez tout simplement pas de validation du tout, Vous pouvez simplement avoir la méthode Dans mon cas, je n'ai besoin de supprimer la validation que lors de la soumission des formulaires tout en conservant la validation du côté client, donc Ce qui suit: p> dataannotationsValidatorProvider code> et remplacer la méthode
getvalidators code>.
dataannotationsValidatorProvider code> à partir de
modelvalidatorproviders.providers code> et ajoutez votre nouveau. p>
getvalidators code> renvoyer une collection vide. P>