You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@abdera.apache.org by Garrett Rooney <ro...@electricjellyfish.net> on 2006/10/09 03:36:56 UTC

Problems decoupling extensions from parser back end

So, on the flight out to ApacheCon I finally got a chance to hack on
my "stop requiring extensions to be intimately familiar with the
parser back end" project.  I played around enough to flesh out my
ideas for how to make that work, but I ended up running into a brick
wall, and I'm curious if others have any ideas for how to go forward
from here.

So, my plan was to make Factory.newExtensionElement actually take an
Element object representing the current element as one of its
arguments.  The ExtensionFactory implementations would be responsible
for taking this Element and returning a new one of the proper type,
most likely by returning a wrapper class that forwards through to the
underlying Element for all but the extension specific functionality.
i.e. my OpenSearch ItemsPerPage implementation would look like this:

public class ItemsPerPageImpl
  extends WrapperElement
  implements ItemsPerPage {

  private static final long serialVersionUID = 4343427206133794002L;

  public ItemsPerPageImpl(Element wrapped)
  {
    super(wrapped);
  }

  public int getCount()
  {
    return Integer.parseInt(getText());
  }

  public void setCount(int count)
  {
    setText(String.valueOf(count));
  }
}

If you wanted to provide a constructor that gives back an empty
ItemsPerPage that someone could use to construct a feed you'd just
provide a constructor or helper method that takes a Factory object as
an argument.  Actually, it really should have that, it's just that I
never implemented that side of things for the OpenSearch extensions.
Also, assume a WrapperElement class that just implements all methods
as forwarding to another element object.

So, what's the problem with this?  Well, the issue is that the current
parser back end REALLY wants all Elements that it messes with to
extend from OMElement, like FOMElement does, and in
FOMFactory.createElement we die with a ClassCastException when we try
to cast from the return value of newExtensionElement to an OMElement,
because the element we get back extends from WrapperElement not
OMElement.

So to make this work, we need to make the FOM* stuff not assume that
all Element objects are OMElements.  I started working on pushing that
change through, but got frustrated at all the places that seem to make
that assumption.  Obviously, as long as those assumptions remain each
extension is going to have to have some intimate knowledge of the
underlying parser, or it won't be able to return the appropriate type
of objects.

My question is, is there any other solution I'm missing?  Is it
reasonable to expect our parser internals to just speak in terms of
Elements?  Should I head down that road first, before making the
actual extension changes?  If not, shouldn't we be asking why our code
needs to know more about the underlying objects but our consumers
shouldn't?  If we find that functionality useful, wouldn't other
people?  Just thinking out loud at this point, I really don't know
enough about the parser implementation to know if I'm even on the
right track here.

Thoughts?

-garrett

Re: Problems decoupling extensions from parser back end

Posted by James M Snell <ja...@gmail.com>.
This is definitely a difficult problem (which is why I completely punted
on it during the initial design and implementation ;-) ...). As you've
discovered, because of the way Axiom has been designed, we're
particularly dependent on the OM* classes in pretty much every aspect of
our implementation.

There are basically three reasons why we are using Axiom in the first place:

 1. The incremental parsing model is very efficient
 2. The fact that it maintains the complete XML infoset makes it
possible for us to support things like XML Digital Signatures
 3. Efficient and well-implemented XML serialization

The first is by far the most important.  If we can get the FOM* objects
speaking just in terms of the org.apache.abdera.model.* interfaces
without sacrificing any of the above three points, then we should do so.

FOMParser and FOMFactory will always need to understand the OM* base.
The various FOMElement derived classes could be made agnostic with a bit
of effort.

- James

Garrett Rooney wrote:
> [snip]
> My question is, is there any other solution I'm missing?  Is it
> reasonable to expect our parser internals to just speak in terms of
> Elements?  Should I head down that road first, before making the
> actual extension changes?  If not, shouldn't we be asking why our code
> needs to know more about the underlying objects but our consumers
> shouldn't?  If we find that functionality useful, wouldn't other
> people?  Just thinking out loud at this point, I really don't know
> enough about the parser implementation to know if I'm even on the
> right track here.
> 
> Thoughts?
> 
> -garrett
>