Skip to content
MonitorComponent.java 10.9 KiB
Newer Older
/**
 *
 */
package alma.TMCDB.MonitorCollectorImpl;

import java.util.HashMap;
import java.util.Map;

import org.omg.CORBA.Any;
import org.omg.CORBA.InterfaceDef;
import org.omg.CORBA.InterfaceDefHelper;
import org.omg.CORBA.Object;

import alma.ACS.CBdoublePOA;
import alma.ACS.CharacteristicComponent;
import alma.ACS.CharacteristicComponentDesc;
import alma.ACS.NoSuchCharacteristic;
import alma.ACS.Property;
import alma.ACS.PropertyDesc;
import alma.TMCDB.MonitorBlob;
import alma.TMCDB.MonitorDataBlock;
import alma.TMCDB.doubleBlobDataSeqHolder;
import alma.acs.container.ContainerServices;
import alma.acs.time.TimeHelper;
import alma.acstime.Epoch;
import alma.TMCDB.MonitorCollectorImpl.MonitorPoint;

/**
 * @author Claudio Tanci
 *
 */
public class MonitorComponent {

	ContainerServices containerServices_m;
	CharacteristicComponent component_m;
	CharacteristicComponentDesc compDesc_m;
	int numOfProp_m;

	// Monitoring state
	boolean monitoring_m;

	/*
	 *  Time of monitoring start
	 *	TODO which Java type? is CORBA::ULongLong in acsCommonC.h
	 *  here is a long for compatibility with monitorDataBlock_m.startTime et similar
	 */
	Epoch m_monitoringStartTime;

	/*
	 * List of monitored points, in C++ is a list with seqIndex_m as index. Here
	 * I'll use an HashMap with names as keys for the moment
	 */
	Map<String, MonitorPoint> monitorPoints_m;

	/*
	 * Index for each monitored points in monitorDataBlock_m.monitorBlobs[].
	 * Names as keys.
	 * TODO: evaluate monitorPoints_m implementation as an array as in C++ implementation to get rid of this.
	 */
	Map<String, Integer> monitorBlocksIndex_m = new HashMap<String, Integer>();

	MonitorDataBlock monitorDataBlock_m;

	/**
	 * @param comp
	 * @param m_containerServices
	 */
	public MonitorComponent(CharacteristicComponent comp,
			ContainerServices m_containerServices) {

		containerServices_m = m_containerServices;
		component_m = comp;
		compDesc_m = comp.descriptor();
		numOfProp_m = compDesc_m.properties.length;
		monitorDataBlock_m = new MonitorDataBlock();
		monitorDataBlock_m.componentName = comp.name();
		monitorDataBlock_m.startTime = 0;
		monitorDataBlock_m.stopTime = 0;
	}

//	public void finalize() {
//		// TODO log this, if this happen there is a bug somewhere as close() as to be called.
//		close();
//	}

	/*
	 * Implements an C++ implementation destructor equivalent.
	 * To be called when the monitor point is not used anymore.
	 */
	public void close() {
		for (String propName : monitorPoints_m.keySet()) {
			monitorPoints_m.get(propName).stopMonitoring();
			monitorPoints_m.get(propName).deactivate(containerServices_m);
		}
	}

	public void enable_archiving(String propertyName) {

		String prop = component_m.name()+":"+propertyName;

		System.out.println("---> MonitorComponent.enable_archiving "+prop);

		for (String propName : monitorPoints_m.keySet()) {
			if (monitorPoints_m.get(propName).getPropertyName().equals(prop))
				monitorPoints_m.get(propName).enable_archiving();
		}
	}

	public synchronized void addAllProperties() {

		System.out.println("---> MonitorComponent.addAllProperties");

		// TODO: what implementation of List/Collection for monitorPoints_m?
		monitorPoints_m = new HashMap<String, MonitorPoint>(numOfProp_m);
		monitorDataBlock_m.monitorBlobs = new MonitorBlob[numOfProp_m];

		for (PropertyDesc p : compDesc_m.properties) {

			/*
			 * Type of property, for reference the following data could be used:
			 * type.toString()      IOR:000000000000002649444C[...]
			 * type.id()            IDL:alma/ACS/ROlong:1.0
			 * type.name()          ROlong
			 * type.type().toString alma::ACS::ROlong
			 */
			Object idef = p.property_ref._get_interface_def();
			InterfaceDef type = InterfaceDefHelper.narrow(idef);

			System.out.println("---> MonitorComponent.addAllProperties " + p.name + " " + type.name()
					+ " ");
			System.out.flush();

			/*
			 * TODO in C++ ACS::TimeInterval, is
			 * there an equivalent in Java? I'll use an long here.
			 */

			long monitoringInterval = propertyArchivingInterval(p);
			if (monitoringInterval != 0) {
				addProperty(p.name, type.name(), p.property_ref,
						monitoringInterval);
			}
		}
	}

	private long propertyArchivingInterval(PropertyDesc p) {

		Property property = p.property_ref;

		Any anyCharacteristic;
		String strCharacteristic;

		try {
			anyCharacteristic = property
					.get_characteristic_by_name("archive_mechanism");
			strCharacteristic = anyCharacteristic.extract_string();

			if (strCharacteristic.equals("monitor_collector")) {

				// reading archive_max_int property
				anyCharacteristic = property
						.get_characteristic_by_name("archive_max_int");
				strCharacteristic = anyCharacteristic.extract_string();

				double archiveMaxInt = Double.parseDouble(strCharacteristic);
				archiveMaxInt *= 10000000.0; // we have to convert to 100s nsec.

				// reading min_timer_trig property
				anyCharacteristic = property
						.get_characteristic_by_name("min_timer_trig");
				strCharacteristic = anyCharacteristic.extract_string();

				double minTimerTrigger = Double.parseDouble(strCharacteristic);
				minTimerTrigger *= 10000000.0; // we have to convert to 100s nsec.

				if (archiveMaxInt < minTimerTrigger) {
					// we can not get values faster than minTimmerTrigger
					/*
					 * TODO log as in C++: ACS_LOG(LM_FULL_INFO
					 * ,"MonitorComponent::propertyArchivingInterval",
					 * (LM_WARNING,
					 * "Because archive_max_int (%f) is smaller than min_timer_trig(%f), the values of property %s (%s) will be collected with time trigger: %f ."
					 * , archiveMaxInt, minTimerTrigger,
					 * propertyDesc->name.in(), property->_repository_id(),
					 * minTimerTrigger ));
					 */

					return (long) minTimerTrigger;
				} else {
					return (long) archiveMaxInt;
				}

			} else {
				/*
				 * TODO log as in C++: ACS_LOG(LM_FULL_INFO
				 * ,"MonitorComponent::propertyArchivingInterval", (LM_DEBUG,
				 * "Values from property %s (%s) will NOT be collected, because archive_mechanism is NOT set to 'monitor_collector', but to: %s."
				 * ,
				 */

				// archive_mechanism is NOT monitor_collector
				return 0;
			}

		} catch (NoSuchCharacteristic e) {
			// TODO Log?
//			e.printStackTrace();
			return 0;
		}
	}

	private void addProperty(String propertyName, String propertyType,
			alma.ACS.Property propertyRef, long archivingInterval) {



		MonitorPoint mp;

		// Adding the index property on monitorBlocksIndex_m
		int index = monitorBlocksIndex_m.size();
		monitorBlocksIndex_m.put(propertyName, index);

		/*
		 * A note from the C++ implementation:
		 * Here we have to check for the type.
		 * We could do using _is_a(..), but it is a remote call, ... or put to
		 * an any and get type out.
		 * Here we use if but could be something else
		 */
		if (propertyType.endsWith("double")) {

			System.out.println("--->      double                  "+propertyName+", "+propertyType+", "+propertyRef+", "+archivingInterval);

			if (propertyType.startsWith("RO")) {

				monitorDataBlock_m.monitorBlobs[index] = new MonitorBlob();
				mp = new MonitorPoint<CBdoublePOA, doubleBlobDataSeqHolder>(propertyName, propertyRef, propertyType, alma.TMCDB.doubleValueType.value, archivingInterval, monitorDataBlock_m.monitorBlobs[index]);

				monitorPoints_m.put(propertyName, mp);
				System.out.println("---> MonitorComponent added Property "+propertyName);

			}
//				else {
//
//				mp = new Monitorable(TPROP, propertyName, archivingInterval, property, typeOfData, mb);
//			}



			System.out.println("---> monitorPoints_m:");
			for (String m : monitorPoints_m.keySet()) {
				System.out.println("---> "+m);
			}
		}
	}

	public void startMonitoring() {

		System.out.println("---> MonitorComponent.startMonitoring");
		System.out.println("---> # monitor points: "+monitorPoints_m.size());
		for (String propName : monitorPoints_m.keySet()) {
			System.out.println("----> "+propName);
			System.out.println("----> "+monitorPoints_m.get(propName).toString());
		}


		for (String propName : monitorPoints_m.keySet()) {
//			monitorPoints_m.get(propName).startMonitoring(containerServices_m);
			monitorPoints_m.get(propName).startMonitoring(containerServices_m);
		}

		// set monitoring state
		monitoring_m = true;

		m_monitoringStartTime = TimeHelper.getTimeStamp();

		// In C++ implementation a second getTimeStamp() is called, here I'll reuse m_monitoringStartTime.
		// bogdan: here we set start and stop time to the same value so that can later use stopTime to set startTime in fillSeq
		monitorDataBlock_m.startTime = m_monitoringStartTime.value;
		monitorDataBlock_m.stopTime  = m_monitoringStartTime.value;
	}

	public void stopMonitoring() {

		System.out.println("---> MonitorComponent.stopMonitoring");
		if (monitoring_m) {
			for (String propName : monitorPoints_m.keySet()) {
				monitorPoints_m.get(propName).stopMonitoring();
			}
	
			// set monitoring state
			monitoring_m = false;
	
			// set proper start and stop time
			// TODO: as in C++ implementation, but why re-set again startTime?
			monitorDataBlock_m.startTime = m_monitoringStartTime.value;
	
			monitorDataBlock_m.stopTime  = TimeHelper.getTimeStamp().value;
		}
	}

	public MonitorDataBlock getMonitorDataBlock() {
		return monitorDataBlock_m;
	}

	public void set_archiving_interval(String propertyName, long time) {

		String prop = component_m.name()+":"+propertyName;

		System.out.println("---> MonitorComponent.set_archiving_interval "+prop);

		for (String propName : monitorPoints_m.keySet()) {
			if (monitorPoints_m.get(propName).getPropertyName().equals(prop))
				monitorPoints_m.get(propName).set_archiving_interval(time);
		}
	}

	public void suppress_archiving(String propertyName) {

		String prop = component_m.name()+":"+propertyName;

		System.out.println("---> MonitorComponent.suppress_archiving "+prop);

		for (String propName : monitorPoints_m.keySet()) {
			if (monitorPoints_m.get(propName).getPropertyName().equals(prop))
				monitorPoints_m.get(propName).suppress_archiving();
		}

	}

	public synchronized void setDeviceSerialNumber(String serialNumber) {

		System.out.println("---> MonitorComponent.setDeviceSerialNumber");

		monitorDataBlock_m.deviceSerialNumber = serialNumber;
	}

	public synchronized void setPropertySerialNumber(String propertyName,
			String[] serialNumbers) {

		System.out.println("---> MonitorComponent.setPropertySerialNumber");

		for (String propName : monitorPoints_m.keySet()) {

			// TODO: equals or contains?
			if (monitorPoints_m.get(propName).getPropertyName().equals(propertyName)) {

				monitorPoints_m.get(propName).setPropertySerialNumber(serialNumbers);
			}
		}

	}

	public synchronized void fillSeq() {

		System.out.println("---> MonitorComponent.fillSeq");

		if (monitoring_m) {
			// TODO: really it could be undefined here?
			monitorDataBlock_m.startTime = m_monitoringStartTime.value;
			m_monitoringStartTime = TimeHelper.getTimeStamp();
		}

		for (String propName : monitorPoints_m.keySet()) {
			monitorPoints_m.get(propName).fillSeq();
		}

		if (monitoring_m) {
			monitorDataBlock_m.stopTime = TimeHelper.getTimeStamp().value;
		}

	}
}