Questions and comments about resource registration

4 views
Skip to first unread message

Chris Nicola

unread,
Jan 19, 2011, 8:22:56 PM1/19/11
to OpenRasta
So I'm having some trouble with the registration of resources and Uri
mapping. Basically I don't like the way I am doing it right now.
There seems to be a lot of redundancy, unnecessary registration etc.
So I am asking if there is a better way I can do this.

First I a couple things Ive been finding myself doing that I don't
really like too much:

1. Why do I have to register resource types at all in the first place?

Requests and responses are simply serialization of data, it should
either serializes the resource returned from the handler method or
serialization fails. I see no reason why I would need or want to do
this. I find myself with a handler that returns both a Resource and a
collection Resource[] and I have to register both in my
configuration. This makes no sense to me.

2. Registering trans-coders each time. It seems like I should be able
to wire up a set of transcoders that serialize/deserialize everything
based on Accepts. Even for webforms it would make more sense to be
able to look up the web form based on conventions (similar to MVC)
rather than specify a page for each and every resource.

Anyways here is the code, for the very small number of API endpoints I
have so far I feel like this is way too much configuration. I also
don't like having to update the configuration for almost every change
I make to the API. Is there a better way I should be doing this?

https://gist.github.com/787236

Thanks, I'd really appreciate any help or suggestions.
Chris

Sebastien Lambla

unread,
Jan 20, 2011, 3:40:43 AM1/20/11
to open...@googlegroups.com
Hi Chris,

OpenRasta is resource-oriented, and fight you into designing your system around that concept. That may well be why you find the experience frustrating, as the framework will try and fight you when you try to deviate from that architectural style. To answer your questions more specifically:

1. The web is about resources and representations.

Any "thing" that has a URI is an independent resource that may have one or more representations. As such, Resource and Resource[] are two different things with two distinct URIs and as such you need to register both. There's a good reason for that: while you may be able to POST to your /resources, you probably will only be able to PUT to /resources/{id}. Two different resources with two different set of operations, and as such the config API forces you down the path of registering them independently.

In HTTP architectures, the request and response messages are only there to transfer representations of those resources (what I assume you call serialization in your question): you request an operation to be done on a specific resource (a POST to /resources) and expect to get the state about the result of that operation in the result, usually with a status code and a representation that describes what happened.

In your example, your config shouldn't even work. You're trying to register two different resources at the same URI, which won't work: there's no way anymore to tell what operations and representations are available. The framework at that point should throw an error, we don't right now which is a known issue with the 2.0 series.

2. Each resource may have its own representations, and usually does (in the case of html templates using webforms, sparkview etc)

We do support inheritance-based selection for codecs, so if you register a codec for object, it will kick in everytime: ResourceSpace.Has.ResourcesOfType<object>().WithoutUri.TranscodedBy<YourCodec>().


So yes indeed the resource registration forces you to model resources, and that's because OpenRasta is resource-oriented. If you don't want to model them, you'll get into a lot of complexities in trying to get OpenRasta to work.

If you find the registration API too noisy, you can simply write an extension method that will simply make those calls for you. There is no convention support in 2.0, mostly because people have just been building their own on top of OpenRasta, and you can probably do the same thing. For example, now that you have a resource class for each of your resources, you can simply create your handlers to implement an interface (say IResourceHandler<T>), add that to each of the handlers (so you have a one-to-one mapping between your resource class and the resource handler), register those in the container (either through the .Uses.CustomDependency or through your native container registration API), and write an extension method that automatically register ResourcesOfType<T>().HandledBy<IResourceHandler<T>>().

If you don't want to model the resource type itself or separate what constitutes accessible resources in your architecture, then you're out of luck, as it's the core concept in OpenRata.

Chris Nicola

unread,
Jan 20, 2011, 1:06:48 PM1/20/11
to OpenRasta
Thanks, that gives me some ideas for how I might be able to make this
work better. I also understand what you mean and I am aware REST is
focused around defining resources but to me that doesn't actually
explain why we need to be explicit about registering them since it
tells us nothing we need to actually make REST work. Obviously in
principle I should only return one resource type per Uri
representation, but that is (and should) be determined by the type I
return from the method that is matched to the Uri. I stick by the
assertion that defining it in the configuration is a completely
redundant step and is creating unnecessary friction in the API.

Anyways, I'll play with it a bit and see if I can find a more
conventional approach. The bottom line is, I do really feel it is a
bit noisy compared to simply mapping routes to handler methods. I
realize that REST is based on RESTful resources, but that doesn't
explicitly imply a particular registration method for those resources.

Chris

On Jan 20, 12:40 am, Sebastien Lambla <s...@serialseb.com> wrote:
> Hi Chris,
>
> OpenRasta is resource-oriented, and fight you into designing your system around that concept. That may well be why you find the experience frustrating, as the framework will try and fight you when you try to deviate from that architectural style. To answer your questions more specifically:
>
> 1. The web is about resources and representations.
>
> Any "thing" that has a URI is an independent resource that may have one or more representations. As such, Resource and Resource[] are two different things with two distinct URIs and as such you need to register both. There's a good reason for that: while you may be able to POST to your /resources, you probably will only be able to PUT to /resources/{id}. Two different resources with two different set of operations, and as such the config API forces you down the path of registering them independently.
>
> In HTTP architectures, the request and response messages are only there to transfer representations of those resources (what I assume you call serialization in your question): you request an operation to be done on a specific resource (a POST to /resources) and expect to get the state about the result of that operation in the result, usually with a status code and a representation that describes what happened.
>
> In your example, your config shouldn't even work. You're trying to register two different resources at the same URI, which won't work: there's no way anymore to tell what operations and representations are available. The framework at that point should throw an error, we don't right now which is a known issue with the 2.0 series.
>
> 2. Each resource may have its own representations, and usually does (in the case of html templates using webforms, sparkview etc)
>
> We do support inheritance-based selection for codecs, so if you register a codec for object, it will kick in everytime: ResourceSpace.Has.ResourcesOfType<object>().WithoutUri.TranscodedBy<YourCod ec>().

Sebastien Lambla

unread,
Jan 20, 2011, 1:30:18 PM1/20/11
to open...@googlegroups.com
Well, OpenRasta specifically focuses on resources as the endpoints as opposed to URI as the endpoints. The reason for that is again to respect the behavior by which one resource may have one URI and respond to multiple methods called on it.

As for returning one resource "type" per URI, well this is certainly *not* in principle, if you do, you break how http and the web works, there's no two way about it. OpenRasta uses the resource type as a key that binds together a set of handlers, a set of uris and a set of transcoders.

That said, if you had tried something along the lines of the following, you'll see that part of what you think you have to disagree with already works perfectly.

ResourceSpace.Has.ResourcesOfType<Customer>().AtUri("/customers").HandledBy<CustomerHandler>();

ResourceSpace.Has.ResourcesOfType<object>().WithoutUri.TranscodedBy<JsonDataContractCodec>();

class CustomerHandler { public Project GetSomethingOrSummin() { return new Project(); } } <-- returns Project encoded with the json codec

Yes, OpenRasta will use your return type on the outgoing route to select the correct codec, and use the type you registered to select an incoming handler. After that, the inputs and outputs of the hadnler method are matched independently, so if you had done the object registration i talked about, chances are passing any of the registered types as a parameter to the method, and returning any of those, will also work just fine with the codec architecture.

If you dislike the fluetn API, as I've explained, scanning the types in your assembly and creating your own convention as i just shown you is a matter of mintes.

Seb
________________________________________
From: open...@googlegroups.com [open...@googlegroups.com] on behalf of Chris Nicola [chni...@gmail.com]
Sent: 20 January 2011 18:06
To: OpenRasta
Subject: [openrasta] Re: Questions and comments about resource registration

Reply all
Reply to author
Forward
0 new messages