State of the Art in Industry Component Architecture - A Comparative Analysis of COM+ and JavaBeans

Shamik Basu

CSE 584

 

What should a component architecture provide?

 

  1. A standard that allows plug and play interaction of components.
  2. Platform independence. Components running on different platforms should be able to talk to each other.
  3. Language independence. Developers should be given the freedom of writing components in their favorite programming language and still have the components talking to each other.
  4. Make component development simple.
  5. Make common actions easy to do. Actions that are used by many components should be abstracted out and provided as services.
  6. Enable new ways for components to interact with each other. This is subtly different from the previous point in that component techniques that are not yet in vogue but stand to be of great use to component developers should be introduced by the architecture in order to bring them into the mainstream.
  7. Provide good performance for the componentized apps. All the above features are useless if the performance of componentized apps is not good enough to be usable.

 

Ease of use is an underlying theme in many of the above points but this broad concept can still be broken up into a few areas.

 

Let us now examine how the two main architectures prevalent in the industry match up against these requirements. COM (Component Object Model) is provided by Microsoft. I use the term classic COM to refer to the implementation of COM that is currently available on the market (in Windows NT4 and Windows 98). COM+ is the next generation of this technology and it is available on Beta2 of Windows 2000. JavaBeans is the component model provided by Sun.

 

Plug and play interaction

Most people understand at a gut level how a complex system made up of pieces should function. Take the home entertainment system as an example. Say you’ve got a TV, VCR, CD player, receiver and speakers all hooked up. You buy a videotape (it could be from TDK, Sony or any other company) and you pop it into the VCR. It starts playing and the picture shows up on the TV and sound emanates from the speakers. If you would like to get a better picture and sound you can replace the VCR with a DVD player. Or you could put in a larger TV. Standards make this possible. Each component is talking a standard interface to the other components and hence the system continues to work when components are replaced with others that speak the same interface. Hence, the 2 most important features needed for plug and play interaction are:

 

  1. Encapsulation. Each component must speak to the others through published and well-known interfaces. No assumptions must be made about the implementations behind the interfaces.
  2. Dynamic linking of components. Plug and play would not work if the identities of the other components in the system were hard coded into a component. The system would then in effect become a monolithic system since none of its pieces can be replaced independently of the others.

 

Encapsulation is difficult to promote through a standard since the individual component developers have to follow good coding practices and not make any assumptions about the way the other components they are interacting with are implemented. All component interactions should be through published interfaces.

 

Dynamic linking is easier to promote through the architecture. It should be possible to dynamically discover

  1. If a component exists that speaks a certain interface.
  2. What the capabilities of a particular component are.

In JavaBeans, a Beans collection lists the available beans. The BeanInfo interface can be called on each bean to get a list of the interfaces, events, methods and properties supported by a bean. In COM+, the developer can call the CoCreateInstance API with an interface id and a pointer to an object that supports this interface is returned, if it exists. The developer can then use the QueryInterface method to find out what other interfaces this object supports.

 

Platform independence

The computing world is comprised of heterogeneous environments with many coexisting platforms. Components running on one platform should be able to speak to components running on a different platform since this is an artificial technological barrier that end users should not have to deal with.

 

COM/COM+ defines a binary standard so objects from one platform can talk to objects from a different one. Implementations of COM have shipped for Solaris, the Mac and UNIX. However, the advanced features introduced by COM+ are all available only on Windows since a COM+ runtime has not been implemented for the other platforms yet. JavaBeans talk to the Java VM so any platform that has a Java VM implementation will support the Beans.

 

Language independence

The architecture should not impose a language on the developer. It should instead allow the developer to use the language of their choice.

 

Development tools have to be enhanced to support JavaBeans and COM+ but both architectures provide lots of benefits if the tools do incorporate support for them.

 

Make component development simple

The architecture should contain elements that development tools can incorporate in order to make development of components simpler.

 

Both COM+ and JavaBeans support a way for development tools to find out the methods, properties and events supported by a component. This functionality is absolutely essential to have in a component architecture. Both architectures have a way of autogenerating this data and a component developer override if needed.

 

In the JavaBeans model, at design time in a visual environment, the developer interacts with the bean through a property sheet that shows the available properties of the bean and property editors for each property. JavaBeans provides default implementations of these interfaces. However, a bean can implement the Customizer interface to display its own property sheet and the PropertyEditor interface for any given property to show a custom property editor. In a programmatic environment, the developer just sets properties through the methods available through the interfaces.

 

Classic COM did not focus on the development tool at all. It just defined a way for objects to communicate with each other. COM+ has an enormously more ambitious target – it provides support for the development tool to extend the language it supports. COM+ is based on a general activation and interception architecture that is built into its runtime. Let us consider the Visual C++ integrated development environment (IDE) as an example of how this works. Once the IDE incorporates COM+ support, it can provide a keyword for creating COM objects. Attributes can be associated with the creation of this object (again, syntax is defined by the IDE). The attributes allowed for an object can be found from the metadata associated with the object. The IDE could show a dropdown listing the attributes of the object. COM+ will associate a context with this object at creation time and it will intercept all calls to the object and make it behave according to its attributes. Thus, COM+ keeps track of all references to the object and also all services used by the object. Reference counting, the bane of COM programming until now, is delegated to the COM+ runtime. The interception architecture also allows external services to be registered that can be called before invoking any method on a COM+ object.

 

The interesting distinction here is that JavaBeans focuses on making visual interaction at design time much easier whereas COM+ makes programmatic interaction at design time much easier. I think a best of both worlds solution would be optimal. Component specified UI in a visual interaction environment is ideal of course but it would be nice to also have visual support in the programmatic customization mode. E.g. the component should be able to explain what its properties are and how to use them rather than just list them. Since this is all design time info, it does not need to hinder runtime performance.

 

Make common actions easy to do

There are many tasks that a large cross section of components needs to do. The architecture should provide easy ways of accomplishing these actions. The actions supported by the architecture should be picked very carefully because indiscriminate addition of tasks could bloat the runtime and really hinder performance. Only tasks that appeal to a wide range of components should be supported. This part of the component architectures can easily degenerate into a feature war between different companies since it is not clearly defined. Here are the tasks currently supported:

 

  1. Property interactions: JavaBeans has 2 new kinds of properties – bound and constrained. A PropertyChange event is fired by the architecture every time the value of a bound property changes. The same effect can be achieved through events but since this activity is done so often the JavaBeans architects made it a part of the architecture. This is a valuable addition. Constrained properties allow other beans to bind to them (the binding objects are called listeners). The listeners get notified before a property value changes and the listeners can veto the change by throwing a VetoException. It does not seem like this is such a common activity and its addition to the framework is not fully justifiable. COM+ does not support either of these interactions.
  2. Events: Events are a very valuable part of any component architecture since they allow an interested object B to get notified of a change in object A rather than having B repeatedly querying A for some value. COM+ enables an interesting new publish and subscribe event mechanism. In classic COM, event sinks had to register themselves with the event source and the source had to keep track of all the listeners and fire the event on each of them. JavaBeans uses the same model as classic COM. In the COM+ model, the source notifies the COM+ Event Service of its available events. Event sinks let the service know that they are interested in certain published events. The service forwards the event from the source to all interested sinks. Publishers can implement filters that restrict the kinds of objects that see their events. The power of this approach is that a component written in one language can be notified of events from a component written in a different language. Of course JavaBeans don’t need these since all compiled beans end up in Java but it is a valuable feature addition to COM.
  3. Persistence. Most objects need to persist themselves in some way or the other unless they are completely stateless. JavaBeans provides extensive support in order to make this simple for the bean developer. For the simple case where the bean wants its internal state persisted, this is trivial. The JavaBeans architecture automatically persists and restores the internal state of a bean. If there are variables that the bean does not want persisted, they should be marked as transient by the developer. Everything else is persisted. COM+ does not provide any such support although the IPersistStorage interface can be used to persist any data that a component needs into structured storage. However, the COM+ component developer always has to do this extra work.
  4. Support for distributed computing. In today’s Web world, this is an absolutely essential feature in any component architecture. A component running on one machine should be able to transparently invoke a component on a different machine. COM+ components do this through DCOM (distributed COM) and RPC while JavaBeans do this through RMI (remote method invocation). Both mechanisms are remarkable similar and to a programmer they both look just like procedure calls in code. COM+ provides the additional feature of dynamic load balancing. A component can be installed on several machines with one registered as the router and component invocations are then dynamically load balanced among the different servers. This is extremely useful for scaling a componentized solution.
  5. Security. COM+ server applications can have role based or process access based (this is the classic COM model) security. In process access based security, the server process impersonates the client’s access privileges and accesses resources based on that. COM+ adds cloaking capabilities. Previously, servers could only access local resources. Now components can forward the client’s credentials to remote machines. In role-based security, groups of users can be assigned access privileges. These are extremely fine grained – roles can be assigned to individual methods of interfaces. JavaBeans are subject to the standard Java security model. When they run as untrusted applets they are not allowed to access the disk or the network. The Enterprise JavaBeans (EJB) specification enables more security features and this is described in the EJB section later in the paper.

 

Enable new ways for components to interact with each other

This area of component architectures could also lead to a feature war but it is also an important way of injecting new technology into the mainstream.

 

COM+ introduces the following interesting new (i.e. new to the mainstream) technologies:

  1. Queued requests. The Microsoft Message Queue Server (MSMQ) technology has been incorporated into COM+. This enables a new way of interaction between components that was not possible between COM components. Classic COM components always had to be running at the same time to communicate with each other. With MSMQ, this restriction is removed. The client can send messages to a persisted queue and the server processes these when it runs. This could lead to interesting efficiencies in tasks where an immediate response from the server is not required.
  2. In memory database (IMDB). Many apps, especially ones responding to web queries, need to retrieve fairly static data from persistent tables. E.g. an app may use the zip code to fill in city and state info in a form. If the app has to read this information from a disk-based database every time, performance problems occur. The IMDB can be used to cache a table in memory and the data would then be loaded from disk just once. Since RAM is relatively cheap, this is an easy way to greatly enhance performance. It is primarily useful for read only scenarios but could be useful in reducing the number of writes across a network too.
  3. Support for transactions. A lot of components these days need atomic transactions with multiple databases and facility to commit/rollback. COM+ allows for very easy addition of transaction support to a component. It is also possible to make one transaction span multiple components by specifying this in the COM+ Explorer UI. In this way separately developed components can be combined into one application and still support commit/rollback for an operation that the combined application considers to be a single entity.

 

Performance

Performance is, as always, the most important feature.

 

As we have seen before, a component can have design time and runtime pieces. If the component developer wants to make the component very easy to customize and very user friendly (and complex components should certainly strive to do this), the design time component could get very large. The design time code is not needed at all during runtime. An interesting efficiency introduced by JavaBeans is that since the bean is made up of Java class files, only the runtime class files need to be downloaded at runtime, significantly reducing the over the wire cost of downloading the component. Since the COM+ component is comprised of a single DLL/EXE, this cannot be achieved in a simple way. The component developer could break the component into a design time component and a run time component and have the design time component set the state of the runtime component in some way. But this is certainly harder than the JavaBeans way of achieving this efficiency since it is built into the language in that case.

 

If a bean is written exclusively in Java to keep the cross platform option viable, its performance may suffer depending on the speed of the Java VM on a given platform. This can be improved by writing platform specific native code called by the bean. COM+ objects written in C++, VB etc have to be recompiled to move from one platform to another. Their performance will, however, be significantly better since they run native code.

 

Scalability is a very important issue in components that are deployed on enterprise servers. To improve scalability, COM+ allows object pooling. From the COM+ Explorer tool, an attribute can be set on a component to specify its pool size. If an object is expensive to create, object pooling is ideal for it. COM+ then reuses objects from the pool instead of creating them every time they are accessed. However, the component developer must write his component more carefully if he allows it to be pooled. COM+ also pools limited resources (e.g. database connections).

 

Enterprise JavaBeans (EJB)

This is a new specification announced by Sun and worked on jointly by Sun, IBM and other vendors. It enables the building of JavaBeans for the enterprise i.e. it allows life cycle management, transactions, resource pooling and security. It defines a concept called an EJB container. The Enterprise JavaBean talks through the EJB specification to the container. The client talks to the container. The container is responsible for implementing all platform specific security, transaction, state management and pooling support. Software vendors are expected to sign up to add EJB support to their systems. This is a very interesting approach since Sun does not provide any implementation and yet provides a cross platform enterprise solution. The two potential problems here are the chicken and egg problem – until EJB containers are written by popular vendors, no one is going to write the enterprise beans and it will be difficult to persuade vendors to add EJB support without useful beans already out there. Sun has to very actively evangelize this platform in order to jumpstart EJB development. The other problem is that subtle implementation differences may arise between the support provided by the different container implementations.

 

Conclusion:

We see a big gap between classic COM and JavaBeans, but if we compare COM+ and JavaBeans, the 2 architectures are remarkably similar.

 

COM+ provides a runtime library that basically functions as a VM since components written in different languages communicate with each other through the COM+ runtime. This removes a large part of the drawbacks COM had. JavaBeans, of course, talk entirely through the Java VM.

 

If we consider COM+ vs. JavaBeans and the Enterprise JavaBeans specification, the list of features is fairly similar. COM+ has some significantly more useful features already implemented and rolled into it like transaction support, resource pooling, state management, security and persistent queue support. In COM+ these enterprise features are tied tightly into Windows, whereas EJB provides the framework for a cross platform solution although the onus is on the vendors to provide the implementations. COM+ objects can also communicate across process boundaries whereas Beans can only communicate inside a process. This might affect existing apps that are wrapped to become parts of these new architectures.

 

Other than these differences, technically, both architectures are about the same. The huge difference from the practical point of view is COM+ provides a complete implementation for a single platform whereas JavaBeans provides a specification for all platforms that needs to be implemented by different software vendors.

 

 

Bibliography: