|
Common Object Request Broker Architecture (CORBA) is a middleware specification maintained by the Object Management Group (OMG) based in Framingham, Massachusetts. CORBA specifies the standards by which various Object Request Broker (ORB) vendors can implement products and assures interoperability between various vendor products. CORBA consists largely of specifications for Interface Definition Language (IDL). These specifications in turn describe interfaces to the key elements of CORBA which include the Core, the Services, and the Facilities. One of the services is the Persistent Object Service (POS). With the OMGs Persistent Object Service (POS) Version 1 slated for retirement under the OMG Sunset Policy, which does not require backward compatibility, an RFP has recently been adopted and issued for a Version 2. This version will be called the Persistent State Service (PSS) and will not require compliance with any aspects of its predecessor Version 1.0. Starting from a clean sheet of paper may lead to a significantly new and improved perspective to the problem of distributed object persistence from the standpoint of a CORBA standard specification. If you need to develop and deploy applications that include CORBA based interfaces to persistent data in a way such that future standards are easily retrofitted, you will need to know more about the underlying issues and at least some of the more reasonable alternatives. The New CORBA Persistent State Service (PSS)Numerous problems are associated with the legacy Persistent Object Service (POS) Version 1. They include a complex interface, a lack of current and future intentions for implementations, and not meeting current persistence needs. The goals of the PSS version 2 RFP, which was accepted by the OMG in Montreal in June of 1997, include addressing these problems, while at the same time being readily applicable to existing storage technologies, and focusing on a way for CORBA objects to maintain their own persistent state. The lead time between proposal submission to the adoption of a finalized OMG PSS specification is likely to be considerable. During this interim period another closely related service, the Object Transaction Service (OTS)which is based on the X/Open Specificationhas rapidly matured with three vendor implementations due to for release in 1998. Companies planning products include Transarc and IONA Technologies based on the Encina++ transaction monitor, and BEA Systems Tuxedo. Some topics covered in following sections:
Point integrations in the form of collaborations between database vendors and ORB vendors exist and are likely to continue to fill the gap until a reasonable and well adopted Version of POS comes about. Probably one of the most dramatic examples of a point integration is IONA Technologies Orbix Database Adapter Framework (ODAF) formally announced on 25 June, 1997. ODAF integrates with leading object database vendors including Object Design Inc. (ObjectStore) and Versant, with planned integrations for O2 Technologies and Ontos Technology. In addition, a relational database adapter offered by Persistence Software extends coverage to most major relational database vendors including Oracle, Sybase, and Informix. Whether a datastore is based on a relational model or an object model (RDBMS vs. ODBMS) changes the complexion of the solutions; often imposing itself on the domain object model (discussed later in this paper). Third party vendors such as Persistence Software, Inc. and Subtleware offer object-to-relational adapters that allow mapping of an object model to a logical data model (LDM). Persistence Software also includes a Live Object Cache much like those provided with most object databases. Depending upon the type of application, different caching techniques based on objects or clusters of objects can offer tremendous improvements in throughput, well beyond page caching often incorporated in relational database products. Figure 1 - Orbix Database Adapter Framework [click to enlarge]
Architectural Alternatives to
Persistent Distributed Objects A Microsoft only set of clients could make use of Open Database Connectivity (ODBC) or Data Access Objects (DAO) mechanisms for database connectivity to relational only databases. Since Windows owns the desktop, and RDBMS is still dominant as a persistent storage mechanism, this approach has a broad appeal. ODBC and DAO access data in its relational tabular form and are not directly applicable to the discussion of persistence of domain objects per se. Persistence of Domain objects requires a mapping process between the object and relational models or the use of an ODBMS. When designed properly, such a system generally makes the domain objects as independent as possible from their persistence. Subtleware and Persistence Software are provide this type of capability. The same logic behind using Microsofts ODBC/DAO is often applicable to Java Database Connectivity (JDBC) as well. The key being that JDBC is a mechanism for accessing relational databases that does not lock the clients into Microsoft exclusively. In anticipation of low cost Network Computers (NCs) which are on the horizon, this could be a very important consideration. NC’s may achieve a significant market penetration in many commercial vertical markets based on low cost and ease of use. Another consideration, is that many of the object database vendors such as O2 and Object Design also have adapters that support SQL. This makes the object database look like a relational database and thus can be suited for ODBC drivers. However, these mechanisms are normally intended to permit the use of products such as PowerBuilder and Crystal Reports as well as ad hoc queries rather than providing an object interface for Java or C++. The alternative to the Microsoft approach is to use a CORBA interface, allowing access to persistent objects from Microsoft ActiveX, OLE, Visual Basic, Visual C++, and Java. In addition, CORBA interfaces can be accessed from Unix and mainframe platforms. Using CORBA as an underlying middleware enables information to be accessed as true objects and data-centric relational tables or C-like structs. Figure 2 illustrates the various combinations between platforms, types of datastores, and middleware. The balance of this paper describes CORBA as the middleware of choice for accessing persistent data and objects. The OMG is in the process of adopting the new PSS specification, so we will consider the architectural alternatives that exist between now and the time that the new specification is adopted and implemented by multiple vendors. Figure 2 - Platforms, Datastores, and Middleware Combinations [click to enlarge]
Mapping Persistent Server Objects to IDL Generated Skeletons
Perhaps even more important is the notion that domain objects should
know little or nothing about persistence and middleware. Domain objects may need to be used in a variety of contexts, and should not be unnecessarily restricted to being CORBA objects as is the case with inheriting from a skeleton. For instance, a phone number may be accessed as a CORBA interface or it may be used as query object placed on the stack as a parameter to a lookup method. In either case it would be desirable to have an unencumbered object that can be used externally by CORBA but doesnt necessarily have to be.
Figure 3 - Business object generated from IDL compiler [click to enlarge]CORBA offers another model for mapping called the delegation (aka TIE) approach which satisfies the requirement of being able to be a CORBA object or a standalone object for any purpose whatsoever. Delegation comes with a performance penalty, but this is seen as insignificant in the face of overall invocation benchmarks with are typically measured in milliseconds. The final point to consider here relates to the use of CASE technology. While there are still some hold-outs discounting the usefulness of CASE tools to represent models and generate code, there is a growing capability among CASE tool vendors along with a growing acceptance on behalf of projects to use them. Making the skeletons themselves persistent is not really a valid option since they are intended to be largely opaque to the programmer. Hence, they will not be considered further whether a BOA implementation or a TIE approach is used, the domain object will always be treated separately. Figure 4 - CORBA TIE mapping model [click to enlarge]
Should CORBA Persistence be a service or an adapter or both? Figure 5 illustrates the primary functions of the Basic Object Adapter (BOA) for CORBA 2.0. Just as Persistence is undergoing a metamorphosis in the OMG, so too is the basic architecture. CORBA 2.x is on the drawing board and promises to offer some significant enhancements to the BOAsome of which may be useful for incorporating extensions to the BOA that will be germane to the issue of persistence. Existing services such as naming and transactions and are described by IDL interfaces implemented by various vendors and as such do not require extensions to the object request broker itself. However, some of the requirements for dealing with special issues posed with persistence might lead to extending the functionality of the BOA if not including a completely separate Object Adapter... perhaps the Persistent Object Adapter. With regard to generating and interpreting object references, it is necessary to consider the varying degrees to which database vendors implement persistent object references. Secondly, the way objects are activated and registered as active are going to be significantly different. Fortunately for developers, these issues will be addressed in the immediate term through point integrations between ORB and database vendors, and in the long term hopefully through PSS V2.0. Functions of the Basic Object Adapter
Figure 5 - Basic Object Adapter (BOA) [click to enlarge]
Performance issues and tuning Latency time becomes especially apparent when dealing with separate ORB domains interconnected via half or full bridges that require the use of Inter-operable Object References (IORs). Method invocations via IIOP (Internet Inter-orb Operability Protocol) guarantee that two CORBA 2.0 compliant ORBs can inter-operate across different domains, but such portability is not without cost in terms of latency time. Several things should become readily apparent just from the mere mention of such a disparity in access and invocation times. First, multithreading offers distinct advantages on the persistent server side and second, that graphs of objects need to be examined in terms of the level of detail presented at the ORB interface level. The degree of granularity of interfaces is an application architecture choice. But suffice it to say that if even the most fine grained objects have interfaces, and they are part of a graph requested by a client, and if there is a considerable number of them, then at the worst case latency timings across the network, an unacceptable amount of time may be imposed. This solution is unacceptable to most implementations and since it is often reasonable for an OLTP client to wait not longer than 3 seconds for a response to a query, one query against the ORB which in turn can retrieve a series of smaller fine-grained objects by value may be a reasonable, if not the only, way to go.
Illustrating a persistent model with fine-grained objects In the following example, an over-simplified version of a time series is presented in a context that imposes throughput constraints along with platform and language independence against a model containing fine-grained objects. The problem domain for this example is illustrated in Figure 6 and the following bulleted list. This problem domain emphasizes the need for a wide variety of platforms and languages to be able to use an interface that delivers time series information. In fact, such an example illustrates how in a typical charting application, the basic time series data is often applied to indicators (formulas such as moving averages, etc) that are often plotted in the same graph window as the fundamental time series. Indicators, could be implemented as adapters written in different languages and reside on different platforms than the applications on the server retrieving the time series, or those on a client that apply them to a graph.
An automated trading system (that generates buy/sell signals for securities) is an example in which several different systems may be involved. For example, such a system typically involves the use of one or more special indicators applied to an underlying time series. Threshold parameters cause buy or sell signals to be generated. For instance, using two moving averages, one fast and one slow could generate buy/sell signals as the two averages cross each other. Of course in practice, such systems based on technical analysis of a time series are much more complicated. The time series server system in this case may be implemented in Unix and retrieve time series data from a variety of sources including relational databases, object databases and perhaps even other external sources for certain types of instruments (securities) and indices. A different platform and language may be used for taking time-series data retrieved from the time series server and adding value through supplying various indicators (some of which may be based on aproprietary formula). Again, yet another system may be used for doing analysis of the indicators to provide buy/sell signals, and finally a different system for graphing the combined results of the fundamental time series, the indicators and the buy sell signals. A superior degree of flexibility may be achieved by permitting the use of different platforms, and languages along with insuring the ability to use ActiveX or Java Applets for final rendering in a web browser. As shown in Figure 6, requirements for such heterogeneous languages and platforms point to the need for middleware that does not limit the development of charting, trading, or indicator generators to any specific language or platform. Figure 6 - Heterogeneous languages and platforms require flexible middleware [click to enlarge]As a result of the desire to use a standardized non-platform specific interface to the Historical Time Series server, CORBA is the middleware of choice for this example. The next item to consider is the composition of an interface that meets requirements as outlined in Figure 6. Two things worth considering are the granularity of information associated with one element of a time series and our throughput requirements. This brings us immediately to the discussion of Objects By Value. Objects By Value are important here because even with a very fast network with invocations occurring within a single domain (no bridges) the overhead of getting each attribute associated with a time series element would be throughput prohibitive. Another close relative to the issue of objects by value is messaging, which may involve guaranteed non-duplicated delivery of a message between a sender and receiver. The OMG is currently in the process of defining a service for passing objects by value, as well as Messaging. In the meantime, there are several point integrations available from popular vendors such as RogueWave and ObjectSpace for passing objects by value, and IONA Technologies provides integration with IBMs MQSeries. However, if we are to remain within the current specifications for CORBA and require that clients to the time series server do not have to have vendor specific libraries to retrieve objects by value, or incorporate messaging, we put significant restraints on the set of fully CORBA compliant available solutions to the throughput problem. Figure 7 illustrates some of the possible solutions available along with their correspondence to standards, throughput, and development effort. Figure 7 - Some throughput solutions [click to enlarge]Three options in Figure 7 dealing with sequences deserve special attention since they meet the fully CORBA compliant criteria. An IDL sequence is a standard CORBA mechanism for passing typed collections. Sequences may be either bounded or un-bounded. The overloading of the [ ]operator allows for easy iteration of a sequence by a client. As previously mentioned, a sequence of interfaces to elements of a time series would be prohibitively slow because each parameter within the element requires separate method invocations over the network. An improvement to this would be to use a CORBA struct definition with parameters. Since a struct passes its data members by value rather than requiring the time consuming method invocations for each parameter. However, this still might not be fast enough since even a relatively simple charting client can require several hundred time series elements, and each element would need to invoke iterative operations over the network to retrieve structs one at a time as the sequence is iterated by the client. Figure 8 - Time series flow diagram [click to enlarge]An even more attractive alternative, but one requiring some tradeoffs is to use a sequence of arrays of structs. An array is sent in its entirety over the network, but is not dynamic at runtime and needs to be defined statically at compile time. Consequently, in using such an idiom, the size of the struct needs to be chosen after careful analysis of the exact nature of the types of calls. For purposes of illustration, we have chosen an array size of 1000. In this scenario, a simple call requiring only a couple hundred elements would unnecessarily consume network bandwidth. Figure 8 represents one possible underlying object model for the server. The model as shown would be most appropriate for a server using an object database or a relational adapter such as that offered by Persistence Software for storing Instruments and Items. The TimeSeries class provides a facade that delegates queries to the underlying Instrument and Item classes, and is the only class in this particular example bound to a CORBA interface. In the event a relational datastore were used for persistence, the Item and/or Instrument classes may or may not be necessary. The TimeSeries facade could access the relational database directly and supply the results to the CORBA interface. Figure 9 - Array of structs diagram [click to enlarge]Recent versions of some popular CASE tools offer the ability to generate IDL. Figure 9 was produced using Rational Rose Version 4.0.5 with code generation properties set to generate CORBA IDL. Sequences definitions in the form of typedefs are represented as rectangles with code generation properties set to typedef implementation. Finally, Figure 10 shows the resulting IDL that would be supplied as the input to an ORB vendors IDL compiler. IDL compilers generate stubs for clients and skeletons for servers which can be modified and bound with appropriate languages for either context. Note that the IDL interface for TimeSeries_idl does not map exactly to the underlying TimeSeries object. While the IDL interface supplies two methods, one for retrieving a sequence of arrays of structs, and one for retrieving a sequence of structs; there is only a single method on the TimeSeries domain object that returns a reference to an STL vector. This type of mismatch between IDL interfaces and underlying domain objects is quite common and has implications both in terms of modeling with CASE tools and integrating with persistence mechanisms. Figure 10 - IDL Interface Example
In this example we provide only an interface to classes that have transient lifecycles. In a different example, we might also supply an interface for the Security class which is persistent. In such a case, the BOA would need to be specialized. Specialization of the BOA needs to include the ability to load the object from the database based on a persistent object identifier (OID in ODMG parlance). Suddenly, we have two types of object identifiersone for the ORB and one for the persistent datastore. This requires a mapping which may take one of several forms depending on whether the datastore is relational or object and whether the identifier is valid across many databases or just one. Additional mechanisms are also necessary depending upon whether the object reference is newly created, or already references a persistent object.
Conclusions
Domain objects should be designed with full orthogonality of their type to persistence and middleware. Ideally, these objects should not be required to know anything about either of these infrastructure elements of an overall system architecture. Unfortunately, the datastore type often dictates alternative domain object models based on the requirements for simplicity, making full orthogonality of type with persistence and middleware more of a goal than a reality. Throughput considerations are important and do in fact influence the structure of interfaces. The need to address retrieving information from fine-grained objects is just one example. As architects and developers we spend a considerable amount of time looking over the horizon to the next formal specification and its subsequent implementation. This is certainly true for persistence and objects by value. Meanwhile, other services such as the Object Transaction Service (OTS) and Naming are well specified and have multiple implementations available from several vendors. Dont let emerging standards hinder your current development efforts. Allow for new standards and transitions (such as POS to PSS) by building a robust and adaptable architecture. Well keep charting the changes so you can make informed decisions. Resource Links
© 1998 SYSNETICS, Incorporated. All rights reserved. webmaster@sysnetics.com |