Je ne peux parler que par expérience avec Guice, mais voici mon point de vue. En résumé, la configuration basée sur les annotations réduit considérablement la quantité de données que vous devez écrire pour assembler une application et facilite le changement de ce qui dépend de ce qui est... souvent sans même avoir à toucher aux fichiers de configuration eux-mêmes. Pour ce faire, elle rend les cas les plus courants absolument triviaux au prix de rendre certains cas relativement rares... légèrement plus difficile à gérer.
Je pense que c'est un problème d'être trop dogmatique sur le fait que les classes n'ont "aucune idée de l'injection". Il ne devrait pas y avoir de référence au conteneur d'injection dans le code d'une classe. Je suis tout à fait d'accord avec cela. Cependant, il faut être clair sur un point : les annotations ne sont pas des codes . En elles-mêmes, elles ne changent rien au comportement d'une classe... vous pouvez toujours créer une instance d'une classe avec des annotations comme si elles n'existaient pas du tout. Vous pouvez donc cesser complètement d'utiliser un conteneur DI et laisser les annotations en place sans aucun problème.
Lorsque vous choisissez de ne pas fournir d'indications de métadonnées sur l'injection au sein d'une classe (c'est-à-dire des annotations), vous vous débarrassez d'une source précieuse d'informations sur les dépendances requises par cette classe. Vous êtes obligé de répéter cette information ailleurs (dans le XML, par exemple) ou de vous fier à une magie peu fiable comme le câblage automatique qui peut conduire à des problèmes inattendus.
Pour répondre à certaines de vos questions spécifiques :
Il aide à se débarrasser de XML
La configuration XML présente de nombreux inconvénients.
- C'est terriblement verbeux.
- Il n'est pas sûr sans outils spéciaux.
- Il impose l'utilisation d'identifiants de type chaîne. Là encore, ce n'est pas sûr sans l'aide d'un outil spécial.
- Il ne tire aucun avantage des caractéristiques du langage, nécessitant toutes sortes de constructions hideuses pour faire ce qui pourrait être fait avec une simple méthode dans le code.
Cela dit, je sais que beaucoup de gens utilisent le XML depuis suffisamment longtemps pour être convaincus qu'il est parfait et je ne m'attends pas vraiment à les faire changer d'avis.
Dans de nombreux cas, il n'existe qu'une seule implémentation pour chaque interface.
Il n'y a souvent qu'une seule implémentation de chaque interface pour le une seule configuration d'une application (par exemple, la production). L'idée est qu'au démarrage de votre application, vous n'avez généralement besoin de lier une interface à une seule implémentation. Celle-ci peut ensuite être utilisée dans de nombreux autres composants. Avec la configuration XML, vous devez indiquer à chaque composant qui utilise cette interface d'utiliser cette liaison particulière de cette interface (ou "bean" si vous voulez). Avec la configuration basée sur les annotations, il suffit de déclarer la liaison une fois et tout le reste est pris en charge automatiquement. C'est très important et cela réduit considérablement la quantité de configuration que vous devez écrire. Cela signifie également que lorsque vous ajoutez une nouvelle dépendance à un composant, vous ne devez souvent rien changer à votre configuration !
Le fait que vous ayez des implémentations fictives d'une interface n'est pas pertinent. Dans les tests unitaires, il suffit généralement de créer l'objet fantaisie et de le transmettre soi-même... cela n'a rien à voir avec la configuration. Si vous mettez en place un système complet pour les tests d'intégration avec certaines interfaces en utilisant plutôt des objets fantaisie... cela ne change rien. Pour le test d'intégration du système, vous n'utilisez toujours qu'une seule implémentation et vous ne devez la configurer qu'une seule fois.
XML : Vous pouvez injecter n'importe quoi n'importe où
Vous pouvez le faire facilement dans Guice et j'imagine que vous le pouvez aussi dans CDI. Ce n'est donc pas comme si l'utilisation d'un système de configuration basé sur les annotations vous empêchait absolument de le faire. Cela dit, je me risquerais à dire que la majorité des classes injectées dans la majorité des applications sont des classes auxquelles vous pouvez ajouter une annotation @Inject
à vous-même si elle n'est pas déjà là. L'existence d'une bibliothèque Java standard légère pour les annotations (JSR-330) permet à un plus grand nombre de bibliothèques et de frameworks de fournir plus facilement des composants avec des annotations. @Inject
dans le futur, aussi.
Plus d'une implémentation d'une interface
Les qualificatifs sont une solution à ce problème et, dans la plupart des cas, ils devraient convenir parfaitement. Cependant, dans certains cas, vous voulez faire quelque chose où l'utilisation d'un qualificateur sur un paramètre dans une classe injectée particulière ne fonctionnerait pas... souvent parce que vous voulez avoir plusieurs instances de que chacun utilisant une implémentation ou une instance d'interface différente. Guice résout ce problème avec quelque chose appelé PrivateModule
s. Je ne sais pas ce que le CDI offre à cet égard. Mais encore une fois, c'est un cas qui est minoritaire et ça ne vaut pas la peine de faire souffrir le reste de votre configuration tant que vous pouvez le supporter.