MVC - Cio de l'Unité - assurez-vous que le contrôleur dispose d'un constructeur public sans paramètre
Problème
Je suis à l'aide de l'Unité du Cio et qui a bien fonctionné, mais comme je l'ai garder l'ajout d'une fonctionnalité, il devient de plus en plus difficile à repérer toutes les erreurs, parce que l'Unité fournit une erreur qui est le symptôme de l'erreur, de ne pas l'erreur:
"Message":"An error has occurred.","ExceptionMessage":"An error occurred
when trying to create a controller of type 'MyController'. Make sure that the
controller has a parameterless public
constructor.","ExceptionType":"System.InvalidOperationException"
Fond
J'ai un MVC, Web Api contrôleur qui a une dépendance sur une instance du Gestionnaire (de domaine):
public class MyController : ApiController
{
private IMyManager MyManager { get; set; }
public MyController(IMyManager myManager)
{
this.MyManager = myManager;
}
...
}
L'erreur ci-dessus se produit parce que le Cio cartographie de la IMyManager échoue. Comme il échoue, je n'ai pas de paramètre, ce qui signifie que MyController est appelée à l'aide d'un constructeur sans paramètre, mais comme il n'existe pas (et ne devrait pas), j'ai l'erreur ci-dessus.
Ce que j'ai essayé
Donc, l'erreur que j'obtiens est pas la "vraie" erreur. La chose la plus évidente est de faire en sorte que chaque nouvelle mise en œuvre, est enregistré en vertu du Cio, j'ai vérifié et ils sont. - Je le faire manuellement pour garder les choses gérable (ô ironie!).
- Je le faire comme ceci:
container.RegisterType<IMyManager, MyManager>();
Mais, ce n'est pas la question.
Une des solutions que j'ai fait était une dépendance circulaire. J'ai changé toutes les personnes impliquées constructeurs et les méthodes d'utilisation de la propriété des valeurs, pas les instances.
J'ai vérifié toutes les personnes impliquées classes et il n'y a plus de dépendances circulaires.
Encore, le problème persiste.
La question
Que puis-je faire pour trouver le problème réel? Vérification manuelle des dépendances est beaucoup trop généraux, parce que la structure est un ensemble complexe de plus profond des dépendances. Et cela va s'aggraver à mesure que l'application évolue.
Sinon, si l'Unité tout obscurcit toujours ces messages (sans être en mesure de corriger cela), il y a des alternatives qui fournissent la peine d'informations d'erreur?
Mise à JOUR
Par demande, le message d'erreur complet (bien que je ne pense pas que la stacktrace est très utile):
{"Message":"An error has occurred.","ExceptionMessage":"An error occurred when trying to create a controller of type 'MyController'. Make sure that the controller has a parameterless public constructor.","ExceptionType":"System.InvalidOperationException","StackTrace":" at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.Create(HttpRequestMessage request, HttpControllerDescriptor controllerDescriptor, Type controllerType)
at System.Web.Http.Controllers.HttpControllerDescriptor.CreateController(HttpRequestMessage request)
at System.Web.Http.Dispatcher.HttpControllerDispatcher.<SendAsync>d__1.MoveNext()","InnerException":{"Message":"An error has occurred.","ExceptionMessage":"Type 'MyProject.Web.Api.Controllers.MyController' does not have a default constructor","ExceptionType":"System.ArgumentException","StackTrace":" at System.Linq.Expressions.Expression.New(Type type)
at System.Web.Http.Internal.TypeActivator.Create[TBase](Type instanceType)
at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.GetInstanceOrActivator(HttpRequestMessage request, Type controllerType, Func`1& activator)
at System.Web.Http.Dispatcher.DefaultHttpControllerActivator.Create(HttpRequestMessage request, HttpControllerDescriptor controllerDescriptor, Type controllerType)"}}
Mise à JOUR 2
J'ai creusé un peu plus profond et vérifié toutes les dépendances (ils sont assez massif), mais tout est enregistré et chargé correctement. Là aussi ne sont pas toutes les dépendances circulaires, donc autant que je peux dire tout ce que "devrait", travail. Car il n'ai-je pas conclure qu'il y a une erreur qui se passe qui n'est pas d'être jetés.
Jetez un oeil à cette q/r: stackoverflow.com/a/15910758/264697. Il suffit de remplacer les mots "de l'API Web" avec "MVC" et "Simple Injecteur" avec "l'Unité" et vous aurez une bonne description de ce qui se passe ici. TLDR; Inscrivez vos contrôleurs explicitement.
L'unité de ne pas cacher les erreurs et les erreurs que vous avez des erreurs produites par l'Unité de ce que je peux voir. Il semble que vous n'avez pas votre WebAPI accroché pour l'injection de dépendance. Vous devez le configurer pour utiliser le même conteneur si vous ne l'avez pas déjà. Ne l'injection de dépendance travailler dans l'un de vos WebAPI contrôleurs, ou est-ce le premier?
Notez que vous devez poster à l'exception complète l'information + la trace de la pile, parce que, souvent, contient des informations essentielles nous en dire plus sur ce qui se passe. Sans cette information, il nous suffit de deviner.
OriginalL'auteur Spikee | 2015-10-14
Vous devez vous connecter pour publier un commentaire.
Si le message d'erreur indique que vous avez besoin d'un constructeur sans paramètre, qui me donne à penser que l'Unité n'est pas enregistré pour WebAPI, même s'il est inscrit à votre ASP.NET application MVC. Si votre Cio fonctionne correctement, il ne devrait pas avoir besoin d'un paramaterless constructeur, car il devrait être en mesure de résoudre les dépendances qui existent au sein de votre constructeur du contrôleur.
WebAPI a son propre pipeline de ASP.NET MVC par exemple WebAPI peut être OWIN hébergé, c'est pourquoi il a besoin de raccorder séparément, même si elles existent dans le même projet.
Vous devez brancher votre WebAPI à la résolution de dépendances au sein de votre UnityConfig, je crois qu'il y a un exemple ici: http://www.devtrends.co.uk/blog/using-unity.mvc5-and-unity.webapi-together-in-a-project
Dans l'exemple ci-dessus il y a deux lignes pour la configuration, mais ils partagent le même conteneur et donc les mêmes liaisons - vous n'avez pas à définir deux fois. Si vous jamais venu à séparer les WebAPI projet à partir de la ASP.NET MVC, vous devez disposer d'un récipient séparé et des liaisons.
En termes de trouver le problème, ou l'Unité de masquage d'erreurs à partir de vous, dans mon expérience, ce n'est tout simplement pas le cas. L'erreur que vous rencontrez est directement à partir de ASP.NET MVC. En utilisation normale, sans un Cio, vous avez besoin d'un constructeur sans paramètre... avec un Cio, il contrôle la création des contrôleurs et donc résout les dépendances.
Je ne suis pas le downvoter (je n'ai pas le privilège encore) mais ce n'est pas une bonne réponse parce que j'ai dit Cio n'a fonctionné très bien avant l'ajout de nouvelles fonctionnalités. Il y a "quelque chose" qui ne va pas dans le nouveau développement, et non pas le code existant.
Veuillez répondre aux questions suivantes: Combien de WebAPI contrôleurs avez-vous dans votre projet? Combien d'entre eux sont actuellement en train de travailler avec l'injection de dépendance? Veuillez indiquer en détail comment vous accrocher votre WebAPI contrôleurs jusqu'à votre Unité de conteneur. Ensuite, nous pouvons juger si c'est une bonne réponse ou pas...
Tous les contrôleurs de travaux injection de paramètres, avec les instances de se jeter dans qui ont des dépendances formant une structure trop complexe à résumer ici.
Désolé, j'aurais été plus clair dans ce que je faisais référence le code de la réponse de référencement ASP.NET MVC. L'API Web de configuration seront encore nécessaires.
OriginalL'auteur Luke
Je l'ai trouvé, le problème est que je suis la refonte du code existant, dans la même solution, ce qui signifie qu'il va y avoir des doublons de fichiers avec des noms identiques.
Dans ce cas particulier, j'ai eu une interface qui a été exactement le même comme un déjà existant. Quelque part profondément dans le code que j'ai utilisé le mauvais espace de noms, ce qui signifie que le Cio cartographie a été incorrect.
Donc, quelque chose comme ceci:
J'ai:
et
Ce que je faisais dans la cartographie a été:
où IMyManager dans ce cas est nouveau.les gestionnaires.IMyManager, comme il se doit.
L'un des consommateurs de cette dépendance devrait IMyManager de l'espace de noms vieux.les gestionnaires de.
Mise à jour le consommateur à utiliser le nouvel espace de noms, il fixe.
Make sure that the controller has a parameterless public constructor.
? Vous devez avoir modifié la configuration de l'.Il a été un moment mais: Si mon constructeur attend un paramètre de type
new.managers.IMyManager
et ma liaison est fait pourold.managers.IMyManager
, il ne va jamais arriver à le constructeur, car il existe une différence significative dans la définition. C'est juste difficile pour avis à la valeur nominale. Un paramètre qui n'est pas identifié signifie la signature du constructeur n'était pas appariés. Sens, il recherche la valeur par défaut constructeur sans paramètre. Qui n'existe pas, sur le but.Étrange, en général si c'est le cas, le conteneur IoC reconnaître qu'il était incapable de se lier d'une interface et de produire un message d'erreur spécifique en conséquence. Le constructeur sans paramètre message d'erreur est produit par le framework MVC lui-même lorsqu'il ne peut pas créer une instance d'un contrôleur.
Venez sur l'homme, cette question n'a pas été touché depuis le mois d'octobre et hier, je reçois un downvote à peu près en même temps que votre réponse. Mais quoi que ce soit.
Je n'ai pas voter, je le promets. 🙁
OriginalL'auteur Spikee
Je pense que vous devriez ajouter un autre constructeur de votre contrôleur.
Si c'est encore une erreur, vous devez vérifier les composants de ce registre pour Application_Start (en Global.asax). Dans UnityConfig.cs :
Rendre la valeur par défaut pour le contrôleur.
Dans Application_Start() (Global.asax.cs et Mondial.asax)
Dans mon projet, j'ai deux constructeurs. public MyController(IMyManager myManager) { this.MyManager myManager; } public et MyController() {}. Il fonctionne bien.
Comment instancier les dépendances si le constructeur par défaut est utilisé?
CIO est rendu inutile avec votre suggestion
OriginalL'auteur Ken Nguyen