Ok, if you have somehow stopped by this post, you have 2 options depending on your knowledge. If you are an experienced developer with microservices and spring cloud experience, you can fork the project from github and download config repository and try to run the whole system according to this post. If you are not an experienced developer, you should start with the first post of the series. In this post, i will analyze the microservice project that i have built and mention couple of different alternative tools or approaches. I was going to introduce these tools but it would make this post way too long. So it will be in another post. I will ask questions like "what did we do", "why did we do it", "did we do it right" and "what did we gain or sacrifice" kind of questions. The aforementioned microservice architecture that i have coded is represented in the image below.
We have created a ticketing app that runs on microservices. It has a Gateway, Discovery Server, Config Server as the backbone of the system. We have connected the small services to Eureka with load balancing. We have routed the requests with Gateway to Eureka and provided resilience with fallback routes. Then we have coded small services and failovers with REST endpoints that has no involvement with business side. We have designed functions for users, activities and the payment processes as small services by grouping the relevant methods together.
After this implementations, we have coded a consumer web MVC app and implemented the SAGAs for business flows. It reaches to small services with JWT headers for security via the gateway. MVC app also coordinates the service calls and manages exceptions according to the responses. Config Server helped us to store the spring boot configurations in a github repository and serve them to services. The databases i have used was MySql but it wasn't a vital point of the microservice. All of this is sponsored by spring cloud :)
We could have started with domain driven design and define bounded contexts. I have kind of skipped that part by dictating my own decisions. I think in this design, a user, an activity and a payment process can be bounded contexts because everyone can agree on what they are. But i might be wrong, i would be glad to hear your thoughts about how to implement domain driven design for this architecture.
We used a pattern called gateway pattern i guess but when it comes to microservices, that is just a name. Because we have also used a SAGA pattern and circuit breaker pattern. If you define a web service with patterns, i am 100% sure everyone will draw a different image in their mind. That is why i have never mentioned any pattern during the series. You should be aware of them of course, but, deciding which one to use is going to determine how long your microservice will be able to live and prosper. So the question of WHY is important. Let 's take a look at my reasons.
Every choice you have made must have a reason. It better be a logical or practical one, rather than "i knew this way" or "they told me this way". I have made several decisions about technologies and tools and the whole architecture.
These were the reasons that i can remember to the most crucial decisions i have made throughout this journey. I have created this system with zero hands-on experience and some implementations were changed along the way. But in the end, this is what caused the image you see above. My reasoning can be wrong, all of these can be argued. There could be better answers to these concerns. But you have to be able to answer the question of why. After all, you are aiming to have some sort of gaining from these decisions. It brings the next question.
I think i have gained something with the decisions i have made.
If i am not fooling myself these are the advantages of my system. I could be short sided here. Remember we had requirements, limitations and goals. Just because we have achieved our goals, doesn't mean we have covered all possible problems and requirements. It also doesn't mean that we did the right thing or solved the problems the right way. Roast me in the comments :) If i am honest about the system, i should also mention the disadvantages of the system as far as i can see. This part usually becomes clear after putting your microservice into use.
Well it looks like i have created the most awesome microservice implementation ever. Again, i could be short sided here because my ticketing app is imaginary and i might have a biased view. A second opinion from out of the system can get you a new perspective. Furthermore i can never honestly answer the question "did i do it right". I have met the requirements, implemented solutions according to my criterias and limitations. I would say i did it right, if i have achieved the expected results. But microservices is an abstract and vague concept. There are trade offs instead of de factos. If you are still not convinced that i have mastered the microservices, you are right :) I have questions that even i can't answer.
I would be glad to hear your thought about these questions in the comments. Most of these are the results of "did i do it right" questions.
Ok, i am technically done with the microservice. The jury heard me out and now i have a working project. But i am always tended to be a dreamer or philosopher. I have 2 "what if" questions and solutions in my mind, as alternative solutions. These are the conclusions i have made with my experience.
There is a possibility that in time, these business operations and transactions may become way too complex and big. I think that would cause 2 things: Longer response times and huge controller or service methods. In this case, i would stick with my own design because i want the services to be small and free. I could try modularizing MVC app with maven modules according to SAGAs, so that i can separate the code a little bit. Also design patterns are helpful to write understandable code. You are basically implementing some sort of Visitor pattern inside the MVC app.
I can't help with response times since no matter what i do, huge business flows will cause lots of service calls. But if they get computationally heavy on the MVC app, i guess load balancing before MVC app would be what i do. It is all to prevent spaghetti relationship among the services with message queue approach.
But no matter what i do, i think there is always a choreograpghy based microservice architecture that can be a solution for some situations. I might implement an example of it one day. I have one more question already.
In this case i may not need a gateway and eureka. As far as i know, i can put a message queue (kafka / rabbitmq / activemq) right in the center of the system like a network hub. I can also make every service a message listener that listens to these queues by subscribing. MVC app starts a message and that queue is listened by the first service. It receives the payload and does its own thing and puts it to the next relevant queue according to business flow or the information inside the payload. This is a mixture of Chain of Responsibility and Mediator design patterns.
This would create lots of queues for all sorts of business flows, which i don't see logical. I would also desperately need Sleuth + Zipkin (or any other tool) for distributed tracing. MVC app would also wait for these queues for an answer and this would dictate a rective framework to use. This is how i can see choreography working.
At the end of this journey, one thing is for sure. All of the decisions, tools and implementations can be questioned or critisized. I have learned and developed some kind of microservice solution and met the tools. I don't see any solution bewteen coordinator and message queue implementations. Here is my takeaway from all this:
With this post i have completed my goal to have a running Spring Cloud microservice. Congratulate yourself if you have done the same thing with zero experience. After this point, there comes the management of the microservices. You see, we have to manually run and deploy the services everytime we change things. That is why "continuous integration" and "continuous deployment" comes into play. This would take you to another journey called Devops. I will briefly write about it some day. This series is done. It took 2 months to write the code and 7 blog posts. See you at the next post :)
Leave a comment