I am posting the conclusions of my conversations yesterday with Emmanuel regarding the ServerEntry API and various related matters here for tracking and availability to the community. Also I am adding additional information on how far we have progressed in phase II.
The Entry API is a new programming interface for managing entries, their attributes and the values in those attributes. This API is going to replace the JNDI interfaces (Attribute and Attributes) we were using up until this point as part (phase II) of the big bang refactoring initiative. We have discovered several shortcomings with using JNDI interfaces and one of them deals with how entries, attributes and values are managed. The server-side specific extension is a ServerEntry. Unlike JNDI interfaces it's interfaces are DN and schema aware. These new interfaces are designed to prevent anomalies that result with attribute and value containment when schema is not properly consulted.
Likewise we are replacing other JNDI constructs like the NamingEnumeration with a new interface that is better suited to operations within the lower data handling layers of the server. The Cursor interface is the new interface that will replace NamingEnumerations. This API is more specifically geared towards our needs and prevents several issues we've faced with the JNDI NamingEnumeration interface which is generalized to accommodate every naming system that SUN could think of.
A ServerEntry requires knowledge of schema information to make sure things like, removal, addition and value lookups occur properly. A ServerEntry extends Entry. The LDAP codec which could operate on a client or on a server must [de]marshal LDAP PDU's into these objects. Rather than instantiate these objects itself we realized that it is best off delegating instantiation to some kind of factory which can be handed to it. This way if in a server the proper kinds of entries with schema knowledge are created transparently, and on the client side schema a different kind of factory can be used which does not need schema information.
We have a bit of a chicken and egg problem while configuring the server. The server needs ServerEntry instances for the RootDSE and for the root of partitions (the namingContexts). To start the server some minimum of schema information is required. For this reason we plan to make the DirectoryService either extend the EntryFactory interface or have it contain a reference to an EntryFactory implementation. Further more the default constructor on the DefaultDirectoryService will initialize the bootstrap schemas needed to minimally startup the server so it can initialize properly. This way the DirectoryService object or it's contained ServerEntryFactory will be able to instantiate ServerEntry objects on behalf of requestors with a means to access at least a minimal set of schema information.
Emmanuel and I were debating whether to use containment or inheritance. I prefer containment myself but Emmanuel pointed out that the interface for ServerEntryFactory is simple and has a single method. So perhaps having DirectoryService extend this interface for now is more pragmatic. If the interface grows we can re-factor and use containment instead. Emmanuel can comment but I think he wants to avoid calls like:
directoryService.getEntryFactory().newEntry( new LdapDN( "..." ) );
Instead with extension we would have:
directoryService.newEntry( new LdapDN( "..." ) );
So the later looks like a cleaner approach. I will soon implement this. I already committed a portion of this in this revision:
Cursor API Progress
I guess most of you see the commit messages go by and notice that I am working in my sandbox on the Cursor API which is to replace the use of NamingEnumerations in the core. I did this so I would not break many things in the big bang which some of you are working on. This has not progressed as rapidly as I wanted it to. However there are some deep changes that will impact several aspects of the server and the way it conducts search operations so this is not a simple matter.
I do have what feels like an almost complete interface. The Cursor is working well and solving several issues that we have had with NamingEnumerations. It will also allow us to eventual (after 2.0 I guess) move the search algorithm out of the Partitions. There are also several freedoms that come with this new API that I am discovering as I use it specifically because it is bidirectional with next() and previous() methods unlike the NamingEnumeration which is not.
Right now I am really worried about the impact this has on the server. It takes a lot for me to branch privately so I may abandon this work if the next week or two does not make me more confident.