Java Dynamic Management Kit 3.2 Programming Guide
[ Previous ][ Fast Back ]Chapter 14. M-Let, Bootstrap and Launcher Services[ Fast Forward ][ Next ]

M-Let Service

The management applet or m-let service enables an agent to obtain m-beans from a remote .jar file. The agent does this by loading an m-let text file, which specifies information on the m-beans to be obtained. The information on each m-bean is specified in a single instance of a tag, called the MLET tag. The location of the m-let text file is specified by a URL. When an m-let text file is loaded, an instance of each m-bean specified in the file is created. The operation of the m-let service is illustrated in Figure 14-1.

Using the m-let services involves:

Figure 14-1. Operation of the M-Let Service

fig737.epsi

The MLET Tag

The MLET tag specifies an m-bean to be obtained. The syntax of the MLET tag is similar to the syntax of the APPLET HTML tag.

<MLET
   CODE=class | OBJECT=serfile
   ARCHIVE="archivelist"
   [CODEBASE=codebaseURL]
   [NAME=mbeanname]
   [PERSISTENT=true|false]
   [VERSION=version]
>
   [paramlist]
</MLET>

CODE=class

This attribute specifies the full Java class name, including package name, of the m-bean to be obtained. The compiled .class file of the m-bean must be contained in one of the .jar files specified by the ARCHIVE attribute. Either CODE or OBJECT must be present.

OBJECT=serfile

This attribute specifies the.ser file that contains a serialized representation of the m-bean to be obtained. This file must be contained in one of the .jar files specified by the ARCHIVE attribute. If the .jar file contains a directory hierarchy, specify the path of the file within this hierarchy. Otherwise a match will not be found. Either CODE or OBJECT must be present.

ARCHIVE="archivelist"

This mandatory attribute specifies one or more .jar files containing m-beans or other resources used by the m-bean to be obtained. One of the .jar files must contain the file specified by the CODE or OBJECT attribute. If archivelist contains more than one file:

All .jar files in archivelist must be stored in the directory specified by the code base URL.

CODEBASE=codebaseURL

This optional attribute specifies the code base URL of the m-bean to be obtained. It identifies the directory that contains the .jar files specified by the ARCHIVE attribute. Specify this attribute only if the .jar files are not in the same directory as the m-let text file. If this attribute is not specified, the base URL of the m-let text file is used.


Note - Multiple MLET tags with the same code base URL share the same instance of the MLetClassLoader class.


NAME=mbeanname

This optional attribute specifies the object name to be assigned to the m-bean instance when the m-let service registers it. If mbeanname starts with the colon character (:), the domain part of the object name is the domain of the agent. The m-let service invokes the getDomain() method of the Framework class to obtain this information.

PERSISTENT=true | false

This optional attribute specifies whether the m-bean instance will be persistent. If the attribute is true, the m-bean will be persistent. If the attribute is false the m-bean will not be persistent. If this attribute is omitted, the m-bean will not be persistent.

VERSION=version

This optional attribute specifies the version number of the m-bean and associated .jar files to be obtained. This version number can be used to specify that the .jar files are loaded from the server to update those stored locally in the cache the next time the m-let text file is loaded. The version parameter must be one or more non-negative decimal integers each separated by a dot from the one that precedes it. For information on how to use version control with the m-let service, see Version Control Mechanism.

paramlist

This optional attribute specifies a list of one or more parameters for the m-bean to be instantiated. This list is passed as a modification list to the initCmf() method of the m-bean to be instantiated. Each parameter in paramlist corresponds to a modification in the modification list. Use the following syntax to specify each item in paramlist:
<PARAM NAME=propertyName VALUE=value>

where:

The m-let service passes all the values in the modification list as String objects. Make sure that the initCmf() method of the m-bean includes the code required to cast each String object into an instance of the appropriate type. For example, if the property is an integer, you have to cast the String object passed by the m-let service into an int.

Example

Example 14-1 shows an example of an MLET tag in an m-let text file. In this example, the m-bean Example.class is present in the file example1.jar. The file example2.jar contains other resources required by the m-bean Example.class. The .jar files are stored in the directory specified by the URL http://www.foo.com/jars. The domain part of the object name to be assigned to the m-bean instance is the domain of the agent. The m-let service invokes the getDomain() method of the Framework class to obtain this information. The text example.instance=1 makes up the remainder of the object name. Version 1.0 of the m-bean Example.class is to be obtained.

Example 14-1. Example MLET Tag
<MLET
   CODE=Example.class
   ARCHIVE="example1.jar, example2.jar"
   CODEBASE=http://www.foo.com/jars
   NAME=:example.instance=1
   PERSISTENT=true
   VERSION=1.0
>
</MLET>

Security

The m-let service derives security from tools provided as part of the JavaŽ 2 SDK, Standard Edition, version 1.2. Dynamically loaded code runs in a specific protection domain that is defined by a given codebase and signer or set of signers. Protection domains each have a set of permissions that are defined in a policy file. Use the policytool to write the policy file and the jarsigner tool to sign your .jar files. The policytool and jarsigner tools are supplied with the JavaŽ 2 SDK. For further information on policytool and policy files, see the JavaŽ 2 SDK product documentation.

When the policy file has been created, run the m-let service with the default security manager specifying the location of the policy file.

Adding the M-Let Service

Before using the m-let service, you must add it to an agent. To add the m-let service, create an instance of one of these classes:

Only one instance of the m-let service is allowed in a Java Dynamic Management agent. If there is already an instance of one of the above classes in an agent, it is not permitted to create an instance of the other class in the same agent.

Example 14-2 shows how to add the m-let service without version control to an agent. For an example of how to add the m-let service with version control, refer to Applying Version Control.

Example 14-2. Adding the M-Let Service (no Version Control)
// Add the simple m-let service
//
String mletName = "com.sun.jaw.impl.agent.services.mlet.MLetSrv";
MLetSrv mletSrv = (MLetSrv) cmf.newObject( mletName, domain + ":" +
    "com.sun.jaw.impl.agent.services.mlet.MLetSrvMO", null );

Loading an M-Let Text File

To load an m-let text file, an agent or manager application must invoke a load URL method of an instance of the m-let service. When the m-let text file is loaded, an instance of the m-bean specified in each MLET tag is created. By repeatedly invoking the load URL method, it is possible to populate a Java Dynamic Management agent while it is running. The m-let service provides methods for loading an m-let text file with or without error checking.

Loading and Error Checking an M-Let Text File

The m-let service provides different methods for loading a URL, depending on whether the method is to be invoked by an agent or a manager. Each of these methods has a different return value. To load an m-let text file with error checking, invoke one of these methods, depending on the type of application you are writing:

Application

Method

Returns

Agent

performLocalLoadURL()

A vector of object references to the m-beans instantiated.

Manager

performRemoteLoadURL()

A vector of m-let tags that define the m-beans instantiated.

By parsing the vector returned, it is possible to perform error checking when an m-let text file is loaded.

Example 14-3 shows code required to enable an agent to load an m-let text file.

Example 14-3. Loading an M-Let Text File
Vector beans = mlet.performLocalLoadURL( "http://www.foo.com/jars/test.htm" );

Parsing the Vector Returned in an Agent

When the performLocalLoadURL() method is invoked by an agent, it returns a vector containing one entry per MLET tag in the m-let text file loaded. Each entry specifies either the reference of the m-bean instantiated, or a throwable object (that is, an error or an exception) if the m-bean cannot be instantiated. Parsing the vector returned by the performLocalLoadURL() method enables you to:

An example of parsing the vector returned by a load URL method invoked by an agent is shown in Example 14-4.

Example 14-4. Parsing the Vector Returned in an Agent
// Invoke load URL method of the m-let service (agent side)
//
try {
   System.out.println("Invoking load URL method on an agent...");
   Vector beans = mlet.performLocalLoadURL("file:/home/mletdir/test.txt");
   if (beans.isEmpty()) {
      System.out.println("Vector beans is empty");
   } else {
      System.out.println("---> Start walking through Vector beans");
      int id = 0;
      Object instance;
      ObjectName mybeanName;
      for (Enumeration e = beans.elements(); e.hasMoreElements(); ) {
         id = id + 1;
         instance = e.nextElement();
            if (instance instanceof Throwable) {
               System.out.println("Error or exception, problem while creating
                                   m-bean --->");

               System.out.println("The throwable object is: " + instance);
            } else {
               System.out.println("M-bean creation succeeded --->");
               System.out.println("The object reference of the m-bean is: " +
                                   instance);
               // If the instance is not registered, do it now.
               mybeanName = new ObjectName(cmf.getDomain() + ":mybean.id=" +
                                           id);
               cmf.addObject(instance, mybeanName);
           }
        }
        System.out.println("---> Stop walking through Vector beans");
    }
} catch (ServiceNotFoundException e) {
   System.err.println("Got an exception !");
   e.printStackTrace();
}

Parsing the Vector Returned in a Manager

When the performRemoteLoadURL() method is invoked by a manager, it returns a vector containing one entry per MLET tag in the m-let text file loaded. Each entry specifies either an m-let tag that defines the m-bean instantiated, or a throwable object (that is, an error or an exception) if the m-bean could not be instantiated. Parsing the vector returned by the performLocalLoadURL() method enables you to verify whether each m-bean was instantiated as requested.

An example of parsing the vector returned by a load URL method invoked by a manager is shown in Example 14-5.

Example 14-5. Parsing the Vector Returned in a Manager
// Invoke load URL method of the m-let service (manager side)
//
try {
    System.out.println("Invoking load URL method on a manager ...");
    Vector beans = mletmo.performRemoteLoadURL("file:/home/mletdir/test.txt");
    if (beans.isEmpty()) {
        System.out.println("Vector beans is empty");
    } else {
        System.out.println("---> Start walking through Vector beans");
        Object instance;
        for (Enumeration e = beans.elements(); e.hasMoreElements(); ) {
            instance = e.nextElement();
            if (instance instanceof Throwable) {
                System.out.println("Error or exception, problem while creating
                                   m-bean --->");
                System.out.println("The throwable object is: " + instance);
            } else {
                System.out.println("M-bean creation succeeded --->");
                System.out.println("The MLET tag representation of this m-bean
                                   is: " + ((MLet)instance).toString());
            }
        }
        System.out.println("---> Stop walking through Vector beans");
    }
} catch (ServiceNotFoundException e) {
    System.err.println("Got an exception !");
    e.printStackTrace();
}

Loading an M-Let Text File Without Performing Error Checks

To load an m-let text file without performing any error checking, invoke the performLoadURL() method of the m-let service. This method does not return, so no error checking is possible. It is allowed in the code of an agent or a manager. Therefore, use this method if you want to write code that can be used both for an agent and a manager. An example showing code for loading an m-let text file without performing any error checking is shown in Example 14-6.

Example 14-6. Loading an M-Let Text File Without Performing Any Error Checking
// Invoke load URL method (no error checking)
//
try {
    System.out.println("Invoking load URL method...");
    mlet.performLoadURL("file:/home/mletdir/test.txt");
} catch (ServiceNotFoundException e) {
    System.err.println("Got an exception !");
    e.printStackTrace();
}

Exception Handling

A load URL method throws an exception if any of the following are true:

Object Name of the M-Let Service Class Loader

Before instantiating an m-bean specified in an MLET tag, the m-let service creates and registers a class loader. It does this to make sure that a class loader is available that will obtain classes from the correct location. The class loader is required to load the m-bean class and the Java classes in any .jar files specified in the MLET tag. The object name of the class loader is required by any manager that needs to load classes by using this class loader (for example, a manager that invokes the cb_newMO() method and specifies this class loader). The m-let service registers the class loader it creates with an object name of the form:
defaultDomain:JavaClass.codebase=baseURL

where:

Specifying the Object Name of the M-Bean

When an m-bean specified in an MLET tag is instantiated, you can register it with the repository yourself or you can let the m-let service register the m-bean. The Java Dynamic Management Kit allows you to specify the object name of the m-bean in either of the following ways:

Use the NAME attribute of the MLET tag if an initCmf() method is defined for the m-bean and you want the NAME attribute to be passed as the object name parameter. You can also use the NAME attribute of the MLET tag for an m-bean that does not have an initCmf() method if you want the m-bean instance to be registered with the repository by the m-let service.

You can omit the NAME attribute of the MLET tag if an object name is specified in the initCmf() method. If an object name is specified in the initCmf() method, the m-bean will register with the repository using that object name. You can also omit the NAME attribute of the MLET tag for an m-bean that does not have an initCmf() method if you do not want the m-bean instance to register with the repository.

Using the NAME Attribute of the MLET Tag

If you use the NAME attribute of the MLET tag to specify the object name of the m-bean instance, the instance is registered with this name. The method invoked to register the instance depends on how the m-bean is implemented:

Omitting the NAME Attribute of the MLET Tag

If you omit the NAME attribute of the MLET tag, the method invoked to register the instance and the supplier of the object name depends on the implementation of the m-bean:

Instantiating an M-Bean From Another M-Bean

The m-let service enables you to use the initCmf() method of an m-bean that it loads to instantiate other m-beans. To do this, add code to the initCmf() method for:

This is shown in Example 14-7.

Example 14-7. Instantiating an M-Bean From Another M-Bean
public void initCmf(Framework cmf, ObjectName name) throws
  IllegalAccessException, ServiceNotFoundException,
  InstanceAlreadyExistException {

  // Add this m-bean under the control of the framework.
  //
  cmf.addObject(this, name);

  // Instantiate and register an instance of the m-bean MyBean.
  // NOTE:
  //      By adding the m-bean in this way to the framework,
  //      the initCmf method IS NOT called.
  //

  ObjectName mbNameA = new ObjectName(cmf.getDomain()+":MyBean.id=A");
  MyBean mbA = new MyBean();
  cmf.addObject(mbA, mbNameA);

  // Retrieve the codebase of the MLetClassLoader that loaded this class,
  // and compose the MLetClassLoader object name.
  String codebase =
((MLetClassLoader)this.getClass().getClassLoader())
.getCodeBase().toString();
  ObjectName mletloader = new
ObjectName(cmf.getDomain()+":"+ServiceName.MLETLOADER+"
.codebase="+codebase);

  // Instantiate and register a new m-bean in the agent.
  ObjectName mbNameB = new ObjectName(cmf.getDomain()+":MyBean.id=B");
  MyBean mbB = (MyBean) cmf.newObject("MyBean", mbNameB, mletloader, null);
}

Instantiating and Running an M-Bean

If you want an m-bean which has been instantiated using the m-let service to start automatically as soon as it is instantiated, make sure that the m-bean implements the java.lang.Runnable interface. When the m-let service instantiates the m-bean, it creates a new thread and invokes the run() method of the m-bean.

Caching and Version Control

Applying version control to an m-bean enables the m-let service to reduce network traffic by not loading .jar files from a server unless it is necessary. When you apply version control, .jar files are stored locally in the cache. Unless the m-let text file specifies that new versions must be loaded from the server, .jar files are loaded from the cache. For more information, see Cache Directories. If you do not apply version control to an m-bean, the .jar files are always loaded from the server when an m-let text file is loaded.

Applying Version Control

Applying version control to an m-bean loaded by the m-let service involves:

Cache Directories

The directory in which cache files are stored by default depends on the environment:

Operating Environment

Default Cache Directory

Solaris

installDir/SUNWconn/jaw/var/mletcache

Windows NT

installDir\SUNWconn\jaw\var\mletcache

To change the default cache directory, invoke the setCacheDirectory() method of the m-let service instance. The setCacheDirectory() method does not create the directory that you specify, the directory must already exist. Example 14-8 shows how to add the m-let service with version control and change the cache directory.

Example 14-8. M-Let Service with Version Control
// Add the MLetCacheVersionSrv
//
String mletName = "com.sun.jaw.impl.agent.services.mlet.MLetCacheVersionSrv";
MLetCacheVersionSrv mletSrv = (MLetCacheVersionSrv)
        cmf.newObject(mletName, domain + ":" +
        "com.sun.jaw.impl.agent.services.mlet.MLetCacheVersionSrvMO", null);

// Set the directory for caching if you want.
mletSrv.setCacheDirectory("/home/foo");

Version Control Mechanism

When the m-let text file is loaded, the m-let service compares the version number specified in the MLET tag with the current version number of the m-bean, which is stored locally. If the version number specified in the MLET tag is greater than the current version number, the .jar files are loaded from the server to replace those stored locally in the cache. The current version number is updated to the value specified in the MLET tag. If the version number specified in the MLET tag is less than or equal to the current version number, the .jar files in the cache are used.

Implementing Your Own Version Control Mechanism

To implement your own version control mechanism, create a Java class that extends the com.sun.jaw.impl.agent.services.mlet.MLetCacheVersionSrv class. In your Java class, override the check() method of the com.sun.jaw.impl.agent.services.mlet.MLetCacheVersionSrv class.


[ Previous ][ Home ][ Next ]
M-Let, Bootstrap and Launcher Services[ Up ]Bootstrap Service