The World’s Leading Microsoft .NET Magazine
   
 
The .NET Addict's Blog

My Top Tags

                                                           

My RSS Feeds








I heart FeedBurner

Latest Diggs - Programming

Computers Blogs - Blog Top Sites

Site Hits

Total: 4,887,616
since: 19 Jan 2005

Enterprise Web Services Manifesto - RESTful Architecture and the Programmable Web

posted Tue 19 Aug 08

First, let me apologize for my lack of posting. I've been really busy taking up to 4 night classes per week and I'm working on a super ultra-top-mega secret book project with a friend and colleague. The only hint I can drop is that the book is going to kick ass. Look for more details soon!

Now, on to REST. I don't need to go into too much detail here about what exactly REST is - I know that most of the readers of this blog are well versed in Web Services technologies and architectural patterns. The thing that I want to cover is that REST is an architectural decision, it is not a protocol or a wire format or even an industry standard. It is a set of recommendations for how you organize the information exposed by your Web Services. Before I go into detail here, I personally think that REST is the way to go. Unless you have a particular need to be strapped into the SOAP/WS-* roller coaster, your Web Service should be exposing resources via RESTful URLs. I can't imagine why people would chose not to do so.

Here's a quick summary of the main tenets of REST in case you're not familiar with the concept:

  • Application state and functionality are both considered resources. This is key to RESTful thinking - everything is a resource. Learn that phrase, love it, and live it.
  • Every resource is addressable through a unique URL. Fielding's original paper on REST only requires a universal syntax, but if we're talking about Web services here, the universal resource address syntax is a URL. Hint: URL stands for Uniform Resource Locator.
  • Every resource in the system shares a uniform interface for the transfer of state between the client and the resource (a decent, but somewhat stretched analogy is that a resource is the server in a client/server scenario). This means that the list of operations possible on a given resource is well-defined, and the list of content types describing the state being transferred is also well-defined.
    • HTTP already has a strict set of operations: PUT, GET, DELETE, POST (and optionally HEAD)
    • HTTP also has a strict set of available content-types.
    • Therefore, transferring state between RESTful URLs is ideally suited to being done over HTTP.
  • According to Fielding (the first person to really put REST into the public eye), REST must be:
    • Client-Server
    • Stateless
    • Cacheable
    • Layered. This means that connected components within a system are unable to "see past" that which they are currently doing. A properly layered framework means that a layer can only see the 1 layer immediately below it, and no others.

I could attempt to summarize why I like REST so much, but instead there's a quote from Fielding's paper (which I believe is also in Wikipedia) that does the job way better than I could:

REST’s client-server separation of concerns simplifies component implementation, reduces the complexity of connector semantics, improves the effectiveness of performance tuning, and increases the scalability of pure server components. Layered system constraints allow intermediaries—proxies, gateways, and firewalls—to be introduced at various points in the communication without changing the interfaces between components, thus allowing them to assist in communication translation or improve performance via large-scale, shared caching. REST enables intermediate processing by constraining messages to be self-descriptive: interaction is stateless between requests, standard methods and media types are used to indicate semantics and exchange information, and responses explicitly indicate cacheability.

Before getting into the example, I feel the need to again state that REST is not a wire format. You cannot compare REST to SOAP, or REST to POX, or REST to JSON. They are not the same type of animal nor do they solve the same kinds of problems. REST is an architecture for designing distributed applications that calls for universally and uniquely addressable resources.

Let's take a look at a sample of what RESTful URLs might look like. In this sample, let's "RESTify" a help desk service. This help desk service is responsible for managing support tickets. Each support ticket also has a list of work items that contain a log of the work done by support personnel on that ticket. The help desk service also needs to support searching, but in a RESTful manner. This is done by considering the collection of search results to be its own resource. Here are some sample RESTful URLs:

URLMethodPresumed Action
/helpdesk/ticketsGETReturns a list of all help desk tickets
/helpdesk/tickets/100329312GETReturns a payload representing just the ticket with a primary key of 100329312.
/helpdesk/ticketsPOSTCreates a new ticket based on the payload in the HTTP POST body
/helpdesk/tickets/100329312PUTModifies the ticket with ID of 100329312.
/helpdesk/tickets/100329312/workitemsGETRetrieves a log of all activity belonging to the given ticket.
/helpdesk/tickets/100329312/workitems/15GETRetrieves work item #15 belonging to the given ticket
/helpdesk/tickets/100329312/workitemsPOSTCreates a new work item for an existing ticket
/helpdesk/tickets/100329312/workitems/15PUTModifies work item #15
/helpdesk/tickets/100329312DELETEDeletes ticket 10032912. Assumed that all related/child data will also be deleted in this operation.
/helpdesk/tickets/searchresults/bobGETRuns a keyword query against the phrase ‘bob’ on all tickets in the system

Another common use of REST is to use a slash (/) or semi-colon (;) to further subdivide a resource into views. For example, if you wanted to look at the list of helpdesk tickets but you wanted the "newunassigned" view (which is a really handy view to have!), then you might use the following URL:

/helpdesk/tickets/newunassigned

or

/helpdesk/tickets;newunassigned

A lot of Ruby folks seem to dislike the semi-colon syntax as they think it's "old school", but I like it as it visually distinguishes between a sub-view of a resource and an actual sub-resource. This gives different weight to the "newunassigned" sub-view than a sub-resource like "orderitems".

So how do you go about taking a problem domain and converting it into a service that adheres to RESTful architecture principals? Here's a few guidelines that I use when doing this myself:

  1. Identify Resources
    In this step you want to take a look at your problem domain and the data flowing through your system and see if you can identify the resources available to clients that will eventually be exposed via the service.
  2. Identify how client applications will use resources
    Once you have the list of resources, construct a set of use cases for how client applications will access those resources. This is often an overlooked step but it can be extremely englightening and highlight potential areas where your list of resources may need to be re-organized. Remember that resources are logical resources. If you find you have a 1:1 mapping between SQL tables and resources, you need to go back to the drawing board.
  3. Construct RESTful URL schemes (service contract)
    Using the information obtained in steps 1 and 2, build your URLs. These URLs are essentially the service contract for your RESTful service. Think of it as really, really simple WSDL - just a list of URLs. At this point, don't worry about the message payload format - you can build that later.
  4. Utilize REST URLs in test cases/sample scenarios
    Now that you have your URLs, run through some sample scenarios and use cases for your client application. Usually what happens is I find that I've got about 75% of your URLs right but the rest need work.
  5. Refine
    Finally, take the knowledge you gained in step 4 and repeat steps 1 through 4 until you can get through step 4 without finding any obvious flaws in the URL scheme. Now you can get down to the dirty business of defining your payloads (probably with XSD if you're doing a regular POX implementation) and actually coding up the service and client.

So what does all this mean and why am I posting this? The Web Services scene has changed tremendously since I first started this blog a couple of years ago. A couple of years ago I didn't know much about REST, I wasn't doing anything with social networking, and most people in the industry were thinking, "Web Services? WTF. Just another stupid fad." They couldn't have been more wrong.

So now I'm taking my thoughts on Web Services applications from having spent the last 6 years of my life building them. I remember back in the good old days when they weren't called Web Services and what we were doing was "hacking HTTP to take XML payloads", probably because we were building distributed systems that couldn't communicate properly via DCOM or CORBA. We've come a long way since then and I want to do this series of blog posts covering my thoughts on Web Services as they stand now. This is all my own personal opinion, so feel free to ignore it or flame it, I'm doing this as much for my own edification as I am for yours ;)

Enjoy, and more posts will be forthcoming!

tags:                  

links: digg this    del.icio.us    technorati    reddit

AddThis Social Bookmark Button




Tag Related Posts

What's New in Silverlight 3

Fri 20 Mar 09 2:38 P GMT-05

Building RESTful Java Web Services with JAX-RS

Mon 23 Feb 09 8:42 P GMT-05
tags:                    

Know thine Enemy: RESTful Web Services in ... Java!

Sun 11 Jan 09 2:08 P GMT-05
tags:                    

Enterprise Web Services Manifesto - Wire Formats

Tue 02 Sep 08 1:43 P GMT-05
tags:                

MobileMe vs. Live Mesh - Round 1

Wed 11 Jun 08 12:20 A GMT-05

CLINQ v1 Demo - Network Message Filtering

Wed 09 Jan 08 7:47 P GMT-05
tags:        

LINQ to REST - A much better name for Astoria

Tue 11 Dec 07 1:23 P GMT-05
tags:        

My Appearance in the RIA Shootout on sys-con.tv

Tue 05 Jun 07 11:41 A GMT-05
tags:              

Orcas' Hidden Gem - The managed PNRP stack

Fri 11 May 07 6:45 P GMT-05
tags:        

Will Silverlight be DOA?

Mon 16 Apr 07 8:02 P GMT-05

On MUDs

Thu 08 Mar 07 5:00 A GMT-05
tags:                    

What I think is a bug in WCF POX messaging

Thu 04 Jan 07 4:58 P GMT-05
tags:      

Ulysses Agenda Makes Redmond Developer News

Wed 29 Nov 06 7:10 P GMT-05
tags:                

Ulysses Agenda - Network Engine Test 1

Mon 09 Oct 06 2:26 A GMT-05
tags:              

ASP.NET vs Ruby on Rails : Round 2 (Agility)

Thu 05 Oct 06 11:02 A GMT-05
tags:                      

ASP.NET vs Ruby on Rails : Round 1

Wed 04 Oct 06 1:37 P GMT-05
tags:                

Ulysses Agenda : First Cut Networking Design

Thu 14 Sep 06 12:46 A GMT-05
tags:                  

First Impressions of Windows Vista RC1

Thu 07 Sep 06 1:30 P GMT-05
tags:                      

Scrobbles, Diggs, Flickrs and Tags Oh My!

Tue 01 Aug 06 5:25 P GMT-05

.NET Framework 3.0 June CTP is out!

Fri 23 Jun 06 6:23 P GMT-05
tags:                

Tech-Ed 2006 - Session Reviews

Tue 13 Jun 06 6:22 P GMT-05
tags:                    

SOA Manifesto

Thu 26 Jan 06 10:38 P GMT-05
tags: