Grande question!
En ce qui concerne le développement du World Wide Web, que se passe-t-il si vous posez également les questions suivantes.
"Si une mauvaise entrée utilisateur est fournie à un contrôleur à partir d'une interface utilisateur, le contrôleur doit-il mettre à jour la vue dans une sorte de boucle cyclique, forçant les commandes et les données d'entrée à être précises avant de les traiter ? Comment? Comment la vue est-elle mise à jour dans des conditions normales Est-ce qu'une vue est étroitement couplée à un modèle? La validation des entrées utilisateur est-elle la logique métier principale du modèle, ou est-elle préliminaire et devrait donc se produire à l'intérieur du contrôleur (car les données d'entrée utilisateur font partie de la demande)?
(En effet, peut-on et devrait-on retarder l'instanciation d'un modèle jusqu'à ce qu'une bonne entrée soit acquise?)
Mon avis est que les modèles doivent gérer une circonstance pure et vierge (autant que possible), sans être gênée par une validation d'entrée de requête HTTP de base qui devrait se produire avant l'instanciation du modèle (et certainement avant que le modèle n'obtienne des données d'entrée). Étant donné que la gestion des données d'état (persistantes ou non) et des relations API est le monde du modèle, laissez la validation d'entrée de requête HTTP de base se produire dans le contrôleur.
Résumant.
1) Validez votre itinéraire (analysé à partir de l'URL), car le contrôleur et la méthode doivent exister avant que quoi que ce soit d'autre puisse avancer. Cela devrait certainement se produire dans le domaine du contrôleur frontal (classe Router), avant d'arriver au vrai contrôleur. Duh. :-)
2) Un modèle peut avoir de nombreuses sources de données d'entrée: une requête HTTP, une base de données, un fichier, une API et, oui, un réseau. Si vous allez placer toute votre validation d'entrée dans le modèle, vous envisagez la validation d'entrée de demande HTTP partie des exigences commerciales du programme. Affaire classée.
3) Pourtant, il est myope de passer par le coût de l'instanciation de beaucoup d'objets si l' entrée de requête HTTP n'est pas bonne! Vous pouvez savoir si ** l'entrée de requête HTTP ** est bonne ( fournie avec la requête ) en la validant avant d'instancier le modèle et toutes ses complexités (oui, peut-être même plus de validateurs pour les données d'entrée / sortie API et DB).
Testez les éléments suivants:
a) La méthode de requête HTTP (GET, POST, PUT, PATCH, DELETE ...)
b) Contrôles HTML minimum (en avez-vous assez?).
c) Contrôles HTML maximum (en avez-vous trop?).
d) Corriger les contrôles HTML (avez-vous les bons?).
e) Encodage d'entrée (est-ce généralement l'encodage UTF-8?).
f) Taille d'entrée maximale (l'une des entrées est-elle largement hors limites?).
N'oubliez pas que vous pouvez obtenir des chaînes et des fichiers, donc attendre que le modèle soit instancié peut devenir très coûteux lorsque les demandes arrivent sur votre serveur.
Ce que j'ai décrit ici correspond à l' intention de la demande via le contrôleur. L'omission de la vérification d' intention rend votre application plus vulnérable. L'intention ne peut être que bonne (en respectant vos règles fondamentales) ou mauvaise (sortir de vos règles fondamentales).
L'intention d'une demande HTTP est une proposition tout ou rien. Tout passe ou la demande n'est pas valide . Pas besoin d'envoyer quoi que ce soit au modèle.
Ce niveau de base de l' intention de demande HTTP n'a rien à voir avec les erreurs de saisie utilisateur standard et la validation. Dans mes applications, une requête HTTP doit être valide des cinq façons ci-dessus pour que je puisse l'honorer. Dans un mode de défense en profondeur , vous n'obtenez jamais de validation d'entrée utilisateur côté serveur si l' une de ces cinq choses échoue.
Oui, cela signifie que même l'entrée de fichiers doit être conforme à vos tentatives frontales de vérifier et d'indiquer à l'utilisateur la taille de fichier maximale acceptée. Uniquement HTML? Pas de JavaScript? D'accord, mais l'utilisateur doit être informé des conséquences du téléchargement de fichiers trop volumineux (principalement, il perdra toutes les données du formulaire et sera expulsé du système).
4) Cela signifie-t-il que les données d'entrée de requête HTTP ne font pas partie de la logique métier de l'application? Non, cela signifie simplement que les ordinateurs sont des appareils finis et que les ressources doivent être utilisées à bon escient. Il est logique d'arrêter les activités malveillantes le plus tôt possible. Vous payez plus en ressources de calcul pour attendre de l'arrêter plus tard.
5) Si l' entrée de demande HTTP est mauvaise, la demande entière est mauvaise . Voilà comment je le vois. La définition d'une bonne entrée de requête HTTP est dérivée des exigences commerciales du modèle, mais il doit y avoir un point de démarcation des ressources. Combien de temps laisserez-vous vivre une mauvaise demande avant de la tuer et de dire: "Oh, hé, tant pis. Mauvaise demande."
Le jugement n'est pas simplement que l'utilisateur a fait une erreur de saisie raisonnable, mais qu'une requête HTTP est tellement hors limites qu'elle doit être déclarée malveillante et arrêtée immédiatement.
6) Donc, pour mon argent, la requête HTTP (MÉTHODE, URL / route et données) est TOUT bonne ou RIEN d'autre ne peut continuer. Un modèle robuste a déjà des tâches de validation à gérer, mais un bon berger de ressources dit: "Mon chemin, ou le chemin du haut. Venez correct, ou ne venez pas du tout."
Mais c'est votre programme. "Il y a plus d'une façon de le faire." Certains moyens coûtent plus cher en temps et en argent que d'autres. La validation ultérieure des données de requête HTTP (dans le modèle) devrait coûter plus cher pendant la durée de vie d'une application (en particulier si elle est mise à l'échelle ou augmentée).
Si vos validateurs sont modulaires, la validation de l'entrée de requête HTTP * de base ** dans le contrôleur ne devrait pas poser de problème. Il vous suffit d'utiliser une classe Validator stratégique, où les validateurs sont parfois également composés de validateurs spécialisés (e-mail, téléphone, jeton de formulaire, captcha, ...).
Certains voient cela comme complètement faux, mais HTTP en était à ses balbutiements lorsque le gang des quatre a écrit Design Patterns: Elements of Re-usable Object-Oriented Software .
================================================== ========================
Maintenant, en ce qui concerne la validation d'entrée utilisateur normale (une fois que la requête HTTP a été jugée valide), il met à jour la vue lorsque l'utilisateur gâche et que vous devez y penser! Ce type de validation d'entrée utilisateur doit se produire dans le modèle.
Vous n'avez aucune garantie de JavaScript sur le front-end. Cela signifie que vous n'avez aucun moyen de garantir la mise à jour asynchrone de l'interface utilisateur de votre application avec des états d'erreur. Une véritable amélioration progressive couvrirait également le cas d'utilisation synchrone.
La prise en compte du cas d'utilisation synchrone est un art qui se perd de plus en plus parce que certaines personnes ne veulent pas passer par le temps et se tracasser pour suivre l'état de toutes leurs astuces d'interface utilisateur (afficher / masquer les contrôles, désactiver / activer les contrôles , indications d'erreur, messages d'erreur) sur le serveur principal (généralement en suivant l'état des tableaux).
Mise à jour : Dans le diagramme, je dis que le View
devrait faire référence au Model
. Non. Vous devez transmettre les données à View
partir du Model
pour conserver le couplage lâche.