Great to get started on this work.
I'd like to see some examples of how this is used [I have one below]; I think
that would establish context for discussion. With just the raw API, one has to
envision how things interact, which is difficult.
From the client side, the moniker RiakObject is actually not too good. In
technical terms, it is of cause a riak_object - but to a Java programmer, it
doesn't feel right for it to have that name. It's more like a KeyValueHolder,
a RiakEntry (makes you think of Map.Entry), or something like that. I'll vote
for calling it RiakEntry, or just plain Entry (we have name spaces in Java, you
know...)
It is hard to convey that it is important to get one of these "riak objects",
update it, and stash it back in there. I.e. the fact that a RiakEntry has the
"optimistic concurrency state" (in popular speek) needed to later do the
update. One naturally just want to create a new one and put into the store;
and that aspect should perhaps be hinted in the name of this core class, and in
the flow of the API.
Perhaps, for this very reason, store() should be an operation *directly on the
RiakEntry*; and then guide people by the way these are obtained.
I like the idea of modeling buckets explicitly, but then why not have store
method on the RiakEntry?
Anyway, here is some sample code we can discuss from:
RiakClient renamed to Riak
RiakObject renamed to Entry
Bucket - new concept in the API
Riak c = ...; // probably some ugly factory pattern to create a RiakClient
here //
Bucket b = c.get("people");
// example 1
Entry e = b.get("russelb"); // does GET /riak/people/russeldb
e.set("application/json", "{ name: \"Russel Brown\" }" );
e.store();
Then, have a special method to create new entries:
// example 2
Entry e2 = b.create("krab"); // does not issue GET /riak/people/krab
b.set("Kresten Krab Thorup"); // implies text/plain;charset=utf-8
b.store();
The latter (example 2) would issue a "PUT" w/no vector clock; whereas the
former (example 1) automatically grabs the vector clock from the GET. If you
sure Bucket.get("no-such-key") then the only "harm done" is that you spent an
extra round trip to the server trying to find the VC for no-such-key.
In fluent style, this would be
c.getBucket("people").get("krab").set("Kresten Crap Throwup").store();
// and/or
c.get("people", "krab").set("XXX").store();
Which captures the flow that the vector clock needs to be there for the store.
Likewise, this will make it much more sound to delete things, because you also
need the entry (includin gth VC) to delete an object properly
bucket.get("krab").delete()
makes a lot more sense than
bucket.create("krab").delete()
WHICH IS GREAT! Because we want people to pass in VC to delete operations ...
those should really also be replayable, which I am sure they will be one day :-)
Kresten
On Mar 23, 2011, at 11:05 , Russell Brown wrote:
> Hi,
> I'm trying to make the Java client easier to use and less tied to underlying
> implementation so I've started designing a new API.
>
> I've put some interfaces up at
> https://github.com/russelldb/riak-java-client-api
>
> I'd really appreciate any comments you may have.
>
> My intention is to adapt the existing client(s) to these interfaces and
> deprecate the old client API gradually (so there will be backward
> compatibility for a few releases.) I'll also be reusing the existing client
> implementations underneath the API, this isn't a wholesale re-write.
>
> I hope you can take some time to let me know what you think. I'll put my
> thickest skin on.
>
> Many thanks
>
> Russell
>
> PS It is all maven'd up so just clone and mvn eclipse:eclipse if you want to
> get a good look.
> <ATT00001..txt>
_______________________________________________
riak-users mailing list
[email protected]
http://lists.basho.com/mailman/listinfo/riak-users_lists.basho.com