I want to design an application using AWS as IAAS, Docker as PAAS and Spring Boot and Spring cloud as application technology.
For this, I googled and read a lot of blogs and watch videos but could not find any answer for that.
I developed one application using Spring Boot and Spring cloud technology, and the application architecture looks like below image.
This design looks good and working fine as per expectation.
Now the new task is, I need to use the cloud (AWS) as Infrastructure and Docker.
For that, I designed one more architecture, and it looks like below image.
The component as follows:
ELB - (Elastic Load Balancer) -> Target Group (Part of Auto Scaling) -> EC2 instance (will be created more on demand)
Now if I want to integrate my previous design then I think there is not need of Zuul server here because this load balancing is done by ELB, the second I do not need Service Discovery component as well because it will be done by Target AutoScale group.
I am a little bit confused here with Spring Cloud and AWS infrastructure.
Could someone help me to make really simple how I can integrate these components to work together?
Thanks
Why Spring Cloud with AWS ?
Let's take example when you need Spring Cloud even if your architecture is deployed on AWS infra :
Imagine your Product service need to communicate with your Order Service, in this case you will see Spring Cloud utility.
You don't see the necessity of Spring Cloud because you don't have an internal communication (between your services) and this is the role of Registry service.
Why Gateway service (Zuul in your architecture) ?
Again, your current architecture don't use (need) the powerful of Gateway pattern.
Let's assume your system need to aggregate multiple results from different services to response to client request. You can do this in Gateway (Zuul in your case).
Another advantage to use Gateway service is you can use it as a unified front door to your system, which allows a browser, mobile app or other user interface to consume services from multiple hosts without managing cross-origin resource sharing (CORS) and authentication for each one.
Important :
It's fine to not use Spring Cloud, is not a rule or THE right way to implement microservices architecture. If you don't need it don't use it.
Related
While trying to create a web application for shared drawing I got stuck on a problem regarding Kubernetes and scaling. The application uses an ASP.NET Core backend with SignalR for sharing the drawing data across its users. For scaling out the application I am using a deployment for each microservice of the system. For the SignalR part though, additional configuration is required.
After some research I have found out about the possibility to sync all instances of the SignalR backend either through the use of Azures SignalR Service or the use of a Redis backplane. The latter of which I have gotten to work on my local minikube environment. I am not really happy with this solution because of the following reasons:
My main concern is that like this I have created a hard bottleneck in
the system. Unlike in a chat application where data is sent only once
in a while, messages are sent for every few points drawn in the
shared drawing experience by any client. Simply put, a lot of traffic
can occur and all of it has to pass through the single Redis backplane.
Additionally to me it seems unneccessary to make all instances of the SignalR backend talk to each
other. In this application shared drawing does only occur in small groups of up to 10 clients lets
say. Groups of this size can easily be hosted on a single instance.
So without syncing all instances of the SignalR backend I would have to route the clients connection based on the SignalR group name to the right instance of the SignalR backend when the client is trying to join a group.
I have found out about StatefulSets which allow me to have a persistent address for each backend pod in the cluster. I then could somehow associate the SignalR group IDs with the pod addresses they are running on in lets say another look up microservice. The problem with this is that the client needs to be able to access the right pod from outside of the cluster where that cluster internal address does not really help.
Also I am wondering if there isnt a whole better approach to the problem since I am very new to the world of kubernetes. I would be very greatful for your thoughts on this issue and any hint towards a (better) solution.
I'm currently trying to create a tracing tool for fun (which supports gRPC tracing) and was confused as to whether or not I was thinking about this architecture properly. A tracing tool keeps track of the entire workflow/journey of the request (from the moment a user clicks the button, to when the request goes to the API gateway, between microservices, and back.
Let's say the application is a bookstore, and it is broken up to 2 microservices, maybe account and books. Let's say that there is a User Interface, and when you click a button, it allows a user to favorite a book. I'm only using 2 microservices to keep this example simple.
**Different parts of the Fake/Mock up application**
UI ->
nginx -> I wanted to use this as an API Gateway.
microservice 1 -> (Contains data for all Users of a bookstore)
microservice 2 -> (Contains data for all the books)
**So my goal is to figure a way to trace that request. So we can imagine the request goes to nginx
Concern #1: When the request goes to nginx, it is HTTP. Cool, but when the request is sent to the microservice, it is a grpc call (or over http2). Can nginx get an http request and then send that request over http2...? Not sure if I'm wording this correctly or not. I know nginx plus supports http2. I also know that grpc has a grpc gateway too.
Concern #2: Containerization. Do I have to containerize both microservices individually, or would I have to containerize the entire docker container itself. Is it simple to link nginx and docker?
Concern #3: When tracing gRPC requests (finding out how much time a request is fulfilled), I'm considering using a middleware logger or a tracing API (opentracing, jaegar, etc.) to do this. How else would I figure out how long it takes for gRPC to make requests?
I was wondering if it was possible to address these concerns, if my thought process is correct, and if this architecture is feature.
Most solutions in the industry are implemented on top of a container orchestration solution (Kubernetes, Docker Swarm, etc).
It is usually not a good idea to "containerize" and manage reverse proxy yourself.
The reverse proxy should be aware of all the containers status (by hooking to orchestrator) and dynamically update its configuration when a container created, crashed, or relocated (due to a machine gets out of service).
Kubernetes handles GRPC using the mesh networks. Please take a look at kubernetes service mesh.
If you decided to use Traefik and Docker Swarm check out traefik h2c support.
In conclusion, consider more modern alternatives to Nginx when you want to load balance GRPC.
I am using JHipster 6.4.1 to generate an Oauth2 (Okta) Microservice application with a React UI / API Gateway.
I understand that the Microservice application/s can support multiple instances under the same
Registry and will use a round-robin approach to load balancing and in this way can horizontally scale.
My understanding is that the Gateway application with Oauth2 uses a stateful Spring Security implementation (JSESSIONID cookie), so the same stateless scalability approach cannot work here.
Are there any recommended solutions for applying scalability to the Gateway application?
You can use Spring Session to share your sessions between gateway instances, there's usually nothing wrong being stateful if the state is small, can be easily replicated and does not contain business data.
I have tried the SCDF Security with UAA + LDAP example (link).
However, Im looking for some more Security approaches while using SCDF local. It 'll be great if having example (source, document)
It is not an official sample, but we have another full-blown UAA based end-to-end solution that works with local, and as well the other platform choices that we support.
See: jvalkeal/randomstuff/dataflow-uaa.
With this, you can run UAA as a standalone process served at 8080, and SCDF+Skipper running separately it can negotiate with and use the UAA backend for authentication/authorization flows. Feel free to customize the uaa.yaml with desired users, roles, and the associated scopes. Once again, all this is outside of SCDF, and it comes down to how much you'd want to rely on UAA like identity providers.
Keycloak is another excellent option for a local deployment experience. I believe there's a Docker image for Keycloak.
I am trying to setup Spring Cloud Data Flow (SCDF) to run in Local mode and how few questions which may help me decide if its a suitable platform for my requirements.
Even though the recommendation is to use Cloud Foundry, Kubernetes etc as task execution environment my preference to run things on production is local mode mainly because I don't have a lot of workload and cant deal with all the additional complexity. Now in local mode will I be able to run all types of SCDF apps, namely Streams, Jobs and tasks with no limitations? Some parts of the document mentions that only Jobs can be run in local mode.
Security - I am looking to put controls in place around deployment of apps and operational access to the tool (dashboard) and do see the support for LDAP with roles as an option but the whole concept of using Cloudfoundry UAA, another product to drive the user managements seems like an overkill. Is there no way to configure the tool with an existing LDAP server? Found the following in one of the LDAP issues in Github but its not clear whether it uses UAA in its docker image. Worst case I wont mind if the dashboard can be run in a view/read only mode.
https://github.com/spring-cloud/spring-cloud-dataflow/issues/2871
If Spring Cloud Data Flow were a purely monolithic application, integrating all aspects of security directly into the app is definitely easier to to wrap one's mind around. This is how Spring Cloud Data Flow originally started out from a security perspective and thus, versions of Spring Cloud Dataflow <2.0.0 supported what we labelled traditional security.
However, even before 2.0.x Spring Cloud Data Flow:
Had to integrate with external platforms such as Cloud Foundry
Became more and more microservices oriented (e.g. by using Skipper)
As a result 2 parallel security architectures had emerged, one using traditional security and the other one driven by OAuth2/OpenID Connect.
This started to become increasingly harder to maintain and for 2.0.x we decided to exclusively focus on OAuth2/OpenID Connect. However, we still had to support a rich set of enterprise features such as Roles, LDAP integration etc. As such, we find that the open-source, production-ready CloudFoundry User Account and Authentication (UAA) Server is an excelling choice. Its LDAP support and features actually exceeds the features offered by Spring Cloud Dataflow <2.0.0.
So yes, in order to setup security for Spring Cloud Data Flow locally, you need to run the UAA. And the UAA would also provide the LDAP support. Technically, Spring Cloud Data Flow has no awareness of the LDAP setup at all.
I hope this provides some background regarding how the Spring Cloud Data Flow security architecture emerged. Please have a look at the reference documentation and the aforementioned SCDF Security with UAA + LDAP example. Don't hesitate to reach out in case of further questions!
Disclaimer: I am a committer on the project.
Starting from v2.0, we delegate to UAA for authentication and authorization. There are a variety of write-ups on this matter; a more comprehensive one to look at is the end-to-end sample on how all this could be put together locally. You do not need CF or K8s, all this can run locally also. We rely on UAA as the gateway to standardize on end-to-end SSO across all the client tools, including shell, dashboard, RESTful APIs, CTR, etc.,
Sample: SCDF Security with UAA + LDAP. For further reading, please refer to the security section in the ref. guide.
Lastly, we do not recommend Local for a production install, but I understand that resiliency and/or restartability of apps under failure condition is not a requirement for some workloads.