5 Managing a Domain's Configuration with JMX

This chapter describes how to use JMX to manage a WebLogic Server domain's configuration. It explains how to edit MBean attributes; how to list and undo changes; how to track the activation of changes; and how to set and get encrypted MBean attribute values. It also includes best practices for editing and handling exceptions.

This chapter includes the following sections:

To understand the process of changing a WebLogic Server domain and activating the changes, see Managing Configuration Changes in Understanding Domain Configuration for Oracle WebLogic Server.

Editing MBean Attributes: Main Steps

To edit MBean attributes:

  1. Start an Edit Session.

    All edits to MBean attributes occur within the context of an edit session, and within each WebLogic Server domain only one edit session can be active at a time. Once a user has started an edit session, WebLogic Server locks other users from accessing the pending configuration MBean hierarchy. See Managing Locks.

  2. Change Attributes or Create New MBeans.

    Changing an MBean attribute or creating a new MBean updates the in-memory hierarchy of pending configuration MBeans. If you end your edit session before saving these changes, the unsaved changes will be discarded.

  3. Save Changes to the Pending Configuration Files.

    When you are satisfied with your changes to the in-memory hierarchy, save them to the domain's pending configuration files. Any changes that you save remain in the pending configuration files until they have been activated or explicitly reverted. If you end your edit session before activating the saved changes, you or someone else can activate them in a subsequent edit session.

    You can iteratively make changes and save changes before activating them. For example, you can create and save a server. Then you can configure the new server's listen port and listen address and save those changes. Organizing your code in this way can facilitate correcting any validation errors.

  4. Activate Your Saved Changes.

    When you activate your changes, WebLogic Server copies the saved, pending configuration files to all servers in the domain. Each server evaluates the changes and indicates whether it can consume them. If it can, then it updates its active configuration files and in-memory hierarchy of configuration MBeans.

  5. Restart any server instances that have been updated with changes that require a server restart.

For an example of editing MBeans and activating the edits, see Example: Changing the Administration Port.

Start an Edit Session

To start an edit session:

  1. Initiate a connection to the Edit MBean Server.

    The connection returns an object of type java.management.MBeanServerConnection.

    See Make Remote Connections to an MBean Server.

  2. Get the object name for ConfigurationManagerMBean.

    ConfigurationManagerMBean provides methods to start and stop edit sessions, and save, undo, and activate configuration changes. (See ConfigurationManagerMBean in MBean Reference for Oracle WebLogic Server.)

    Each domain has only one instance of ConfigurationManagerMBean and it is contained in the EditServiceMBean ConfigurationManager attribute. EditServiceMBean is your entry point for all edit operations. It has a simple, fixed object name and contains attributes and operations for accessing all other MBeans in the Edit MBean Server.

    To get the ConfigurationManagerMBean object name, use the following method:

    MBeanServerConnection.getAttribute(
        ObjectName object-name, String attribute)
    

    In the preceding method syntax:

    • object-name represents the literal "com.bea:Name=EditService,Type=weblogic.management.mbeanservers.edit.EditServiceMBean", which is the object name of EditServiceMBean.

    • attribute represents the literal "ConfigurationManager", which is the name of the attribute in EditServiceMBean that contains ConfigurationManagerMBean.

  3. Start an edit session.

    To start an edit session, invoke the ConfigurationManagerMBean startEdit(int waitTime, int timeout) operation, where:

    • waitTime represents the number of milliseconds ConfigurationManagerMBean waits to establish a lock on the edit MBean hierarchy. You cannot establish a lock if other edits are in progress unless you have administrator privileges (see Managing Locks).

    • timeout represents the number of milliseconds you have to complete your edit session. If the time expires before you save or activate your edits, all of your unsaved changes are discarded.

    The startEdit operation returns either of the following:

    • If it cannot establish a lock on the edit tree within the amount of time that you specified, it throws weblogic.management.mbeanservers.edit.EditTimedOutException.

    • If it successfully locks the edit tree, it returns an object name for DomainMBean, which is the root of the edit MBean hierarchy.

Change Attributes or Create New MBeans

To change the attribute values of existing MBeans, create new MBeans, or delete MBeans:

  1. Navigate the hierarchy of the edit tree and retrieve an object name for the MBean that you want to edit. To create or delete MBeans, retrieve an object name for the MBean that contains the appropriate factory methods.
  2. To change the value of an MBean attribute, invoke the MBeanServerConnection.setAttribute(object-name, attribute) method, where:
    • object-name represents the object name of the MBean that you want to edit.

    • attribute represents a javax.management.Attribute object, which contains the name of the MBean attribute that you want to change and its new value.

    To create an MBean, invoke the MBean's create method. For example, the factory method to create an instance of ServerMBean is createServer(String name) in DomainMBean. In MBean Reference for Oracle WebLogic Server, each MBean describes the location of its factory methods. (See ServerMBean.)

  3. (Optional) If you organize your edits into multiple steps, consider validating your changes after each step by invoking the ConfigurationManagerMBean validate() operation.

    The validate method verifies that all unsaved changes satisfy dependencies between MBean attributes and makes other checks that cannot be made at the time that you set the value of a single attribute.

    If it finds validation errors, the validate() operation throws an exception of type weblogic.management.mbeanservers.edit.ValidationException. See Exception Types Thrown by Edit Operations.

    Validating is optional because the save() operation also validates changes before saving.

Save Changes to the Pending Configuration Files

Save your changes by invoking the ConfigurationManagerMBean save() operation.

Activate Your Saved Changes

To activate your saved changes throughout the domain:

  1. Invoke the ConfigurationManagerMBean activate(long timeout) operation where timeout specifies how many milliseconds the operation has to complete.

    The activate operation returns an object name for an instance of ActivationTaskMBean, which contains information about the activation request. See Listing and Undoing Changes.

    When the activate operation succeeds or times out, it releases your lock on the editable MBean hierarchy.

  2. Close your connection to the MBean server by invoking JMXConnector.close().

Example: Changing the Administration Port

The code example in Example 5-1 changes the context path that you use to access the WebLogic Server Administration Console for a domain. This behavior is defined by the DomainMBean ConsoleContextPath attribute.

Note the following about the code example:

Example 5-1 Example: Changing the Administration Console's Context Path

import java.io.IOException;
import java.net.MalformedURLException;
import java.util.Hashtable;

import javax.management.Attribute;
import javax.management.MBeanServerConnection;
import javax.management.MalformedObjectNameException;
import javax.management.ObjectName;
import javax.management.remote.JMXConnector;
import javax.management.remote.JMXConnectorFactory;
import javax.management.remote.JMXServiceURL;
import javax.naming.Context;

public class EditWLSMBeans {
   private static MBeanServerConnection connection;
   private static JMXConnector connector;
   private static final ObjectName service;

   // Initializing the object name for EditServiceMBean
   // so it can be used throughout the class.
   static {
      try {
        service = new ObjectName(
           "com.bea:Name=EditService,Type=weblogic.management.mbeanservers.
            edit.EditServiceMBean");
      } catch (MalformedObjectNameException e) {
         throw new AssertionError(e.getMessage());
      }
   }

   /**
   * ----------------------------------------------------------
   * Methods to start an edit session.
   * NOTE: Error handling is minimal to help you see the 
   *       main steps in editing MBeans. Your code should
   *       include logic to catch and process exceptions.
   * ----------------------------------------------------------
   */

   /*
   * Initialize connection to the Edit MBean Server.
   */
   public static void initConnection(String hostname, String portString,
      String username, String password) throws IOException,
      MalformedURLException {

      String protocol = "t3";
      Integer portInteger = Integer.valueOf(portString);
      int port = portInteger.intValue();
      String jndiroot = "/jndi/";
      String mserver = "weblogic.management.mbeanservers.edit";

      JMXServiceURL serviceURL = new JMXServiceURL(protocol, hostname, port,
      jndiroot + mserver);

      Hashtable h = new Hashtable();
      h.put(Context.SECURITY_PRINCIPAL, username);
      h.put(Context.SECURITY_CREDENTIALS, password);
      h.put(JMXConnectorFactory.PROTOCOL_PROVIDER_PACKAGES,
         "weblogic.management.remote");
         connector = JMXConnectorFactory.connect(serviceURL, h);
         connection = connector.getMBeanServerConnection();
   }

   /**
   * Start an edit session.
   */
   public ObjectName startEditSession() throws Exception {
      // Get the object name for ConfigurationManagerMBean.
      ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
         "ConfigurationManager");

      // Instruct MBeanServerConnection to invoke
      // ConfigurationManager.startEdit(int waitTime int timeout).
      // The startEdit operation returns a handle to DomainMBean, which is
      // the root of the edit hierarchy.
      ObjectName domainConfigRoot = (ObjectName) 
         connection.invoke(cfgMgr,"startEdit", 
         new Object[] { new Integer(60000),
         new Integer(120000) }, new String[] { "java.lang.Integer",
         "java.lang.Integer" });
      if (domainConfigRoot == null) {
         // Couldn't get the lock
         throw new Exception("Somebody else is editing already");
      }
      return domainConfigRoot;

   /**
   * ----------------------------------------------------------
   * Methods to change MBean attributes.
   * ----------------------------------------------------------
   */

   /**
   * Modify the DomainMBean's ConsoleContextPath attribute.
   */
   public void editConsoleContextPath(ObjectName cfgRoot) throws Exception {
      // The calling method passes in the object name for DomainMBean.
      // This method only needs to set the value of an attribute
      // in DomainMBean.
      Attribute adminport = new Attribute("ConsoleContextPath", new String(
         "secureConsoleContext"));
      connection.setAttribute(cfgRoot, adminport);
      System.out.println("Changed the Administration Console context path to " +
         "secureConsoleContext");
   }

   /**
   * ----------------------------------------------------------
   * Method to activate edits.
   * ----------------------------------------------------------
   */
   public ObjectName activate() throws Exception {
      // Get the object name for ConfigurationManagerMBean.
      ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
         "ConfigurationManager");
      // Instruct MBeanServerConnection to invoke
      // ConfigurationManager.activate(long timeout).
      // The activate operation returns an ActivationTaskMBean.
      // You can use the ActivationTaskMBean to track the progress
      // of activating changes in the domain.
      ObjectName task = (ObjectName) connection.invoke(cfgMgr, "activate",
         new Object[] { new Long(120000) }, new String[] { "java.lang.Long" });
      return task;
   }

   public static void main(String[] args) throws Exception {
      String hostname = args[0];
      String portString = args[1];
      String username = args[2];
      String password = args[3];

      EditWLSMBeans ewb = new EditWLSMBeans();

      // Initialize a connection with the MBean server.
      initConnection(hostname, portString, username, password);

      // Get an object name for the Configuration Manager.
      ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
         "ConfigurationManager");

      // Start an edit session.
      ObjectName cfgRoot = ewb.startEditSession();
      // Edit the server log MBeans.
      ewb.editConsoleContextPath(cfgRoot);

      // Save and activate.
      connection.invoke(cfgMgr, "save", null, null);
      ewb.activate();

      // Close the connection with the MBean server.
      connector.close();
   }
}

Exception Types Thrown by Edit Operations

Table 5-1 describes all of the exception types that WebLogic Server can throw during edit operations. When WebLogic Server throws such an exception, the MBean server wraps the exception in javax.management.MBeanException. (See MBeanException in the Java SE 7 API Specification at http://docs.oracle.com/javase/7/docs/api/javax/management/MBeanException.html.)

Table 5-1 Exception Types Thrown by Edit Operations

Exception Type Thrown When
EditTimedOutException

The request to start an edit session times out.

NotEditorException

You attempt to edit MBeans without having a lock or when an administrative user cancels your lock and starts an edit session.

ValidationException

You set an MBean attribute's value to the wrong data type, outside an allowed range, not one of a specified set of values, or incompatible with dependencies in other attributes.

Listing and Undoing Changes

The following sections describe working with changes that you have made during an edit session:

WebLogic Server describes changes in a Change object, which is of type javax.management.openmbean.CompositeType. See CompositeType in the Java SE 7 API Specification at http://docs.oracle.com/javase/7/docs/api/javax/management/openmbean/CompositeType.html.

Through JMX, you can access information about the changes to a domain's configuration that have occurred during the current server session only. WebLogic Server maintains an archive of configuration files, but the archived data and comparisons of archive versions is not available through JMX.

List Unsaved Changes

For each change that you make to an MBean attribute, WebLogic Server creates a Change object which contains information about the change. You can access these objects from the ConfigurationManagerMBean Changes attribute until you save the changes. See ConfigurationManagerMBean in MBean Reference for Oracle WebLogic Server.

Any unsaved changes are discarded when your edit session ends.

To list unsaved changes:

  1. Start an edit session and change at least one MBean attribute.
  2. Get the value of the ConfigurationManagerMBean Changes attribute and assign the output to a variable of type Object[].
  3. For each object in the array, invoke Object.toString() to output a description of the change.

    Because Change is a javax.management.openmbean.CompositeType, you can also cast each item in the array as a CompositeType and invoke CompositeType methods on the change. See CompositeType in the Java SE 7 API Specification at http://docs.oracle.com/javase/7/docs/api/javax/management/openmbean/CompositeType.html.

Example 5-2 Example Method that Lists Unsaved Changes

public void listUnsaved() throws Exception {
   ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
   "ConfigurationManager");
   Object[] list = (Object[])connection.getAttribute(cfgMgr, "Changes");
   int length = (int) list.length;
   for (int i = 0; i < length; i++) {
      System.out.println("Unsaved change: " + list[i].toString());
   }
}

The code in Example 5-2 creates a method that lists unsaved changes. It assumes that the calling method has already established a connection to the Edit MBean Server.

List Unactivated Changes

When anyone saves changes, WebLogic Server persists the changes in the pending configuration files. The changes remain in these files, even across multiple editing sessions, unless a user who has started an edit session invokes the ConfigurationManagerMBean undoUnactivatedChanges() operation, which reverts all unactivated changes from the pending files.

The ConfigurationManagerMBean UnactivatedChanges attribute contains Change objects for both unsaved changes and changes that have been saved but not activated. (There is no attribute that contains only saved but unactivated changes.) See ConfigurationManagerMBean Unactivated Changes in MBean Reference for Oracle WebLogic Server.

To list changes that you have saved in the current editing session but not activated, or changes that your or others have saved in previous editing sessions but not activated:

  1. Start an edit session and change at least one MBean attribute.
  2. Get the value of the ConfigurationManagerMBean UnactivatedChanges attribute and assign the output to a variable of type Object[].
  3. For each object in the array, invoke Object.toString() to output a description of the change.

    Because Change is a javax.management.openmbean.CompositeType, you can also cast each item in the array as a CompositeType and invoke CompositeType methods on the change. See CompositeType in the Java SE 7 API Specification at http://docs.oracle.com/javase/7/docs/api/javax/management/openmbean/CompositeType.html.

Example 5-3 Example Method that Lists Unactivated Changes

public void listUnactivated() throws Exception {
   ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
   "ConfigurationManager");
   Object[] list = (Object[])connection.getAttribute(cfgMgr,
      "UnactivatedChanges");
   int length = (int) list.length;
   for (int i = 0; i < length; i++) {
      System.out.println("Unactivated changes: " + list[i].toString());
   }
}

The code in Example 5-3 creates a method that lists unactivated changes. It assumes that the calling method has already established a connection to the Edit MBean Server.

List Changes in the Current Activation Task

When you activate changes, WebLogic Server creates an instance of ActivationTaskMBean, which contains one Change object for each change that is being activated. You can access these ActivationTaskMBeans from either of the following:

  • The ConfigurationManagerMBean activate() method returns an object name for the ActivationTaskMBean that describes the current activation task.

  • The ConfigurationManagerMBean CompletedActivationTasks attribute can potentially contain a list of all ActivationTaskMBean instances that have been created during the current Administration Server instantiation. See Listing All Activation Tasks Stored in Memory.

To list changes in the current activation task only:

  1. Start an edit session.
  2. Assign the output of the activate operation to an instance variable of type javax.management.ObjectName.
  3. Get the value of the ActivationTaskMBean Changes attribute. and assign the output to a variable of type Object[].
  4. For each object in the array, invoke Object.toString() to output a description of the change.

    Because Change is a javax.management.openmbean.CompositeType, you can also cast each item in the array as a CompositeType and invoke CompositeType methods on the change. See CompositeType in the Java SE 7 API Specification at http://docs.oracle.com/javase/7/docs/api/javax/management/openmbean/CompositeType.html.

Example 5-4 Example Method that Lists Changes in the Current Activation Task

public void activateAndList() 
   throws Exception {
   ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
      "ConfigurationManager");
   ObjectName task = (ObjectName) connection.invoke(cfgMgr, "activate",
      new Object[] { new Long(120000) }, new String[] { "java.lang.Long" });
   Object[] changes = (Object[])connection.getAttribute(task, "Changes");
   int i = (int) changes.length;
   for (int i = 0; i< i; i++) {
      System.out.println("Changes activated: " + changes[i].toString());
   }
}

The code in Example 5-4 creates a method that lists all changes activated in the current editing session. It assumes that the calling method has already established a connection to the Edit MBean Server.

Undoing Changes

ConfigurationManagerMBean provides two operations for undoing changes made during an editing session:

  • undo

    Reverts unsaved changes.

  • undoUnactivatedChanges

    Reverts all changes, saved or unsaved, that have not yet been activated. If other users have saved changes in a previous editing session but not activated those changes, invoking the ConfigurationManagerMBean undoUnactivatedChanges() operation reverts those changes as well.

    After you invoke this method, the pending configuration files are identical to the working configuration files that the active servers use.

To undo changes, start an edit session and invoke the ConfigurationManagerMBean undo or undoUnactivatedChanges operation.

For example:

connection.invoke(cfgMgr, "undo", null, null); 

Tracking the Activation of Changes

In addition to maintaining a list of changes, each ActivationTaskMBean that WebLogic Server creates when you invoke the activate operation describes which user activated the changes, the status of the activation task, and the time at which the changes were activated.

The Administration Server maintains instances of ActivationTaskMBean in memory only; they are not persisted and are destroyed when you shut down the Administration Server. Because the ActivationTaskMBean instances contain a list of Change objects (each of which describes a single change to an MBean attribute), they use a significant amount of memory. To save memory, by default the Administration Server maintains only a few of the most recent ActivationTaskMBean instances in memory. To change the default, increase the value of the ConfigurationManagerMBean CompletedActivationTasksCount attribute.

The following sections describe working with instances of ActivationTaskMBean:

Listing the Status of the Current Activation Task

When you invoke the activate operation, WebLogic Server returns an ActivationTaskMBean instance to represent the activation task.

The ActivationTaskMBean State attribute describes the status of the activation task. This attribute stores an int value and ActivationTaskMBean defines constants for each of the int values. See ActivationTaskMBean in MBean Reference for Oracle WebLogic Server.

To list the status of the current activation task:

  1. Start an edit session and change at least one MBean attribute.
  2. Invoke the ConfigurationManagerMBean activate(long timeout) operation and assign the output to a variable of type ActivationTaskMBean.
  3. Get the value of the ActivationTaskMBean State attribute.

Listing All Activation Tasks Stored in Memory

The ActivationTaskMBean that the activate operation returns describes only a single activation task. The Administration Server keeps this ActivationTaskMBean in memory until you purge it (see Purging Completed Activation Tasks from Memory) or the number of activation tasks exceeds the value of the ConfigurationManagerMBean CompletedActivationTasksCount attribute.

To access all ActivationTaskMBean instances that are currently stored in memory (see Example 5-5):

  1. Connect to the Edit MBean Server. (You do not need to start an edit session.)
  2. Get the value of the ConfigurationManagerMBean CompletedActivationTasks attribute and assign the output to a variable of type Object[].
  3. (Optional) For each object in the array, get and print the value of ActivationTaskMBean attributes such as User and State.

    See ActivationTaskMBean in MBean Reference for Oracle WebLogic Server.

  4. (Optional) For each object in the array, get the value of the Changes attribute. Invoke Object.toString() to output the value of the Change object.

Example 5-5 Example Method that Lists All Activation Tasks in Memory

public void listActivated() throws Exception {
   ObjectName cfgMgr = (ObjectName) connection.getAttribute(service,
   "ConfigurationManager");
   ObjectName[] list = (ObjectName[])connection.getAttribute(cfgMgr,
      "CompletedActivationTasks");
   System.out.println("Listing completed activation tasks.");
   int length = (int) list.length;
   for (int i = 0; i < length; i++) {
      System.out.println("Activation task " + i);
      System.out.println("User who started activation: " +
         connection.getAttribute(list[i], "User"));
      System.out.println("Task state: " + connection.getAttribute(list[i],
         "State"));
      System.out.println("Start time: " + connection.getAttribute(list[i],
         "StartTime"));

      Object[] changes = (Object[])connection.getAttribute(list[i], "Changes");
      int l = (int) changes.length;
      for (int y = 0; y < l; y++) {
         System.out.println("Changes activated: " + changes[y].toString());
      }
   }
}

Purging Completed Activation Tasks from Memory

Because the ActivationTaskMBean instances contain a list of Change objects (each of which describes a single change to an MBean attribute), they use a significant amount of memory.

If the Administration Server is running out of memory, you can purge completed activation tasks from memory. Then decrease the value of the ConfigurationManagerMBean CompletedActivationTasksCount attribute.

To purge completed activation tasks from memory, connect to the Edit MBean Server and invoke the ConfigurationManagerMBean purgeCompletedActivationTasks operation.

For example:

connection.invoke(cfgMgr, "purgeCompletedActivationTasks", null, null);

Managing Locks

To prevent changes that could leave the pending configuration MBean hierarchy in an inconsistent state, only one user at a time can edit MBeans. When a user invokes the ConfigurationManagerMBean startEdit operation, the ConfigurationManagerMBean prevents other users (locks) from starting edit sessions.

The following actions remove the lock:

  • The ConfigurationManagerMBean activate operation succeeds or times out.

    You can use the ActivationTaskMBean waitForTaskCompletion operation to block until the activation process is complete.

  • The ConfigurationManagerMBean stopEdit operation succeeds.

  • A user with administrator privileges invokes the ConfigurationManagerMBean cancelEdit operation while another user has the lock.

    For example, connection.invoke(cfgMgr, "cancelEdit", null, null);

  • An edit session has been started under a user identity and another process starts an edit session under the same user identity.

    For example, if you use the WebLogic Server Administration Console to start an edit session and shortly afterwards use the WebLogic Scripting Tool (WLST) to start an edit session under the same user identity, the WLST session will remove the lock from your WebLogic Server Administration Console session.

    To prevent another process from starting an edit session under your user identity, get an exclusive lock by passing a boolean of value true to the startEdit operation. See startEdit(waitTimeInMillis, timeOutInMillis, exclusive) in the MBean Reference for Oracle WebLogic Server.

All unsaved changes are lost when the lock is removed.

Best Practices: Recommended Pattern for Editing and Handling Exceptions

Oracle recommends that you organize your editing code into several try-catch blocks. Such an organization will enable you to catch specific types of errors and respond appropriately. For example, instead of abandoning the entire edit session if a change is invalid, your code can save the changes, throw an exception and exit without attempting to activate invalid changes.

JMX agents wrap all exceptions in a generic exception of type javax.management.MBeanException. A JMX client can use the MBeanException.getTargetException() to unwrap the wrapped exception.

Consider using the following structure (see the pseudo-code in Example 5-6):

  • A try block that connects to the Edit MBean Server, starts an edit session, and makes and saves changes.

    After this try block, one catch block for each of the following types of exception wrapped within MBeanException:

    • EditTimedOutException

      This exception is thrown if the ConfigurationManagerMBean startEdit() operation cannot get a lock within the amount of time that you specify.

    • NotEditorException

      This exception is thrown if the edit session times out or an administrator cancels your edit session. (See Managing Locks.)

    • ValidationException

      This exception is thrown if you set a value in an MBean that is the wrong data type, outside an allowed range, not one of a specified set of values, or incompatible with dependencies in other attributes.

      Within the code that handles ValidationException, include a try block that either attempts to correct the validation error or stops the edit session by invoking the ConfigurationManagerMBean stopEdit() operation. If the try block stops the edit session, its catch block should ignore the NotEditorException. This exception indicates that you no longer have a lock on the pending configuration MBean hierarchy; however, because you want to abandon changes and release your lock anyway, it is not an error condition for this exception to be thrown.

  • A try block that activates the changes that have been saved.

    The ConfigurationManager activate(long timeout) operation returns an instance of ActivationTaskMBean, which contains information about the activation task. Oracle recommends that you set the timeout period for activate() to a minute and then check the value of the ActivationTaskMBean State attribute.

    If State contains the constant STATE_COMMITTED, then your changes have been successfully activated in the domain. You can use a return statement at this point to end your editing work. The lock that you created with startEdit() releases after the activation task succeeds.

    If State contains a different value, the activation has not succeeded in the timeout period that you specified in activate(long timeout). You can get the value of the ActivationTaskMBean Error attribute to find out why.

    After this try block, one catch block to catch the following type of wrapped exception:

    NotEditorException 
    

    If this exception is thrown while trying to activate changes, your changes were not activated because your edit session timed out or was cancelled by an administrator.

  • (Optional) A try block that undoes the saved changes.

    If your class does not return in the activation try block, then your activation task was not successful. If you do not want these saved changes to be activated by a future attempt to activate changes, then invoke the ConfigurationManagerMBean undoUnactivatedChanges() operation.

    Otherwise, the pending configuration files retain your saved changes. The next time any user attempts to activate saved changes, WebLogic Server will attempt to activate your saved changes along with any other saved changes.

    After this try block, one catch block to ignore the following type of wrapped exception:

    NotEditorException 
    
  • A try block to stop the edit session.

    If your activation attempt fails and you are ready to abandon changes, there is no need to wait until your original timeout period to expire. You can stop editing immediately.

    After this try block, one catch block to ignore the following type of exception:

    NotEditorException 
    
  • Throw the exception that is stored in the ActivationTaskMBean Error attribute.

Example 5-6 Code Outline for Editing and Exception Handling

try {
   //Initialize the connection and start the edit session
...
   ObjectName domainConfigRoot = (ObjectName) connection.invoke(cfgMgr,
      "startEdit", 
      new Object[] { new Integer(30000), new Integer(300000) },
      new String[] { "java.lang.Integer", "java.lang.Integer" });

   // Modify the domain 
   ...
   // Save your changes
    connection.invoke(cfgMgr, "save", null, null);

} catch (MBeanException e) {
   Exception targetException = e.getTargetException();
   if (targetException instanceof EditTimedOutException) {
      // Could not get the lock. Notify user
      ...
      throw new MyAppCouldNotStartEditException(e);
   }
   if (targetException instanceof NotEditorException) {
      ...
      throw new MyAppEditSessionFailed(e);
   }
   if (targetException instanceof ValidationException) {
      ...
      try {
        connection.invoke(cfgMgr, "stopEdit", null, null);
      // A wrapped NotEditorException here indicates that you no longer have a
      // lock on the pending configuration MBean hierarchy; however, 
      // because you want to abandon changes and release your lock anyway,
      // it is not an error condition for this exception to be thrown 
      // and you can safely ignore it.
      } catch (MBeanException e) {
         Exception targetException = e.getTargetException();
         if (targetException instanceof NotEditorException) {
            //ignore
         }
      }
      throw new MyAppEditChangesInvalid(e);
   }
   else {
   throw MBeanException (e);
   }
}

// Changes have been saved, now activate them
try {
   // Activate the changes
   ActivationTaskMBean task = (ObjectName) connection.invoke(cfgMgr,
      "activate",
      new Object[] { new Long(60000) }, 
      new String[] { "java.lang.Long" });
   // Everything worked, just return.
   String status = (String) connection.getAttribute(task, "State");
   if (status.equals("4"))
   return;
   // If there is an activation error, use ActivationTaskMBean.getError
   // to get information about the error
   failure = connection.getAttribute(task, "Error");
// If you catch a wrapped NotEditorException, your changes were not activated
// because your edit session ended or was cancelled by an administrator.
// Throw the wrapped exception.
} catch (MBeanException e) {
   Exception targetException = e.getTargetException();
   if (targetException instanceof NotEditorException) {
      ...
      throw new MyAppEditSessionFailed(e);
   }
}

// If your class executes the remaining lines, it is because activating your
// saved changes failed.
// Optional: You can undo the saved changes that failed to activate. If you
// do not undo your saved changes, they will be activated the next time 
// someone attempts to activate changes.
// try {
//     {
//      connection.invoke(cfgMgr, "undoUnactivatedChanges", null, null);
// catch(MBeanException e) {
//   Exception targetException = e.getTargetException();
//   if (targetException instanceof NotEditorException) {
//      ...
//      throw new MyAppEditSessionFailed(e);
//   }
// }

// Stop the edit session
try {
   connection.invoke(cfgMgr, "stopEdit", null, null);
   // If your activation attempt fails and you are ready to abandon
   // changes, there is no need to wait until your original timeout 
   // period to expire. You can stop editing immediately 
   // and you can safely ignore any wrapped NotEditorException.
} catch (MBeanException e) {
   Exception targetException = e.getTargetException();
   if (targetException instanceof NotEditorException) {
      //ignore
   }
}
...
// Output the information about the error that caused the activation to
// fail.
throw new MyAppEditSessionFailed(connection.getAttribute(task, "Error"));

Setting and Getting Encrypted Values

To prevent unauthorized access to sensitive data such as passwords, some attributes in WebLogic Server configuration MBeans are encrypted. The attributes persist their values in the domain's config.xml file as an encrypted string and represent the in-memory value in the form of an encrypted byte array. The names of encrypted attributes end with Encrypted. For example, the ServerMBean exposes the password that is used to secure access through the IIOP protocol in an attribute named DefaultIIOPPasswordEncrypted. To support backwards compatibility, and to enable remote JMX clients to set passwords for WebLogic Server MBeans, each encrypted attribute provides a less secure means to encrypt and set its value.

The following sections describe how to work with encrypted attributes:

Set the Value of an Encrypted Attribute (Recommended Technique)

To use this technique (see Example 5-7):

  1. In the same WebLogic Server JVM that hosts the MBean attribute, write a value to a byte array.
  2. Pass the byte array to the weblogic.management.EncryptionHelper.encrypt(byte[]) method and pass its return value to the MBeanServerConnection.setAttribute method.

    Avoid assigning the encrypted byte array to a variable because this causes the unencrypted byte array to remain in memory until it is garbage collected and the memory is reallocated.

  3. Clear the original byte array using the weblogic.management.EncryptionHelper.clear() method.

Example 5-7 Example: Set the Value of an Encrypted Attribute (Recommended Technique)

public void editDefaultIIOPPassword(ObjectName cfgRoot) throws Exception {
   // Get the ServerMBean from the DomainMBean
   ObjectName server = (ObjectName) connection.invoke(cfgRoot,
      "lookupServer", new Object[] { "myserver" },
   new String[] { "java.lang.String" });
   // Get new password from standard in. Assign it to a byte array.
   System.out.println("Enter new password and press enter: ");
   byte userinput[] = new byte[10];
   System.in.read(userinput);
   // Encrypt the byte array and set it as the encrypted
   // attribute value.
   Attribute newpassword = new Attribute("DefaultIIOPPasswordEncrypted",
      weblogic.management.EncryptionHelper.encrypt(userinput));
   connection.setAttribute(server, newpassword);
   System.out.println("New password is set to: " + 
      connection.getAttribute(server, "DefaultIIOPPasswordEncrypted"));
   // Clear the byte array.
   weblogic.management.EncryptionHelper.clear(userinput);
   }

Set the Value of an Encrypted Attribute (Compatibility Technique)

Prior to 9.0, JMX clients used a different technique for setting encrypted values. JMX clients can continue to use this compatibility technique, and if you want to set encrypted values from a remote JMX client, this is the only technique available. The compatibility technique is less secure because it creates a String that contains your unencrypted password. Even though WebLogic Server converts the String to an encrypted byte array, the String will remain in memory until it is garbage collected and the memory is reallocated.

To use the compatibility technique:

  1. Write a value to a String.
  2. Pass the String as a parameter to the MBeanServerConnection.setAttribute method, but instead of setting the value of the encrypted attribute, set the value for the corresponding non-encrypted attribute.

    WebLogic Server converts the String to an encrypted byte array and sets it as CustomIdentityKeyStorePassPhraseEncrypted. (It does not set a value for CustomIdentityKeyStorePassPhrase).

    For example, to set the CustomIdentityKeyStorePassPhraseEncrypted from a remote JMX client, invoke the MBeanServerConnection.setAttribute for an attribute named CustomIdentityKeyStorePassPhrase.

For example:

public void editDefaultIIOPPassword(ObjectName cfgRoot, String password) 
    throws Exception {
    // Get the ServerMBean from the DomainMBean
    ObjectName server = (ObjectName) connection.invoke(cfgRoot, "lookupServer",
        new Object[]{"myserver"},new String[]{"java.lang.String"});
    Attribute newpassword = new Attribute("DefaultIIOPPassword",
       "mypassword");
    connection.setAttribute(server, newpassword);
} 

Back Up an Encrypted Value

To make a backup copy of a password, use the getter method of the MBean's encrypted value to retrieve the encrypted byte array. Then write the value of the byte array to a file. WebLogic Server does not provide APIs or other utilities for decrypting values that it has encrypted.

If you need to restore the password value, you can load the saved value into a byte array and pass it as a parameter to the MBeanServerConnection.setAttribute method (see Set the Value of an Encrypted Attribute (Recommended Technique)).

Note:

Because each WebLogic Sever domain uses its own encryption algorithm, you must back up and restore passwords separately for each domain even if the unencrypted value for the password is the same for all domains.

Instead of backing up the same encrypted password for each domain, you can use the getter method of an MBean's corresponding unencrypted value. This getter unencrypts the password and copies into a String. The String will not be erased from memory until it is garbage collected and the memory is reallocated.