Providing support for instance pooling

Benefits of instance pooling

EAServer components can optionally support instance pooling. Instance pooling allows EAServer clients to reuse component instances. By eliminating the resource drain caused by repeated allocation of component instances, instance pooling improves the overall performance of EAServer.

Specifying pooling options in the wizards

When you create an EAServer component using one of the PowerBuilder wizards, you have the option to specify one of the pooling options for the component shown in Table 24-2.

Table 24-2: EAServer component pooling options

Pooling option

Description

Supported

The component is always pooled after each client use. When this option is selected, the CanBePooled event is not triggered for the component.

This option has the effect of setting the component’s pooling property to TRUE. If the Automatic Demarcation/Deactivation setting for the component is enabled, instances are pooled after each method invocation. If the setting is disabled, instances are pooled when the component calls the SetComplete (or SetAbort) method of the TransactionServer context object.

Not supported

By default, the component is not pooled after each client use. However, you can override the default behavior by scripting the CanBePooled event. In the CanBePooled event, you can specify programmatically whether a particular component instance should be pooled. If you script the CanBePooled event, this event is triggered after each client use.

This option has the effect of setting the component’s pooling property to FALSE.

Controlling the state of a pooled instance

When you create an EAServer component that supports instance pooling, that component may need to reset its state after each client has finished using the pooled instance.

To allow you to control the state of a component, EAServer triggers one or more of the events shown in Table 24-3 during the lifecycle of the component.

Table 24-3: Component state events

Event

PBM code

Activate

PBM_COMPONENT_ACTIVATE

CanBePooled

PBM_COMPONENT_CANBEPOOLED

Deactivate

PBM_COMPONENT_DEACTIVATE

When the component’s pooling option is set to Supported (the pooling property is set to TRUE), you may need to script the Activate and Deactivate events to reset the state of the pooled component. This is necessary if the component maintains state in an instance, shared, or global variable.

When the component’s pooling option is set to Not Supported (the pooling property is set to FALSE), you can optionally script the CanBePooled event to specify whether a particular component instance should be pooled. If you script the CanBePooled event, you may also need to script the Activate and Deactivate events to reset the state of the pooled component. If you do not script the CanBePooled event, the component instance is not pooled.

The EAServer Component Target and Object wizards automatically include the Activate and Deactivate events to a custom class user object that will be deployed as an EAServer component. If you want to script the CanBePooled event, you need to add this event yourself. If you do this, be sure to map the event to the correct PBM code.

NoteConstructor and Destructor are fired once When instance pooling is in effect, the Constructor and Destructor events are fired only once for the component. The Constructor and Destructor events are not fired each time a new client uses the component instance. Therefore, to reset the state of a component instance that is pooled, add logic to the Activate and Deactivate events, not the Constructor and Destructor events.

Maximum and minimum pool sizes

Instance pooling can decrease client response time, but can also increase memory usage in the server. You can configure the maximum and minimum pool size to constrain the memory used to maintain an instance pool by setting options on the Resources tab page in EAServer Manager. For example, a heavily used component should have higher minimum and maximum pool sizes than a less commonly used component.

EAServer does not preallocate instances for the pool. The pool size grows as additional instances are required to satisfy client requests, up to the maximum specified size (if a maximum size is specified). Once the minimum pool size is reached, the size will not shrink below this size. To release idle pooled instances, EAServer has a garbage collector thread that runs periodically. Each time it runs, the garbage collector removes one idle instance from the pool, unless the minimum pool size has been reached.

If you configure a minimum pool size, configure a maximum size that is slightly larger. The difference between the maximum and minimum size provides a damping factor that prevents repeated instance allocation and deallocation if the actual pool size hovers near the minimum size.

You can set environment variables to configure the way memory is managed in PowerBuilder and EAServer. For more information, see “Configuring memory management” and the technical document EAServer/PowerBuilder Memory Tuning and Troubleshooting.

The lifecycle of a component

To understand how instance pooling works, you need to understand the lifecycle of a component instance. This is what happens during the component lifecycle:

  1. The component is typically instantiated on the first method invocation. When this occurs on a component developed in PowerBuilder, EAServer creates a new PowerBuilder session for the component to run in.

  2. The PowerBuilder session creates the instance of the PowerBuilder nonvisual object that represents the EAServer component. Creating the object causes the Constructor event to be fired.

  3. After the object has been instantiated, EAServer triggers the Activate event on the nonvisual object to notify the object that it is about to be used by a new client. At this point, the component must ensure that its state is ready for execution.

  4. EAServer then executes the method called by the client on the component.

  5. When the component indicates that its work is complete, EAServer triggers the Deactivate event to allow the component to clean up its state. If the Automatic Demarcation/Deactivation setting for the component is enabled, the Deactivate event is triggered automatically after each method invocation. If the setting is disabled, the Deactivate event is triggered when the component calls the SetComplete (or SetAbort) method of the TransactionServer context object.

  6. If you have selected the Not Supported pooling option (or set the component’s pooling property to FALSE) and also scripted the CanBePooled event, EAServer triggers this event to ask the component whether it is able to be pooled at this time. The CanBePooled event allows the component instance to selectively enable or refuse pooling.

    The return value of the CanBePooled event determines whether the component instance is pooled. A return value of 1 enables pooling; a return value of 0 disables pooling. If the CanBePooled event has not been scripted, then by default the instance is not pooled.

    NoteWhat happens when the pooling property is enabled When you select the Supported pooling option (or set the component’s pooling property to TRUE), component instances are always pooled and the CanBePooled event is never triggered.

  7. If an instance is not pooled after deactivation, EAServer triggers the Destructor event. Then it destroys the PowerBuilder object and terminates the runtime session.