/*
 * Copyright 2004 Sun Microsystems, Inc.  All rights reserved.
 * This software is the proprietary information of Sun Microsystems, Inc.
 * Use is subject to license terms.
 *
 * Copyright 2004 Sun Microsystems, Inc.  Tous droits réservés.
 * Ce logiciel est propriété de Sun Microsystems, Inc.
 * Distribué par des licences qui en restreignent l'utilisation.
 *
 * ident        "@(#)CIBRangeStatisticImpl.java 1.11     04/07/15 SMI"
 *
 */

package com.sun.mfwk.cib.sdk.statistics;

import com.sun.mfwk.cib.statistics.CIBRangeStatistic;
import com.sun.mfwk.cib.statistics.CIBStatistic;
import javax.management.openmbean.CompositeData;

import java.util.logging.Logger;
import com.sun.mfwk.util.log.MfLogService;

import javax.management.openmbean.CompositeDataSupport;
import javax.management.openmbean.CompositeData;
import javax.management.openmbean.CompositeType;
import javax.management.openmbean.OpenType;
import javax.management.openmbean.SimpleType;
import javax.management.openmbean.OpenDataException;

/**
 * Provides a default implementation of a CIBRangeStatistic
 */
public class CIBRangeStatisticImpl
    extends CIBStatisticImpl
    implements CIBRangeStatistic {

  static final Logger logger = MfLogService.getLogger("cib-sdk");
  static final String className = "CIBRangeStatisticImpl";

  private long myCurrent = RESET_VALUE;
  private long myHighWaterMark = RESET_VALUE;
  private long myLowWaterMark = RESET_VALUE;

  private static String[] itemNames = {
      "Name",
      "Description",
      "Unit",
      "LastSampleTime",
      "StartTime",
      "HighWaterMark",
      "LowWaterMark",
      "Current"};

  private static String[] itemDescriptions = {
      "Name",
      "Description",
      "Unit",
      "LastSampleTime",
      "StartTime",
      "HighWaterMark",
      "LowWaterMark",
      "Current"};

  private static OpenType[] itemTypes = {
      SimpleType.STRING,
      SimpleType.STRING,
      SimpleType.STRING,
      SimpleType.LONG,
      SimpleType.LONG,
      SimpleType.LONG,
      SimpleType.LONG,
      SimpleType.LONG};

  private static CompositeType statisticType = null;

  /**
   * Constructor
   * @param name String
   * @param description String
   */
  public CIBRangeStatisticImpl(String name, String description) {
    super(name, description, "RANGE");
    logger.exiting(className, "Constructor");
  }

  /**
   * Set the current value of the statistic object
   * @param current long
   */
  public void setCurrent(long current) {
    logger.entering(className, "setCurrent", new Long(current));
    myCurrent = current;
  }

  /**
   * Set the highWaterMark of the statistic object
   * @param highWaterMark long
   */
  public void setHighWaterMark(long highWaterMark) {
    logger.entering(className, "setHighWaterMark", new Long(highWaterMark));
    myHighWaterMark = highWaterMark;
  }

  /**
   * Set the lowWaterMark of the statistic object
   * @param lowWaterMark long
   */
  public void setLowWaterMark(long lowWaterMark) {
    logger.entering(className, "setLowWaterMark", new Long(lowWaterMark));
    myLowWaterMark = lowWaterMark;
  }

  /**
   * Get the current value of the statistic object
   * @return long
   */
  public long getCurrent() {
    logger.exiting(className, "getCurrent" + new Long(myCurrent));
    return myCurrent;
  }

  /**
   * Get the LowWaterMark of the statistic object
   * @return long
   */
  public long getHighWaterMark() {
    logger.exiting(className, "getHighWaterMark" + new Long(myHighWaterMark));
    return myHighWaterMark;
  }

  /**
   * Get the LowWaterMark of the statistic object
   * @return long
   */
  public long getLowWaterMark() {
    logger.exiting(className, "getLowWaterMark" + new Long(myLowWaterMark));
    return myLowWaterMark;
  }

  /**
   * Returns a composite data representing the statistic object
   * @return CompositeData
   */
  public CompositeData toCompositeData() throws OpenDataException {
    logger.entering(className, "toCompositeData");
    try {
      statisticType = new CompositeType("CIBRangeStatistic",
                                        "Common monitoring Range Statistic",
                                        itemNames,
                                        itemDescriptions,
                                        itemTypes);
      Object[] itemValues = {
          getName(),
          getDescription(),
          getUnit(),
          new Long(getLastSampleTime()),
          new Long(getStartTime()),
          new Long(this.getHighWaterMark()),
          new Long(this.getLowWaterMark()),
          new Long(this.getCurrent())
      };

      CompositeDataSupport data = null;

      data = new CompositeDataSupport(statisticType,
                                      itemNames, itemValues);
      logger.exiting(className, "toCompositeData", data);
      return data;
    }

    catch (OpenDataException e) {
      logger.throwing(className, "toCompositeData", e);
      logger.exiting(className, "toCompositeData");
      throw e;
    }

  }

  /**
   * Returns a CIBStatistic object from a composite data
   * @return CIBStatistic
   */
  public CIBStatistic fromCompositeData(CompositeData data) {
    logger.entering(className, "fromCompositeData", data);
    String name = (String) data.get("Name");
    String description = (String) data.get("Description");
    String unit = (String) data.get("Unit");
    Long lastSampleTime = (Long) data.get("LastSampleTime");
    Long startTime = (Long) data.get("StartTime");
    Long highWaterMark = (Long) data.get("HighWaterMark");
    Long lowWaterMark = (Long) data.get("LowWaterMark");
    Long current = (Long) data.get("Current");

    // Create a new statistic
    CIBRangeStatisticImpl statistic = new CIBRangeStatisticImpl(name,
        description);

    ( (CIBStatisticImpl) statistic).setLastSampleTime(lastSampleTime.longValue());
    ( (CIBStatisticImpl) statistic).setStartTime(startTime.longValue());

    statistic.setHighWaterMark(highWaterMark.longValue());
    statistic.setLowWaterMark(lowWaterMark.longValue());
    statistic.setCurrent(current.longValue());
    logger.exiting(className, "fromCompositeData", statistic);
    return statistic;
  }

  /**
   * Reset the statistic object
   */
  public void reset() {
    logger.entering(className, "reset");
    super.reset();
    myCurrent = RESET_VALUE;
    myHighWaterMark = RESET_VALUE;
    myLowWaterMark = RESET_VALUE;
    logger.exiting(className, "reset");
  }

  /**
   * Returns a printable statistic object
   * @return String
   */
  public String toString() {
    String str = super.toString();
    String strHigh = "HighWaterMark=" + this.getHighWaterMark() +
        super.strSeparator;
    String strLow = "LowWaterMark=" + this.getLowWaterMark() +
        super.strSeparator;
    String strCurrent = "Current=" + this.getCurrent() + super.strSeparator;
    return new String(str + strHigh + strLow + strCurrent);
  }

}
