Saturday, July 2, 2011

Extending OpenNMS

The OpenNMS installation directory contains etc/ directory which contains all kind of configuration files which require to run openNMS, it has various configuration files for each daemon module, for example for capability daemon there is capsd.xml for collector daemon it has capsd.xml and for dataCollection definition it has jmx-dataCollection.xml for Mbeans definition, similarity for snmp there is dataCollection.xml for defining what OID’s need to be collected for SNMP services.

Now this etc directory also contains service-configuration.xml which has all module definition plus which method to be invoked for loading the module. These modules can be daemon or non daemon depending upon the requirement. all module follows standard MBean criteria. These modules are started in the sequence they are mention in the file. I mean top most will be executed first and the bottom most ( which is embedded jetty-web server) will be the last.

 

<service-configuration>
  <service>
    <name>:Name=XSLTProcessor</name>
    <class-name>mx4j.tools.adaptor.http.XSLTProcessor</class-name>
  </service>
  <service>
    <name>:Name=HttpAdaptor</name>
    <class-name>mx4j.tools.adaptor.http.HttpAdaptor</class-name>
    <attribute>
      <name>Port</name>
      <value type="java.lang.Integer">8180</value>
    </attribute>
    <attribute>
      <name>Host</name>
…………………………………….

If we add new service definition here, the OpenNMS will load our service ..

for example let say we want to delete all logs or previous data collected on starting up openNMS, we have to add our service in this xml then only openNMS could start our service.

<service-configuration>

<service>
  <name>OurService:Name=CleanupService</name>
  <class-name>org.ourservice.Clean</class-name>
  <invoke at="start" pass="0" method="start"/>

</service>
  <service>
    <name>:Name=XSLTProcessor</name>
    <class-name>mx4j.tools.adaptor.http.XSLTProcessor</class-name>
  </service>
  <service>
    <name>:Name=HttpAdaptor</name>
    <class-name>mx4j.tools.adaptor.http.HttpAdaptor</class-name>
    <attribute>
      <name>Port</name>
      <value type="java.lang.Integer">8180</value>
    </attribute>
    <attribute>
      <name>Host</name>

now CleanupService will be triggered first. for starting this service start method will be invoked of Clean class. The clean Class must implement MBean.
create CleanMBean interface and declare start method signature.

package org.ourservice;

public interface CleanMBean {
    public void start();
}

now create Clean class and implement CleanMBean interface, also implement logic to clean the data.

package org.ourservice;

public class Clean implements CleanMBean {
    public void start(){
       System.out.println(“Cleaned all”);

     }

}

 

 

After compiling the Clean class and other dependant classes. create classes directory inside openNMS installation directory and put all our classes inside. then start openNMS.

Java5 Instumentation API

The instrumentation API is for run time byte manupulation, or you can say bytecode engineering. 

we have to define our instrumentation agent which consist starting point same as main method of any java application with different arguments.

String : arguments to this agent..

Instrumentation object, instrumentation agent is a class with a special method, with a predefined signature, that the JVM will invoke before the rest of the application for you to set up any instrumentation code. Generally, instrumentation is the act of transforming classes for profiling purposes: for example, an interesting feature provided by the instrumentation framework is the ability to measure the memory usage of an object. 
 

import java.lang.instrument.Instrumentation;

public class MyAgent {
    public static void premain(String agentArguments,
            Instrumentation instrumentation) {

        MyTransFormer transformer = new MyTransFormer();
        instrumentation.addTransformer(transformer);
        Node node = new Node();
        long size = instrumentation.getObjectSize(node);
        System.out.println("size of "+ node.getClass().getSimpleName() + size);
    }
}

we have compiled the agent class and  we need to package it into a jar , we also need to create a manifest file

Premain-Class: MyAgent 
java -javaagent:myagent.jar TestMain
 
creating transformer
import java.lang.instrument.ClassFileTransformer; 
import java.security.ProtectionDomain;

public class MyTransFormer implements ClassFileTransformer {


    public MyTransFormer() {
        super();
    }


public byte[] transform(ClassLoader loader, String className,
            Class redefiningClass, ProtectionDomain domain, byte[] bytes) {
        // some changes in byte code // there are some standard API for byte
        // code modification exp: BCEL, ASM etc…
        return bytes;
    }
}


There are some links i went while reading .



  1. http://www.javalobby.org/java/forums/t19309.html#92037417

  2. http://www.cs.nuim.ie/~jpower/Research/instrument/#examples

  3. http://www.javamex.com/tutorials/memory/instrumentation.shtml

Search Ranjeet's Blog