ParamGetLocalFile.cc 7.7 KB
/*
 * ParamGetLocalFile.cc
 *
 *  Created on: 21 nov. 2014
 *      Author: AKKA
 */

#include "LocalFileInterfaceConfig.hh"
#include "ParamGetLocalFile.hh"
#include "VirtualInstrumentManager.hh"

#include <stdlib.h>

#include "Parameter.hh"
#include "ParamData.hh"
#include "ParamMgr.hh"
#include "DataSetMgr.hh"
#include "DicError.hh"
#include "TimeUtil.hh"
#include "Helper.hh"

namespace AMDA {

namespace LocalFileInterface {

ParamGetLocalFile::ParamGetLocalFile(Parameter &parameter) :
		ParamGet_CRTP<ParamGetLocalFile>(parameter),
		_paramId(""), _paramType(LocalParamType::TYPE_UNKNOWN), _paramDim1Size(0),
		_paramDim2Size(0), _paramMinSampling(0.), _paramMaxSampling(0.), _timeFormat(LocalTimeFormat::DOUBLE), _fillValue(NAN),
		_viId(""), _timeStamp(0), _pusher(NULL)
{

}

ParamGetLocalFile::ParamGetLocalFile(const ParamGetLocalFile &pParamGetLocalFile, Parameter &parameter) :
		ParamGet_CRTP<ParamGetLocalFile>(pParamGetLocalFile, parameter),
		_paramId(pParamGetLocalFile._paramId),
		_paramType(pParamGetLocalFile._paramType),
		_paramDim1Size(pParamGetLocalFile._paramDim1Size),
		_paramDim2Size(pParamGetLocalFile._paramDim2Size),
		_paramMinSampling(pParamGetLocalFile._paramMinSampling),
		_paramMaxSampling(pParamGetLocalFile._paramMaxSampling),
		_timeFormat(pParamGetLocalFile._timeFormat),
		_infoRequestList(pParamGetLocalFile._infoRequestList),
		_fillValue(pParamGetLocalFile._fillValue),
		 _viId(pParamGetLocalFile._viId), _timeStamp(pParamGetLocalFile._timeStamp),
		 _pusher(pParamGetLocalFile._pusher)
{

}

ParamGetLocalFile::~ParamGetLocalFile()
{
	//delete the pusher if needed
	if (_pusher != NULL)
		delete _pusher;
}

TimeStamp ParamGetLocalFile::init()
{
	LOG4CXX_DEBUG(gLogger, "ParamGetLocalFile::init");
	//get Virtual Instrument
	_vi = VirtualInstrumentManager::getInstance()->getVirtualInstrument(
			_viId);

	//create file reader
	if (!_vi->createFileReader(_timeFormat))
	{
		BOOST_THROW_EXCEPTION(AMDA::AMDA_exception() << AMDA::errno_code(AMDA_LOCALFILE_READER) << AMDA::ex_msg(std::string("Cannot create corresponding file reader")));
	}

	//get time param id
	if (!_vi->updateTimeId())
	{
		BOOST_THROW_EXCEPTION(AMDA::AMDA_exception() << AMDA::errno_code(AMDA_LOCALFILE_TIMEPARAM) << AMDA::ex_msg(std::string("Cannot detect time param Id")));
	}

	//get calib info
	getCalibInfo();

	//create pusher
	LocalParamType paramType = _paramType;
	int paramDim1Size = _paramDim1Size;
	int paramDim2Size = _paramDim2Size;
	_pusher = _vi->createPusher(_paramId,paramType,paramDim1Size,paramDim2Size);

	if (_pusher == NULL)
	{
		BOOST_THROW_EXCEPTION(AMDA::AMDA_exception() << AMDA::errno_code(AMDA_TYPE_DATA_UNKNOWN) << AMDA::ex_msg(std::string("Cannot create param data")));
	}

	//set link to the param data
	_paramData = ParamDataSPtr(_pusher->getParamData());

	_paramData->setMinSampling(_paramMinSampling);

	// Get ParamFlow instance only if there is at least one TimeInterval to process
	// and if delta is not equal to 0.
	if (_timeIntervalList->size() != 0 && !(_timeIntervalList->size() == 1 && (_timeIntervalList->front()._stopTime - _timeIntervalList->front()._startTime) == 0) )
	{
		_paramFlow = _vi->getParamFlow(_paramId, _timeIntervalList,paramType,paramDim1Size,paramDim2Size);
	} else if (_timeIntervalList->size() == 0) {
		LOG4CXX_WARN(gLogger, "ParamGetLocalFile::init => List of time interval is empty");
	} else {
		// Nothing to do
	}

	if (_timeStamp == 0 && _signatureTrigger != "") {
		// _signatureTrigger must be a name of xml parameter file
		_timeStamp = AMDA::Helpers::Helper::dateOfFile(
				_signatureTrigger.c_str());
	}
        
        setGlobalStart(_vi->getGlobalStartTime());
        setGlobalStop(_vi->getGlobalStopTime());

	return _timeStamp;
}


unsigned int ParamGetLocalFile::write()
{
	unsigned int result = 0;

	if (_paramFlow.get() == nullptr)
	{
		BOOST_THROW_EXCEPTION(AMDA::AMDA_exception() << AMDA::ex_msg("Param flow not yet initialized for parameter '" + _paramId));
	} else {
		// Nothing to do
	}

	//get packet and push it in ParamData
	LOG4CXX_DEBUG(gLogger, "ParamGetLocalFile::write " << _paramId);
	LocalParamDataPacket* lPacket = _paramFlow->get(_paramId);
	if (lPacket) {
		_pusher->setFillValue(_fillValue);
		do {
			if (lPacket->isNoData()) {
				LOG4CXX_DEBUG(gLogger, "ParamGetLocalFile::write => no data packet");
				_paramData->getTimeList().push_back(lPacket->getStartTime());
				_pusher->putNaN();
				_paramData->getTimeList().push_back(lPacket->getStopTime());
				_pusher->putNaN();
				result += 2;
			}
			else {
				result += _pusher->put(lPacket);
			}
			delete lPacket;
			lPacket = _paramFlow->tryGet(_paramId);
		} while(lPacket);
	}

	// Push up the information if all time interval was processed.
	_paramData->getIndexInfo()._timeIntToProcessChanged = _paramFlow->isTimeIntToProcessChanged(_paramId);
	_paramData->getIndexInfo()._noMoreTimeInt =  _paramFlow->isNoMoreTimeInt(_paramId);

	// if time interval changed store index which delimit the end of the time interval.
	if (_paramData->getIndexInfo()._timeIntToProcessChanged || (!_paramData->getIndexInfo()._timeIntToProcessChanged && result == 0)) {
		unsigned int lEndTimeIntIndex = _paramData->getIndexInfo()._nbDataToProcess;
		_paramData->getIndexInfo()._endTimeIntIndexList.push_back(lEndTimeIntIndex);
	}
	else {
		// Nothing to do.
	}

	return result;
}

void ParamGetLocalFile::getCalibInfo() {
	for (InfoRequestList::iterator lIt = _infoRequestList.begin(); lIt != _infoRequestList.end(); ++lIt)
	{
		auto lInfoName = *lIt;
		if (_parameter.getInfoList().find(lInfoName) == _parameter.getInfoList().end()) {
			LOG4CXX_INFO( gLogger, "ParamGetLocalFile:getCalibInfo( " << lInfoName << "')");
			_parameter.setInfoValues(*lIt, _vi->getFileInfo(lIt->c_str()));
		}
	}
}

/*
 * @overload DataWriter::getMinSampling
 */
double ParamGetLocalFile::getMinSampling()
{
	return getParamMinSampling();
}

void ParamGetLocalFile::updateInfo(Parameter & parameter)
{
	LOG4CXX_DEBUG(gLogger, "ParamGetLocalFile::updateInfo - " << parameter.getId());
	if (parameter.getInfoId().empty())
		parameter.setInfoId(parameter.getId());

	//Param info
	AMDA::Info::ParamInfoSPtr paramInfo = AMDA::Info::ParamMgr::getInstance()->getParamInfoFromId(parameter.getInfoId(),true);

	if (paramInfo == nullptr)
		return;

	//if a fill value defined => save it
	if (!isnan(paramInfo->getFillValue()))
		_fillValue = paramInfo->getFillValue();

	//fill value automatically replace by nan in the Pusher
	paramInfo->setFillValue(NAN);

	//Add parameter info id as parameter name if no exist
	if (paramInfo->getName().empty())
		paramInfo->setName(_paramId);

	//Add parameter info id as parameter short name if no exist
	if (paramInfo->getShortName().empty())
		paramInfo->setShortName(_paramId);

	std::string datasetId = paramInfo->getDatasetId();
	if (datasetId.empty())
		//get vi ID as dataset id if no dataset info defined
		datasetId = _vi->getVIId();

	//link dataset info to param info
	paramInfo->setDatasetId(datasetId);

	//Dataset info
	AMDA::Info::DataSetInfoSPtr datasetInfo = AMDA::Info::DataSetMgr::getInstance()->getDataSetInfoFromId(datasetId,true);

	if (datasetInfo == nullptr)
		return;

	//Add dataset id as dataset name if no exist
	if (datasetInfo->getName().empty())
		datasetInfo->setName(_vi->getVIId());

	//Set sampling values
	datasetInfo->setMinSampling((int)_paramMinSampling);
	datasetInfo->setMaxSampling((int)_paramMaxSampling);

	//Set global start time
	std::stringstream isoTime;
	TimeUtil::formatTimeDateInIso(_vi->getGlobalStartTime(), isoTime);
	datasetInfo->setGlobalStart(isoTime.str());

	//Set global stop time
	isoTime.str("");
	TimeUtil::formatTimeDateInIso(_vi->getGlobalStopTime(), isoTime);
	datasetInfo->setGlobalStop(isoTime.str());

	//Set source
	datasetInfo->setSource("CDPP/AMDA Local base");
}

} /* namespace LocalFileInterface */
} /* namespace AMDA */