avalon-phoenix-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Igor Fedorenko <ifedore...@thinkdynamics.com>
Subject Re: three improvements to avalon/phoenix
Date Tue, 27 Aug 2002 14:00:40 GMT
Peter Donald wrote:
> Hi,
> Okay - after playing with your code for a while, heres my current thoughts.
> On Thu, 22 Aug 2002 01:18, Igor Fedorenko wrote:
>>During implementation of the block factories I've got a few issues I
>>would like to discuss.
>>First, it is not clear to me if block factories belong to applications
>>or to the kernel. 
> My impression is that Factories are generally something that a user may want 
> to use and thus they should really be in "userland". However while we are 
> "evolving" them I think it is best we keep them in "kernel" land. That way we 
> can change them with little regard to backwards compatability - at least 
> until we move them back into userland. Thoughts? 
Well, here is the reason I did not implement it this way. Consider my 
remote jmx use case. Proxy block remote-mbean depends on "userland" 
object remote-jmx-server. For me it is a strong indication that 
remote-mbean belongs to "userland". Proxy block and its factory are 
tightly coupled that makes it desirable to deploy factory into userland 
  as well. Think for example about classloading issues we would have to 
solve if the factory was deployed into kernel.

> Then again it may only be "power" users who use factorys so we may be able to 
> get away with a set of them in kernel and just having the implementation keys 
> point to sufficently detailed descriptors.
>>Here are my pros and cons
>>Factories are part of applications
>>Pro: factories provide application specific logic to initialize blocks
>>thus they belong to applications
>>Con: factories provide application metadata (specifically, BlockInfo)
>>this means they must be up-and-running before an application is started.
>>Initialization of factories as part of application startup has following
>>problems - factories' lifecycle needs to be managed separately from
>>other application blocks; it is difficult to verify application
>>consistency due to the fact that factories must be started before rest
>>of the application is even assembled.
> We already handle listeners differently and the next rev of the kernel will 
> likely handle lots of different styles of components. So we can build it with 
> this in mind. We could easily make it so that
> * all factorys get started, then
> * all listeners get started, then
> * all blocks get started
This is exactly what the patch does ;-). The issue here is that 
factories must be started before application is assembled what makes it 
difficult to verify application and initialize factories with 
application context.

>>Second, implementation of objects returned from
>>BlockFactory#createObject gets pretty ugly.
>>To describe the problem better let me introduce usage scenario we can
>>talk about. My test system consists of two JVM (JVM-A and JVM-B). JVM-A
>>runs MX4J MBeanServer and has "mydomain:name=mybean" mbean of type
>>test.MyMBean and JRMP adaptor for remote access. JVM-B run phoenix
>>application which has block "jmx-client" that needs services provided by
>>"mydomain:name=mybean". Both JVM-A and JVM-B have same lifetime, i.e.
>>they both started and stopped simultaneously. Lets also assume that
>>JVM-B has "remote-jmx-server" block that provides service
>>"mx4j.connector.RemoteMBeanServer" and knows how to connect to JVM-A.
>>Problem: write and deploy "remote-mbean" block that provides service
>>"test.MyMBean" to JVM-B.
>>The issue is that "remote-mbean" block needs to implement service
>>interface which is not known at block's compile time as well as a number
>>of avalon's interfaces (Serviceable in particular). My original proposal
>>had new phoenix interface "org.apache.avalon.phoenix.Invokeable" which
>>extends "java.lang.reflect.InvocationHandler". Implementation of this
>>interface informs phoenix that it should call block.invoke(..) when
>>somebody wants to use block's services. Now I also want to introduce yet
>>another interface "org.apache.avalon.phoenix.ProxyProvider" that'll have
>>single method "Object getProxy()" and will serve same purpose as
>>Invokeable but use proxy object provided by the block.
> I am not sure I entirely follow this. But let me just get this straight. We 
> have a local block that is dynamically defined to implement some interface 
> "MyRemoteService" - which it does not know at compile time?
> I think I would like to see that solved in the followin manner. Each factory 
> is responsible for defining the object in whatever way they see fit. The end 
> result is just that the object coming out of the factory must implement the 
> service interfaces and any avalon interfaces it needs to implement.
> This way, both proxy and Invokable become implementation details of the 
> factory rather than part of the phoenix API layer. So your factory would end 
> up having a method like
> public Object createBlock( ... )
> {
>   MyBlockDelegator delegator = ...;
>   //delegator is serviceable
>   Class remoteInterface = determineRemoteInterface();
>   myInvocationHandler = new ...;
>   Class[] api = new Class[] { Serviceable.class, remoteInterface };
>   return Proxy.newProxyInstance( classloader, api, myInvocationHandler );
> }
> By doing it this way, we only have to get the factory API right and we can 
> experiment to our hearts content whether to use proxys, or Invocable or 
> whatever really. Like?
I agree that Invocable/ProxyProvider interfaces are irrelevant to
factories (consider them as another separate improvement), however 
without them it would be more difficult/tedious/error-prone to solve 
original problem of "importing" remote service into phoenix apps.

Igor Fedorenko
Think smart. Think automated. Think Dynamics.

To unsubscribe, e-mail:   <mailto:avalon-phoenix-dev-unsubscribe@jakarta.apache.org>
For additional commands, e-mail: <mailto:avalon-phoenix-dev-help@jakarta.apache.org>

View raw message