Chapter 3. Web services and service-oriented architecture
3.2 Introduction to service-oriented architecture
3.2.2 Designing connectionless services
The question of whether services should be stateful or stateless has been discussed frequently in relation to SOA. However, the issue is complicated by whether it really is possible to draw a clear line between state and business data. Many service interactions must be stateful in order to play a role in ongoing business processes or interactions; the issue is how we should design such services so as to maximize the flexibility of the architecture and the processes it supports.
To answer this issue, we return to the key to SOA: defining behavior in the interface. In doing so, we do away with considering stateful and stateless
Interaction state Declared Matching of messages or events to long-lived processes by explict process or transaction IDs in semantic interface, or by application data (for example, customer ID).
Service Choreography technology may provide some facility to use a variety of input data to associate messages with specific instances of processes.
Primary key matching technology such as provided by WebSphere InterChange Server. The emerging WS-ResourceFramework
provides a standard model for associating services with stateful resources.
Enterprise Application Integration
middleware support for message aggregation and correlation.
Customized solutions involving custom message headers.
services, and instead declare that services, whether they deal with stateful business behavior (for example, the renewal process for an insurance policy) or stateless business behavior (such as performing an exchange rate calculation) should be connectionless.
Connectionless services are those that do not allow or require a service
requester and a specific, executable instance of the service provider to maintain a relationship between service invocations. The successful implementation of connectionless services depends on two considerations:
The use of technology that prevents handles being retained to specific executable instances.
The design of service interfaces that do not depend on implicit, shared knowledge created through a sequence of interactions between a specific requester and provider.
The first consideration is relatively easy to address: When stateless protocols such as asynchronous messaging are used to invoke services, this criterion is fulfilled. When technologies that are capable of supporting stateful behavior are used, the features of the technology that manipulate state (for example,
HTTPSession or cookies) should not be used. Meeting this criterion might imply the use or assessment of specific communication technologies, or the application of design and development guidelines to the implementation of systems that participate in the SOA.
The second criterion can only be fulfilled through its application as a design principle to the design of the individual service interface. Table 3-2 shows an example of both a connected and connectionless design for two services. In this example, a store system in a consumer electronics shop is trying to charge the cost of an expensive television to a card account that belongs to Bruce; the cost is high enough that the store system must explicitly authorize the transaction with the card supplier.
Table 3-2 Connected and connectionless service interactions
Connectionless Connected
Service Client: Can Bruce pay $1000 for a new television?
Service Provider: Yes
Service Client: Charge
Bruce
$1000 for a new televisionService Provider: OK
Service Client: Can Bruce pay $1000 for a new television?
Service Provider: Yes
Service Client: Charge
him
$1000 for a new televisionService Provider: OK All of the business data is defined in the
interface
Part of the business data (the fact that we are dealing with Bruce) is implied in the sequence
Chapter 3. Web services and service-oriented architecture 47 The Connectionless example in the table shows that the interface to each call specifies all of the data that is required to perform the service, other than business information owned by the service provider. For example, Bruce’s card balance and credit limit are not part of the service interface because they are business information owned by the card provider. However, the fact that Bruce is the owner of the account that is relevant to this specific transaction is a part of the interface, because both the service to authorize the payment and the service to make the payment must relate to the same cardholder. If this information were not part of the service interface (as in the Connected example), then the specific, executable instances of the service client and the service provider would have to maintain a reference to each other in order to identify the correct context.
This could cause difficulty if, for example, the physical server that supports the instance of the service provider crashed; in such as case, what happens to the instance of the service that remembers that it was dealing with Bruce? Was the state of that instance safely stored somewhere prior to the failure, perhaps in a database? If so, how does the service requester then connect to another executable instance of the service that somehow knows which information to read from the database? All of these issues should be familiar to anyone who has developed stateful distributed applications, such as J2EE or WebSphere
applications that make use of the Java HTTPSession object.
The principle that services should be designed to be connectionless is really saying that for a shared sequence of activity, each instance of that activity should be identified uniquely (for example, through a transaction ID or, in this case through a customer ID, Bruce), and that the identity should form part of all service calls. Even better would be to explicitly define and share the process definition, as the emerging BPEL4WS standard could do.