Package org.jboss.soa.esb.listeners.message

Source Code of org.jboss.soa.esb.listeners.message.ServiceMessageCounter$LongHolder

/*
* JBoss, Home of Professional Open Source
* Copyright 2006, JBoss Inc., and individual contributors as indicated
* by the @authors tag. See the copyright.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/

package org.jboss.soa.esb.listeners.message;

import java.io.Serializable;
import java.lang.reflect.Method;
import java.util.Enumeration;
import java.util.Hashtable;

import javax.management.Attribute;
import javax.management.AttributeList;
import javax.management.AttributeNotFoundException;
import javax.management.DynamicMBean;
import javax.management.InstanceAlreadyExistsException;
import javax.management.InstanceNotFoundException;
import javax.management.IntrospectionException;
import javax.management.InvalidAttributeValueException;
import javax.management.MBeanAttributeInfo;
import javax.management.MBeanException;
import javax.management.MBeanInfo;
import javax.management.MBeanNotificationInfo;
import javax.management.MBeanOperationInfo;
import javax.management.MBeanRegistrationException;
import javax.management.MBeanServer;
import javax.management.NotCompliantMBeanException;
import javax.management.Notification;
import javax.management.NotificationBroadcasterSupport;
import javax.management.ObjectName;
import javax.management.ReflectionException;

import org.apache.log4j.Logger;
import org.jboss.mx.util.MBeanServerLocator;
import org.jboss.soa.esb.helpers.ConfigTree;
import org.jboss.soa.esb.listeners.ListenerTagNames;

/**
* Service message counter is a MBean that displays an action-by-action breakdown of
* how many failed and successful messages have been processed and shows the processing time
* of each.
*
* Alert thresholds have also been added to this bean.   There are thresholds on the
* size of the message as well as the length of the message for both services and for
* individual actions.   The alerts will produce a log4j warning as well as provide for the
* option of JMX integration with other products.
*
* @author <a href="mailto:tcunning@redhat.com">tcunning@redhat.com</a>
* @since Version 4.2
*/
public class ServiceMessageCounter extends NotificationBroadcasterSupport
  implements DynamicMBean, Serializable {
  private Hashtable<String, IntHolder> actionCounterHash;
  private Hashtable<String, IntHolder> actionFailedCounterHash;
  private Hashtable<String, LongHolder> actionProcessTimeHash;
  private Hashtable<String, LongHolder> actionBytesProcessedHash;
  private Hashtable<String, LongHolder> actionBytesFailedHash;

  private Hashtable<String, Long> actionLengthThresholdHash;
  private Hashtable<String, Long> actionTimeThresholdHash;

  private String serviceDescription = "";
  private String[] actionNames;
  private final ObjectName listObjectName ;
 
  private int serviceCount;
  private long bytesFailed;
  private long bytesProcessed;
  private long bytesOverall;
  private long timeProcessed;
 
  private int notificationindex;
  private Long alertTime = new Long("-1");
  private Long alertLength = new Long("-1");

  public static final String SERVICE_LENGTH_NOTIFICATION_TYPE = "org.jboss.esb.message.service.length.alert";
  public static final String SERVICE_TIME_NOTIFICATION_TYPE = "org.jboss.esb.message.service.time.alert";
  public static final String ACTION_LENGTH_NOTIFICATION_TYPE = "org.jboss.esb.message.action.length.alert";
  public static final String ACTION_TIME_NOTIFICATION_TYPE = "org.jboss.esb.message.action.time.alert";

  public static final String RESET_COUNTER = "resetCounter";
  private static final String MESSAGE_COUNTER = "messages successfully processed count";
  private static final String FAILED_MESSAGE_COUNTER = "messages failed count";
  private static final String PROCESSING_TIME = "processing time";
  private static final String BYTES_FAILED = "failed bytes";
  private static final String BYTES_PROCESSED = "processed bytes";
 
  private static final String OVERALL_SERVICE_COUNT = "overall service message count";
  private static final String OVERALL_BYTES = "overall service count bytes";
  private static final String OVERALL_BYTES_PROCESSED = "overall processedbytes";
  private static final String OVERALL_BYTES_FAILED = "overall failed bytes";
  private static final String OVERALL_TIME_PROCESSED = "overall service time processed";
 
  private static final String SERVICE_DESCRIPTION = "service description";
  private static final String ALERT_TIME = "service alert time";
  private static final String ALERT_LENGTH = "service alert length";
  private static final String ALERT_TIME_DESC = "set service alert time";
  private static final String ALERT_LENGTH_DESC = "set service alert desc";
 
  private static final String ACTION_ALERT_TIME = "action alert time";
  private static final String ACTION_ALERT_LENGTH = "action alert length";
  private static final String ACTION_ALERT_TIME_DESC = "set action alert time";
  private static final String ACTION_ALERT_LENGTH_DESC = "set action alert length";
 
  private static final int NANOSECONDS_PER_MILLISECONDS = 1000000;
 
  private static final Logger logger = Logger.getLogger(ServiceMessageCounter.class);

  public String getDescription() {
    return serviceDescription;
  }
 
  public void setServiceDescription(String serviceDescription) {
    this.serviceDescription = serviceDescription;
  }
 
  /**
   * Service alert time getter
   * @return max message processing time for the service before an alert is fired
   */
  public Long getAlertTime() {
    return alertTime;
  }
 
  /**
   * Service alert time setter
   * @param alertTime max message size passing through service before an alert is fired
   */
  public void setAlertTime(Long alertTime) {
    this.alertTime = alertTime;
  }

  /**
   * Service alert length getter
   * @return max length of message passing through service before an alert is fired
   */
  public Long getAlertLength() {
    return alertLength;
  }

  /**
   * Service alert length setter
   * @param alertLength max message processing time for the service before an alert is fired
   */
  public void setAlertLength(Long alertLength) {
    this.alertLength = alertLength;
  }

  /**
   * Action alert time getter
   * @return max message processing time before an alert is fired
   */
  public Long getActionAlertTime() {
    return alertTime;
  }

  /**
   * Action alert time setter
   * @param alertLength max time (ms) the action can take before an alert is fired.
   */
  public void setActionAlertTime(Long alertTime) {
    this.alertTime = alertTime;
  }
 
  /**
   * Action alert length getter
   * @return max message size passing through action before an alert is fired
   */
  public Long getActionAlertLength() {
    return alertLength;
  }

  /**
   * Action alert length setter
   * @param alertLength max message size passing through action before an alert is fired
   */
  public void setActionAlertLength(Long alertLength) {
    this.alertLength = alertLength;
  }
    
  /**
   * Constructor
   * @param f_config config tree
   * @param objectName The name to use as the MBean.
   */
  public ServiceMessageCounter(ConfigTree f_config, final String objectName) {
    actionCounterHash = new Hashtable<String, IntHolder>();
    actionFailedCounterHash = new Hashtable<String, IntHolder>();
    actionProcessTimeHash = new Hashtable<String, LongHolder>();
    actionBytesProcessedHash = new Hashtable<String, LongHolder>();
    actionBytesFailedHash = new Hashtable<String, LongHolder>();

    actionLengthThresholdHash = new Hashtable<String, Long>();
    actionTimeThresholdHash = new Hashtable<String, Long>();
   
    notificationindex = 0;
   
    if (f_config.getAttribute(ListenerTagNames.SERVICE_ALERT_LENGTH_TAG) != null) {
      alertLength = new Long(f_config.getAttribute(ListenerTagNames.SERVICE_ALERT_LENGTH_TAG));
    }
   
    if (f_config.getAttribute(ListenerTagNames.SERVICE_ALERT_TIME_TAG) != null) {
      alertTime = new Long(f_config.getAttribute(ListenerTagNames.SERVICE_ALERT_TIME_TAG));
    }
 
    if (f_config.getAttribute(ListenerTagNames.SERVICE_DESCRIPTION_TAG) != null) {
      serviceDescription = f_config.getAttribute(ListenerTagNames.SERVICE_DESCRIPTION_TAG);
    }
   
    init(f_config);
    ObjectName listObjectName = null ;
    try
    {
      listObjectName = new ObjectName("jboss.esb:" + objectName);
    }
    catch (final Exception ex)
    {
      logger.error("Unexpected exception creating MBean object name, counter will be unregistered", ex);
    }
    this.listObjectName = listObjectName ;
  }
 
  /**
   * Return an action id.   If there's an action name, use that, if not,
   * use the "action" attribute on the action.
   * @param ct config tree
   * @return action id
   */
  private String getActionId(ConfigTree ct) {
    if (ct.getAttribute("name") != null) {
      return ct.getAttribute("name");
    } else if (ct.getAttribute("action") != null) {
      return ct.getAttribute("action");
    }
    return null;
  }
 
  /**
   * Increment the total message count of this service.
   */
  public synchronized void incrementTotalCount() {
    serviceCount += 1 ;
  }
 
  /**
   * Initialize the bean.
   * @param configTree The current configuration.
   */
  private void init(final ConfigTree configTree) {
    ConfigTree[] actionList = configTree.getChildren(ListenerTagNames.ACTION_ELEMENT_TAG);
    final int numActions = actionList.length ;
    actionNames = new String[numActions] ;
   
    for (int count = 0 ; count < numActions ; count++) {
      final ConfigTree actionConfig = actionList[count] ;
      String actionId = getActionId(actionConfig);
      actionCounterHash.put(actionId + " " + MESSAGE_COUNTER, new IntHolder());
      actionFailedCounterHash.put(actionId + " " + FAILED_MESSAGE_COUNTER, new IntHolder());
      actionProcessTimeHash.put(actionId + " " + PROCESSING_TIME, new LongHolder());
      actionBytesFailedHash.put(actionId + " " + BYTES_FAILED, new LongHolder());
      actionBytesProcessedHash.put(actionId + " " + BYTES_PROCESSED, new LongHolder());
      if (actionConfig.getAttribute(ListenerTagNames.ACTION_ALERT_LENGTH_TAG) != null) {
        actionLengthThresholdHash.put(actionId, new Long(actionConfig.getAttribute(ListenerTagNames.ACTION_ALERT_LENGTH_TAG)));
      }
      if (actionConfig.getAttribute(ListenerTagNames.ACTION_ALERT_TIME_TAG) != null) {
        actionTimeThresholdHash.put(actionId, new Long(actionConfig.getAttribute(ListenerTagNames.ACTION_ALERT_TIME_TAG)));
      }
      actionNames[count] = actionId ;
    }
    serviceCount = Integer.valueOf(0);
    bytesProcessed = Long.valueOf(0);
    bytesFailed = Long.valueOf(0);
    bytesOverall = Long.valueOf(0);
    timeProcessed = new Long (0);
  }
 
  /**
   * Reset the counters - set all the entries in the action counter hash
   * and in the action process time hash to zero.
   */
  public synchronized void resetCounter() {
    serviceCount = 0 ;
    bytesProcessed = 0 ;
    bytesFailed = 0 ;
    bytesOverall = 0;
    timeProcessed = 0;
       
    for (String key : actionCounterHash.keySet()) {
      actionCounterHash.put(key, new IntHolder());
    }
   
    for (String key : actionFailedCounterHash.keySet()) {
      actionFailedCounterHash.put(key, new IntHolder());
    }
   
    for (String key : actionProcessTimeHash.keySet()) {
      actionProcessTimeHash.put(key, new LongHolder());
    }
   
    for (String key : actionBytesFailedHash.keySet()) {
      actionBytesFailedHash.put(key, new LongHolder());
    }
   
    for (String key : actionBytesProcessedHash.keySet()) {
      actionBytesProcessedHash.put(key, new LongHolder());
    }
  }
 
  /**
   *  This creates the MBeanInfo object provided.     We are returning generic
   *  text for the attribute descriptions (the word Property and the name of the
   *  attribute), all of the attributes are read-only, and we provide four
   *  invocation methods - start/stop/initialise/destroy on the Lifecycle.
   */
    public synchronized MBeanInfo getMBeanInfo() {
   
    int count = actionCounterHash.size() + actionProcessTimeHash.size()
      + actionFailedCounterHash.size() + actionBytesProcessedHash.size()
      + actionBytesFailedHash.size() + actionLengthThresholdHash.size()
      + actionTimeThresholdHash.size() + 8; // the extra 6 here are overall service count, failed byte size
                        // processed byte size, overall bytes, alert time, and alert
                        // length
        MBeanAttributeInfo[] attrs = new MBeanAttributeInfo[count];
        int counter = 0;
             
    for (String key : actionCounterHash.keySet()) {
            attrs[counter] = new MBeanAttributeInfo(
                    key, "java.lang.Integer", "Property " + key, true, false, false);
            counter++;
    }
   
    for (String key : actionProcessTimeHash.keySet()) {
            attrs[counter] = new MBeanAttributeInfo(
                    key, "java.lang.Double", "Property " + key, true, false, false);
            counter++;
    }
   
    for (String key : actionFailedCounterHash.keySet()) {
            attrs[counter] = new MBeanAttributeInfo(
                    key, "java.lang.Integer", "Property " + key, true, false, false);
            counter++;
    }
   
    for (String key : actionBytesFailedHash.keySet()) {
      attrs[counter] = new MBeanAttributeInfo(
          key, "java.lang.Long", "Property " + key, true, false, false);
      counter++;
    }
   
    for (String key : actionBytesProcessedHash.keySet()) {
      attrs[counter] = new MBeanAttributeInfo(
          key, "java.lang.Long", "Property " + key, true, false, false);
      counter++;
    }   
   
    MBeanAttributeInfo overallCount = new MBeanAttributeInfo(OVERALL_SERVICE_COUNT, "java.lang.Integer",
        "Property " + OVERALL_SERVICE_COUNT, true, false, false);
    attrs[counter] = overallCount;
    counter++;
   
    MBeanAttributeInfo overallBytesProcessed = new MBeanAttributeInfo(OVERALL_BYTES_PROCESSED, "java.lang.Long",
        "Property " + OVERALL_BYTES_PROCESSED, true, false, false);
    attrs[counter] = overallBytesProcessed;
    counter++;
   
    MBeanAttributeInfo overallBytesFailed = new MBeanAttributeInfo(OVERALL_BYTES_FAILED, "java.lang.Long",
        "Property " + OVERALL_BYTES_FAILED, true, false, false);
    attrs[counter] = overallBytesFailed;
    counter++;
   
    MBeanAttributeInfo overallBytes = new MBeanAttributeInfo(OVERALL_BYTES, "java.lang.Long",
        "Property " + OVERALL_BYTES, true, false, false);
    attrs[counter] = overallBytes;
    counter++;   

    MBeanAttributeInfo overallTimeProcessed = new MBeanAttributeInfo(OVERALL_TIME_PROCESSED, "java.lang.Long",
        "Property " + OVERALL_TIME_PROCESSED, true, false, false);
    attrs[counter] = overallTimeProcessed;
    counter++;   
   
    MBeanAttributeInfo description = new MBeanAttributeInfo(SERVICE_DESCRIPTION, "java.lang.String",
        "Property " + SERVICE_DESCRIPTION, true, false, false);
    attrs[counter] = description;
    counter++;
   
    try {
      Method alertTimeGetter = this.getClass().getMethod("getAlertTime", new Class[0]);
      Method alertTimeSetter = this.getClass().getMethod("setAlertTime", new Class[]{Long.class});
      MBeanAttributeInfo alertTimeInfo = new MBeanAttributeInfo(ALERT_TIME, ALERT_TIME_DESC,
          alertTimeGetter, alertTimeSetter);
      attrs[counter] = alertTimeInfo;
      counter++;
    } catch (SecurityException e) {
      e.printStackTrace();
    } catch (NoSuchMethodException e) {
      e.printStackTrace();
    } catch (IntrospectionException e) {
      e.printStackTrace();
    }
   
    try {
      Method alertLengthGetter = this.getClass().getMethod("getAlertLength", new Class[0]);
          Method alertLengthSetter = this.getClass().getMethod("setAlertLength", new Class[]{Long.class});
          MBeanAttributeInfo alertLengthInfo = new MBeanAttributeInfo(ALERT_LENGTH, ALERT_LENGTH_DESC,
              alertLengthGetter, alertLengthSetter);
          attrs[counter] = alertLengthInfo;
          counter++;
    } catch (SecurityException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (NoSuchMethodException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (IntrospectionException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
           
    try {
      Enumeration<String> keys = actionLengthThresholdHash.keys();
      while (keys.hasMoreElements()) {
        String actionId = keys.nextElement();
        Method alertLengthGetter = this.getClass().getMethod("getActionAlertLength", new Class[0]);
        Method alertLengthSetter = this.getClass().getMethod("setActionAlertLength", new Class[]{Long.class});
        MBeanAttributeInfo alertLengthInfo = new MBeanAttributeInfo(actionId + " " + ACTION_ALERT_LENGTH,
            actionId + " " + ACTION_ALERT_LENGTH_DESC,
            alertLengthGetter, alertLengthSetter);
        attrs[counter] = alertLengthInfo;
        counter++;
      }
    } catch (SecurityException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (NoSuchMethodException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (IntrospectionException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }

    try {
      Enumeration<String> keys = actionTimeThresholdHash.keys();
      while (keys.hasMoreElements()) {
        String actionId = keys.nextElement();
        Method alertLengthGetter = this.getClass().getMethod("getActionAlertTime", new Class[0]);
        Method alertLengthSetter = this.getClass().getMethod("setActionAlertTime", new Class[]{Long.class});
        MBeanAttributeInfo alertLengthInfo = new MBeanAttributeInfo(actionId + " " + ACTION_ALERT_TIME,
            actionId + " " + ACTION_ALERT_TIME_DESC,
            alertLengthGetter, alertLengthSetter);
        attrs[counter] = alertLengthInfo;
        counter++;
      }
    } catch (SecurityException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (NoSuchMethodException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    } catch (IntrospectionException e) {
      // TODO Auto-generated catch block
      e.printStackTrace();
    }
    MBeanNotificationInfo[] notifications = getNotificationInfo();
   
        MBeanOperationInfo[] opers = {
          new MBeanOperationInfo(
              RESET_COUNTER, "Reset the counter",
                  null, "void", MBeanOperationInfo.ACTION)
        };
        return new MBeanInfo(
                this.getClass().getName(), "Service Message Counter MBean",
                attrs, null, opers, notifications); // notifications
  }

  /* (non-Javadoc)
   * @see javax.management.DynamicMBean#getAttribute(java.lang.String)
   */
  public synchronized Object getAttribute(String key) throws AttributeNotFoundException, MBeanException, ReflectionException {
      if (actionCounterHash.containsKey(key)) {
        return actionCounterHash.get(key).value;
      } else if (actionProcessTimeHash.containsKey(key)) {
        long processTotal = actionProcessTimeHash.get(key).value;
        String actionId = key.substring(0, key.indexOf(PROCESSING_TIME)-1);
        int successCount = actionCounterHash.get(actionId + " " + MESSAGE_COUNTER).value;
        Double value = null;
       
        if (successCount > 0) {
          value = ((double) processTotal / successCount);
        } else {
          value = null;
        }
        return value;
      } else if (actionFailedCounterHash.containsKey(key)) {
        return actionFailedCounterHash.get(key).value;
      } else if (actionBytesFailedHash.containsKey(key)) {
        return actionBytesFailedHash.get(key).value;
      } else if (actionBytesProcessedHash.containsKey(key)) {
        return actionBytesProcessedHash.get(key).value;
      } else if (OVERALL_SERVICE_COUNT.equals(key)) {
        return serviceCount;
      } else if (OVERALL_BYTES_PROCESSED.equals(key)) {
        return bytesProcessed;
      } else if (OVERALL_BYTES_FAILED.equals(key)) {
        return bytesFailed;
      } else if (OVERALL_BYTES.equals(key)) {
        return bytesOverall;
      } else if (OVERALL_TIME_PROCESSED.equals(key)) {
        return timeProcessed;
      } else if (ALERT_TIME.equals(key)) {
        return alertTime;
      } else if (ALERT_LENGTH.equals(key)) {
        return alertLength;
      } else if (SERVICE_DESCRIPTION.equals(key)) {
        return serviceDescription;
      } else if (key.endsWith(ACTION_ALERT_LENGTH)) {
        String temp = key.replace(" " + ACTION_ALERT_LENGTH, "");
        return actionLengthThresholdHash.get(temp);
      } else if (key.endsWith(ACTION_ALERT_TIME)) {
        String temp = key.replace (" " + ACTION_ALERT_TIME, "");
        return actionTimeThresholdHash.get(temp);
      }
      return null;
    }

  /* (non-Javadoc)
   * @see javax.management.DynamicMBean#getAttributes(java.lang.String[])
   */
  public synchronized AttributeList getAttributes(String[] arg0) {
    AttributeList attributeList = new AttributeList();
    for (String key : actionCounterHash.keySet()) {
      Attribute at = new Attribute(key, actionCounterHash.get(key).toString());
      attributeList.add(at);
    }
   
    Attribute overallCount = new Attribute(OVERALL_SERVICE_COUNT, serviceCount);
    attributeList.add(overallCount);
   
    for (String key : actionProcessTimeHash.keySet()) {
      long processTotal = actionProcessTimeHash.get(key).value;
      String actionId = key.substring(0, key.indexOf(PROCESSING_TIME));
      IntHolder successCount = actionCounterHash.get(actionId + " " + MESSAGE_COUNTER);
      String avgTime = null;
      if (successCount != null && successCount.value > 0 ) {
        avgTime = ((double) processTotal / successCount.value) + " ns";
      }
      Attribute at = new Attribute(key, avgTime);
      attributeList.add(at);
    }
   
    for (String key : actionFailedCounterHash.keySet()) {
      Attribute at = new Attribute(key, actionFailedCounterHash.get(key).toString());
      attributeList.add(at);
    }

    for (String key : actionBytesFailedHash.keySet()) {
      Attribute at = new Attribute(key, actionBytesFailedHash.get(key).toString());
      attributeList.add(at);
    }
   
    for (String key : actionBytesProcessedHash.keySet()) {
      Attribute at = new Attribute(key, actionBytesProcessedHash.get(key).toString());
      attributeList.add(at);
    }
   
    return attributeList;
  }

  /* (non-Javadoc)
   * @see javax.management.DynamicMBean#invoke(java.lang.String, java.lang.Object[], java.lang.String[])
   */
  public Object invoke(String method, Object[] arg1, String[] arg2) throws MBeanException, ReflectionException {
    if (method.equalsIgnoreCase(RESET_COUNTER)) {
        resetCounter();
      return "Invoking the " + method + " on the lifecycle.";
    } else {
      throw new ReflectionException(new NoSuchMethodException(method));
    }
  }

  /* (non-Javadoc)
   * @see javax.management.DynamicMBean#setAttribute(javax.management.Attribute)
   */
  public void setAttribute(Attribute arg0) throws AttributeNotFoundException, InvalidAttributeValueException, MBeanException, ReflectionException {
    if (ALERT_TIME.equals(arg0.getName())) {
      alertTime = (Long) arg0.getValue();
    } else if (ALERT_LENGTH.equals(arg0.getName())) {
      alertLength = (Long) arg0.getValue();
    } else if (arg0.getName().endsWith(ACTION_ALERT_LENGTH)) {
        String temp = arg0.getName().replace(" " + ACTION_ALERT_LENGTH, "");
        actionLengthThresholdHash.remove(temp);
        actionLengthThresholdHash.put(temp, (Long) arg0.getValue());
      } else if (arg0.getName().endsWith(ACTION_ALERT_TIME)) {
        String temp = arg0.getName().replace (" " + ACTION_ALERT_TIME, "");
        actionTimeThresholdHash.remove(temp);
        actionTimeThresholdHash.put(temp, (Long) arg0.getValue());
      }
  }

  /* (non-Javadoc)
   * @see javax.management.DynamicMBean#setAttributes(javax.management.AttributeList)
   */
  public AttributeList setAttributes(AttributeList arg0) {
    return null;
  }

  /**
   * Register this MBean with JBoss.
   */
  protected void registerMBean() {
    if (listObjectName == null) {
      return ;
    }
    MBeanServer mbeanServer = null;
    try {
      mbeanServer = MBeanServerLocator.locateJBoss();
    } catch (IllegalStateException ise) {
      // If we can't find a JBoss MBeanServer, just return
      // Needed for unit tests
      return;
    }
   
    try {
      mbeanServer.registerMBean(this, listObjectName);

      MessageAlerts alerts = new MessageAlerts();
      // Find out whether the MessageAlerts Bean has been registered
      try {
        ObjectName alertObjectName = new ObjectName("jboss.esb:service=MessageAlerts");
        if (!mbeanServer.isRegistered(alertObjectName)) {
          mbeanServer.registerMBean(alerts, alertObjectName);
        }
       
        if (isAlertsEnabled()) {
          addNotificationListener(alerts, null, null);
        }
      } catch (Exception e) {
        logger.warn("", e);
      }
    } catch (InstanceAlreadyExistsException e) {
      logger.warn("", e);
    } catch (MBeanRegistrationException e) {
      logger.warn("", e);
    } catch (NotCompliantMBeanException e) {
      logger.warn("", e);
    }
  }
 
  /**
   * Unregister this MBean with JBoss.
   */
  protected void unregisterMBean() {
    if (listObjectName == null) {
      return ;
    }
    MBeanServer mbeanServer = null;
    try {
      mbeanServer = MBeanServerLocator.locateJBoss();
    } catch (IllegalStateException ise) {
      // If we can't find a JBoss MBeanServer, just return
      // Needed for unit tests
      return;
    }
   
    try {
      mbeanServer.unregisterMBean(listObjectName);
    } catch (InstanceNotFoundException e) {
      logger.warn("", e);
    } catch (MBeanRegistrationException e) {
      logger.warn("", e);
    }
  }
 
  /*
   * Produce alerts for services if the length or time thresholds are met.
   */
  public synchronized void alertService (ActionStatusBean asb) {
    if (!(this.getAlertTime().longValue() < 0)) {
        if ( (asb.getServiceTime() / NANOSECONDS_PER_MILLISECONDS) > this.getAlertTime().longValue()) {
          String alert = this.getObjectName().toString()
              + " service alert time " + (asb.getServiceTime() / NANOSECONDS_PER_MILLISECONDS)
              + " took longer than " + this.getAlertTime()
              + " ms";
          logger.warn(alert);
          Notification n = new Notification (ALERT_TIME, this,
              notificationindex++, System.currentTimeMillis(), alert);
          sendNotification(n);
        }           
      }         
   
    if (!(this.getAlertLength().longValue() < 0)) {
      if (asb.getBytesProcessed() > this.getAlertLength().longValue()) {
          String alert = this.getObjectName().toString()
              + " service message size " + asb.getBytesProcessed()
              + " was larger than " + this.getAlertLength()
              + " bytes";
          logger.warn(alert);
          Notification n = new Notification (ALERT_LENGTH, this, 
              notificationindex++, System.currentTimeMillis(), alert);
          sendNotification(n);
      }
    }
  }

  public boolean isAlertsEnabled() {
    boolean value = ((this.getAlertLength().longValue() > 0) ||
        (this.getAlertTime().longValue() > 0) ||
        (this.getActionAlertLength().longValue() > 0) ||
        (this.getActionAlertTime().longValue() > 0));
    return value;
  }
 
  /*
   * Produce alerts for actions if the length or time thresholds are met.
   */
  public synchronized void alertAction (ActionStatusBean asb, String actionName) {
    long actionTime = -1;
    if ((actionName != null) && (actionTimeThresholdHash.containsKey(actionName))) {
      actionTime = actionTimeThresholdHash.get(actionName);
    }
    if (!(actionTime < 0)) {
        if ( (asb.getProcTime() / NANOSECONDS_PER_MILLISECONDS) > actionTime) {
          String alert = this.getObjectName().toString() + " service, " + actionName
              + " action alert time " + (asb.getProcTime() / NANOSECONDS_PER_MILLISECONDS)
              + " took longer than " + actionTime
              + " ms";
          logger.warn(alert);
          Notification n = new Notification (ACTION_ALERT_TIME, this,
              notificationindex++, System.currentTimeMillis(), alert);
          sendNotification(n);
        }           
      }         

    long actionLength = -1;
    if ((actionName != null) && (actionLengthThresholdHash.containsKey(actionName))) {
      actionLength = actionLengthThresholdHash.get(actionName);
    }
    if (!(actionLength < 0)) {
      if (asb.getBytesProcessed() > actionLength) {
          String alert = this.getObjectName().toString() + " service, " + actionName
              + " action message size " + asb.getBytesProcessed()
              + " was larger than " + actionLength
              + " bytes";
          logger.warn(alert);
          Notification n = new Notification (ACTION_ALERT_LENGTH, this,
              notificationindex++, System.currentTimeMillis(), alert);
          sendNotification(n);
      }
    }
  }
 
  /**
   * Update the ServiceMessageCounter
   * @param asb ActionStatusBean
   */
  public synchronized void update(ActionStatusBean asb) {   
    String actionName = actionNames[asb.getProcCount()];    
   
    if (ActionStatusBean.ACTION_SENT.equals(asb.getStatus())) {
      IntHolder count = actionCounterHash.get(actionName + " " + MESSAGE_COUNTER);
      count.value++ ;
      LongHolder time = actionProcessTimeHash.get(actionName + " " + PROCESSING_TIME);
      time.value += asb.getProcTime();
      timeProcessed += asb.getProcTime();
      LongHolder bProcessed = actionBytesProcessedHash.get(actionName + " " +  BYTES_PROCESSED);
      bProcessed.value += asb.getBytesProcessed();     
     
      alertAction(asb, actionName);
      if (asb.getProcCount() == (actionNames.length-1)) {
        bytesProcessed += asb.getBytesProcessed();
        alertService(asb);
      }
    } else if (ActionStatusBean.ACTION_FAILED.equals(asb.getStatus())) {
      IntHolder count = actionFailedCounterHash.get(actionName + " " + FAILED_MESSAGE_COUNTER);
      count.value++ ;
      LongHolder time = actionProcessTimeHash.get(actionName + " " + PROCESSING_TIME);
      time.value += asb.getProcTime();
      timeProcessed += asb.getProcTime();
      LongHolder bFailed = actionBytesFailedHash.get(actionName + " " +  BYTES_FAILED);
      bFailed.value += asb.getBytesProcessed();
      bytesFailed += asb.getBytesProcessed();
      alertService(asb);
    }
   
    if (asb.getProcCount() == 0) {
      bytesOverall += asb.getBytesProcessed();
   
  }
 
  protected ObjectName getObjectName()
  {
    return listObjectName;
  }
 
  // Very basic holder classes
  private static final class IntHolder implements Serializable
  {
    int value ;
    @Override
    public String toString() {
      return Integer.toString(value);
    }
  }
 
  private static final class LongHolder implements Serializable
  {
    long value ;
    @Override
    public String toString() {
      return Long.toString(value);
    }
  }

  @Override
  public MBeanNotificationInfo[] getNotificationInfo() {
        return new MBeanNotificationInfo[] {
                new MBeanNotificationInfo(new String[] {SERVICE_TIME_NOTIFICATION_TYPE, SERVICE_LENGTH_NOTIFICATION_TYPE, ACTION_TIME_NOTIFICATION_TYPE, ACTION_LENGTH_NOTIFICATION_TYPE},
                    "javax.management.Notification", "JBoss ESB message alert notification")
        };
  }
 
}
TOP

Related Classes of org.jboss.soa.esb.listeners.message.ServiceMessageCounter$LongHolder

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.