| Architect: Reusable Services
What is a Reusable Service?
by Gabriel Bechara
The use of standards is important for service reuse, but standards alone can't guarantee reuse.
Published March 2009
One way of defining a reusable service is by the principles to which it adheres. Chief among those are the SOA principles that are the foundation for all SOA architectures. While a variety of patterns and practices may be applied to the development and use of services, those foundational SOA principles are independent of the implementations, protocols, standards, and technologies that may be used within a service-oriented architecture. The use of standards is important for reuse (through interoperability), but those standards alone can't guarantee reuse.
Those fundamental SOA principles have been widely recognized and adopted, but it is good to go through them again (and again). The success of your SOA approach will depend on the strength of your adherence to those principles. Achieving and maintaining that adherence is much easier now thanks to the mature SOA infrastructures available in today's marketplace.
This article describes fundamental SOA principles using mature SOA infrastructures. These principles can be used as a starting point for your SOA discussions regardless of your organization's SOA maturity level.
SOA fundamental principles
Business purpose, identification, and business reusability within a governed environment
Service identification can be accomplished using a top-down, bottom-up, or meet-in-the-middle. While each approach has its advantages, the top-down approach is appropriate if you want to improve reuse and ROI in the medium/long term. The top-down approach is business driven and should be supported by a strong sponsor. A tactical approach, mixing top-down and bottom-up, may be used as a start. In all cases a service must be related to a business purpose/process, and should provide a measurable business value at some point.
Figure 1: The top-down approach
The design time contract (specifications) is completed after identifying the service. You will then need to define run-time contracts (QoS, SLA, availability, throughput), the interfaces (the WSDL for SOAP Web Service), the policies (security, usages), and the implementations (code).
A service must be also visible across the entire organization. It must be prescribed for use in specific projects in order to avoid redundancy and duplication. It should be associated with the business and governed throughout the entire lifecycle, from design time to runtime. Service reuse must be measured, and should always be related to the corresponding business value that was the original driver for the development of the service. Strive for reuse on an enterprise level. The logic behind the service should not be limited to the individual concerns of an activity within a single business process; it should address multiple activities within multiple enterprise-wide processes.
Loose coupling between service consumers and service providers is one of the most important principles. One strategy for loose coupling is to use the service interface (the WSDL for a SOAP Web Service) to limit this dependency, hiding the service implementation from the consumer. Loose coupling can be addressed by encapsulating the service functionalities in a manner that limits the impact of changes to the implementation on the service interface. However, at some point you will need to change the interface and manage versioning without impacting service consumers, in addition to managing multiple security constraints, multiple transports, and other considerations.
The mediation pattern, using an enterprise service bus (ESB), will help in achieving this. Mediation will take loose coupling to the highest level. It will establish independence between consumers and providers on all levels, including message formats, message types (including SOAP, REST, XML, binary) and transport protocols (including HTTP, HTTPS, JMS). Architecturally speaking this means the separation of concerns between consumers and providers on the transport, message type, and message format levels. This will promote reuse and broaden the scope of SOA so it can be extended from a single department to the enterprise and beyond. The same service can be reused with different security constraints and different formats. Exposing services to external partners is an additional way of promoting reuse. This exposure may consist of having different messages, different transports, or different security policies for the same business service.
Autonomy enables service reuse. The more services are independent from one another — having their own resources (database, legacies, etc.) — the more reuse and composition will be possible with those services. This autonomy will also facilitate service adaptation to changing constraints in terms of availability, QoS, SLA, scalability, and so on. This will also prepare the services to take advantage of what virtualization has to offer in terms of dynamic resource allocation. However, complete autonomy for each service may not make sense in some contexts. For instance, services that access legacies will share resources with existing legacy clients. Autonomy can be achieved, on the functional level, for all services belonging to the same functional building block. Those services can and should be completely autonomous relative to other services belonging to other functional building blocks. (See An Introduction to Enterprise Architecture for a definition of the functional building blocks.)
A reusable service should be stateless. It may have a context within its stateless execution, but it will not have an intermediary state waiting for an event or a call-back. The retention of state-related data must not extend beyond a request/response on a service. State management consumes a lot of resources, and this can affect the scalability and availability that are required for a reusable service.
In some cases you may need to deal with state information for conversational services, or for long running business processes. Long running processes will have a state and can be invoked as services, but they should be considered as special cases, and should be referred to as composite applications rather than reusable services. (I will expand on that point later.)
Long running processes should relate to business processes, and they need to quickly adapt to business changes. In order to promote agility, long running processes should not be reused within a composition of services. Rather, they can be invoked/activated using SOAP Web Services.
The same reasoning applies to presentation services. A presentation service should be stateless and autonomous. A portlet is autonomous and it can be composed and reused in multiple portals. However, a portal being used for the federation or mashup of presentation services may have dependencies that make it a poor candidate for consideration as a reusable service.
Finding the correct granularity has been a primary concern for architects since the beginning of distributed information systems. Within J2EE architectures and EJBs, DTO (Data Transfer Object) patterns where considered for populating multiple entities, with one call, as value objects. But we still needed the stubs on the client side to deal with un-marshalling the objects. With SOAP we have looser coupling, rendering reuse agnostic with regard to the technical stubs, but it is still necessary to find the correct granularity to promote reuse.
Composition is the process by which services are combined to produce composite applications or composite services. A composite application consists of the aggregation of services to produce an enterprise portal or enterprise process. A composite service consists of an aggregation of services that produces another reusable service. It's just like combining electronic components to create a computer motherboard, and then using that motherboard in a computer. Think of the motherboard as a reusable composite service that is a component of the computer, and of the computer as the composite application.
Service Component Architecture (SCA) offers a model for creating service components. A service component exposes services, references other services, and has properties common to all services in the component. SCA defines a service-based model for assembling services to compose other reusable composite services, and defines the wiring that connects the service components within a composite. The composite also exposes services, references other services, and has a set of properties. SCA also defines a way to deploy those assemblies on multiple runtimes within an SCA domain.
SCA composites may have components running in one or more Java VM instances on one or more machines. Composition may be accomplished using an enterprise service bus that exposes the composite as a service that will be used by enterprise business processes or composite portals.
Figure 2: SCA composites
Composability facilitates reuse by making it easier for architects to use existing services to fulfill new or augmented business requirements. SCA augments the capabilities that allow the reorganization of services into the new compositions required by new composite applications (enterprise processes and composite portals).
While service prescription is important as a means of mandating design time service reuse, runtime service discovery is equally important. An enterprise repository can play an essential role in prescriptive reuse, while a service registry with UDDI capabilities can substantially improve service discoverability during runtime.
Applying the Principles to a Data Access Service
I have chosen to present a CRUD (Create, Read, Update, Delete) data service to illustrate the application of the aforementioned principles. In order to avoid confusion, the identification of CRUD services should not be compared to the ordinary CRUD operations performed on simple entities. A CRUD service should be autonomous, stateless, and reusable. Particular attention should be paid to granularity. One implication is that the CRUD service should not participate in a global two-phase commit (2PC) transaction, as started by another service within a composition. The problem is that the use of 2PC transactions will diminish the service's autonomy and reusability. SOAP does not (yet) support distributed transactions (WS-Transaction is still a specification), and the potential complexity of distributed 2PC transactions requires that they be confined to a single service.
Figure 3: A CRUD service
The CRUD service is exposed through an ESB. The ESB offers the isolation necessary for the evolution of the CRUD service without impacting the consumers. In terms of SCA, the service exposed by the ESB is the reusable composite, and the boundary of the JTA transaction is confined within the CRUD service.
Figure 4: SCA Service Assembly Model of the CRUD Service
So even if an ESB (addressed natively or through an RMI transport) can expose RMI services that can participate in 2PC transactions, those same services might also be reused and exposed using SOAP over HTTP. The reusability of a service depends on its consumption capacity, its ability to be consumed by multiple consumers on multiple protocols.
The composite CRUD service should be governed centrally and prescribed for reuse, with centralized access to the contracts (design time, runtime, usages), and its reuse must be measurable. Measuring reuse is important. An understanding of which assets are being reused, which are not, and why, is essential in guiding the evolution of your SOA.
So what is a reusable Service? It is an autonomous, reusable, discoverable, stateless functionality that has the necessary granularity, and can be part of a composite application or a composite service. A reusable service should be identified with a business purpose, and that purpose should form the basis of the service's specifications (design-time contract). A service's constraints, including security, QoS, SLA, usage policies, may be defined by multiple run-time contracts, multiple interfaces (the WSDL for a SOAP Web Service), and multiple implementations (the code). A reusable service should be governed at the enterprise level throughout its entire lifecycle, from design-time through run-time. Its reuse should be promoted through a prescriptive process, and that reuse should be measured.
The ultimate success of your SOA depends on a variety of technical and organizational factors. The principles described in this article will help to insure the reusability and reuse of the services within that SOA. That reuse, in turn will help to insure the success of your SOA.
Gabriel Bechara is a principal business consultant with Oracle Corp. A 15-year veteran of the software industry, Gabriel has served as an architect and advisor on large projects, providing practical experience and feedback on concepts that can provide a foundation for building new information systems. His interests include methodologies for defining software and enterprise architectures, with a strong focus on business integration and SOA.