SlideShare a Scribd company logo
1 of 58
Download to read offline
Hypermedia APIs
@jankronquist
Hypermedia API:s @ Jayway
Rickard Öberg (~2010)!
Qi4j & Streamflow!
Usecases as your API!
Mattias Arthursson & Karl-Johan Stenflo (~2011)!
JAX-RS-HATEOAS!
HATEOAS with Standard Java APIs!
Mads Enevoldsen & Jan Kronquist (~2011)!
Forest (CQS conventions, sensible default links, constraints...)!
Gustaf Nilsson Kotte (~2012)!
Adaptive HTML as your API
Outline
Example domain!
REST introduction (Richardson maturity model)!
Exploring media types!
html!
collection+json!
hal+json
Example domain
Rock - Paper - Scissors
Opening gambit
http://www.worldrps.com/gambit-play
Opening gambit
http://www.worldrps.com/gambit-play
http://rps.com
The future Facebook of Rock Paper Scissors!
Millions of users!
Many games per user
Playing the game
Player A
Player B
Server
rock
paper
Player B: paper
Player A: rock
Game 123
Game 123	

winner: Player B	

loser: Player A
CREATED WAITING
GAME WON
GAME TIED
any move
other move	

(victory)
other move	

(tie)
T
Introducing REST
Towards REST
REST architectural style!
Defined by Roy Fielding !
Richardson maturity model
http://martinfowler.com/articles/richardsonMaturityModel.html
Level 0 - Not at all RESTful
Single resource, single verb!
Examples:!
SOAP, XML-RPC, JSON-RPC
Level 0 - Example
POST /api
--> { "method": “viewGame", "params": ["123"]}
<-- { "result": { "state": "waiting"},
"error": null}
POST /api
--> { "method": "makeMove", "params": ["123","rock"]}
<-- { "result": { "state": "won",
"winner": "player1",
"loser": "player2"},
"error": null}
Level 0 - Analysis
HTTP as transport protocol!
Problems!
No client side caching!
Tight coupling
Level 0 - In the wild
JSON/RPC over HTTP!
Why?!
Simplicity!
Track all user actions!
If it ain’t broke, don't fix it
Level 1 - Resources
Many resources, single verb!
/api/games/123
/api/players/player1
Almost “object oriented”
Level 1 - Example
POST /api/games/123
--> { "method": "viewGame"}
<-- { "result": { "state": "waiting"},
"error": null}
POST /api/games/123
--> { "method": "makeMove", "params": ["rock"]}
<-- { "result": { "state": "won",
"winner": "player1",
"loser": "player2"},
"error": null}
Level 1 - Analysis
Still just using HTTP as transport
Level 2 - Verbs
Resources, verb and status codes!!
GET, POST, PUT, DELETE...
200 OK, 304 Not Modified, 404 Not found…
RESTish!
Uniform interface
HTTP 101
GET - safe!
POST - danger!!
PUT - idempotent!
!
Note!
GET will not modify the resource, but other clients might!
Interleaving other requests might break idempotency
GET /api/games/123
<-- 200 OK
<-- { "state": "waiting"}
POST /api/games/123
--> { "move": "rock"}
<-- 200 OK
<-- { "state": "won",
"winner": "player1",
"loser": “player2"}
Level 2 - Example
GET /api/games/123
<-- 200 OK
<-- { "state": "waiting"}
POST /api/games/123
--> Content-Type: application/json
--> { "move": "rock"}
<-- 200 OK
<-- { "state": "won",
"winner": "player1",
"loser": "player2"}
Level 2 - Mediatype json
Level 2 - Mediatype form
GET /api/games/123
<-- 200 OK
<-- { "state": "waiting"}
POST /api/games/123
--> Content-Type: application/x-www-form-urlencoded
--> move=rock
<-- 200 OK
<-- { "state": "won",
"winner": "player1",
"loser": "player2"}
$ curl -d move=rock http://rps.com/api/games/123
Level 2 - In the wild
Verbs: GET, DELETE, PUT!
Resources: buckets, objects, acls, policies…!
Why?!
CRUD operations!
GET allows caching
Level 2 - Analysis
Using HTTP, not fighting it!
Problems!
Client must construct URLs!
Client must contain business rules
GET /api/games
<-- 200 OK
<-- { "totalCount": 23,
"offset": 0,
"pageSize": 10,
"items": [{"id": "111",
"players": ["jan", "cecilia"]},
{"id": "222",
"players": ["jan", "mike"]},
{"id": "333",
"players": ["cecilia", "mike"]},
...]}
Level 2 - Constructing URLs
GET /api/games?offset=10 GET /api/games?page=2
How to navigate to page 2?
GET /api/games
<-- 200 OK
<-- { "totalCount": 23,
"offset": 0,
"pageSize": 10,
"items": [{"id": "111",
"players": ["jan", "cecilia"]},
{"id": "222",
"players": ["jan", "mike"]},
{"id": "333",
"players": ["cecilia", "mike"]},
...]}
Level 2 - Constructing URLs
GET /api/games/{game.id}
Navigating to game
Level 2 - Business logic
GET /api/games/123
<-- 200 OK
<-- { "state": "waiting",
"players": ["ply1", "ply2"],
"moves": { "ply1" : true}
}
Should the client display the move selector?
Level 2 - Business logic solved?
GET /api/games/123
<-- 200 OK
<-- { "state": "waiting",
"players": ["ply1", "ply2"],
"moves": { "ply1" : true},
"shouldMove": true
}
Level 3 - Hypermedia Controls
Links & forms!
REST as defined by Roy Fielding
Hypermedia is defined by the presence of application control information embedded within, !
or as a layer above, the presentation of information
The simultaneous presentation of information and controls such that the information
becomes the affordance through which the user obtains choices and selects actions.
GET /api/games
<-- 200 OK
<-- { "totalCount": 23,
"offset": 0,
"pageSize": 10,
"next": "/api/games?offset=10",
"items": [{"href": "/api/games/111",
"players": ["jan", "cecilia"]},
{"href": "/api/games/222",
"players": ["jan", "mike"]},
{"href": "/api/games/333"
"players": ["cecilia", "mike"]},
...]}
Level 3 - Example (links)
Level 3 - Example (form)
<html>	
<body>	
<ol id="players">	
<li>Jan</li>	
<li>Cecilia</li>	
</ol>	
<form action="/api/games/111" method="POST">	
<select name="move">	
<option value="rock">Rock</option>	
<option value="paper">Paper</option>	
<option value="scissors">Scissors</option>	
</select>	
<input type="submit"/>	
</form>	
</body>	
</html>
Level 3 - Opportunity: Extra moves
<select name="move">	
<option value="rock">Rock</option>	
<option value="paper">Paper</option>	
<option value="scissors">Scissors</option>	
<option value="lizard">Lizard</option>	
<option value="spock">Spock</option>	
</select>
Level 3 - Changing the rules
For one of the players: Flip a coin!
head - he must play rock!
tail - he can play whatever he wants!
!
How can the other player take advantage of this?
http://blog.gtorangebuilder.com/2014/04/gto-brain-teaser-1-exploitation-and.html
<select name="move">	
<option value="rock">Rock</option>	
</select>
Level 3 - In the wild
Media types &
other tools
Media types
Format!
application/json, text/xml, text/plain, text/csv!
Domain specific!
text/vcard, text/calendar, application/calendar+json!
Hypermedia!
text/html, application/xhtml+xml!
application/vnd.collection+json, application/vnd.hal+json!
application/vnd.siren+json, application/vnd.amundsen-uber+json
GET /api/games
<-- 200 OK
<-- Content-Type: application/json
<-- { "totalCount": 23,
"offset": 0,
"pageSize": 10,
"next": "/api/games?offset=10",
...
}
json
xhtml
GET /api/games
<-- 200 OK
<-- Content-Type: application/xhtml+xml
<--
<html>	
<body>	
	<a href="/api/games?offset=10">Next</a>	
	 <div id="totalCount">23</div>	
<ol id="games">	
<li>...</li>	
<li>...</li>	
</ol>	
</body>	
</html>
collection+json
CRUD for collections of objects!
Parts of the document:!
items!
links!
queries!
templates!
errors
GET /api/games
<-- 200 OK
<-- Content-Type: application/vnd.collection+json
<-- { "collection": {
"version" : "1.0",
"href" : "http://rps.com/api/games",
"links" : [
{"rel" : "next", "href" : "/api/games?offset=10"}
],
"items" : [
{ ... },
{ ... }
]
}
}
collection+json
Anatomy of a Link
target url (href)!
human readable string (title)!
semantic information (rel)!
returned media types (type)!
!
http method (method)!
secondary key (name)!
support media types for requests (accept)
RFC 5988
Standard rels
item!
collection!
next!
edit!
enclosure!
latest-version!
self
http://www.iana.org/assignments/link-relations/link-relations.xml
Custom rels
Register with IANA :-)!
Just make up your own :-)!
move!
URI!
http://rps.com/rels/move!
CURIE!
rps:move!
http://rps.com/rels/{rel}
Forms / templates
More than links!
Allow user input!
May provide!
Default values!
Data types!
Possible values
html form
<html>	
<body>	
<ol id="players">	
<li>Jan</li>	
<li>Cecilia</li>	
</ol>	
<form action="/api/games/111" method=“POST" name="move">	
<select name="move">	
<option value="rock">Rock</option>	
<option value="paper">Paper</option>	
<option value="scissors">Scissors</option>	
</select>	
<input type="submit"/>	
</form>	
</body>	
</html>
GET /api/games/111
<-- 200 OK
<-- Content-Type: application/vnd.collection+json
<-- { "collection": {
"version" : "1.0",
"href" : "http://rps.com/api/games/111",
"template" : {
"data" : [{
"name" : "move",
"value" : "",
"prompt" : "Your move"
}]
}
}
}
collection+json template for writes
Forced resource structure
Collection	

of games
/api/games/
Game 111
/api/games/111
Collection of
moves for game
111
/api/games/111/moves
Player 1 move
for game 111
/api/games/111/moves/ply1
item
rps:moves
item
GET /api/games/111
<-- 200 OK
<-- Content-Type: application/vnd.collection+json
<-- { "collection": {
"version" : "1.0",
"href" : "http://rps.com/api/games/111",
"links" : [
{"rel" : "rps:moves", "href" : "/api/games/111/moves"}
],
...
}
}
The game links to moves
GET /api/games/111/moves
<-- 200 OK
<-- Content-Type: application/vnd.collection+json
<-- { "collection": {
"version" : "1.0",
"href" : "http://rps.com/api/games/111/moves",
"template" : {
"data" : {
"name" : "move",
"value" : "",
"prompt" : "Your move"
}
}
}
}
moves collection contain template
URI templates
Constructing paths



Form-style!
Making a move



Creating a new game
RFC 6570
"http://rps.com/api/games/111{?move}"
"http://rps.com/api/games/{gameId}"
"http://rps.com/api/games{?player1,player2}"
application/vnd.hal+json
Minimalistic (plain old json)!
"_links" with mandatory rels!
"_embedded" (recursive!)
GET http://rps.com/api/games/123
<-- {
!
!
!
!
!
!
!
!
!
!
!
!
!
!
"createdAt" : "2014-05-22T16:24:01",
"state" : "waiting"
}
hal+json
GET http://rps.com/api/games/123
<-- {
!
!
!
!
!
!
!
!
"_links": {
"rps:move": {
"href": "http://rps.com/api/games/123{?move}",
"templated": true
}
}
"createdAt" : "2014-05-22T16:24:01",
"state" : "waiting"
}
hal+json
GET http://rps.com/api/games/123
<-- { "_embedded": {
"rps:player" : [{
"_links": { "self": {"href" : "http://rps.com/api/players/111"},
"name": "Jan"
}, {
"_links": { "self": {"href" : "http://rps.com/api/players/222"},
"name": "Cecilia"
}]
},
"_links": {
"rps:move": {
"href": "http://rps.com/api/games/123{?move}",
"templated": true
}
}
"createdAt" : "2014-05-22T16:24:01",
"state" : "waiting"
}
hal+json
Application state, not objects
GET http://rps.com/api/players/111/games/123
<-- { "_links": {
"rps:game": {"href" : "http://rps.com/api/games/123"},
"rps:move": {
"href": "http://rps.com/api/games/123{?move}",
"templated": true
}
}
}
GET http://rps.com/api/players/111/games/123
<-- { "_embedded": {
"rps:game" : [{
"_links": { "self": {"href" : "http://rps.com/api/games/123"},
"createdAt" : "2014-05-22T16:24:01",
"state" : "waiting"
}]
},
"_links": {
"rps:move": {
"href": "http://rps.com/api/games/123{?move}",
"templated": true
}
}
}
Application state, not objects
Summary
Hypermedia simplifies client development!
No constructing of URLs!
Opportunities for less business logic!
Pick a mediatype with reasonable semantics!
Consider form-encoded when POSTing!
Some useful tools!
CURIE, URITemplates

More Related Content

Viewers also liked (12)

Watercolors. Acuarelas (Steve Hanks)
Watercolors. Acuarelas (Steve Hanks)Watercolors. Acuarelas (Steve Hanks)
Watercolors. Acuarelas (Steve Hanks)
 
About Sacramento Real Estate
About Sacramento Real EstateAbout Sacramento Real Estate
About Sacramento Real Estate
 
DESERT. George Corominas (2)
DESERT. George Corominas (2)DESERT. George Corominas (2)
DESERT. George Corominas (2)
 
Linked In2
Linked In2Linked In2
Linked In2
 
Intd
IntdIntd
Intd
 
Imagination
ImaginationImagination
Imagination
 
Armed with Tools
Armed with ToolsArmed with Tools
Armed with Tools
 
Git hacking
Git hackingGit hacking
Git hacking
 
絕美冰域 南極
絕美冰域 南極絕美冰域 南極
絕美冰域 南極
 
College Marketing Best Practices - Cory 2013
College Marketing Best Practices - Cory 2013College Marketing Best Practices - Cory 2013
College Marketing Best Practices - Cory 2013
 
Iguazu Falls1
Iguazu Falls1Iguazu Falls1
Iguazu Falls1
 
Mito.Myth.
Mito.Myth.Mito.Myth.
Mito.Myth.
 

Similar to Hypermedia APIs - GeekOut

Similar to Hypermedia APIs - GeekOut (20)

Nodejs Explained with Examples
Nodejs Explained with ExamplesNodejs Explained with Examples
Nodejs Explained with Examples
 
Nodejsexplained 101116115055-phpapp02
Nodejsexplained 101116115055-phpapp02Nodejsexplained 101116115055-phpapp02
Nodejsexplained 101116115055-phpapp02
 
Ruby MVC from scratch with Rack
Ruby MVC from scratch with RackRuby MVC from scratch with Rack
Ruby MVC from scratch with Rack
 
RESTful Web APIs – Mike Amundsen, Principal API Architect, Layer 7
RESTful Web APIs – Mike Amundsen, Principal API Architect, Layer 7RESTful Web APIs – Mike Amundsen, Principal API Architect, Layer 7
RESTful Web APIs – Mike Amundsen, Principal API Architect, Layer 7
 
Battle of NoSQL stars: Amazon's SDB vs MongoDB vs CouchDB vs RavenDB
Battle of NoSQL stars: Amazon's SDB vs MongoDB vs CouchDB vs RavenDBBattle of NoSQL stars: Amazon's SDB vs MongoDB vs CouchDB vs RavenDB
Battle of NoSQL stars: Amazon's SDB vs MongoDB vs CouchDB vs RavenDB
 
Computational Social Science, Lecture 09: Data Wrangling
Computational Social Science, Lecture 09: Data WranglingComputational Social Science, Lecture 09: Data Wrangling
Computational Social Science, Lecture 09: Data Wrangling
 
Automatic discovery of Web API Specifications: an example-driven approach
Automatic discovery of Web API Specifications: an example-driven approachAutomatic discovery of Web API Specifications: an example-driven approach
Automatic discovery of Web API Specifications: an example-driven approach
 
Jsonp null-meet-02-2015
Jsonp null-meet-02-2015Jsonp null-meet-02-2015
Jsonp null-meet-02-2015
 
Android and REST
Android and RESTAndroid and REST
Android and REST
 
Progressive web apps
Progressive web appsProgressive web apps
Progressive web apps
 
HTTP API for Free? Check out CouchDB
HTTP API for Free? Check out CouchDBHTTP API for Free? Check out CouchDB
HTTP API for Free? Check out CouchDB
 
Html5 For Jjugccc2009fall
Html5 For Jjugccc2009fallHtml5 For Jjugccc2009fall
Html5 For Jjugccc2009fall
 
WebCamp: Developer Day: Архитектура Web-приложений: обзор современных решений...
WebCamp: Developer Day: Архитектура Web-приложений: обзор современных решений...WebCamp: Developer Day: Архитектура Web-приложений: обзор современных решений...
WebCamp: Developer Day: Архитектура Web-приложений: обзор современных решений...
 
Roll Your Own API Management Platform with nginx and Lua
Roll Your Own API Management Platform with nginx and LuaRoll Your Own API Management Platform with nginx and Lua
Roll Your Own API Management Platform with nginx and Lua
 
FP - Découverte de Play Framework Scala
FP - Découverte de Play Framework ScalaFP - Découverte de Play Framework Scala
FP - Découverte de Play Framework Scala
 
David Gómez G. - Hypermedia APIs for headless platforms and Data Integration ...
David Gómez G. - Hypermedia APIs for headless platforms and Data Integration ...David Gómez G. - Hypermedia APIs for headless platforms and Data Integration ...
David Gómez G. - Hypermedia APIs for headless platforms and Data Integration ...
 
Cdm mil-18 - hypermedia ap is for headless platforms and data integration
Cdm mil-18 - hypermedia ap is for headless platforms and data integrationCdm mil-18 - hypermedia ap is for headless platforms and data integration
Cdm mil-18 - hypermedia ap is for headless platforms and data integration
 
Building APIs in an easy way using API Platform
Building APIs in an easy way using API PlatformBuilding APIs in an easy way using API Platform
Building APIs in an easy way using API Platform
 
Testing API platform with Behat BDD tests
Testing API platform with Behat BDD testsTesting API platform with Behat BDD tests
Testing API platform with Behat BDD tests
 
Implementing Server Side Data Synchronization for Mobile Apps
Implementing Server Side Data Synchronization for Mobile AppsImplementing Server Side Data Synchronization for Mobile Apps
Implementing Server Side Data Synchronization for Mobile Apps
 

Recently uploaded

%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
masabamasaba
 
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
masabamasaba
 
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
masabamasaba
 
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
masabamasaba
 

Recently uploaded (20)

%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
%+27788225528 love spells in Huntington Beach Psychic Readings, Attraction sp...
 
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Toronto Psychic Readings, Attraction spells,Brin...
 
WSO2CON 2024 - Does Open Source Still Matter?
WSO2CON 2024 - Does Open Source Still Matter?WSO2CON 2024 - Does Open Source Still Matter?
WSO2CON 2024 - Does Open Source Still Matter?
 
AI & Machine Learning Presentation Template
AI & Machine Learning Presentation TemplateAI & Machine Learning Presentation Template
AI & Machine Learning Presentation Template
 
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
%+27788225528 love spells in Colorado Springs Psychic Readings, Attraction sp...
 
%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa
 
%in ivory park+277-882-255-28 abortion pills for sale in ivory park
%in ivory park+277-882-255-28 abortion pills for sale in ivory park %in ivory park+277-882-255-28 abortion pills for sale in ivory park
%in ivory park+277-882-255-28 abortion pills for sale in ivory park
 
%in kempton park+277-882-255-28 abortion pills for sale in kempton park
%in kempton park+277-882-255-28 abortion pills for sale in kempton park %in kempton park+277-882-255-28 abortion pills for sale in kempton park
%in kempton park+277-882-255-28 abortion pills for sale in kempton park
 
%in Midrand+277-882-255-28 abortion pills for sale in midrand
%in Midrand+277-882-255-28 abortion pills for sale in midrand%in Midrand+277-882-255-28 abortion pills for sale in midrand
%in Midrand+277-882-255-28 abortion pills for sale in midrand
 
OpenChain - The Ramifications of ISO/IEC 5230 and ISO/IEC 18974 for Legal Pro...
OpenChain - The Ramifications of ISO/IEC 5230 and ISO/IEC 18974 for Legal Pro...OpenChain - The Ramifications of ISO/IEC 5230 and ISO/IEC 18974 for Legal Pro...
OpenChain - The Ramifications of ISO/IEC 5230 and ISO/IEC 18974 for Legal Pro...
 
WSO2Con2024 - WSO2's IAM Vision: Identity-Led Digital Transformation
WSO2Con2024 - WSO2's IAM Vision: Identity-Led Digital TransformationWSO2Con2024 - WSO2's IAM Vision: Identity-Led Digital Transformation
WSO2Con2024 - WSO2's IAM Vision: Identity-Led Digital Transformation
 
WSO2CON 2024 - Freedom First—Unleashing Developer Potential with Open Source
WSO2CON 2024 - Freedom First—Unleashing Developer Potential with Open SourceWSO2CON 2024 - Freedom First—Unleashing Developer Potential with Open Source
WSO2CON 2024 - Freedom First—Unleashing Developer Potential with Open Source
 
%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa%in tembisa+277-882-255-28 abortion pills for sale in tembisa
%in tembisa+277-882-255-28 abortion pills for sale in tembisa
 
WSO2CON 2024 - API Management Usage at La Poste and Its Impact on Business an...
WSO2CON 2024 - API Management Usage at La Poste and Its Impact on Business an...WSO2CON 2024 - API Management Usage at La Poste and Its Impact on Business an...
WSO2CON 2024 - API Management Usage at La Poste and Its Impact on Business an...
 
Artyushina_Guest lecture_YorkU CS May 2024.pptx
Artyushina_Guest lecture_YorkU CS May 2024.pptxArtyushina_Guest lecture_YorkU CS May 2024.pptx
Artyushina_Guest lecture_YorkU CS May 2024.pptx
 
Announcing Codolex 2.0 from GDK Software
Announcing Codolex 2.0 from GDK SoftwareAnnouncing Codolex 2.0 from GDK Software
Announcing Codolex 2.0 from GDK Software
 
WSO2CON 2024 - WSO2's Digital Transformation Journey with Choreo: A Platforml...
WSO2CON 2024 - WSO2's Digital Transformation Journey with Choreo: A Platforml...WSO2CON 2024 - WSO2's Digital Transformation Journey with Choreo: A Platforml...
WSO2CON 2024 - WSO2's Digital Transformation Journey with Choreo: A Platforml...
 
%in Soweto+277-882-255-28 abortion pills for sale in soweto
%in Soweto+277-882-255-28 abortion pills for sale in soweto%in Soweto+277-882-255-28 abortion pills for sale in soweto
%in Soweto+277-882-255-28 abortion pills for sale in soweto
 
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
%+27788225528 love spells in Atlanta Psychic Readings, Attraction spells,Brin...
 
%in Rustenburg+277-882-255-28 abortion pills for sale in Rustenburg
%in Rustenburg+277-882-255-28 abortion pills for sale in Rustenburg%in Rustenburg+277-882-255-28 abortion pills for sale in Rustenburg
%in Rustenburg+277-882-255-28 abortion pills for sale in Rustenburg
 

Hypermedia APIs - GeekOut

  • 2. Hypermedia API:s @ Jayway Rickard Öberg (~2010)! Qi4j & Streamflow! Usecases as your API! Mattias Arthursson & Karl-Johan Stenflo (~2011)! JAX-RS-HATEOAS! HATEOAS with Standard Java APIs! Mads Enevoldsen & Jan Kronquist (~2011)! Forest (CQS conventions, sensible default links, constraints...)! Gustaf Nilsson Kotte (~2012)! Adaptive HTML as your API
  • 3. Outline Example domain! REST introduction (Richardson maturity model)! Exploring media types! html! collection+json! hal+json
  • 5. Rock - Paper - Scissors
  • 8. http://rps.com The future Facebook of Rock Paper Scissors! Millions of users! Many games per user
  • 9. Playing the game Player A Player B Server rock paper Player B: paper Player A: rock Game 123 Game 123 winner: Player B loser: Player A CREATED WAITING GAME WON GAME TIED any move other move (victory) other move (tie) T
  • 11. Towards REST REST architectural style! Defined by Roy Fielding ! Richardson maturity model http://martinfowler.com/articles/richardsonMaturityModel.html
  • 12. Level 0 - Not at all RESTful Single resource, single verb! Examples:! SOAP, XML-RPC, JSON-RPC
  • 13. Level 0 - Example POST /api --> { "method": “viewGame", "params": ["123"]} <-- { "result": { "state": "waiting"}, "error": null} POST /api --> { "method": "makeMove", "params": ["123","rock"]} <-- { "result": { "state": "won", "winner": "player1", "loser": "player2"}, "error": null}
  • 14. Level 0 - Analysis HTTP as transport protocol! Problems! No client side caching! Tight coupling
  • 15. Level 0 - In the wild JSON/RPC over HTTP! Why?! Simplicity! Track all user actions! If it ain’t broke, don't fix it
  • 16. Level 1 - Resources Many resources, single verb! /api/games/123 /api/players/player1 Almost “object oriented”
  • 17. Level 1 - Example POST /api/games/123 --> { "method": "viewGame"} <-- { "result": { "state": "waiting"}, "error": null} POST /api/games/123 --> { "method": "makeMove", "params": ["rock"]} <-- { "result": { "state": "won", "winner": "player1", "loser": "player2"}, "error": null}
  • 18. Level 1 - Analysis Still just using HTTP as transport
  • 19. Level 2 - Verbs Resources, verb and status codes!! GET, POST, PUT, DELETE... 200 OK, 304 Not Modified, 404 Not found… RESTish! Uniform interface
  • 20. HTTP 101 GET - safe! POST - danger!! PUT - idempotent! ! Note! GET will not modify the resource, but other clients might! Interleaving other requests might break idempotency
  • 21. GET /api/games/123 <-- 200 OK <-- { "state": "waiting"} POST /api/games/123 --> { "move": "rock"} <-- 200 OK <-- { "state": "won", "winner": "player1", "loser": “player2"} Level 2 - Example
  • 22. GET /api/games/123 <-- 200 OK <-- { "state": "waiting"} POST /api/games/123 --> Content-Type: application/json --> { "move": "rock"} <-- 200 OK <-- { "state": "won", "winner": "player1", "loser": "player2"} Level 2 - Mediatype json
  • 23. Level 2 - Mediatype form GET /api/games/123 <-- 200 OK <-- { "state": "waiting"} POST /api/games/123 --> Content-Type: application/x-www-form-urlencoded --> move=rock <-- 200 OK <-- { "state": "won", "winner": "player1", "loser": "player2"} $ curl -d move=rock http://rps.com/api/games/123
  • 24. Level 2 - In the wild Verbs: GET, DELETE, PUT! Resources: buckets, objects, acls, policies…! Why?! CRUD operations! GET allows caching
  • 25. Level 2 - Analysis Using HTTP, not fighting it! Problems! Client must construct URLs! Client must contain business rules
  • 26. GET /api/games <-- 200 OK <-- { "totalCount": 23, "offset": 0, "pageSize": 10, "items": [{"id": "111", "players": ["jan", "cecilia"]}, {"id": "222", "players": ["jan", "mike"]}, {"id": "333", "players": ["cecilia", "mike"]}, ...]} Level 2 - Constructing URLs GET /api/games?offset=10 GET /api/games?page=2 How to navigate to page 2?
  • 27. GET /api/games <-- 200 OK <-- { "totalCount": 23, "offset": 0, "pageSize": 10, "items": [{"id": "111", "players": ["jan", "cecilia"]}, {"id": "222", "players": ["jan", "mike"]}, {"id": "333", "players": ["cecilia", "mike"]}, ...]} Level 2 - Constructing URLs GET /api/games/{game.id} Navigating to game
  • 28. Level 2 - Business logic GET /api/games/123 <-- 200 OK <-- { "state": "waiting", "players": ["ply1", "ply2"], "moves": { "ply1" : true} } Should the client display the move selector?
  • 29. Level 2 - Business logic solved? GET /api/games/123 <-- 200 OK <-- { "state": "waiting", "players": ["ply1", "ply2"], "moves": { "ply1" : true}, "shouldMove": true }
  • 30. Level 3 - Hypermedia Controls Links & forms! REST as defined by Roy Fielding Hypermedia is defined by the presence of application control information embedded within, ! or as a layer above, the presentation of information The simultaneous presentation of information and controls such that the information becomes the affordance through which the user obtains choices and selects actions.
  • 31. GET /api/games <-- 200 OK <-- { "totalCount": 23, "offset": 0, "pageSize": 10, "next": "/api/games?offset=10", "items": [{"href": "/api/games/111", "players": ["jan", "cecilia"]}, {"href": "/api/games/222", "players": ["jan", "mike"]}, {"href": "/api/games/333" "players": ["cecilia", "mike"]}, ...]} Level 3 - Example (links)
  • 32. Level 3 - Example (form) <html> <body> <ol id="players"> <li>Jan</li> <li>Cecilia</li> </ol> <form action="/api/games/111" method="POST"> <select name="move"> <option value="rock">Rock</option> <option value="paper">Paper</option> <option value="scissors">Scissors</option> </select> <input type="submit"/> </form> </body> </html>
  • 33. Level 3 - Opportunity: Extra moves <select name="move"> <option value="rock">Rock</option> <option value="paper">Paper</option> <option value="scissors">Scissors</option> <option value="lizard">Lizard</option> <option value="spock">Spock</option> </select>
  • 34. Level 3 - Changing the rules For one of the players: Flip a coin! head - he must play rock! tail - he can play whatever he wants! ! How can the other player take advantage of this? http://blog.gtorangebuilder.com/2014/04/gto-brain-teaser-1-exploitation-and.html <select name="move"> <option value="rock">Rock</option> </select>
  • 35. Level 3 - In the wild
  • 37. Media types Format! application/json, text/xml, text/plain, text/csv! Domain specific! text/vcard, text/calendar, application/calendar+json! Hypermedia! text/html, application/xhtml+xml! application/vnd.collection+json, application/vnd.hal+json! application/vnd.siren+json, application/vnd.amundsen-uber+json
  • 38. GET /api/games <-- 200 OK <-- Content-Type: application/json <-- { "totalCount": 23, "offset": 0, "pageSize": 10, "next": "/api/games?offset=10", ... } json
  • 39. xhtml GET /api/games <-- 200 OK <-- Content-Type: application/xhtml+xml <-- <html> <body> <a href="/api/games?offset=10">Next</a> <div id="totalCount">23</div> <ol id="games"> <li>...</li> <li>...</li> </ol> </body> </html>
  • 40. collection+json CRUD for collections of objects! Parts of the document:! items! links! queries! templates! errors
  • 41. GET /api/games <-- 200 OK <-- Content-Type: application/vnd.collection+json <-- { "collection": { "version" : "1.0", "href" : "http://rps.com/api/games", "links" : [ {"rel" : "next", "href" : "/api/games?offset=10"} ], "items" : [ { ... }, { ... } ] } } collection+json
  • 42. Anatomy of a Link target url (href)! human readable string (title)! semantic information (rel)! returned media types (type)! ! http method (method)! secondary key (name)! support media types for requests (accept) RFC 5988
  • 44. Custom rels Register with IANA :-)! Just make up your own :-)! move! URI! http://rps.com/rels/move! CURIE! rps:move! http://rps.com/rels/{rel}
  • 45. Forms / templates More than links! Allow user input! May provide! Default values! Data types! Possible values
  • 46. html form <html> <body> <ol id="players"> <li>Jan</li> <li>Cecilia</li> </ol> <form action="/api/games/111" method=“POST" name="move"> <select name="move"> <option value="rock">Rock</option> <option value="paper">Paper</option> <option value="scissors">Scissors</option> </select> <input type="submit"/> </form> </body> </html>
  • 47. GET /api/games/111 <-- 200 OK <-- Content-Type: application/vnd.collection+json <-- { "collection": { "version" : "1.0", "href" : "http://rps.com/api/games/111", "template" : { "data" : [{ "name" : "move", "value" : "", "prompt" : "Your move" }] } } } collection+json template for writes
  • 48. Forced resource structure Collection of games /api/games/ Game 111 /api/games/111 Collection of moves for game 111 /api/games/111/moves Player 1 move for game 111 /api/games/111/moves/ply1 item rps:moves item
  • 49. GET /api/games/111 <-- 200 OK <-- Content-Type: application/vnd.collection+json <-- { "collection": { "version" : "1.0", "href" : "http://rps.com/api/games/111", "links" : [ {"rel" : "rps:moves", "href" : "/api/games/111/moves"} ], ... } } The game links to moves
  • 50. GET /api/games/111/moves <-- 200 OK <-- Content-Type: application/vnd.collection+json <-- { "collection": { "version" : "1.0", "href" : "http://rps.com/api/games/111/moves", "template" : { "data" : { "name" : "move", "value" : "", "prompt" : "Your move" } } } } moves collection contain template
  • 51. URI templates Constructing paths
 
 Form-style! Making a move
 
 Creating a new game RFC 6570 "http://rps.com/api/games/111{?move}" "http://rps.com/api/games/{gameId}" "http://rps.com/api/games{?player1,player2}"
  • 52. application/vnd.hal+json Minimalistic (plain old json)! "_links" with mandatory rels! "_embedded" (recursive!)
  • 53. GET http://rps.com/api/games/123 <-- { ! ! ! ! ! ! ! ! ! ! ! ! ! ! "createdAt" : "2014-05-22T16:24:01", "state" : "waiting" } hal+json
  • 54. GET http://rps.com/api/games/123 <-- { ! ! ! ! ! ! ! ! "_links": { "rps:move": { "href": "http://rps.com/api/games/123{?move}", "templated": true } } "createdAt" : "2014-05-22T16:24:01", "state" : "waiting" } hal+json
  • 55. GET http://rps.com/api/games/123 <-- { "_embedded": { "rps:player" : [{ "_links": { "self": {"href" : "http://rps.com/api/players/111"}, "name": "Jan" }, { "_links": { "self": {"href" : "http://rps.com/api/players/222"}, "name": "Cecilia" }] }, "_links": { "rps:move": { "href": "http://rps.com/api/games/123{?move}", "templated": true } } "createdAt" : "2014-05-22T16:24:01", "state" : "waiting" } hal+json
  • 56. Application state, not objects GET http://rps.com/api/players/111/games/123 <-- { "_links": { "rps:game": {"href" : "http://rps.com/api/games/123"}, "rps:move": { "href": "http://rps.com/api/games/123{?move}", "templated": true } } }
  • 57. GET http://rps.com/api/players/111/games/123 <-- { "_embedded": { "rps:game" : [{ "_links": { "self": {"href" : "http://rps.com/api/games/123"}, "createdAt" : "2014-05-22T16:24:01", "state" : "waiting" }] }, "_links": { "rps:move": { "href": "http://rps.com/api/games/123{?move}", "templated": true } } } Application state, not objects
  • 58. Summary Hypermedia simplifies client development! No constructing of URLs! Opportunities for less business logic! Pick a mediatype with reasonable semantics! Consider form-encoded when POSTing! Some useful tools! CURIE, URITemplates