Your SlideShare is downloading. ×
Confoo2013 make your java-app rest enabled
Upcoming SlideShare
Loading in...5
×

Thanks for flagging this SlideShare!

Oops! An error has occurred.

×
Saving this for later? Get the SlideShare app to save on your phone or tablet. Read anywhere, anytime – even offline.
Text the download link to your phone
Standard text messaging rates apply

Confoo2013 make your java-app rest enabled

633
views

Published on


0 Comments
1 Like
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
633
On Slideshare
0
From Embeds
0
Number of Embeds
2
Actions
Shares
0
Downloads
9
Comments
0
Likes
1
Embeds 0
No embeds

Report content
Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
No notes for slide

Transcript

  • 1. Make your java appREST enabledAnthony Dahanne Confoo 2013 — Feb. 28th, 2013
  • 2. About me …§ Software Engineer at Terracotta – Working on EhCache management REST API and webapp (aka Terracotta Management Console, TMC) – Strong interest in CI, build tools (maven) – Android developer when time permits ... Confoo 2013 2
  • 3. Terracotta§ Founded 2003 in San Francisco, CA§ Joined Software AG in 2011§ Present in India, Europe and pretty much all over the globe!§ The company behind : Confoo 2013 3
  • 4. Agenda§ The Terracotta Management Console example§ Introduction to REST, Java integration – REST – The Java case : JAX-RS§ Securing your REST interface – JEE included authc and authz options – Apache Shiro§ Final words... 2
  • 5. The Terracotta Management Console example
  • 6. Terracotta EhCache : Simplified architecture (Web) app Business logic DAO Database JVM 5
  • 7. Terracotta EhCache : Simplified architecture (Web) app Business logic DAO Database JVM 5
  • 8. Terracotta EhCache : Simplified architecture (Web) app Business logic DAO Database JVM 5
  • 9. Terracotta EhCache : Simplified architecture (Web) app Business logic DAO Database EhCache JVM 5
  • 10. Terracotta EhCache : Simplified architecture (Web) app Business logic DAO Database EhCache JVM 5
  • 11. Terracotta EhCache : Simplified architecture (Web) app (Web) app Database Business logic Business logic DAO DAO EhCache EhCache JVM JVM 5
  • 12. Terracotta EhCache : Simplified architecture (Web) app (Web) app Database Business logic Business logic DAO DAO EhCache EhCache JVM JVM 5
  • 13. Terracotta EhCache : Simplified architecture (Web) app (Web) app Database Business logic Business logic DAO DAO EhCache EhCache JVM JVM 5
  • 14. Terracotta EhCache : Simplified architecture (Web) app (Web) app Database Business logic Business logic DAO DAO EhCache EhCache JVM JVM 5
  • 15. Simplified architecture : management agents(Web) appEhCache JVM 7
  • 16. Simplified architecture : management agents(Web) app RestEhCache Agent JVM 7
  • 17. Simplified architecture : management agents(Web) app Rest RestEhCache Agent Agent JVM 7
  • 18. Simplified architecture : management agents(Web) app Rest RestEhCache Agent Agent JVM Http Client Http Client Terracotta Management Server 7
  • 19. Simplified architecture : management agents(Web) app Rest RestEhCache Agent Agent JVM Http Client Http Client Terracotta Management Server REST API 7
  • 20. Simplified architecture : management agents(Web) app Rest RestEhCache Agent Agent JVM Http Client Http Client Terracotta Management Server REST API Terracotta Management Console JS + CSS Browser 7
  • 21. Simplified architecture : management agents(Web) app Rest RestEhCache Agent Agent JVM Http Client Http Client Terracotta Management Server REST API Terracotta Management Console cURL JS + CSS HTTP Script Browser 7
  • 22. What you can do with the TMC§ Access your Caches / Cache Managers stats§ Restart a Terracotta server§ Clear a cache§ Dynamically change your Cache / CM config 8
  • 23. What you can do with the TMC§ Access your Caches / Cache Managers stats§ Restart a Terracotta server§ Clear a cache§ Dynamically change your Cache / CM config§ Demo ! 8
  • 24. Introduction to REST, Java Integration
  • 25. A few words about REST…§ Web services leveraging standard HTTP verbs – GET,POST,PUT,DELETE,OPTIONS,HEAD§ Conneg (multiple representations) – to negotiate the format (JSON, XML, etc.)§ Stateless communication§ HATEOAS 10
  • 26. JAX-RS : Java specification for REST Services§ Version 1.1 appeared in Java EE 6§ Server only spec (until 2.0, out Q2 2013)§ Annotations driven API§ Oracle / Sun Jersey is the reference impl. – Redhat Resteasy, Restlet, Apache CXF are among others 11
  • 27. JAX-RS : Binding your REST services to yourapp§ Using web.xml: 13
  • 28. JAX-RS : Binding your REST services to yourapp§ Customizing loading of resources 14
  • 29. JAX-RS : Annotations available 15
  • 30. JAX-RS : Annotations available§ @Provider§ @Path§ @GET, @PUT, @POST, @DELETE and @HEAD§ @Produces§ @Consumes 15
  • 31. JAX-RS : Annotations available§ @Provider§ @Path @Path(“/cars/{id}”)§ @GET, @PUT, @POST, @DELETE and @HEAD§ @Produces§ @Consumes 15
  • 32. JAX-RS : Annotations available§ @Provider§ @Path @Path(“/cars/{id}”)§ @GET, @PUT, @POST, @DELETE and @HEAD§ @Produces @Produces(“application/json”,”text/plain”)§ @Consumes 15
  • 33. JAX-RS : Annotations available§ @Provider§ @Path @Path(“/cars/{id}”)§ @GET, @PUT, @POST, @DELETE and @HEAD§ @Produces @Produces(“application/json”,”text/plain”)§ @Consumes @Consumes(“application/xml”) 15
  • 34. JAX-RS : Annotations available to bindparameters – @PathParam -> path segment. – @QueryParam -> HTTP query parameter. – @MatrixParam -> HTTP matrix parameter. – @Context ->inject context variables 16
  • 35. JAX-RS : Annotations available to bindparameters – @PathParam -> path segment. @GET @Path("/groups/{groupId}") public Collection<Agent> getAgents(@PathParam("groupId") String groupId) { return configSvc.getAgentsByGroup(groupId, authorizer.getPrincipal()); } – @QueryParam -> HTTP query parameter. – @MatrixParam -> HTTP matrix parameter. – @Context ->inject context variables 16
  • 36. JAX-RS : Annotations available to bindparameters – @PathParam -> path segment. @GET @Path("/groups/{groupId}") public Collection<Agent> getAgents(@PathParam("groupId") String groupId) { return configSvc.getAgentsByGroup(groupId, authorizer.getPrincipal()); } – @QueryParam -> HTTP query parameter. – @MatrixParam -> HTTP matrix parameter. – @Context ->inject context variables @GET @Produces(MediaType.APPLICATION_JSON) Collection<CacheManagerEntity> getCacheManagers(@Context UriInfo info) { String cacheManagerNames = info.getPathSegments().get(1).getMatrixParameters().getFirst("names"); MultivaluedMap<String, String> qParams = info.getQueryParameters(); List<String> attrs = qParams.get(ATTR_QUERY_KEY); } 16
  • 37. JAX-RS : Raw Content Handlers§ By default, you can bind your request payload or your response to streams@PUT@Path("/inputstream")@Produces("text/plain")public Response getInputStream(InputStream is) throws IOException { System.out.println(inputStreamToString(is)); return Response.noContent().build();} 16
  • 38. JAX-RS : Raw Content Handlers § By default, you can bind your request payload or your response to streams@PUT@Path("/inputstream")@Produces("text/plain")public Response getInputStream(InputStream is) throws IOException { System.out.println(inputStreamToString(is)); return Response.noContent().build();}@GET@Path("/outputstream")@Produces("text/plain")public StreamingOutput getOutputStream() { return new StreamingOutput() { @Override public void write(OutputStream output) throws IOException, WebApplicationException { output.write("hello".getBytes()); } };} 16
  • 39. JAX-RS : Adding your own Content Handler§ Implementing – MessageBodyReader<T> : handle the request – MessageBodyWriter<T> : handle the response§ Examples : – FileProvider from jersey-core – AbstractJAXBProvider from jersey-core 16
  • 40. JAX-RS : JAXB Content Handlers§ Using JAXB you can convert POJOs to XML (or JSON) and vice versa @XmlRootElement public final class Agent { private TYPE type; private String name; private String groupId; private String agentLocation; private Integer connectionTimeoutMillis; private Integer readTimeoutMillis; //etc... } 16
  • 41. JAX-RS : Meaningful error responses – Implementing and registering your own ExceptionMapper @Provider public class DefaultExceptionMapper implements ExceptionMapper<Throwable> { public Response toResponse(Throwable exception) { return Response.status(Response.Status.INTERNAL_SERVER_ERROR) .type(MediaType.APPLICATION_JSON_TYPE) .entity( String.format("{"error" : "%s" , "details" : "%s"}", errorMessage, extraErrorMessage)) .build(); } } 16
  • 42. JAX-RS : Testing anyone ?§ Integration testing to validate – the REST API – end to end testing§ How to do integration testing against JAX-RS ? – creating a client and making assertions : • java.net.HttpUrlConnection, Apache HttpClient – RestAssured from Jayway :expect().statusCode(404).when().get("/cacheManagers/hello");String expectedResourceLocation = "/api/config/agents/Local Connection 4343";expect().contentType(ContentType.JSON).body(containsString("Local Connection 4343"), containsString("10000")).statusCode(200).when().get(expectedResourceLocation); 16
  • 43. Securing your REST interface
  • 44. Standard JEE security : certificate authentication§ Basic Authentication§ Form-based login authentication§ Digest Authentication§ SSL Authentication 18
  • 45. Standard JEE security : basic authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Basic realm="Secured Realm" 18
  • 46. Standard JEE security : basic authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Basic realm="Secured Realm"If the user is “anthony” and password is “terracotta”, the client sendsGET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Basic YW50aG9ueTp0ZXJyYWNvdHRhSince base64(anthony:terracotta) = YW50aG9ueTp0ZXJyYWNvdHRh 18
  • 47. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 48. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",uri="/private/index.html",qop=auth,nc=00000001,cnonce="0a4f113b",response="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 49. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",uri="/private/index.html",qop=auth,nc=00000001, Copiescnonce="0a4f113b",response="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 50. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",uri="/private/index.html",qop=auth,nc=00000001, counter Copiescnonce="0a4f113b", randomresponse="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 51. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",uri="/private/index.html",qop=auth,nc=00000001, Copiescnonce="0a4f113b",response="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 52. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",uri="/private/index.html",qop=auth,nc=00000001,cnonce="0a4f113b",response="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 53. Standard JEE security : digest authenticationGET /private/index.html HTTP/1.1Host: www.example.orgHTTP/1.1 401 Authorization RequiredContent-type: text/htmlWWW-Authenticate: Digest realm="MyRealm",qop="auth, auth-int",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093",opaque="5ccc069c403ebaf9f0171e9517f40e41"GET /private/index.html HTTP/1.1Host: www.example.orgAuthorization: Digest username="anthony",realm="MyRealm",nonce="dcd98b7102dd2f0e8b11d0f600bfb0c093", H1=md5(“anthony:MyRealm:password”)uri="/private/index.html",qop=auth, H2=md5(“GET:/private/index.html”)nc=00000001, response = md5(“H1:nonce:nc:cnonce:qop:H2)cnonce="0a4f113b",response="6629fae49393a05397450978507c4ef1",opaque="5ccc069c403ebaf9f0171e9517f40e41" 18
  • 54. Standard JEE security : form-basedauthentication Webapp HTTP Client 18
  • 55. Standard JEE security : form-basedauthentication 1. request protected resource Webapp HTTP Client 18
  • 56. Standard JEE security : form-basedauthentication 1. request protected resource Webapp HTTP Client 2. redirect to the login page j_username j_password 18
  • 57. Standard JEE security : form-basedauthentication 1. request protected resource Webapp HTTP Client 2. redirect to the login page j_username j_security_check j_password 3. submit login form 18
  • 58. Standard JEE security : form-basedauthentication 1. request protected resource Webapp HTTP Client 2. redirect to the login page j_username j_security_check j_password 3. submit login form Success 4. redirect to the protected resource 18
  • 59. Standard JEE security : form-basedauthentication 1. request protected resource Webapp HTTP Client 2. redirect to the login page j_username j_security_check j_password 3. submit login form Success Failure 4. redirect to the protected resource 4f. returns error page 18
  • 60. Standard JEE security : certificate authentication HTTP Client WebappKeystore Truststore Keystore Truststore Server.crt Server.crt Success Failure 18
  • 61. Standard JEE security : certificate authentication 1. request HTTPS protected resource HTTP Client WebappKeystore Truststore Keystore Truststore Server.crt Server.crt Success Failure 18
  • 62. Standard JEE security : certificate authentication 1. request HTTPS protected resource HTTP Client 2. sends cert WebappKeystore Truststore Keystore Truststore Server.crt Server.crt Success Failure 18
  • 63. Standard JEE security : certificate authentication 1. request HTTPS protected resource HTTP Client 2. sends cert WebappKeystore Truststore Keystore Truststore 3. sends cert Client.crt Server.crt Server.crt Client.crt Success Failure 18
  • 64. Standard JEE security : certificate authentication 1. request HTTPS protected resource HTTP Client 2. sends cert WebappKeystore Truststore Keystore Truststore 3. sends cert Client.crt Server.crt Server.crt Client.crt Success Failure 4. returns protected resource 18
  • 65. Standard JEE security : configuration <security-constraint> <display-name>My security constraint</display-name> <web-resource-collection> <web-resource-name>myresource</web-resource-name> <description/> <url-pattern>/protected/*</url-pattern> </web-resource-collection> <auth-constraint> <description/> <role-name>myuser</role-name> </auth-constraint> web.xml </security-constraint> <login-config> <auth-method>FORM</auth-method> <realm-name>My Realm</realm-name> <form-login-config> <form-login-page>/login.jsp</form-login-page> <form-error-page>/error.jsp</form-error-page> </form-login-config> </login-config> <security-role> <description/> <role-name>myuser</role-name> </security-role> 19
  • 66. Security with Apache Shiro§ Shiro is about : – Authentication – Authorization – Realms – Session Management – Cryptography 20
  • 67. Why choose Shiro over JEE security ?§ Shiro is deployment agnostic – not necessarily a webapp§ Shiro secures all the layers of your application – not only the “web layer”§ Highly customizable – Realms, filters, listeners, etc... 20
  • 68. Securing your REST application with Shiro§ Register the Listener and the Filter<listener> <listener-class>c.t.m.s.w.s.TMSEnvironmentLoaderListener</listener-class></listener><filter> <filter-name>securityFilter</filter-name> <filter-class>c.t.m.s.w.s.TMSSecurityFilter</filter-class></filter><filter-mapping> <filter-name>securityFilter</filter-name> <url-pattern>/*</url-pattern> <dispatcher>REQUEST</dispatcher> – <dispatcher>FORWARD</dispatcher> <dispatcher>INCLUDE</dispatcher> <dispatcher>ERROR</dispatcher></filter-mapping> 21
  • 69. Shiro Realms used§ For Terracotta REST agents – TCIdentityAssertionRealm§ For the Terracotta Management Console – TCIniRealm – LdapRealm – ActiveDirectoyRealm 21
  • 70. Example of shiro.ini[main]securityManager = org.apache.shiro.web.mgt.DefaultWebSecurityManagerldapRealm = com.terracotta.management.security.shiro.realm.ActiveDirectoryRealmldapRealm.userDnTemplate = CN={0},CN=Users,DC=mykene,DC=rndlab,DC=locldapRealm.searchBase = DC=mykene,DC=rndlab,DC=locldapRealm.contextFactory.url = ldap://10.21.32.72:389securityManager.realm = $ldapRealmsecurityManager.sessionManager.globalSessionTimeout = 600000mgmtAuthListener = c.t.m.s.a.ManagementAuthenticationListenersecurityManager.authenticator.authenticationListeners = $mgmtAuthListenerauthc.loginUrl = /login.jspauthc.successUrl = /index.jsp –iaauthc = com.terracotta.management.security.shiro.web.filter.TCIdentityAssertionFilter[urls]/login.jsp = authc/logout = logout/** = authc, roles[operator]/rest/** = noSessionCreation, iaauthc, rest[api] 21
  • 71. Final words...
  • 72. Switching to REST for management§ Brought us : – consumption from outside the Java world – scriptability – “firewalls compatibility” – existing monitoring tools (Nagios, etc...) 18
  • 73. Lessons learned creating the rest agents ... 18
  • 74. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning 18
  • 75. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning§ Be a nice REST citizen – respect the HTTP status codes – return meaningful error responses 18
  • 76. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning§ Be a nice REST citizen – respect the HTTP status codes – return meaningful error responses 18
  • 77. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning§ Be a nice REST citizen – respect the HTTP status codes – return meaningful error responses§ Security brings complexity 18
  • 78. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning§ Be a nice REST citizen – respect the HTTP status codes – return meaningful error responses§ Security brings complexity 18
  • 79. Lessons learned creating the rest agents ...§ Prepare for classloading issues – JBoss wants to deploy REST resources using RestEasy – OSGI does not play nice with Jersey resource scanning§ Be a nice REST citizen – respect the HTTP status codes – return meaningful error responses§ Security brings complexity§ Ldap has a lot of different schemas ... 18
  • 80. Useful tools to develop / debug / test§ Fast deploy your REST based application – Maven jetty:run(ner), or tomcat7:run(ner) – JRebel (not to stop/start your container for every change)§ Monitor HTTP traffic – Membrane§ Hand tailor HTTP messages – Curl – Chrome Advanced REST Client (via Chrome Store)§ Inspect your SSL Keystores and Trustores – Keystore Explorer 18
  • 81. Useful resources§ HTTP – Cours du soir, by @paulgreg (en français)§ REST – Roy Fielding’s thesis§ JAX-RS / Jersey – RESTful Java, by @patriot1burke – Arun Gupta presentation on JAX-RS 2.0§ Shiro – Shiro official documentation 18
  • 82. terracotta | terracotta.org Vote now ! https://joind.in/7901 Thank you ! twitter | @anthonydahanne email | adahanne@terracottatech.com blog | blog.dahanne.net

×