335 votes

Faire une méthode privée publique à l'unité de la tester...bonne idée?

Il m'arrive parfois de me retrouver à devoir faire une méthode privée dans une classe public juste à écrire des tests unitaires pour.

Habituellement, ce serait parce que la méthode contient une logique partagée entre d'autres méthodes dans la classe et c'est plus propre pour tester la logique sur son propre, ou une autre raison pourrait être possible, je veux tester logique utilisée dans synchrone fils sans avoir à vous soucier des problèmes de threading.

Faire d'autres gens à trouver eux-mêmes de faire cela, parce que je n'ai pas vraiment envie de le faire?? Personnellement, je pense que le bonus emportent sur les problèmes de la prise d'une méthode publique qui n'a pas vraiment de fournir tout service à l'extérieur de la classe...

Mise à JOUR

Merci pour les réponses tout le monde, semble avoir piqué l'intérêt des peuples. Je pense que le consensus général est un test qui devrait arriver via l'API publique que c'est la seule façon d'une classe ne sera jamais utilisé, et je suis d'accord avec cela. Les quelques cas que j'ai mentionnés ci-dessus où je voudrais le faire ci-dessus ont été rares cas, et j'ai pensé que les avantages de faire cela en valait la peine.

Je peux cependant voir chacuns point qu'il ne devrait jamais arriver. Et en y réfléchissant un peu plus je pense que changer votre code pour accueillir les tests est une mauvaise idée après tout je suppose que le test est un outil de soutien dans un sens et la modification d'un système de "soutien à un outil de soutien à la" si vous, est flagrante mauvaise pratique.

157voto

blank Points 7947

Personnellement, je serais plutôt de l'unité de test à l'aide de l'API publique, et je n'aurais certainement jamais faire la méthode privée publique juste pour le rendre facile à tester.

Si vous voulez vraiment tester la méthode privée dans l'isolement, en Java, vous pouvez utiliser Easymock / Powermock pour vous permettre de le faire.

Vous devez être pragmatique à ce sujet et vous devriez aussi être conscient des raisons pour lesquelles les choses sont difficiles à tester.

'Écouter les tests"- si c'est difficile à tester, c'est que vous dire quelque chose au sujet de votre conception? Pourriez-vous refactoriser à un test de cette méthode serait trivial et facilement couverts par les tests par le biais de l'api publique?

Voici ce que Michael Plumes est-à-dire dans"Travailler Efficacement Avec les Legacy Code"

"Beaucoup de gens passent beaucoup de temps à essayer ot comprendre comment contourner ce problème ... la vraie réponse est que si vous avez l'envie de tester une méthode privée, la méthode ne devrait pas être privé, si ce qui rend la méthode public vous dérange, les chances sont, c'est parce qu'il fait partie d'une catégorie distincte de responsabilité; il devrait être sur une autre classe." [Travailler Efficacement Avec le Code existant (2005) par M. Plumes]

79voto

Eric Lippert Points 300275

Comme d'autres l'ont dit, c'est un peu suspect pour être de tests unitaires méthodes privées; l'unité de test de l'interface publique, pas le privé, les détails de mise en œuvre.

Cela dit, la technique que j'utilise quand je veux unité de tester quelque chose qui est privé, C# est de restreindre l'accessibilité de la protection de privé interne, puis la marque les tests unitaires de l'assemblée comme un ami de montage à l'aide InternalsVisibleTo. Les tests unitaires de l'assemblée sera alors autorisé à traiter les données internes comme public, mais vous n'avez pas à vous soucier accidentellement en ajoutant à votre public de la surface.

65voto

Beaucoup de réponses suggèrent que les tests de l'interface publique, mais à mon humble avis ce n'est pas réaliste - si une méthode n'est quelque chose qui prend 5 étapes, vous aurez envie de tester ces cinq étapes séparément, pas tous ensemble. Cela nécessite de tester tous les cinq méthodes (autres que pour les tests) , autrement, pourraient être private.

La manière habituelle de tester des méthodes "privées" est de donner à chaque classe sa propre interface, et de rendre les méthodes "privées" public, mais ne pas les inclure dans l'interface. De cette façon, ils peuvent encore être testé, mais ils n'ont pas encombrer l'interface.

Oui, cela va se traduire dans le fichier de et classe-la météorisation.

Oui, c'est l' public et private des prescripteurs redondant.

Oui, c'est une douleur dans le cul.

C'est, malheureusement, l'un des nombreux sacrifices que nous faisons pour rendre le code testable. Peut-être l'avenir de la langue (ou une même une future version de C#/Java) ont des caractéristiques de faire de la classe et module de testabilité plus commode; mais en attendant, nous avons à passer par le biais de ces cercles.


Il y en a qui diront que chacune de ces étapes doit être sa propre classe, mais je suis en désaccord - si ils ont tous en commun de l'état, il n'y a pas de raison de créer cinq catégories distinctes, où les cinq méthodes ferait. Pire encore, cela se traduit dans le fichier de et classe-la météorisation. En Plus, il infecte l'API publique de votre module - toutes ces classes doit être nécessairement public si vous voulez les tester à partir d'un autre module (soit ça, ou inclure le code de test dans le même module, ce qui signifie que l'expédition du code de test avec votre produit).

30voto

kan Points 12445

Un test unitaire doit tester le marché public, la seule façon de comment une classe peut être utilisée dans d'autres parties du code. Une méthode privée est la mise en œuvre de détails, vous ne devriez pas le tester, d'autant que les API travaille correctement, la mise en œuvre n'a pas d'importance et peut être modifié sans changements dans les cas de test.

20voto

Thilo Points 108673

Comment informer les colis privé? Puis votre code de test peut le voir (et d'autres classes dans votre forfait), mais il est toujours caché de vos utilisateurs.

Mais vraiment, vous ne devriez pas mettre à l'essai les méthodes privées. Ceux sont des détails de mise en œuvre, et ne fait pas partie du contrat. Tout ce qu'ils ne devraient être couverts par l'appel de méthodes publiques (si ils ont un code qui n'est pas exercé par les méthodes publiques, alors ça devrait aller). Si le code confidentiel est trop complexe, la classe est sans doute trop de choses et dans le besoin de refactoring.

Faire une méthode publique est grand engagement. Une fois que vous faites cela, les gens seront en mesure de l'utiliser, et vous ne pouvez pas il suffit de changer plus.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X