Vous violeriez le principe DRY en mettant cette logique de validation partout où un code postal est utilisé.
D'un autre côté, lorsque vous traitez avec de nombreux pays différents et leurs différents systèmes de code postal, cela signifie que vous ne pouvez pas valider un code postal sans connaître le pays en question. Votre ZipCode
classe doit donc également stocker le pays.
Mais stockez-vous ensuite séparément le pays à la fois dans le Address
(dont le code postal fait également partie) et dans le code postal (pour validation)?
- Si vous le faites, vous violez également DRY. Même si vous n'appelez pas cela une violation DRY (car chaque instance sert un objectif différent), cela prend inutilement de la mémoire supplémentaire, en plus d'ouvrir la porte aux bogues lorsque les deux valeurs de pays sont différentes (ce qu'elles ne devraient logiquement jamais être).
- Ou, alternativement, cela vous oblige à synchroniser les deux points de données pour vous assurer qu'ils sont toujours les mêmes, ce qui suggère que vous devriez vraiment stocker ces données en un seul point, ce qui va à l'encontre de l'objectif.
- Si vous ne le faites pas, ce n'est pas une
ZipCode
classe mais une Address
classe, qui contiendra à nouveau une string ZipCode
qui signifie que nous avons bouclé la boucle.
Par exemple, je peux parler à un analyste commercial d'un code postal au lieu d'une chaîne qui contient un code postal.
L'avantage est que vous pouvez en parler lors de la description du modèle de domaine.
Je ne comprends pas votre affirmation sous-jacente selon laquelle lorsqu'un élément d'information a un type de variable donné, vous êtes en quelque sorte obligé de mentionner ce type chaque fois que vous parlez à un analyste commercial.
Pourquoi? Pourquoi ne pouvez-vous pas simplement parler du "code postal" et omettre complètement le type spécifique? Quel genre de discussions avez-vous avec votre analyste commercial (pas technique!) Où le type de propriété est la quintessence de la conversation?
D'où je viens, les codes postaux sont toujours numériques. Nous avons donc le choix, nous pourrions le stocker comme un int
ou comme un string
. Nous avons tendance à utiliser une chaîne car il n'y a aucune attente d'opérations mathématiques sur les données, mais jamais un analyste métier ne m'a dit que cela devait être une chaîne. Cette décision est laissée au développeur (ou sans doute à l'analyste technique, bien que, selon mon expérience, ils ne traitent pas directement avec le vif du sujet).
Un analyste métier ne se soucie pas du type de données, tant que l'application fait ce qu'elle est censée faire.
La validation est une bête délicate à affronter, car elle repose sur ce que les humains attendent.
D'une part, je ne suis pas d'accord avec l'argument de validation comme moyen de montrer pourquoi l'obsession primitive devrait être évitée, car je ne suis pas d'accord que (en tant que vérité universelle) les données doivent toujours être validées à tout moment.
Par exemple, que se passe-t-il s'il s'agit d'une recherche plus compliquée? Plutôt qu'une simple vérification de format, que se passe-t-il si votre validation implique de contacter une API externe et d'attendre une réponse? Voulez-vous vraiment forcer votre application à appeler cette API externe pour chaque ZipCode
objet que vous instanciez?
C'est peut-être une exigence commerciale stricte, et alors cela est bien sûr justifiable. Mais ce n'est pas une vérité universelle. Il y aura de nombreux cas d'utilisation où cela représente plus un fardeau qu'une solution.
Comme deuxième exemple, lorsque vous entrez votre adresse dans un formulaire, il est courant de saisir votre code postal avant votre pays. Bien qu'il soit agréable d'avoir un retour de validation immédiat dans l'interface utilisateur, ce serait en fait un obstacle pour moi (en tant qu'utilisateur) si l'application m'avertissait d'un "mauvais" format de code postal, car la véritable source du problème est (par exemple) que mon pays n'est pas le pays sélectionné par défaut, et donc la validation s'est produite pour le mauvais pays.
C'est le mauvais message d'erreur, qui distrait l'utilisateur et provoque une confusion inutile.
Tout comme la validation perpétuelle n'est pas une vérité universelle, mes exemples ne le sont pas non plus. C'est contextuel . Certains domaines d'application nécessitent avant tout la validation des données. D'autres domaines ne placent pas la validation aussi haut dans la liste des priorités parce que les tracas qu'ils entraînent entrent en conflit avec leurs priorités réelles (par exemple, l'expérience utilisateur ou la capacité de stocker initialement des données erronées afin qu'elles puissent être corrigées au lieu de ne jamais les autoriser). stocké)
Date de naissance: vérifiez que la date est supérieure à celle indiquée et inférieure à la date d'aujourd'hui.
Salaire: Vérifiez que supérieur ou égal à zéro.
Le problème avec ces validations est qu'elles sont incomplètes, redondantes ou indiquent un problème beaucoup plus important .
Vérifier qu'une date est supérieure à la mentalité est redondant. La mentalité signifie littéralement que c'est la date la plus petite possible. D'ailleurs, où tracez-vous la ligne de pertinence? Quel est l'intérêt d'empêcher DateTime.MinDate
mais d'autoriser DateTime.MinDate.AddSeconds(1)
? Vous choisissez une valeur particulière qui n'est pas particulièrement fausse par rapport à de nombreuses autres valeurs.
Mon anniversaire est le 2 janvier 1978 (ce n'est pas le cas, mais supposons que ce soit le cas). Mais disons que les données de votre application sont fausses, et à la place, il est dit que mon anniversaire est:
- 1er janvier 1978
- 1 janv.1722
- 1er janv.2355
Toutes ces dates sont fausses. Aucun d'eux n'est "plus juste" que l'autre. Mais votre règle de validation ne prendrait que l' un de ces trois exemples.
Vous avez également complètement omis le contexte de la façon dont vous utilisez ces données. Si cela est utilisé par exemple dans un bot de rappel d'anniversaire, je dirais que la validation est inutile car il n'y a pas de mauvaise conséquence particulière à remplir une mauvaise date.
D'un autre côté, s'il s'agit de données gouvernementales et que vous avez besoin de la date de naissance pour authentifier l'identité d'une personne (et si vous ne le faites pas, cela entraîne de graves conséquences, par exemple le refus de la sécurité sociale à quelqu'un), alors l'exactitude des données est primordiale et vous devez pleinement valider les données. La validation proposée que vous avez maintenant n'est pas adéquate.
Pour un salaire, il y a du bon sens en ce sens qu'il ne peut pas être négatif. Mais si vous vous attendez de manière réaliste à ce que des données absurdes soient entrées, je vous suggère de rechercher la source de ces données absurdes. Parce que s'ils ne peuvent pas leur faire confiance pour entrer des données sensibles, vous ne pouvez pas non plus leur faire confiance pour entrer des données correctes .
Si au lieu de cela le salaire est calculé par votre application, et qu'il est possible de se retrouver avec un nombre négatif (et correct)), une meilleure approche serait Math.Max(myValue, 0)
de transformer les nombres négatifs en 0, plutôt que de ne pas échouer la validation. Parce que si votre logique a décidé que le résultat est un nombre négatif, l'échec de la validation signifie qu'il devra refaire le calcul, et il n'y a aucune raison de penser qu'il fournira un nombre différent la deuxième fois.
Et s'il arrive avec un nombre différent, cela vous amène à nouveau à soupçonner que le calcul n'est pas cohérent et ne peut donc pas être fiable.
Cela ne veut pas dire que la validation n'est pas utile. Mais la validation inutile est mauvaise, à la fois parce qu'elle demande des efforts sans vraiment résoudre un problème et donne aux gens un faux sentiment de sécurité.