Month: July 2010

Processing with WebLogic Singleton Services

Posted on Updated on

I’ve recently had cause to come up with a means of running some code on precisely one managed server in a WebLogic cluster at once, and ensure that the functionality is highly available – i.e. it will migrate to a secondary server if the primary fails.  Take the following scenario, for example:

You have a number of managed servers in a WebLogic cluster, and you’re using a market data service such as Reuters RDMS or Bloomberg’s Market Data system.  You want each item of data to be processed exactly once, and you don’t want to (or can’t) make use of JMS as a means of message ordering and distribution.

Fortunately, WebLogic provides an interface that allows you to define a service that will be present on only one server in a cluster at once – the Singleton Service.  Java classes that implement the Singleton Service interface can be plugged into WebLogic’s Service Migration Framework and can therefore benefit from the powerful functionality that the framework offers.

To prepare for the deployment of a singleton service, you need to configure a leasing strategy.  Leasing is the process WebLogic Server uses to manage services that are required to run on only one member of a cluster at a time. Leasing ensures exclusive ownership of a cluster-wide entity. Within a cluster, there is a single owner of a lease. Additionally, leases can failover in case of server or cluster failure.

To configure leasing, you change the “Migration Basis” value in Cluster -> Migration.  You’ve got two choices:  consensus leasing or database leasing.  Setting Migration Basis to Consensus leasing means that the member servers maintain leasing information in-memory, which removes the requirement of having a high-availability database to use leasing.  This does mean that you need to have a node manager running on each managed server node in the cluster.  Once you’ve set this up, you’re ready to write some code.

In its simplest form, a WebLogic Singleton Service looks like this:

package com.blitz8.examples;

import weblogic.cluster.singleton.SingletonService;

public class ProcessorSingletonService implements SingletonService {
  private static final String CLASSNAME = ProcessorSingletonService.class.getName();

  public TradeProcessingSingletonService() {
  }

  public void activate() {
    System.out.println("activate() called for " + CLASSNAME);
  }

  public void deactivate() {
    System.out.println("deactivate() called for " + CLASSNAME);
  }

}

Once compiled this class can be packaged into a deployable artifact (for e.g. an EAR file), and deployed into a WebLogic domain.  Before this service will work, you need to tell WebLogic about it in order to allow WebLogic to register your service with the Service Migration Framework.  This is done by including the following XML stanza in your weblogic-application.xml deployment descriptor:

<singleton-service>
  <class-name>com.blitz8.examples.ProcessorSingletonService</class-name>
  <name>ProcessorSingletonService</name>
</singleton-service>

The schema for the deployment descriptor tells us that this needs to be a direct child of the <weblogic-application> node.

Deploy the artifact containing the weblogic-application.xml deployment descriptor and compiled Singleton Service into your domain.  Look at the server log files for evidence that WebLogic now knows about your Singleton Service, and look out for a message around the time the server switches into RUNNING mode telling you which managed server has been selected to host your Singleton Service.

You should now be able to replace the System.out.println(...) statements with your own business logic code, having proved and understood the concept of a Singleton Service.

Advertisements