Windsor: Designing lazy handlers & lazy handler resolution

7 views
Skip to first unread message

Ayende Rahien

unread,
Aug 11, 2009, 12:25:38 PM8/11/09
to castle-pro...@googlegroups.com
This represents a summary of options for the issues raised in Design questions for resolution of IOC-ISSUE-161 in the users list.
First, I want to define a few terms.
Windsor is using the IHandler abstraction to manage all the construction and management related tasks for a single component.
Managing set of handlers is the responsability of the naming sub system and the entire thing is orchestrated as part of the kernel.

The scenario that came up in the users list is WCF integration.
In this case, it seems like we can simply scan the list of registered services and load that into Windsor using some sort of a custom handler.
This is all static resolution, without needing to do much for us.

One key aspect of the way that Windsor works is that it will not perform external dependency resolution.
That is, Windsor doesn't have any way of asking, at the time of resolution, whatever a component is valid or not (custom parameters aside).
This is done so we can perform as much of the work upfront, vs. having to do it at the time of resolution.

Going to the MEF scenario, let us say we have this:

 class FooService(IUserRepository ..)

And we register that in the container. The IUserRepository is not registered, so FooService is marked as WaitingDependency.

Let us assume further that we have a MEF catalog that can provide that dependency and that we have a MefHandler that can create instances from a MEF catalog.
In order to cleanly integrate that with Windsor, it is not enough that we join the MEF catalog to Windsor. We would have to register all the exports inside the catalog in Windsor as handler, since that is the only way Windsor will mark waiting dependencies as valid.
We would also need to keep track of changes in the catalog (possible with the ExportsChanged event) and refresh them when they change.

Basically, we have two different choices. Forwarding handlers, which would delegate their responsibilities to an external provider, are very easy to build.
Integrating a catalog, however, is a more complex task, since Windsor makes the assumption that it is managing the entire set. 
We can deal with that by basically duplicating a catalog inside Windsor. 
I don't like it very much, to tell you the truth.

A better option is to avoid the entire question and change INamingSubsystem so that we can provide external feedback to it. This would mean that we would still need IHandler abstraction, but it wouldn't be managed by Windsor directly.
The only requirement that we have at that point is that we would need to invoke HandlerRegistered for each component in the catalog that has changed.

Thoughts?

Krzysztof Koźmic

unread,
Aug 11, 2009, 5:10:34 PM8/11/09
to castle-pro...@googlegroups.com
+1 for the last option,

Now, let me go over it so that we're sure we're on the same page.
- Windsor tries, but can't resolve component/dependency 'the old way'.
- It asks ILazyHandlerProvider(s) if any of them can do this given...
probably either type, name or both.
- ILazyHandlerProvider returns IHandler if it can.
- Windsor registers the handler and proceeds with resolution.

Ay?

Ayende Rahien

unread,
Aug 11, 2009, 6:12:46 PM8/11/09
to castle-pro...@googlegroups.com
Nope, at least not the way I see it.
INamingSubsystem get extends to have additional providers.
When I ask for a HasComponent, the naming subsystem queries itself and then all the additional providers until it find one.

On adding a new provider, we invoke HandlerRegistered on all the components that it knows
On change in a provider, we invoke HandlerRegistered on the change.

providers are ordered ( and queried ) in the order they are added.

This gives us a well known system, I think.


2009/8/12 Krzysztof Koźmic <krzyszto...@gmail.com>

Craig Neuwirt

unread,
Aug 11, 2009, 7:24:36 PM8/11/09
to castle-pro...@googlegroups.com
At what point can the handler providers just register with the kernel (lazy registration)

Ayende Rahien

unread,
Aug 11, 2009, 7:39:05 PM8/11/09
to castle-pro...@googlegroups.com
Not sure that I am following the question

2009/8/12 Craig Neuwirt <cneu...@gmail.com>

Craig Neuwirt

unread,
Aug 11, 2009, 8:53:28 PM8/11/09
to castle-pro...@googlegroups.com
Sorry :-)  I think a common pattern would be to give the handler provider an opportunity to register additional components on demand.  So the end result would be a request by the kernel to resolve a particular service which is not currently available at which point the handler provider could possibly register the component based on somehing (web.config, MEF Catalog) and be done with it.  This is in contrast to a true deferred resolution in which a handler surrogate is returned to make kernel dependencies happy, while the actual component is resolved when actually needed.  Does this make sense or did my brain get too much sun ;-) 

2009/8/11 Ayende Rahien <aye...@ayende.com>

Ayende Rahien

unread,
Aug 11, 2009, 10:24:20 PM8/11/09
to castle-pro...@googlegroups.com
Yes, it make sense, but this stands contrary to the way Windsor currently built, and it makes it _hard_ to do things.
More to the point, it kills any way of analyzing the dep graph and deciding if it is safe or not.
Can you think of a good scenario where we want this, vs. just having a provider that give us a list of extended services?

2009/8/12 Craig Neuwirt <cneu...@gmail.com>

Craig Neuwirt

unread,
Aug 12, 2009, 8:27:31 AM8/12/09
to castle-pro...@googlegroups.com
inline

2009/8/11 Ayende Rahien <aye...@ayende.com>

Yes, it make sense, but this stands contrary to the way Windsor currently built, and it makes it _hard_ to do things.
More to the point, it kills any way of analyzing the dep graph and deciding if it is safe or not.
Can you think of a good scenario where we want this, vs. just having a provider that give us a list of extended services?

I agree with you, but at what point will the handlers get registered in the container and how will the handler providers create the handlers?  I would all handlers to be create through the kernel.  I am also worried about timing.  The components from a handler provider should not take precedence over explicitly registered components so if the handler providers is added before the components, how can we ensure that explicit components will come first

Ayende Rahien

unread,
Aug 12, 2009, 1:30:10 PM8/12/09
to castle-pro...@googlegroups.com
I think that it should be done at the point when they are added to the kernel.
Since we don't manage them explicitly, and since we will check the INamingSubSystem before checking the extensions, precedence should not be an issue.

2009/8/12 Craig Neuwirt <cneu...@gmail.com>

Craig Neuwirt

unread,
Aug 12, 2009, 1:43:16 PM8/12/09
to castle-pro...@googlegroups.com
I think I am a little confused.   Could you explain the following statements a little more

On adding a new provider, we invoke HandlerRegistered on all the components that it knows
On change in a provider, we invoke HandlerRegistered on the change.

Do the actual components get registered with kernel at that point? What raised the HandlerRegistered??

If so, it seems to conflict with the following statement

When I ask for a HasComponent, the naming subsystem queries itself and then all the additional providers until it find one.


2009/8/12 Ayende Rahien <aye...@ayende.com>
Reply all
Reply to author
Forward
0 new messages