Tag Archives: REST

“RESTful Java with JAX-RS 2.0, 2nd Edition” by Bill Burke; O’Reilly Media

RESTful Java with JAX-RS 2.0

REST is all the rage now (not without a reason), and in the Java world the standard API for that is JAX-RS (under the JEE umbrella). “RESTful Java with JAX-RS 2.0” is the second edition of Bill Burke’s book on the JAX-RS API. Bill Burke is the creator of RESTEasy and a member of the committee that designed JAX-RS.

The book is divided into two parts, over a dozen short chapters in each. The first part includes a very nice introduction to REST, has a great systematic reference over the API and finally a few words on integration with various frameworks, security, caching etc. The second chapter is basically a workbook – there is downloadable code with a few examples for each chapter, and these chapters basically are a detailed walk through.

The author is careful not to get ahead of himself and starts quite slow, introducing the more advanced, automated and magical features step by step. As a result, the book is a great introduction for complete newcomers. But it doesn’t stop there – it discusses all the more advanced features as well (later), with the same depth and clarity. That makes it a great reference and a cookbook that you’re likely to get back to as use the API in your work.

Everything is well thought out and executed. It’s a very easy read, with each chapter stating the problem that it’s trying to solve, following up with presentation of the relevant part of the API and a number of practical examples. If for some reason you need more, you’re free to explore the workbook or complete running code.

Highly recommended.

Note on edition: I read it on Kindle, no issues at all.

The future may just as well be RESTful

Chris Zheng has just published an article on “Why the future is NOT RESTful”. It made a bit of a splash, but I think it’s based on false assumptions and quite wrong. Here’s why.

Chris observes that client takes more and more responsibilities from the server. He suggests that server is slowly becoming just a database frontend with authorization. I think it’s very wrong if not dangerous.

Server will never be a dumb database frontend except for trivial CRUD applications. If you have more than one user in the system working with the same thing concurrently, you have to have some coordination on server side. If you have any business logic at all, you have to have it on the server side.

Client is becoming thicker, fine. It may have a database, offline state and a lot logic. But it does not mean that server is losing any of its thickness in domain model. We’re only moving the presentation side (all of it), enhancing it, maybe duplicating the domain logic. But ultimately we cannot trust the client about anything. It’s all in hands of the users, exposed to reverse engineering, all kinds of forgery and so on. I can send whatever I want to the server with curl.

Next point: With REST you can’t have security. I’m young, green and new to the game, but is that really true? Does REST mean no authorization, no results filtered for each user? If Jim can see some “accounts” in the system and Jessica some others, does it make it impossible to return different results for GET /account depending on context?

To take it a step further: We’re not talking about the very monolithic view here, are we? REST doesn’t mean that you only can have one representation of an “account”, and only one GET/POST/PUT on it. You can still have more representations, each tailored for a specific use case. Getting a list of Jimmy’s friends would be a completely different endpoint from managing user permissions, account settings etc. Even if they’re all “accounts”.

Another point that Chris is making is that for some reason having one resource for one thing is bad, but there’s little explanation for it except for a restaurant counters analogy. It’s hard to argue if there are no real arguments on the other side, but…

Having concrete, well-defined resources that represent one thing each doesn’t really sound like a bad idea to me. If anything, it’s more like the ideal interface segregation and single responsibility. Are they not desirable anymore? Going back to blurry restaurant analogies – I may go for fries or rice, I do order dessert from a different part of the menu than the main course, I may even order wine from a different menu altogether. I may be served by more than one waiter. Heck, sometimes I may even go for a buffet!

To sum up, REST is more than dumb CRUD, and server is much more than just an authorizing database front end. Popularity of REST is a bit of fashion, it’s just another way to solve the problem, and by no means is it the silver bullet. But still, the future may just as well be RESTful.

“Beautiful REST + JSON APIs” by Les Hazlewood (notes from the talk)

Here’s a summary of a few interesting technical details from a very good presentation on designing REST APIs by Les Hazlewood. Many interesting, elegant and not so obvious solutions here.

  • Keep resources coarse-grained, especially if you’re designing a public API and you don’t know the use cases.
  • Resources are either collections or single instances. They’re always an object, a noun. Don’t mix the URLs with behavior. /getAccount and /createDirectory can easily explode to /getAllAccounts, /searchAccounts, /createLdapDirectory…
  • Collection is at /accounts, instance at /accounts/a1b2c3. Create, read, update and delete with GET/POST/PUT/PATCH/DELETE… Everyone knows, but anyway.
  • Media types:
    • application/json – regular JSON.
    • application/foo+json – JSON of type foo. In my understanding, roughly corresponding to XML schema or DTD.
    • application/foo+json;application – JSON of type foo, where the response type (entity format?) is application.
    • application/json, text/plain – JSON prefered, text acceptable.
  • Versioning:
    • https://api.foo.com/v1
    • Media-Type application/json+foo;application&v=1
  • HREF:
    • Use instead of IDs
    • Sample use:
      GET /accounts/a11b223
      200 OK
      {
        "href": "https://api.foo.com/v1/accounts/a11b223",
        "givenName": "Tony",
        "surname": "Stark",
        "directory": {
          // Instance reference
          "href": "https://api.foo.com/v1/directories/ffb554"
        },
        "groups": {
          // Collection reference
          "href": "https://api.foo.com/v1/accounts/a11b223/groups"
        }
      }
      
    • Reference (link) expansion:
      GET /accounts/a11b223?expand=directory
      {
        "href": "https://api.foo.com/v1/accounts/a11b223",
        "givenName": "Tony",
        "surname": "Stark",
        "directory": {
          "href": "https://api.foo.com/v1/directories/ffb554",
          "name": "Avengers",
          "creationDate": "2013-08-08T14:55:12Z"
        }  
      }
      
    • Partial representations:
      GET /accounts/a11b223?fields=givenName,surname,directory(name)
      
    • Pagination:
      GET .../applications?offset=50&limit=25
      {
        "href": ".../applications",
        "offset": 50,
        "limit": 25,
        "first": { 
          "href": ".../applications?offset=0"
        },
        "prev": {
          "href": ".../applications?offset=25"
        },
        "items": [
          {"href": "..."},
          {"href": "..."}
        ]
      
  • Many-to-many – represent as another, special resource, e.g. /groupMembership. Not so obvious potential benefits: If you make it a resource, it’s easy to reference from either end of the association. If you want, you can easily add data to the association (e.g. creation date, responsible user, whatever).
  • Error handling – credit to Twilio.
    POST /directories
    409 Conflict
    {
      "status": 409,
      "code": 40924, // because HTTP has too few codes
      "property": "name",
      // Ready-to-use user-friendly message:
      "message": "A directory named Avengers already exists",
      // Dev-friendly message, can be stacktrace etc.
      "developerMessage": "A directory named Avengers already 
        exists. If you have a stale local cache, please expire
        it now.",
      "moreInfo": "http://foo.com/docs/api/errors/40924"
    }
    
  • Security – many interesting points here, but one particularly valuable. Authorize on content, not URL. URLs can change and may diverge from security configuration…

It’s too bad that the presenter doesn’t really leave the happy CRUD path. I’d really like to hear his recommendation or examples on more action-oriented use cases (validate or reset user password, approve order, what have we).

The entire presentation is a bit longer than that. I talks quite a lot about why you would want to use REST and JSON, as well as security, caching and other issues.

“Spring Data. Modern Data Access for Enterprise Java” (Book Review)

Spring Data is a relatively young set of tools that seems to be quickly gaining popularity. I got introduced to it by Oliver Gierke at 33rd Degree Conference and immediately got really interested (not to say fell in love).

Spring Data is an elegant combination of tools for almost uniform access to various data stores (JDBC, JPA, MongoDB, Neo4j, Redis and others). It has a very slick way to generate queries automatically (even from method names on repository interfaces), with support for paging and sorting as well as auto-generated CRUD.

It makes it very easy to expose repositories on the web via a REST API (and I mean REST, with HATEOAS in the box). In fact, sometimes all you need is to provide entity mapping (e.g. JPA, but there are ways to do similar things with NoSQL stores) and write the repository interface with the right set of annotations. That can be all you need to get a basic REST data service up and running!

Of course you can mix and match or bring more power in. Write your own queries when you need it. Use the repository as data access layer for a “thicker” business layer. Use whatever other Spring tools you like.

The book itself is really well written. It quickly explains the basic ideas behind the data access API. It starts on familiar ground and shows a new way to solve old annoying problems, demonstrating new, streamlined ways to deal with JPA and JDBC repositories. It also offers a new way to write typesafe queries with all the benefits of IDE support: Querydsl.

Then it shows how you can use most of the same API for NoSQL stores, including MongoDB, Neo4j and Redis. Each of those chapters starts with an introduction to the store itself (what it is, what it’s good for). Then it shows how you can use the Spring Data API for, pardon me, Object-NoSQL mapping and writing repositories and queries. As it progresses it gradually dives deeper in the technical details.

Next section is devoted to rapid application development. It features Spring Roo (which I’m not much interested in, not being a fan of codegen) and the REST repository explorer. The latter is a true gem and worth attention on its own. This chapter is also a very good demonstration of (introduction to?) a complete REST API with hyperlinks, CRUD, search, relationships between resources etc.

Towards the end of the book there are also 3 chapters on Hadoop. The final chapter is devoted to GemFire, a distributed data grid.

Spring Data is definitely worth a close look, and this book is a perfect resource to get started. Authors had a very good plan on what they wanted to say and executed it perfectly. The language is fairly light, clear and easy to follow. The examples are interesting, simple and concise at the same time. Very easy to understand, but not simplistic – they demonstrate the underlying power and do a good job of exposing all the gory details. You get to see a fairly wide and reasonably deep view of the framework.

What else could you possibly want from a technical book? Oh yes, and it has a squirrel on the cover!

Many thanks to Oliver for a copy of the book.