[Mulgara-general] Mulgara API's

Paul Gearon gearon at ieee.org
Fri Feb 22 20:12:03 UTC 2008


On Fri, Feb 22, 2008 at 10:35 AM, Alex Hall <alexhall at revelytix.com> wrote:
> Paul Gearon wrote:
>
>  > Importantly, the server you send the command to is checking to see if
>  > it knows the graph before handing it on to this resolver.  This means
>  > a few things.  Most important is the fact that URIs for a graph need
>  > not specify protocol, location, or service.  This is all done when you
>  > establish a connection.  The URI becomes just a label for a graph.
>  > (However, it is still possible to use a graph URL to find the server,
>  > but this is for backward compatibility).
>
>  This seems to imply that graph URL's and URI's have been disambiguated.
>   Back when I was last working with this software, every graph URI was
>  also a URL using the rmi:// protocol (for graphs stored on a Mulgara
>  server, that is), and the URI was overloaded to be both a label and a
>  locator.  Is this no longer the case?

Not exactly, but we ARE getting there.  The client side stuff has been
updated to allow you to use any URI you like for a model name.
ItqlInterpreterBean will still try to use the protocol and authority
to find a server, but that is for backward compatibility.  If you use
the API, then the following nearly works:

// get a connection
ConnectionFactory factory = new ConnectionFactory();
Connection conn = factory.newConnection("rmi://localhost/server1");

// set up the commands
URI model = URI.create("foo:bar:baz");
Command create = new CreateGraph(model, MODEL_TYPE);
Command load = new Load(dataFile.toURI(), model, false);
Command query = new TqlInterpreter().parseCommand("select $s $p $o
from <" + model + "> where $s $p $o;");

// execute the commands
create.execute(conn);
load.execute(conn);
Answer a = (Answer)query.execute(conn);


>From a client perspective, this all works perfectly.  However, at the
server end, the CreateModelOperation class checks if the model has a
fragment, and fails at this point.  This appears to be a bug, as
opaque URIs are handled elsewhere in the class.  I want to test that
it works properly with resolvers, but I ought to be able to fix this
very soon, and the above code will work.

<snip/>
>  > The code in that class parsed its queries, and if it happened to
>  > notice a graph URL while parsing it would automatically change
>  > sessions, even though it was still in the middle of the parsing
>  > operation.  Even if you provided your own session, it could still
>  > arbitrarily change the session on you.  And all this was buried deep
>  > in the parsing process.  I can't begin to tell you how unmanageable
>  > this was.
>
>  Yes, I have seen some of this code, and I don't think the term
>  "unmanageable" does it justice.

I wanted to use stronger language, but I usually try to be polite in
email.  I was really letting fly when I said "sucked".  :-)

>  > For backward compatibility, the ItqlInterpreterBean is still there,
>  > but now it works differently.  Now it parses a query into a command.
>  > If the command is something that is to operate on a remote server,
>  > then it interrogates the command for the URLs of the graphs it refers
>  > to.  It then establishes new connections (caching old ones for the
>  > current ItqlInterpreterBean) as needed, and issues commands on these.
>  > If it is in a transaction, then any new connections are put into that
>  > transaction as well.  When a transaction completes, then all servers
>  > that have been spoken to during that transaction are informed that the
>  > transaction is complete.  The whole thing performs faster, more
>  > efficiently, and has greater functionality than the previous
>  > ItqlInterpreterBean.
>
>  If I'm following you correctly, this means that processing a single user
>  command can result in the ItqlInterpreterBean coordinating commands
>  across connections to multiple servers.  If that's the case, that seems
>  like a bit too much logic to have on the client side.  Am I missing
>  something here?

For client *code* it is certainly more logic than you want.  But as
soon as I have SPARQL going I'll be documenting how everyone should be
moving to using Connections anyway.  Client code should thereafter
stay away from ItqlInterpreterBean.  This complexity is really to
support the command prompt, which will not be going away.  In the
meantime, it also provides ItqlInterpreterBean functionality to make
it easier to transition.

>  >> Creating commands manually is probably the method I would prefer, if
>  >> the
>  >> alternative is building up an ITQL string and then sending it back
>  >> through the parser.  You're right, this calling convention feels
>  >> pretty
>  >> awkward.  If I decide to go down this route, I would certainly be
>  >> willing to take a look at refactoring that code.
>  >
>  > Actually, it's just a matter of changing it to a visitor pattern.
>  > Connections just need to implement an execute method for every Command
>  > type, with the form:
>  >
>  > Object execute(CommandImplementation cmd) { return cmd.execute(this); }
>  >
>  > This is standard boilerplate visitor pattern stuff, and one of the
>  > reasons I hate Java.  :-)
>  >
>  > It would only take 10 minutes to do.  Maybe I'll do it in the morning.
>  >
>  > (yes, these methods can be avoided by putting all the functionality in
>  > a Connection class, avoiding the callback, but this does not use
>  > encapsulation or information hiding, and makes for a monolithic class,
>  > which is always a bad idea.)
>
>  Monolithic class, as in DatabaseSession? ;-)

Hey, I didn't write it!  :-)

And yes, anything that big make me automatically presume that it isn't
structured well.  Unfortunately, I have other priorities ATM.  One
day.

Regards,
Paul



More information about the Mulgara-general mailing list