We have recently started using the unity container in our code base as a means to reduce our dependency management complexity and things like that. Since our code base is kind of big, and very convoluted (with some very bad practices in some places), I
have not checked in the code yet, and have been experimenting with ways to approach the problem as to not interfere with the rest of the code (this will need to be incremental, so I'm not adding DI to everything just yet, just the basic structure and wiring).
After trying some things, I found an excellent post on stackoverflow, by Mark Heath, about a custom factory extension that would enable one to pass in a factory to create proxy remoting objects instead of concrete classes.
This was very fit to our reality as we have a bunch of separate web applications communicating over remoting, so I replicated the classes here and added the extension to the container. The problem I'm having with this though is that my factory is being called
every time Resolve is called on the container. I would expect it to be called only the first time, and that after that, the stored singleton object would be returned.
My implementation is a bit simpler than his, because I'm not worried about child containers and stuff like that, so there is no need for the custom marker policy class there and all the extra handling on the strategy to find the marker.
So, I basically substituted this:
// Find the container to add this to
var parentMarker = context.Policies.Get<ParentMarkerPolicy>(new NamedTypeBuildKey<ParentMarkerPolicy>(), out parentPolicies);
// TODO: add error check - if policy is missing, extension is misconfigured
// Add lifetime manager to container
parentPolicies.Set<ILifetimePolicy>(ltm, new NamedTypeBuildKey(key.Type));
// And add to LifetimeContainer so it gets disposed
context.Policies.Set(ltm, new NamedTypebuildKey(key.Type));
I'm kind of bummed by the fact that, when I compare two instances returned by consecutive Resolves (in the immediate window for instance), they are actually the same instance. It's as if the strategy is recreating the instance through the factory, but this
newly created instance is not being returned, but the cached one. I think that if I just called Activator.GetObject twice they would be different instances right?
As a matter of fact, I'm not entirely sure what the whole code is doing here, since I've basically copied and adapted it. It would be nice if someone was able to point me to documentation describing the correct steps in implementing a custom extension and how
everything works together. I managed to create a completely custom application block in the Entlib by following the tutorial, but in this case here it is just too hard to get something working as expected without knowing how the underlying mechanics actually
use your classes. If I at least knew what happened in the life cycle of the container, or the steps involved when one requests an object or a BuildUp, and things like that maybe I could work out a solution on my own.
Even so, why is this strategy being called on every resolve for the same object? How are the strategies called anyways? Does it call every strategy in order on the strategy chain in the container, and stops on the first one that sets the BuildComplete flag?
Maybe I'm wiring this the wrong way somehow, and my strategy is running earlier than it should? Am I missing something else here?