Hi Peter,

thanx a lot for this nice example! This is highly appreciated and
enRoute really looks cool, although I want to support more than just
JSON as a content-type.

Anyway, as I see it, the BackendREST service is somewhat comparable to
my planned ReST server implementation in the sense that it actually is a
consumer of the various real backend implementations.

However, what I (ideally) want to achieve is that even the ReST service
does not even know that multiple backends exist.

So, in your example a PUT to create a new BLOB uses the following URI:

/rest/backends/:type/:name

However, what I intend to provide is just this:

/rest/backends/:name

...so that the ReST consumer does not need to care about the different
backends and a "GET /rest/backends" would return all entries, not just
from a single backend. This also allows me then to create a global
caching mechanism for meta-data and also implement more sophisticated
stuff later in the backend routing logic, e.g. moving from File to
InMemory for "hot" data.

As such, also the ReST server-side should not be bothered with the
different backends. In the long-term, I also plan integration for some
kind of process or rules engine which can be used to implement
algorithms for storage tiering, caching policies, geographic or
policy-based data locality, aso.

As those things complicate the actual backend decision logic and/or may
also start executing functionality without any ReST API interaction, I
really would need a unified way of accessing them internally as well.

As OSGi already knows what I would call service instance meta-data (the
service properties usable for filtering), is there any thinking about
call-time meta-data/filtering in a generic fashion?


Thanx a lot,

Ancoron


On 01/08/2015 04:33 PM, Peter Kriens wrote:
> Hmm, all the text ahead what is before ‘Anacron’ should have been
> removed :-( The actual code is on the link.
> 
> I started a few days ago but noticed it was getting too long. This
> morning I just made an enRoute project out of it.
> 
> So please discard any code in my mail and look
> at 
> https://github.com/osgi/osgi.enroute.examples/tree/master/osgi.enroute.examples.backend.application
> 
> Sorry, kind regards,
> 
> Peter Kriens
> 
> 
>> On 8 jan. 2015, at 15:48, Raymond Auge <[email protected]
>> <mailto:[email protected]>> wrote:
>>
>> Peter is there a typo in the addBackend method on the put operation?
>>
>> On Thu, Jan 8, 2015 at 9:45 AM, Peter Kriens <[email protected]
>> <mailto:[email protected]>> wrote:
>>
>>     This is the archetypical use case for OSGi:
>>
>>     interface Backend {
>>        void store( String name, byte[] data ) throws Exception;
>>     }
>>
>>     @Component
>>     public class FrontEnd implements REST {
>>       final Map<String,Backend>  backends = new ConcurrentHashMap<>();
>>
>>       @Reference(multiple=true,dynamic=true)
>>       void addBackend(Backend backend, Map<String,Object> props) {
>>         backends.put(backend, props.get(“type”));
>>       }
>>       void removeBackend(Map<String,Object> props) {
>>         backends.remove(props.get(“type”));
>>       }
>>         
>>       interface PUTRequest extends RESTRequest {
>>         byte[] _body();
>>         String type();    
>>       }
>>
>>       public void putData( PUTRequest req, String [] path ) {
>>         Backend b = backends.get(req.type());
>>         if ( b == null)
>>     throw new FileNotFoundException(“No such type “ + req.type());
>>
>>         String p = Strings.join(path, “/“);
>>         b.store(p, req._body() );
>>       }
>>     }
>>
>>     @Component
>>     public class FileSystemBackend implements Backend {
>>       
>>     Ancoron,
>>     I though the problem was kind of nice for an example so in the
>>     light of the OSgi enRoute work I turned it into a little enRoute
>>     application. I added all the documentation in the readme file. You
>>     can find the app here:
>>
>>     
>> https://github.com/osgi/osgi.enroute.examples/tree/master/osgi.enroute.examples.backend.application
>>
>>     Let me know if this works for you.
>>
>>     Kind regards,
>>
>>     Peter Kriens
>>
>>          
>>>     On 30 dec. 2014, at 23:49, Ancoron Luciferis
>>>     <[email protected]
>>>     <mailto:[email protected]>> wrote:
>>>
>>>     Hi OSGi devs and experts,
>>>
>>>     I've got a problem which I really want to solve in an elegant way
>>>     but I
>>>     think I haven't found the appropriate pieces yet.
>>>
>>>     The problem is the following:
>>>
>>>     I want to create some abstraction for a little data management system
>>>     which should be connected to different data backends at the same time
>>>     (e.g. S3, Dropbox, local/network filesystem, ...).
>>>
>>>     Now let's consider a simple example of the logic involving the
>>>     following
>>>     standard CRUD operations (because I want to publish that in a single
>>>     ReST endpoint):
>>>
>>>     * create (e.g. upload)
>>>     * read (get metadata or list objects/files/buckets/... or just
>>>     download)
>>>     * update (e.g. re-upload or change metadata)
>>>     * delete
>>>
>>>     So, what I actually want is the following:
>>>
>>>     1.) For creating/uploading a new object, a specific data backend
>>>     may be
>>>     specified via HTTP header or determined automatically (e.g. based on
>>>     expected size or some other metadata).
>>>
>>>     2.) For listing existing objects all service instances/data backends
>>>     shall be queried at the same time (in parallel) and results combined
>>>     into a single list.
>>>
>>>     3.) For retrieving object metadata, downloading a specific object,
>>>     modifying, deleting it or executing some other operation with a
>>>     specific
>>>     object, the correct service instance/data backend is called.
>>>
>>>
>>>     So, for case 1 I would need some way to evaluate the contextual
>>>     information of the upcoming service call (in this case the HTTP
>>>     header).
>>>     If that is not available, I'll have to look at some service instance
>>>     information that helps me figuring out where to put some object
>>>     (DNS-SD
>>>     or ZeroConf keep popping up conceptually here in my head).
>>>
>>>     For case 2 I just need to actually execute the same call for each
>>>     available service instance (like a network broadcast).
>>>
>>>     For case 3 I need to know somehow (this could be done by a local
>>>     object
>>>     identity/location mapping) which service instance is responsible (or
>>>     allowed to) manage a specific object.
>>>
>>>
>>>     Now, I could code all this inside the ReST layer. However, what I
>>>     really
>>>     want is to make it abstract in a way that I can hook it into other
>>>     places as well.
>>>
>>>     So, the initial caller 'A' should just have code like this:
>>>
>>>     private B b;
>>>     //...
>>>
>>>     myObjectId = b.create(newObject);
>>>     //...
>>>
>>>     List objects = b.list(filter, sort, paging);
>>>     //...
>>>
>>>     myObject = b.get(myObjectId);
>>>     //...
>>>
>>>     b.updateMetadata(myObjectMetadata);
>>>     //...
>>>
>>>     b.delete(myObjectId);
>>>
>>>
>>>     So that the ReST layer does not even have to know that there is more
>>>     than just one backend.
>>>
>>>     The magic should be done outside in a generic way if possible, so
>>>     that I
>>>     could re-use it as it is for other types of services.
>>>
>>>
>>>     Does that idea sound familiar to someone? Has that been solved
>>>     already
>>>     and I just missed something?
>>>
>>>     I first started with the idea of using an aggregating proxy plus a
>>>     FindHook and stuff, but this imposes the runtime issue that consumers
>>>     need to be refreshed which I want to avoid if possible.
>>>
>>>     The main problem I think here is to present a single service
>>>     instance to
>>>     the consumer for which there actually exists no real service
>>>     registration as it is just some kind of invocation handler with a
>>>     specialized purpose (routing/broadcasting service requests).
>>>
>>>     I would be thankful for any ideas!
>>>
>>>
>>>     Thanx,
>>>
>>>     Ancoron
>>>     _______________________________________________
>>>     OSGi Developer Mail List
>>>     [email protected] <mailto:[email protected]>
>>>     https://mail.osgi.org/mailman/listinfo/osgi-dev
>>
>>
>>     _______________________________________________
>>     OSGi Developer Mail List
>>     [email protected] <mailto:[email protected]>
>>     https://mail.osgi.org/mailman/listinfo/osgi-dev
>>
>>
>>
>>
>> -- 
>> *Raymond Augé*
>> <http://www.liferay.com/web/raymond.auge/profile> (@rotty3000)
>> Senior Software Architect *Liferay, Inc.*
>> <http://www.liferay.com/> (@Liferay)
>> Board Member & EEG Co-Chair, OSGi Alliance <http://osgi.org/>
>> (@OSGiAlliance)
>> _______________________________________________
>> OSGi Developer Mail List
>> [email protected] <mailto:[email protected]>
>> https://mail.osgi.org/mailman/listinfo/osgi-dev
> 
> 
> 
> _______________________________________________
> OSGi Developer Mail List
> [email protected]
> https://mail.osgi.org/mailman/listinfo/osgi-dev
> 

_______________________________________________
OSGi Developer Mail List
[email protected]
https://mail.osgi.org/mailman/listinfo/osgi-dev

Reply via email to