The COM Programming Model

[Previous] [Next]

When you create configured components, you should reference the COM+ Services Type Library in your ActiveX DLL project. This type library defines many of the interfaces that you'll use when you interact with the COM+ runtime. Table 6-1 lists the context-related interfaces that Visual Basic programmers use most commonly.

The COM+ programming model differentiates between two types of context: object context and call context. Object context is created when the SCM creates a new context, and it doesn't generally change across method calls. A call context contains call-specific information and flows across contexts as control is passed from one method to the next.

Table 6-1 Core COM+ Interfaces Used By Visual Basic Programmers

Interface Type Uses Available in MTS?
ObjectContext Object context and call context Transaction control; Programmatic security; Obtaining references to ASP objects such as Request, Response, and Application Yes
ContextInfo Object context Obtaining contextual information about the current context, activity, and transaction No
IContextState Object context Transaction control No
SecurityCallContext Call context Programmatic security No

Programming Against the Object Context

Each context gets an object context, which is a system-provided COM object that holds context-related information. (See Figure 6-10.) The object context also exposes methods that allow you to interact with the COM+ runtime. Some of these methods allow your objects to query the COM+ runtime for information, and others allow you to tell the COM+ runtime to do things for you.

click to view at full size.

Figure 6-10 An object can retrieve a reference to its object context by calling GetObjectContext.

Let's look at a quick example. I'll cover writing COM+ transactions in depth in a later chapter; for now, I'll show a simple example of an object that has finished its work and wants to commit the current transaction. Examine the following code:

 Dim oc As COMSVCSLib.ObjectContext Set oc = GetObjectContext oc.SetComplete 

A call to GetObjectContext allows an object to retrieve a reference to its object context. In this example, the object uses its object context to tell the COM+ runtime that it has completed its work and is voting for the transaction to be committed. Note that you don't have to create an explicit ObjectContext reference. Here's a shorthand version of the previous code that does the same thing:

 GetObjectContext.SetComplete 

A call to GetObjectContext is performed very quickly (because the COM+ runtime stores a reference to the object context in a quickly accessible place known as thread local storage). In general, you won't optimize your code by attempting to minimize the number of calls to GetObjectContext. For example, it doesn't really speed things up when you call GetObjectContext and store the returned reference in a module-level variable. This approach makes your component code more complex without providing any noticeable performance improvements.

Note that an object should never access an object context from a foreign context. In Figure 6-10, for example, Object2 should never acquire a reference to the object context for Context A. This means that you should never pass a reference to an object context in a method. The only context an object should ever use is the one that it acquires with a call to GetObjectContext.

The MTS programming model also includes the ObjectContext interface. In both MTS and COM+, the ObjectContext interface deals with object context as well as call context. When the architects redesigned things for COM+, they decided to add a few new interfaces that were specific to either object context or call context.

The ContextInfo interface is specific to the object context. This interface allows you to retrieve contextual information (primarily the identifying GUIDs) for the current context, activity, and transaction. You can get a reference to a system-provided object that implements the ContextInfo interface through the ObjectContext interface. Here's an example of using the ContextInfo interface to retrieve the GUID that identifies the current context:

 Dim ci As COMSVCSLib.ContextInfo Dim MyContextID As String Set ci = GetObjectContext.ContextInfo MyContextID = ci.GetContextId 

As you can see, the object that implements ContextInfo is contained in the object context. This means that there are two separate objects. In COM-speak, you can say that there are two separate identities.

In addition to exposing a subobject that implements ContextInfo, the object context in COM+ also implements interfaces other than ObjectContext. Some of these other interfaces are accessible only through C++, but one that is accessible through Visual Basic is IContextState.

The IContextState interface, like ContextInfo, is specific to the object context. You use this interface to gain control over your transactions. You might notice that this interface exposes some functionality that's duplicated in the ObjectContext interface. I'll wait until Chapter 8 to get into the details. For now, I'll just show a quick example of acquiring and using an IContextState reference:

 Dim cs As COMSVCSLib.IContextState Set cs = GetObjectContext cs.SetMyTransactionVote TxCommit 

You acquire the reference by calling GetObjectContext and casting the return value to the type IContextState. Moreover, once you call GetObjectContext, you can cast back and forth between the ObjectContext interface and the IContextState interface. You can do this because they represent two interfaces implemented by a single COM identity.

 Dim oc As ObjectContext, cs As IContextState Set oc = GetObjectContext Set cs = oc 

In this example, the second line acquires an ObjectContext connection to the object context. The next line results in a call to QueryInterface to obtain a second reference to the same object. When you understand why this style of casting works the way it does, you'll be glad that you've invested so much time and energy into learning about interface-based programming.

Understanding Call Context

While the object context resides in a single place, the call context travels along with the flow of a chain of method calls. Let's look at an example to get a better understanding of the important concepts. Let's say you've created a form-based client application that's running on a Windows 98 computer. Assume that this client application creates an object in a COM+ server application on a Windows 2000 server and that this object creates a few more objects (some of which are on another Windows 2000 server), as shown in Figure 6-11. When the client application makes a method call that flows across these objects, a logical call chain extends across three different computers. However, as control passes across context, process, and computer boundaries, lots of contextual information flows along with it.

This passing of contextual information along with method calls is made possible through the notion of causality, which was part of COM before MTS and COM+. A causality can be defined as a chain of Object RPC (ORPC) method calls. When the client on the Windows 98 computer invokes a method, the COM runtime creates a new causality and generates a GUID (known as a causality ID) to identify it before making the initial outbound call. As the call is transmitted across the wire, you already know that the method's parameter values are sent along with it. However, you should see that the causality ID and other security-related information are automatically propagated as well. The causality remains alive while the flow of control moves from Object1 to Object2 to Object3 and then all the way back to the client. It seems as if one big call stack extends across the network.

click to view at full size.

Figure 6-11 As a chain of method calls flows across a set of objects, it represents a causality that carries related information known as the call context. In this scenario, a new causality is created each time the client calls a method.

The primary reason for caring about call context relates to security. One interface deals specifically with the call context: SecurityCallContext. This interface allows an object to determine whether COM+ security has been turned on and who the caller is. Here's an example of using this interface:

 Dim scc As COMSVCSLib.SecurityCallContext Dim IsMyAppSecure As Boolean Set scc = GetSecurityCallContext IsMyAppSecure = scc.IsSecurityEnabled() 

You might notice that a few methods are available in both the SecurityCallContext interface and the ObjectContext interface. This is due to the fact that MTS was designed to provide one-stop shopping through the ObjectContext interface. You can use either interface, but the SecurityCallContext interface includes functionality that isn't available in the ObjectContext interface. For this reason, I recommend being consistent and using the SecurityCallContext interface for all your programmatic security.



Programming Distributed Applications with COM+ and Microsoft Visual Basic 6.0
Programming Distributed Applications with Com and Microsoft Visual Basic 6.0 (Programming/Visual Basic)
ISBN: 1572319615
EAN: 2147483647
Year: 2000
Pages: 70
Authors: Ted Pattison

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net