Sergey Prosin
Sergey Prosin

Reputation: 11

Unity2 resolve problem

guys. We are using MS Unity 2 framework for an application.

We have code similar to described below

public class Context:IContext
{
    public IFlow Flow {get;set;}
}

public class SomeFlow:IFlow
{
    public IContext Context {get;set;}
}
...
//Some code for getting IContext object
{
     ...
     IContext context = container.Resolve<IContext>();
     ...
}

We need to describe the relationship between the classes Context and SomeFlow using Unity. And the problem with constructing is while container is constructing Context object it needs to create SomeFlow object which requires Context object and so on. In our case SomeFlow object must contain link to the Context object created before. So the algorithm must be next:

1. Create Context object
2. Create SomeFlow object
3. Point Context.Flow to SomeFlow
4. Point SomeFlow.Context to Context

And the question is how could we describe it with unity?

Upvotes: 1

Views: 95

Answers (2)

Steven
Steven

Reputation: 172666

Alternatively to Mark's answer you can register an InjectionFactory that does the wiring for you. Registering the following delegate prevents you from having to change your application design:

container.Register<IContext>(new InjectionFactory(c =>
{
    var context = container.Resolve<IContext>();
    var flow = container.Resolve<IFlow>();
    context.Flow = flow 
    flow.Context = context;
    return context;
}));

Upvotes: 1

Mark Heath
Mark Heath

Reputation: 49482

You can do this with constructor injection to give the Flow its context, and then in the constructor set up the backwards reference. Here's a simple example:

public interface IContext { IFlow Flow { get; set; } }
public interface IFlow { IContext Context { get; } }

public class Context : IContext
{
    public IFlow Flow { get; set; }
}

public class SomeFlow : IFlow
{
    public SomeFlow(IContext context)
    {
        this.Context = context;
        context.Flow = this;
    }
    public IContext Context { get; set; }
}

[Test]
public void Example()
{
    IUnityContainer container = new UnityContainer();
    container.RegisterType<IContext, Context>();
    container.RegisterType<IFlow, SomeFlow>();
    var flow = container.Resolve<IFlow>();
    Assert.IsInstanceOf<Context>(flow.Context);
    Assert.IsInstanceOf<SomeFlow>(flow);
    Assert.AreSame(flow, flow.Context.Flow);           
}

Upvotes: 2

Related Questions