Knut Wannheden schrieb:
Achim,
Browsing the code in your HiveMind 2.0 experimental branch I jotted
down the following comments / questions:
- The split of the framework and xml sources into separate modules
looks excellent! It makes the framework quite a bit leaner. I found a
few sources which I think maybe ended up in the wrong place (see
following comments).
- The ObjectProvider interface is in the XML source module. I believe
this should be part of the framework. We might for example also want
to use that in the annotation support to inject objects into
parameters of methods creating service implementations.
Yes and no. There might be a use case that justifies putting the
ObjectProviders
in the framework but I don't regard annotations as one.
I wouldn't do anything textual in annotations which could be implemented
in pure java without any extra work. Let's have a look at the
current object providers:
ClassObjectProvider: -> trivial in java code
ConfigurationObjectProvider -> just call getConfiguration() in an
annotated module
ObjectInstanceProvider -> trivial in java code
ServiceObjectProvider -> just call getService() in an annotated module
ServicePropertyProvider -> just call getService() and then any getter method
BeanFactoryProvider -> create the bean manually or call a factory method
For the moment it could stay in the xml module and if needed we could
move it without breaking compatibility?
- On the other hand I wonder if instead the SymbolSource classes along
with the symbol expansion code should be moved into the XML module.
They are used to resolve Ant style ${}-properties in the XML
descriptors. Do we want to support these in other module descriptors
(e.g. annotation based Java classes) also?
I regard it as another simple configuration mechanism for an application.
But there may be better (and even typed) ways to read system properties etc.
My first attempt to break the deep integration with the registry failed
but if we decide to move it to xml I could make another try.
- I noticed the ServiceImplementationFactory is in the xml module.
Maybe we could also move the ServiceInterceptorFactory to the xml
module. Although I think some of its implementations (really only the
LoggingInterceptorFactory) should remain in the framework module which
would mean it can't implement the interface anymore. But IMHO that's
OK, because the first thing that's done in the implemented interface
method is to cast the Object parameter to a List. That could be done
by an adapter implementation in the xml module.
That's exactly how it should be done. I hope we can do it during
the redesign of the interceptor construction, when createInterceptor
will return an interceptor object.
- Now some comments on the registry construction API. I believe an
interface based registry construction API would allow for more
flexibility in the implementations. For example you'd have to
possibility of refactoring the existing *Descriptor classes in the XML
module to implement these interfaces instead of define a mapping. As
another example an implementation could chose to have a single object
implement two interfaces (e.g. ServicePointDef and ImplementationDef).
Further we could then also remove OrderedServiceInterceptorDefinition
and simply note that an implementation class can implement the
Orderable interface if ordering is required.
One problem prevented me from conversion to interfaces at all.
Configurations like ServiceModels, EagerLoad, Startup etc. are defined
in the core framework. Afterwards they get schemas assigned
from the xml module. They are a little ambivalent.
To hold the schema information they would have
to be represented by a xml specific implementation of
ConfigurationPointDefinition
which is not available in the framework when they get constructed.
Natures (or better decorators) solve this problem.
Like you mentioned below only the xml module uses natures in the moment.
This means on the other hand that all the overhead of the separation
between interfaces and implementations would be done for that
single case. Whereas natures doesn't hurt since you are not forced
to use them.
The definition classes doesn't contain any logic besides consistency
checking.
In the meantime I regard it as perfectly valid to use plain beans for them.
The java/xml/annotation-specific parts are done in the constructors which
are realized as interfaces.
- Also I think the API could be simplified by removing the distinction
between resolved and unresolved extensions. That would make the
registry builder responsible for all resolutions.
During the construction of the registry a complete object graph of
definition
items is build up where all unresolved extensions get resolved and placed
into the referenced extension points. It is quite convenient to use the same
data structure here that were used for the definition.
The RegistrySerializer (though far from being usable) uses the graph too.
Moreover it is convenient and IMHO more intuitive to attach an
implementation
defnition directly to an service definition instead of putting it
unresolved into
the module.
- What do you think about removing the natures from the API? Currently
it seems like they're used in the XML implementation to get a
reference to schemas. Maybe the code in the XML module could also just
typecast to the required implementation and get a reference to the
schema that way. IMHO the natures are overcomplicating the API.
Regards,
--knut
Relating to your last posting I'm adding some information to the wiki
currently.
Bye
Achim