Reputation: 11117
I was wondering if it's possible to make an object of a class that has a constructor with an injection of another class.
The class i want to instantiate:
using ClearBlog.IRepository;
using ClearBlog.Models;
namespace ClearBlog.Areas.Admin.Classes
{
public class AdminArticleTags
{
private readonly IGenericRepository<ArticleTag> _db = null;
public AdminArticleTags(IGenericRepository<ArticleTag> db)
{
_db = db;
}
public int InsertNew(int article, int tag)
{
// do smt here
}
}
}
I want to use the InsertNew
method of the above class in another class like this:
using System.Linq;
using System.Web.Mvc;
using ClearBlog.Models;
using ClearBlog.Helpers;
using ClearBlog.IRepository;
using ClearBlog.Areas.Admin.Classes;
namespace ClearBlog.Areas.Admin.Controllers
{
public class Someclass : Controller
{
private readonly IGenericRepository<Tag> _db = null;
public Someclass(IGenericRepository<Tag> db)
{
_db = db;
}
public ActionResult Index()
{
AdminArticleTags at = new AdminArticleTags();
at.InsertNew(10, 15);
}
}
}
That is not possible now because of the constructor expecting an IGenericRepository
.
Is it even possible?
If it's not, then what way do you recommend? mind the fact that I need to use the IGenericRepository
that is the interface used by Ninject to bind to an implementation.
edit:
what I'm trying to do is very simple. I just want to make an object of AdminArticleTags
and access it's method inside Someclass
. even if i make an parameterless constructor for AdminArticlesTags
it gives errors because it not going to inject IGenericRepository
for that object. (because of constructor)
How would i make an object of AdminArticlesTags
and use its methods??
edit2:
this is where i do Ninject bindings:
using Ninject;
using System;
using System.Collections.Generic;
using System.Web.Mvc;
using ClearBlog.IRepository;
using ClearBlog.Repository;
using AutoMapper;
namespace ClearBlog.Infrastructure
{
public class NinjectDependencyResolver : IDependencyResolver
{
private IKernel kernel;
public NinjectDependencyResolver(IKernel kernelParam)
{
kernel = kernelParam;
AddBindings();
}
public object GetService(Type serviceType)
{
return kernel.TryGet(serviceType);
}
public IEnumerable<object> GetServices(Type serviceType)
{
return kernel.GetAll(serviceType);
}
private void AddBindings()
{
kernel.Bind(typeof(IGenericRepository<>)).To(typeof(GenericRepository<>));
kernel.Rebind<IMappingEngine>().ToMethod(context => Mapper.Engine);
}
}
}
Upvotes: 1
Views: 5616
Reputation: 27861
Use Constructor Injection.
If you don't care about obtaining a new instance of AdminArticleTags
every time, then simply inject a AdminArticleTags
into the controller like this:
public class Someclass : Controller
{
private readonly AdminArticleTags m_AdminArticleTags;
public Someclass(AdminArticleTags aat)
{
m_AdminArticleTags = aat;
}
public ActionResult Index()
{
m_AdminArticleTags.InsertNew(15, 42);
}
}
Since you are using Ninject, it would be able to create the controller and pass the correct dependency.
If you require a new instance everytime inside the Index
action, then you need some kind of factory. You can use the Func
class like this:
public class Someclass : Controller
{
private readonly Func<AdminArticleTags> m_AdminArticleTagsFactory;
public Someclass(Func<AdminArticleTags> factory)
{
m_AdminArticleTagsFactory = factory;
}
public ActionResult Index()
{
AdminArticleTags at = m_AdminArticleTagsFactory();
at.InsertNew(15, 42);
}
}
In this case, you would have to install the Ninject.Extensions.Factory nuget package. This will allow the support of resolving Func
based factories. Take a look at this.
An alternative to Func
based factories are factory interfaces. Take a look at this.
Upvotes: 3
Reputation: 111
yes. you can inject code even when the class has a parameterized constructor. though, it depends on how and with what technique/framework you inject.
what you are doing in the example is not injection. just a simple instanciation. in addition, your code will not compile because you did not define an empty or a default constructor.
maybe if you give more details about you are trying to achieve it will be easier to assist specifically.
Upvotes: 0