5

I've got this pattern

public abstract class BaseController : Controller
{
    readonly RepositoryFactory _rep;
    protected RepositoryFactory rep
    {
        get
        {
            return _rep;
        }
    }

    readonly ManageRoles _man;

    readonly ElementAvailableForUser _env;
    protected ElementAvailableForUser env
    {
        get
        {
            return _env;
        }
    }

    public BaseController()
      : this(DependencyResolver.Current.GetService<RepositoryFactory>(),
             DependencyResolver.Current.GetService<ManageRoles>(),
             DependencyResolver.Current.GetService<ElementAvailableForUser>()) { }

    public BaseController(RepositoryFactory rep, ManageRoles man, ElementAvailableForUser env)
    {
        _rep = rep;
        _man = man;
        _env = env;
    }
}

so I am able to do something like this

public class HomeController : BaseController
{
    public ActionResult Index()
    {
        return View(rep.Offers.GetAll());
    }

    public ActionResult Sections()
    {
        return View(env);
    }
}

in all my controller. I'm sure this is antipattern for DI and IoC, so I thin a solution like this

public abstract class BaseController : Controller
{
    ...

    // removed empty constructor

    public BaseController(RepositoryFactory rep, ManageRoles man, ElementAvailableForUser env)
    {
        _rep = rep;
        _man = man;
        _env = env;
    }
}

public class HomeController : BaseController
{
    public HomeController(RepositoryFactory rep, ManageRoles man, ElementAvailableForUser env) : base(rep, man, env) { }

    ...
}

but this solution requires me to insert all dependencies in all controllers and update all constructor if I need a new global variable (like rep) or a new private variable for basecontroller (like man).

Which pattern should I follow and why?

Edit I found this question, and this, but still I can't understand which design patterns should I follow.

2
  • 1
    What makes you think there's a design pattern you should follow? Commented Oct 12, 2011 at 15:08
  • Cause only one of this should be used in my application. Commented Oct 12, 2011 at 15:17

2 Answers 2

3

It doesn't seem like you need the BaseController in this case. I think it would be easier (and more testable) to do something like this:

    public class HomeController : Controller
    {
        private readonly IRepository<Offers> _repository;
        private readonly RoleManager _roleManager;
        private readonly UserManager _userManager;

        public HomeController(IRepository<Offers> repository, RoleManager roleManager, UserManager userManager)
        {
            _repository = repository;
            _roleManager = roleManager;
            _userManager = userManager;
        }
    }

Then you could have your IoC container wire up all of those dependencies automatically for each controller.

Sign up to request clarification or add additional context in comments.

1 Comment

Yes, this could be the case, but I need to populate the object in the same way for all the controller, and I do this in actionexecuting method of base controller.
0

I don't think with the thin solution you need to always declare rep, man, and env. You could take advantage of default/optional parameters.

public BaseController(RepositoryFactory rep = null, ManageRoles man = null, ElementAvailableForUser env = null)
{
    _rep = rep;
    _man = man;
    _env = env;
}

Then you can use named parameter assignments:

public class HomeController : BaseController
{
    public HomeController(ManageRoles man) : base(man: man) { }

    ...
}

1 Comment

Yes, but in this case the IoC doesn't work and "man" results always null if has not been explicited declared in child controller.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.