I needed an SOA case study for my Large-Scale Distributed Systems class today. I wanted something that would be familiar to them so I created an SOA for the n-tier (J2EE) project they'd just completed. The project was to build a student registration system that allowed students to register and pay for classes and also had course, student and payment management interfaces. The goal of this exercise is to re-architect the EJB-based system into an SOA where the module functions are oriented to business context. The scenario I painted to envision why we might take a perfectly serviceable J2EE-based, n-tier architecture and put a SOAP front end on it was the following:
The administration of BYU, BYU-Idaho and BYU-Hawaii have decided to use a single student registration system. The student, registration, and payment modules are to be located in Provo, but each campus will administer its own courses locally. The four modules in the system should be loosely coupled to foster re-use.
Admittedly, its a little contrived, but was aimed at showing that we may want to break the architecture up to foster re-use, but the mixture of local and remote processing is better served by an SOA than a tightly-coupled EJB system.
The EJB project already exists, so the figure at the right shows how the EJB project could be re-architected to yield a Web services based architecture. The new architecture has made some significant changes:
- The courses, schedule, student, and payment modules are all now thought of as separate programs.
- The session beans must be stateless (or new stateless session beans must be created) since SOAP interfaces cannot by added to stateful session beans.
- All interaction between the modules must happen at the SOAP interface (i.e. outside the colored boxes).
- A major consequence of that is that the shared keys between tables in the database are no longer meaningful since the tables are split according to business function.
- The schedule bean is now just a simple bean that manages the schedule (note the simple interface) rather than containing the complete business logic for completing a registration.
There are several design decisions that must be made. First of all, where the business logic used to be in a registration session bean, we now have several options:
- We can create a new EJB for registration that uses the new SOAP interfaces.
- We could expand the Register JavaBean used by the register use-case to contain the business logic and call the SOAP interfaces.
- We could create a separate program that contains the registration business logic.
- We could use an orchestration server to tie everything together.
I have simple created a box labeled "Register Orchestration Client" and left it at that to reflect that any of these options might be chosen.
Another design issue concerns how data is transfered inside the SOAP calls. The data will be quite lengthy and complex. One choice would be to use complex types, but we're probably better off designing specific XML documents for transferring data back and forth between modules.
The interfaces to the modules will need to talk about student, section, and course objects without reference to the keys in the database. There will have to be some namespace created and unique keys added to the namespace to represent these objects, so that, for example, a show method on the Student service will know which object to retrieve.
Authentication and authorization for some of the methods will be required and we won't want to build that into the services themselves. This suggests using a Web services intermediary to serve as the security agent in the architecture. I'd probably use WS-Security in this design because I'm not sure that HTTP authentication is up to the challenge. Also the choice of HTTP authentication implies a strong tie to HTTP. Using WS-Security has other implications for an identity management system that is not shown.
The Payments, Courses, and Student services will all be used directly in most cases without much need for orchestration. Their management interfaces could be JSP/JavaBean combinations that call the old EJB interfaces, JSP/JavaBean combinations that call the SOAP interfaces, or even thick clients.
Obviously the question of transport is an important one. In this case, I don't see a lot of advantage in moving away from HTTP since its easy, but more importantly, the user will expect synchronous interactivity.
Transactions (to ensure atomicity when a schedule is committed and payment made) will be a problem. A WSI broker can provide some help in watching for problems and raising alerts or even taking corrective action without having to build all of that into the services themselves.
The new SOAP interface provides a new "stateless boundary" that must be managed. We're used to the one between the browser and the JSPs and, in fact, considerable infrastructure exists inside the servlet engine to manage this. The SOAP interface has created a second stateless boundary between the presentation and business logic layers and it must be managed in the same way that the browser-server boundary is: when state matters, it must be saved and a token passed back and forth so that the context can be recreated on each invocation.
With only a little extra work, a RESTian alternative to the SOAP interface for each service could be created. We've discussed using XML documents to transfer data. We could also ensure that the objects in the databases that are being manipulated use URL-based keys. I think adding this to the design would be worth the cost in terms of extra complexity and time since it would create a low-overhead means of interfacing to these systems and foster other uses.
Note that each service has an EJB backend only because we started off with an EJB-based, monolithic service. In real life, the student service may be a legacy system with a SOAP interface and other services may be built in alternate technologies, even, GASP!, .NET.
This architecture hasn't been implemented or even fleshed out in a team meeting. I don't claim that this architecture is optimal. In fact, I'm pretty sure that there are some significant improvements that could be made and points I've forgotten. Comments?