CastleWindsor LifeStyle.PerWebRequest behaves like a singleton

I am trying to create a UserService that I can embed in my classes that will contain the user who is currently logged in. I use CastleWindsor as a container.

Now my problem is that I'm trying to make my UserService one-time, so the data collection created by the user at creation will also be deleted when the object is destroyed.

I added the following setting to my Global.asax.cs file:

private static void BootstrapContainer()
{
    _container = new WindsorContainer().Install(FromAssembly.This());

    var controllerFactory = new WindsorControllerFactory(_container.Kernel);
    ControllerBuilder.Current.SetControllerFactory(controllerFactory);

    GlobalConfiguration.Configuration.DependencyResolver = new WindsorDependencyResolver(_container.Kernel);

    _container.Register(Component.For<IUserService>()
        .LifestylePerWebRequest()
        .ImplementedBy<UserService>());

    _container.Register(Component.For<IPrincipal>()
        .LifeStyle.PerWebRequest
        .UsingFactoryMethod(() => HttpContext.Current.User));
}

which is called in mine Application_Start.

My UserService code is as follows:

public interface IUserService
{
    OrganisationBruger User { get; }
    int UserId { get; }
}

public class UserService : IUserService, IDisposable
{
    private readonly IPrincipal _principal;
    private OrganisationBruger _user;
    private readonly DatabaseDataContext _db;

    public UserService(IPrincipal principal, IDatabaseDataContextFactory dataContextFactory)
    {
        _principal = principal;
        _db = dataContextFactory.GetDataContext();
    }

    public OrganisationBruger User => _user ?? (_user = GetUser());
    public int UserId => Convert.ToInt32(_principal.Identity.Name);

    private OrganisationBruger GetUser()
    {
        return _db.OrganisationBrugers.Single(u => u.ID == UserId);
    }

    public void Dispose()
    {
        _db.Dispose();
    }
}

, , , UserService.cs, -. , - , . , DatabaseContext .

, LifestylePerWebRequest , UserService . - ?

+4
3

, " " - . web.config:

<httpModules>
   <add name="PerRequestLifestyle" type="Castle.MicroKernel.Lifestyle.PerWebRequestLifestyleModule, Castle.Windsor"/>
</httpModules>

-, , . , , UserService , Singleton, , .

, , , UserService , LifestylePerWebRequest() LifestyleTransient().

0

, - , IUserService, . Windsor Castle IUserService , ITest singleton.

 _container.Register(Component.For<ITest>()
        .LifestyleSingleton()
        .ImplementedBy<Test>());

public interface ITest
{

}

public class Test: ITest
{
    private readonly IUserService _ser;

    public Test(IUserService ser)
    {
        _ser= ser;
    }
}
0

I have a WindsorHttpControllerActivator that implements IHttpControllerActivator. It registers the controller for disposal, which ensures the creation of a new controller for each request by destroying the old one. This happens when .LifestylePerWebRequest () completes each request.

        public IHttpController Create(
        HttpRequestMessage request,
        HttpControllerDescriptor controllerDescriptor,
        Type controllerType)
    {
        var controller =
            (IHttpController)_container.Resolve(controllerType);

        // Controller disposal ensures new controller for each request, hence DbContexts are fresh and pull fresh data from the DB.
        request.RegisterForDispose(
            new Release(
                () => _container.Release(controller)));

        return controller;
    }

    private class Release : IDisposable
    {
        private readonly Action _release;

        public Release(Action release)
        {
            _release = release;
        }

        public void Dispose()
        {
            _release();
        }
    }
0
source

Source: https://habr.com/ru/post/1625120/


All Articles