Security for Microservices with Spring

035ae18f5f948ab3c8a5cbf40bbea383?s=47 Dave Syer
September 09, 2014

Security for Microservices with Spring

This presentation explores a range of options for securing microservices, ranging from physical network security to token-based authentication with OAuth2. It shows how the combination of rapid development and production-ready features in the modern Spring stack are a perfect mixture for developing secure components in a system composed of microservices. We explore the new features in Spring OAuth2, guide you through the choice of which to use and when, and show how easy they are to enable quickly. Also available (with clickable links) at http://presos.dsyer.com/decks/microservice-security.html.

035ae18f5f948ab3c8a5cbf40bbea383?s=128

Dave Syer

September 09, 2014
Tweet

Transcript

  1. Security for Microservices with Spring Dave Syer, 2012 Twitter: @david_syer

    Email: dsyer@pivotal.io (Security for Microservices with Spring) http://localhost:4000/decks/microservice-security.html 1 of 47 10/09/14 06:47
  2. Agenda What is a Microservice? How would it be secure?

    If I was going to use Spring how would that look? What's the easiest way to get something working? http://localhost:4000/decks/microservice-security.html 2 of 47 10/09/14 06:47
  3. Introduction There is a strong trend in distributed systems with

    lightweight architectures People have started to call them "microservices" So what are people doing about security in such systems? http://localhost:4000/decks/microservice-security.html 3 of 47 10/09/14 06:47
  4. What is a Microservice? HTTP transport (usually). Text-based message content,

    usually JSON. Small, compact messages, and quick responses. REST-ful, or at least inspired by the REST Some degree of statelessness Interoperability. http://localhost:4000/decks/microservice-security.html 4 of 47 10/09/14 06:47
  5. What Are the Security Requirements Stop bad guys from accessing

    your resources Identity and permissions: How is identity and permission information conveyed to a service? How is it decoded and interpreted? What data are needed to make the access decision (user accounts, roles, ACLs etc.)? How is the data managed: who is responsible for storing and retrieving it? How can you verify that the request hasn't been tampered with? http://localhost:4000/decks/microservice-security.html 5 of 47 10/09/14 06:47
  6. HTTP Basic Authentication Something of a lowest common denominator Supported

    on practically all servers natively and out of the box Ubiquitous support on the client side in all languages Good support in Spring Security Spring Boot autoconfigures it out of the box Example: $ curl "https://$username:$password@myhost/resource" http://localhost:4000/decks/microservice-security.html 6 of 47 10/09/14 06:47
  7. Simple Service @Grab('spring-boot-starter-security') @RestController class Application { @RequestMapping("/") def home()

    { [status: 'OK'] } } http://localhost:4000/decks/microservice-security.html 7 of 47 10/09/14 06:47
  8. So what's wrong with that? Nothing, but... Where do you

    get the credentials (the username and password)? Fine for systems where all participants can share secrets securely In practice that means small systems Only supports username/password Only covers authentication No distinction between users and machines http://localhost:4000/decks/microservice-security.html 8 of 47 10/09/14 06:47
  9. Network Security Microservice endpoints not visible outside an internal network

    Very secure Very flexible (e.g. using virtual networks) Suits architecture based on "edge" server http://localhost:4000/decks/microservice-security.html 9 of 47 10/09/14 06:47
  10. So what's wrong with that? Nothing, but... Annoying to debug

    and a little bit fiddly to maintain Configuration is out of the control of developers in many cases for organizational reasons There's no identity or authentication http://localhost:4000/decks/microservice-security.html 10 of 47 10/09/14 06:47
  11. Certificate Based Security Set up SSL on server so that

    request has to contain certificate Spring Security (X.509) can turn that into an Authentication If SSL is in the service layer (i.e. not at the router/loadbalancer) then you have a keystore anyway Example: $ curl -k --cert rod.pem:password https://localhost:8443/hello http://localhost:4000/decks/microservice-security.html 11 of 47 10/09/14 06:47
  12. So what's wrong with that? Nothing, but... There's no user

    identity (only at most the machine) unless browsers have certificates installed Requires keystores and certificates in all applications and services (significantly non-trivial if done properly, but some organizations require it anyway) No fine distinction between users and machines http://localhost:4000/decks/microservice-security.html 12 of 47 10/09/14 06:47
  13. Custom Authentication Token Random identifier per authentication Grant them from

    a central service and/or store in a central database Can be exposed directly via developer UI Re-hydrate authentication in service Spring Security AbstractPreAuthenticatedProcessingFilter and friends Even easier: Spring Session identifier Github example: token is temporary password in HTTP Basic http://localhost:4000/decks/microservice-security.html 13 of 47 10/09/14 06:47
  14. So what's wrong with that? Nothing, but... No separation of

    client app from user authentication Coarse grained authorization (all tokens activate all resources) It's not a "standard" (but there are ready made implementations) For user authentication, need to collect user credentials in app http://localhost:4000/decks/microservice-security.html 14 of 47 10/09/14 06:47
  15. OAuth2 Key Features Extremely simple for clients Access tokens carry

    information (beyond identity) Resources are free to interpret token content http://localhost:4000/decks/microservice-security.html 15 of 47 10/09/14 06:47
  16. So what's wrong with that? Nothing, but... No standard (yet)

    for request signing http://localhost:4000/decks/microservice-security.html 16 of 47 10/09/14 06:47
  17. Quick Introduction to OAuth2 A Client application, often web application,

    acts on behalf of a User, but with the User's approval Authorization Server Resource Server Client application Common examples of Authorization Servers and Resource Servers on the internet: Facebook - Graph API Google - Google APIs Cloud Foundry - Cloud Controller http://localhost:4000/decks/microservice-security.html 17 of 47 10/09/14 06:47
  18. OAuth2 Bearer Tokens Centralizing account management and permissions: OAuth 2.0

    adds an extra dimension - more information for the access decision Standards always help in security Lightweight - easy to curl Requires HTTPS for secure operation, but you can test with HTTP http://localhost:4000/decks/microservice-security.html 18 of 47 10/09/14 06:47
  19. OAuth2 and the Microservice Example command line Client: $ curl

    -H "Authorization: Bearer $TOKEN" https://myhost/resource https://myhost is a Resource Server TOKEN is a Bearer Token it came from an Authorization Server http://localhost:4000/decks/microservice-security.html 19 of 47 10/09/14 06:47
  20. Simple Authorization Server @EnableAuthorizationServer class AuthorizationServer extends AuthorizationServerConfigurerAdapter { @Override

    void configure(ClientDetailsServiceConfigurer clients) throws Exception { clients.inMemory() .withClient("my-client-with-secret")... } } http://localhost:4000/decks/microservice-security.html 20 of 47 10/09/14 06:47
  21. Example token contents Client id Resource id (audience) Issuer User

    id Role assignments http://localhost:4000/decks/microservice-security.html 21 of 47 10/09/14 06:47
  22. JWT Bearer Tokens OAuth 2.0 tokens are opaque to clients

    But they carry important information to Resource Servers Example of implementation (from Cloud Foundry UAA, JWT = signed, base64-encoded, JSON): { "client_id":"cf", "exp":1346325625, "scope": ["cloud_controller.read","openid","password.write"], "aud":["openid","cloud_controller","password"], "iss": "https://login.run.pivotal.io", "user_name":"tester@vmware.com", "user_id":"52147673-9d60-4674-a6d9-225b94d7a64e", "email":"tester@vmware.com", "jti":"f724ae9a-7c6f-41f2-9c4a-526cea84e614" } http://localhost:4000/decks/microservice-security.html 22 of 47 10/09/14 06:47
  23. JWT Authorization Server @EnableAuthorizationServer class AuthorizationServer extends AuthorizationServerConfigurerAdapter { @Bean

    public JwtAccessTokenConverter accessTokenConverter() { return new JwtAccessTokenConverter(); } @Override public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception { endpoints.authenticationManager(authenticationManager) .accessTokenConverter(accessTokenConverter()); } ... // client config } http://localhost:4000/decks/microservice-security.html 23 of 47 10/09/14 06:47
  24. User Approvals An access token represents a user approval: http://localhost:4000/decks/microservice-security.html

    24 of 47 10/09/14 06:47
  25. http://localhost:4000/decks/microservice-security.html 25 of 47 10/09/14 06:47

  26. User Approvals as Token An access token represents a user

    approval: http://localhost:4000/decks/microservice-security.html 26 of 47 10/09/14 06:47
  27. http://localhost:4000/decks/microservice-security.html 27 of 47 10/09/14 06:47

  28. Formal Model for User Approvals It can be an advantage

    to store individual approvals independently (e.g. for explicit revokes of individual scopes): http://localhost:4000/decks/microservice-security.html 28 of 47 10/09/14 06:47
  29. http://localhost:4000/decks/microservice-security.html 29 of 47 10/09/14 06:47

  30. Spring OAuth Support @EnableAuthorizationServer class AuthorizationServer extends AuthorizationServerConfigurerAdapter { @Override

    public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception { endpoints.tokenStore(tokenStore()); } @Bean public ApprovalStore approvalStore() throws Exception { TokenApprovalStore store = new TokenApprovalStore(); store.setTokenStore(tokenStore()); return store; } ... // client config and tokenStore() defined here } http://localhost:4000/decks/microservice-security.html 30 of 47 10/09/14 06:47
  31. Simple Resource Server @EnableResourceServer class ResourceServer { @Bean TokenStore tokenStore()

    throws Exception { ... } } or @EnableResourceServer class ResourceServer { @Bean ResourceServerTokenServices tokenServices() throws Exception { ... } } http://localhost:4000/decks/microservice-security.html 31 of 47 10/09/14 06:47
  32. Simple Client Application @EnableOAuth2Client class ClientApplication { @Autowired // session-scoped

    private OAuth2ClientContext clientContext @Bean OAuth2RestOperations restTemplate() { new OAuth2RestTemplate(resource, clientContext) } ... } http://localhost:4000/decks/microservice-security.html 32 of 47 10/09/14 06:47
  33. Authorization Code Grant Summary Authorization Server authenticates the User 1.

    Client starts the authorization flow and obtain User's approval 2. Authorization Server issues an authorization code (opaque one-time token) 3. Client exchanges the authorization code for an access token. 4. http://localhost:4000/decks/microservice-security.html 33 of 47 10/09/14 06:47
  34. Role of Resource Server Extract token from request and decode

    it 1. Make access control decision Scope Audience User account information (id, roles etc.) Client information (id, roles etc.) 2. Send 403 (FORBIDDEN) if token not sufficient 3. http://localhost:4000/decks/microservice-security.html 34 of 47 10/09/14 06:47
  35. Role of the Authorization Server Grant tokens 1. Interface for

    users to confirm that they authorize the Client to act on their behalf 2. Authenticate users (/authorize) 3. Authenticate clients (/token) 4. #1 and #4 are covered thoroughly by the spec; #2 and #3 not (for good reasons). http://localhost:4000/decks/microservice-security.html 35 of 47 10/09/14 06:47
  36. Client Registration and Scopes For secure channels a client has

    to authenticate itself to obtain a token, so it has to be known to the Authorization Server. Registration provides at a mimimum: authentication (shared secret) registered redirect URI (optional but essential to prevent attacks) allowed scopes (clients are not permitted access to all resources) Also useful: a way to identify which resources can be accessed ownership information (which user registered the client) http://localhost:4000/decks/microservice-security.html 36 of 47 10/09/14 06:47
  37. More on Scopes Per the spec they are arbitrary strings.

    The Authorization Server and the Resource Servers agree on the content and meanings. Examples: Google: https://www.googleapis.com /auth/userinfo.profile Facebook: email, read_stream, write_stream UAA: cloud_controller.read, cloud_controller.write, scim.read, openid Authorization Server has to decide whether to grant a token to a given client and user based on the requested scope (if any). http://localhost:4000/decks/microservice-security.html 37 of 47 10/09/14 06:47
  38. Authentication and the Authorization Server Authentication (checking user credentials) is

    orthogonal to authorization (granting tokens) They don't have to be handled in the same component of a large system Authentication is often deferred to existing systems (SSO) Authorization Server has to be able to authenticate the OAuth endpoints (/authorize and /token) It does not have to collect credentials (except for grant_type=password) http://localhost:4000/decks/microservice-security.html 38 of 47 10/09/14 06:47
  39. OAuth2 and the Microservice Resource Servers might be microservices Web

    app clients: authorization code grant Browser clients (single page app): authorization code grant (better) or implicit grant Mobile and non-browser clients: password grant (maybe with mods for multifactor etc.) Service clients (intra-system): client credentials or relay user token http://localhost:4000/decks/microservice-security.html 39 of 47 10/09/14 06:47
  40. Single Page Apps With backend services CORS restrictions make reverse

    proxy useful (@EnableZuulProxy). Then you can acquire tokens in the client app and relay them to back end. With no backend services, don't be shy, use the session (authorization code flow is vastly superior). Spring Session helps a lot. http://localhost:4000/decks/microservice-security.html 40 of 47 10/09/14 06:47
  41. Relaying User Tokens Front end app sends SSO token with

    user credentials to authenticate back end requests, back ends just relay it to each other as necessary. Simple but possibly flawed: the front end only needs access to user details to authenticate, but you need to give it permission to do other things to allow it access to the back ends. Idea: exchange (with full authentication) the incoming token for an outgoing one with different permissions (client but not scope). Can use password grant (e.g. with the incoming token as a password). http://localhost:4000/decks/microservice-security.html 41 of 47 10/09/14 06:47
  42. OAuth 1.0 Another (slightly older) standard Includes request signing Common

    in early wave public APIs (e.g. Twitter) Spring Security OAuth is full solution at framework level http://localhost:4000/decks/microservice-security.html 42 of 47 10/09/14 06:47
  43. So What's Wrong with That? Nothing but... It's hard work

    for client app developers (crypto) (Notionally at least) superseded by OAuth2 http://localhost:4000/decks/microservice-security.html 43 of 47 10/09/14 06:47
  44. SAML Assertions Another standard with similar features to OAuth2 XML

    based Common infrastructure in enterprise Spring Security SAML provides SP and Consumer roles (not IDP) Request signing is standadized http://localhost:4000/decks/microservice-security.html 44 of 47 10/09/14 06:47
  45. So What's Wrong with That? Nothing but... Painful to set

    up for servers and client Large amounts of XML data in HTTP headers Huge complexity for developers N.B. exchanging SAML assertion for OAuth2 token is quote normal http://localhost:4000/decks/microservice-security.html 45 of 47 10/09/14 06:47
  46. In Conclusion Lightweight services demand lightweight infrastructure Security is important,

    but should be unobtrusive Spring Security makes it all easier Special mention for Spring Session OAuth 2.0 is a standard, and has a lot of useful features Spring Security OAuth aims to be a complete OAuth2 solution at the framework level Cloudfoundry has an open source, OAuth2 identity service (UAA) http://localhost:4000/decks/microservice-security.html 46 of 47 10/09/14 06:47
  47. Links http://github.com/spring-projects/spring-security-oauth http://github.com/spring-projects/spring-security-oauth/tree/master /tests/annotation http://github.com/cloudfoundry/uaa http://blog.spring.io http://blog.cloudfoundry.org http://presos.dsyer.com/decks/microservice-security.html Twitter: @david_syer

    Email: dsyer@pivotal.io http://localhost:4000/decks/microservice-security.html 47 of 47 10/09/14 06:47