0
votes

I'm using NinjectWebCommon to perform the injections in my controllers. I installed the package via Nuget and he created the NinjectWebCommon.cs in my App_Start as it says in the own documentation. I need to know why it does not work as it should, because I follow the documentation step by step. Follows some snippets:

NinjectWebCommon.cs:

public static class NinjectWebCommon
    {
        private static readonly Bootstrapper bootstrapper = new Bootstrapper();

        /// <summary>
        /// Starts the application
        /// </summary>
        public static void Start()
        {
            DynamicModuleUtility.RegisterModule(typeof(OnePerRequestHttpModule));
            DynamicModuleUtility.RegisterModule(typeof(NinjectHttpModule));
            bootstrapper.Initialize(CreateKernel);
        }

        /// <summary>
        /// Stops the application.
        /// </summary>
        public static void Stop()
        {
            bootstrapper.ShutDown();
        }

        /// <summary>
        /// Creates the kernel that will manage your application.
        /// </summary>
        /// <returns>The created kernel.</returns>
        private static IKernel CreateKernel()
        {
            var kernel = new StandardKernel();

            try
            {
                kernel.Bind<Func<IKernel>>().ToMethod(ctx => () => new Bootstrapper().Kernel);
                kernel.Bind<IHttpModule>().To<HttpApplicationInitializationHttpModule>();

                RegisterServices(kernel);
                return kernel;
            }
            catch
            {
                kernel.Dispose();
                throw;
            }
        }

        /// <summary>
        /// Load your modules or register your services here!
        /// </summary>
        /// <param name="kernel">The kernel.</param>
        private static void RegisterServices(IKernel kernel)
        {
            //kernel.Load(AppDomain.CurrentDomain.GetAssemblies());
            kernel.Bind<IFooService>().To<FooService>();
        }
    }

Controller:

public class FooController : Controller
    {
        private readonly IFooService fooService;

        public FooController(IFooService fooService)
        {
            this.fooService = fooService;
        }

        public ActionResult Index()
        {
            return View(this.fooService.All());
        }
    }

This generates this error:

Error activating IFooService No matching bindings are available, and the type is not self-bindable. Activation path:
2) Injection of dependency IFooService into parameter fooService of constructor of type FooController
1) Request for FooController

Suggestions:
1) Ensure that you have defined a binding for IFooService.
2) If the binding was defined in a module, ensure that the module has been loaded into the kernel.
3) Ensure you have not accidentally created more than one kernel.
4) If you are using constructor arguments, ensure that the parameter name matches the constructors parameter name.
5) If you are using automatic module loading, ensure the search path and filters are correct.

Use IoC to resolve instances, but it works only in my HomeController, if I change to another controller using EXACTLY the same code (with the IoC), it generates the error again. Follows the code using the IoC.

using IoC:

private readonly IFooService fooService;

        public HomeController()
        {
            this.fooService = IoC.Instance.Resolve<IFooService>();
        }

        public ActionResult Index()
        {

            ViewBag.MyFoos = this.fooService.All();

            return View();
        }

generates this error:

No matching bindings are available, and the type is not self-bindable.

Error activating IFooService No matching bindings are available, and the type is not self-bindable.

Activation path:
1) Request for IFooService

Suggestions:

1) Ensure that you have defined a binding for IFooService.
2) If the binding was defined in a module, ensure that the module has been loaded into the kernel.
3) Ensure you have not accidentally created more than one kernel. 4) If you are using constructor arguments, ensure that the parameter name matches the constructors parameter name. 5) If you are using automatic module loading, ensure the search path and filters are correct.

2

2 Answers

0
votes

Are you sure you have a binding for ISetorService? I don't see one in the code you've posted.

0
votes

I solved the problem by loading all "NinjectModule" of my application hierarchy.

I thought it was sufficient loading only the main module, then created another statico method within the "NinjectWebCommon" just to separate responsibilities and organizing the code. Below is the code used:

var kernel = new StandardKernel(new Repository(), new Service(), new ValidationAndBusinessRules());

which carry all their Repositories, Services and Validators in creating the Kernel.

private static void RegisterObrigatoryServices(IKernel kernel)
        {
            kernel.Bind<IIdentityProvider>().To<ServiceIdentityProvider>();
            kernel.Bind<Guid>().ToMethod(ctx => default(Guid)).Named("CurrentProcessId");
            kernel.Bind<ISession>().ToMethod(ctx =>
            {
                SessionPoolManager.Update();

                Guid processId = kernel.Get<Guid>("CurrentProcessId", new Parameter[] { });

                if (processId == default(Guid))
                {
                    return SessionFactoryBuilder.SessionFactory(kernel.Get<IIdentityProvider>()).OpenSession();
                }
                else
                {
                    ISession session = SessionPoolManager.Get(processId);
                    if (session == null)
                    {
                        session = SessionFactoryBuilder.SessionFactory(kernel.Get<IIdentityProvider>()).OpenSession();
                        SessionPoolManager.Register(processId, session);
                    }

                    return session;
                }
            });
        }

method created by me within the NinjectWebCommon as mentioned above, only to record the required dependencies.

All this code is basically native and has been inserted into the Nuget Ninject.MVC4 package (installed via Package Manager Console within Visual Studio). This package inserts a class in App_Start directory called "NinjectWebCommon," and it is that I made these changes.

the controler is set to send the package documentation, as follows:

public class HomeController : Controller
        {
            private readonly IFooService fooService;

            public HomeController(IFooService fooService)
            {
                this.fooService = fooService; //Daqui para frente é possível usar normalmente o service.
            }
        }