Upgrade to Pro — share decks privately, control downloads, hide ads and more …

BaselOne 2018: Living on the edge - API Gateways

BaselOne 2018: Living on the edge - API Gateways

Avatar for Christian Schwörer

Christian Schwörer

October 18, 2018
Tweet

More Decks by Christian Schwörer

Other Decks in Programming

Transcript

  1. Microservices without an API Gateway Single Page Application Mobile App

    CHALLENGES:  Same Origin Policy  Cross cutting concerns  Authentication  SSL-Termination  (Security-)Header  Rate limiting & throtteling  etc.  Protecting internal endpoints  Microservice Evolution, Migrations Users Images Comments
  2. Microservices with an API Gateway Single Page Application Mobile App

    CHALLENGES:  Same Origin Policy ✓  Cross cutting concerns ✓  Authentication  SSL-Termination  (Security-)Header  Rate limiting & throtteling  etc.  Protecting internal endpoints ✓  Microservice Evolution, Migrations ✓ API Gateway Users Images Comments
  3.  Core functionality of gateways  Bundles many servers into

    one endpoint  Often provide extras:  rate limiting  request size constraints  serving static content  …  Often, that’s all we need!  Very simple …  to setup  to scale  to provide high availability Reverse Proxy CLIENT PROXY
  4. Reverse Proxy: NGINX server { listen 443; location /users {

    proxy_pass http://localhost:8081; } location /comments { proxy_pass http://localhost:8082; } location /images { proxy_pass http://localhost:8083; } } Users-Service Comments- Service Images-Service
  5.  Application runtime  Slightly higher abstraction  Controlled via

    command line tool Cloud Foundry and Kubernetes  Container runtime  Slightly more control  Controlled via command line tool
  6.  CF assigns applications a service route  Multiple services

    = multiple endpoints  Any API Gateway can be run as application  Simplest solution: NGINX Reverse Proxy Cloud Foundry + Gateway-App
  7. Cloud Foundry: The NGINX Config server { listen {{port}}; #

    This will be replaced by CF magic. location /users/ { proxy_pass http://users.local.pcfdev.io/; } location /comments/ { proxy_pass http://comments.local.pcfdev.io/; } }
  8. In the same directory as the config: cf push \

    api-gateway \ -b https://github.com/cloudfoundry/nginx-buildpack.git \ -i 2 Cloud Foundry: Deploy it!
  9. cf create-route myspace example.com \ --hostname myapp --path foo cf

    map-route my-app example.com \ --hostname myapp –path foo Cloud Foundry: Built-in solution
  10.  Ingress controllers move gateway functionality into infrastructure  Simple

    example: NGINX Ingress Controller  Deployed services declare an ingress object  Kubernetes does the rest  We can do  path-based routing  DNS name-based routing  automated HTTPS cert retrieval with cert-manager  fine tuning on the edge router  … Kubernetes
  11. Kubernetes configuration --- apiVersion: extensions/v1beta1 kind: Ingress metadata: name: user-ingress

    annotations: kubernetes.io/ingress.class: nginx spec: rules: - host: myapp.example.com http: paths: - path: /users backend: serviceName: user-service servicePort: user-service-port spec: rules: - host: myapp.example.com http: paths: - path: /users backend: serviceName: user-service servicePort: user-service-port
  12. kind: Service apiVersion: v1 metadata: name: user-service spec: selector: app:

    user-app ports: - protocol: TCP port: 80 targetPort: 80 name: user-service-port spec: rules: - host: myapp.example.com http: paths: - path: /users backend: serviceName: user-service servicePort: user-service-port
  13.  The “big public clouds” all have solutions  Amazon

    API Gateway  Azure Application Gateway Azure API Management  Google Cloud Endpoints  …  They are all “the same but different” PaaS Solutions
  14.  Cover many features  Reverse Proxying (single endpoint, HTTPS,

    load balancing)  Security, DOS protection, Firewalling, throttling, …  Access control  Availability with SLAs  Monitoring, Logging  Documentation  Billing  Stages, Deployment, Release management  “Edge optimization”   Technical and organizational aspects PaaS Solutions
  15.  Don’t care about ops at all  Enjoy SLAs

     Rock solid under heavy load  Plenty of extra features  Integrate nicely with the respective platform  More expensive  Most do much more than you need …  Horrible unreadable config mess, aren’t we doing “everything aC” now?  Starting is harder than necessary PaaS: Pros and Cons
  16. Zuul 1 June 2013 Evolution of Zuul and Spring Cloud

    Gateway Zuul 2 May 2018 May 2017 Spring Boot 2 (M1) Spring 5 / Project Reactor Today December 2014 Spring Cloud Netflix Zuul Spring Cloud Gateway July 2017 June 2018 M1 Release
  17. Simple Scenario Client API Gateway Cookie: customer-Id Users Images Comments

    Authorization-Header Authorization-Header Authorization-Header
  18. Spring Cloud Gateway  Built on top of the reactive

    Spring ecosystem:  Spring WebFlux, Project Reactor and Spring Boot 2.0  Easily usable predefined filters  Simple way to create custom filters  Predicates and filters are specific to routes  Configuration:  Via configuration file (application.yml)  Via fluent routes API DSL
  19. Defining routes with fluent API-DSL @SpringBootApplication class SpringCloudGatewayApplication { @Bean

    fun customRouteLocator(builder: RouteLocatorBuilder, authFilter: AuthorizationFilter): RouteLocator { return builder.routes { route(id = "users") { path("/users") uri("http://localhost:8081/users") filters { filter(AuthorizationFilter()) } } route(id = "comments") { path("/comments") uri("http://localhost:8082/comments") filters { filter(AuthorizationFilter()) } ...
  20. Creating a custom filter @Component class AuthorizationFilter : GatewayFilter {

    override fun filter(exchange: ServerWebExchange, chain: GatewayFilterChain): Mono<Void> { val cookie = exchange.request.cookies.getFirst("customer-Id") if (cookie?.value.isNullOrEmpty()) { exchange.response.statusCode = HttpStatus.BAD_REQUEST return exchange.response.setComplete() } else { val request = exchange.request .mutate() .header(HttpHeaders.AUTHORIZATION, cookie!!.value) .build() return chain.filter(exchange.mutate().request(request).build()) } }
  21. Netflix Zuul 2  Based on asynchronous, non-blocking Netty framework

     Allows blocking and non-blocking filters  Easily integrates other Netflix OSS technologies  Ribbon (Client side load balancing)  Hystrix (Circuit Breaker)  Eureka (Service Discovery)
  22. Creating a (blocking) filter class MyFilter extends HttpInboundSyncFilter { @Override

    HttpRequestMessage apply(HttpRequestMessage request) { // TODO: implement filter logic } @Override int filterOrder() { return 1 } @Override boolean shouldFilter(HttpRequestMessage request) { return true } }
  23. Routing with InboundFilter class Routes extends HttpInboundSyncFilter { HttpRequestMessage apply(HttpRequestMessage

    request) { SessionContext context = request.getContext() switch (request.getPath()) { case "/users": context.setEndpoint(PROXY_ENDPOINT_FILTER_NAME) context.setRouteVIP("users") break case "/comments": context.setEndpoint(PROXY_ENDPOINT_FILTER_NAME) context.setRouteVIP("comments") break ... } return request }
  24. Creating a custom InboundFilter class AuthorizationFilter extends HttpInboundSyncFilter { HttpRequestMessage

    apply(HttpRequestMessage request) { Cookie cookie = request.parseCookies().getFirst("customer-Id") if (!cookie?.value()?.trim()) { request.getContext().setEndpoint( BadRequestEndpoint.class.getCanonicalName()) } else { request.getHeaders().add(HttpHeaders.AUTHORIZATION, cookie.value()) return request } }
  25.  Centralized, controllable entry point  Simplicity for clients 

    One endpoint  Internal structure concealed  One location to handle transport encryption  Cover cross-functional aspects Gains
  26.  Single point of failure defines requirements:  Availability /

    Deployment  Scale  Monitoring  Defines the capabilities  HTTP2, web sockets, non-blocking, …  Adds to overall latency  “Avoid overambitious API Gateways” (ThoughtWorks Technology Radar 2018)  Development teams might be dependent on central API Gateway team Losses
  27.  Example sources on GitHub  https://github.com/csh0711  https://github.com/i7c/apigw-cf-nginx 

    CloudFoundry  https://www.cloudfoundry.org/blog/context-path-routing/  NGINX  https://www.nginx.com/resources/wiki/  Spring Cloud Gateway  https://cloud.spring.io/spring-cloud-gateway/  Zuul 2  https://medium.com/netflix-techblog/open-sourcing-zuul-2-82ea476cb2b3  https://github.com/Netflix/zuul  Thoughtworks on “Overambitious API Gateways“  https://www.thoughtworks.com/de/radar/platforms/overambitious-api-gateways Links