377 lines
10 KiB
C++
Raw Normal View History

#include "pub_logger_api/logger.h"
#include "boost/thread.hpp"
#include "boost/lexical_cast.hpp"
#include "pub_utility_api/TimeUtil.h"
#include "CMethodSeq.h"
#include "CNodeSeq.h"
#include "CNodeIterator.h"
#include "CMethodFunc.h"
#include "CDbSaveCtrl.h"
#include "CModuleDbAccessMngr.h"
#include "CRecoverNode.h"
#include "CModuleAlarmCreater.h"
CMethodSeq::CMethodSeq(CNodeSeq& seq)
:m_objSeq(seq)
{
m_objSeq.setMethod(this);
}
CMethodSeq::~CMethodSeq()
{
CMethodSeq::interruptExecute();
m_objSeq.setMethod(NULL);
}
bool CMethodSeq::execute()
{
LOGINFO("顺控:[%s] 开始执行!",
m_objSeq.description().c_str()
);
m_objSeq.setStartTime(kbd_public::getUTCTimeSec());
addSeqHistory();
bool bRet = executeChilds();
LOGINFO("顺控:[%s] 结束执行 状态[%s]!",
m_objSeq.description().c_str(),
(bRet ? ("成功") : ("失败"))
);
updateSeqHistory();
return bRet;
}
void CMethodSeq::interruptExecute()
{
std::vector<CMethodFuncAsync* >::iterator iter
= m_vecAsyncThreads.begin();
for (; iter != m_vecAsyncThreads.end(); ++iter)
{
(*iter)->interruptExecuter();
delete *iter;
*iter = NULL;
}
m_vecAsyncThreads.clear();
}
bool CMethodSeq::executeChilds()
{
//将状态 设置为 正在执行
changeStateToStart();
m_objSeq.getAlarmCreater().seqStart(m_objSeq);
//开始处理所有功能, 返回的 列表是 并行功能的队列
ESeqCtrl_NodeState resultState =
startExecuteChilds(m_vecAsyncThreads);
//处理并行功能的结果
ESeqCtrl_NodeState resultAsyncState =
startAsyncExecuteChilds(m_vecAsyncThreads);
//计算出整个顺控的状态
resultState = getAsyncResultState(resultState, resultAsyncState);
switch (resultState)
{
case SEQ_FAILED_STATUS:
changeStateToFailed();
break;
case SEQ_SUCCESS_STATUS:
changeStateToSuccess();
break;
case SEQ_STOP_STATUS:
changeStateToStop();
break;
default:
BOOST_ASSERT(false);
break;
}
//clearAsyncVec(m_vecAsyncThreads);
m_objSeq.getAlarmCreater().seqStop(m_objSeq);
return resultState == SEQ_SUCCESS_STATUS;
}
ESeqCtrl_NodeState CMethodSeq::startExecuteChilds(
std::vector<CMethodFuncAsync* >& vec)
{
ESeqCtrl_NodeState resultState = SEQ_SUCCESS_STATUS;
//遍历子节点
CNodeFuncIterator iter(m_objSeq);
while (iter.hasNext())
{
CNodeFunc& func = iter.getNext();
resultState = doOneFunc(func, vec);
if (resultState != SEQ_SUCCESS_STATUS)
{
break;
}
}
return resultState;
}
ESeqCtrl_NodeState CMethodSeq::startAsyncExecuteChilds(std::vector<CMethodFuncAsync* >& vec)
{
ESeqCtrl_NodeState resultState = SEQ_SUCCESS_STATUS;
//等待并行结束,并行的功能 ,
//并行功能如果执行失败了,并不会影响整个顺控的执行,
//整个顺控的的成功和失败 是 会在所有功能都结束后判断的
bool bAsyncResult = true;
std::vector<CMethodFuncAsync* >::iterator iterVecAsync
= vec.begin();
for (; iterVecAsync != vec.end(); ++iterVecAsync)
{
bAsyncResult = (*iterVecAsync)->waitExecuteEnd();
if (!bAsyncResult)
{
CNodeFunc& func = (*iterVecAsync)->getFuncNode();
resultState = getAsyncResultState(resultState, func.getState());
}
}
return resultState;
}
ESeqCtrl_NodeState CMethodSeq::doOneFunc(
CNodeFunc& func,
std::vector<CMethodFuncAsync* >& vec)
{
//如果没有勾选,则不用执行
if (func.checkStatus()
== CNode::NODE_CHECK_STATUS_UNCHECK)
{
return SEQ_SUCCESS_STATUS;
}
//并行,创建异步 存在异步队列中
if ((!m_objSeq.isSecExe()) && func.isAsync())
{
doOneAsysncFunc(func, vec);
return SEQ_SUCCESS_STATUS;
}
return doOneSysncFunc(func);
}
ESeqCtrl_NodeState CMethodSeq::doOneSysncFunc(CNodeFunc& func)
{
//串行
CMethodFunc funcMethod(func);
funcMethod.execute();
return func.getState();
}
ESeqCtrl_NodeState CMethodSeq::doOneAsysncFunc(CNodeFunc& func, std::vector<CMethodFuncAsync* >& vec)
{
CMethodFuncAsync* pAsyncPro = new CMethodFuncAsync(func);
vec.push_back(pAsyncPro);
//并行的执行失败了,只能等待串行结束后再做处理
return SEQ_SUCCESS_STATUS;
}
void CMethodSeq::clearAsyncVec(std::vector<CMethodFuncAsync* >& vec)
{
std::vector<CMethodFuncAsync* >::iterator iter = vec.begin();
for (; iter != vec.end(); ++iter)
{
delete *iter;
*iter = NULL;
}
vec.clear();
}
void CMethodSeq::notifyStateToHmi()
{
CMbCommunicateInfo& mb = m_objSeq.getMbCmmInfo();
mb.nodeStatusToHmi(m_objSeq);
}
void CMethodSeq::changeStateToStart()
{
m_objSeq.updateState(SEQ_RUNNING_STATUS);
updateSeqRunning(false);
notifyStateToHmi();
}
void CMethodSeq::changeStateToSuccess()
{
m_objSeq.updateState(SEQ_SUCCESS_STATUS);
updateSeqRunning();
notifyStateToHmi();
}
void CMethodSeq::changeStateToFailed()
{
m_objSeq.updateState(SEQ_FAILED_STATUS);
updateSeqRunning();
notifyStateToHmi();
}
void CMethodSeq::changeStateToStop()
{
m_objSeq.updateState(SEQ_STOP_STATUS);
updateSeqRunning();
notifyStateToHmi();
}
void CMethodSeq::changeStateToPause()
{
m_objSeq.updateState(SEQ_PAUSE_STATUS);
updateSeqRunning();
notifyStateToHmi();
}
bool CMethodSeq::updateSeqRunning(bool onlyState)
{
SSeqCtrlRunning info;
memset(&info, 0, sizeof(info));
SNodeSeqActor actor = m_objSeq.getSeqActor();
strcpy(info.seq_name, m_objSeq.nodeName().c_str());
strcpy(info.node_desc, m_objSeq.description().c_str());
info.action_no = 0;
info.func_no = 0;
info.node_type = 0;
info.status = m_objSeq.getState();
info.checked = m_objSeq.checkStatus();
info.start_time = m_objSeq.getStartTime();
info.user_id = actor.user_id;
info.user_groupid = actor.user_grounp_id;
strcpy(info.host_name, actor.host_name.c_str());
strcpy(info.user_name, actor.user_name.c_str());
info.timeflag = m_objSeq.timeFlag();
info.relation = 0;
info.delay_time = 0;
info.fail_strage = 0;
info.isses = m_objSeq.isSecExe();
//strcpy(info.key_id_tag, m_ptrAction->keyIdTag().c_str());
info.targetvalue = 0;
info.location_id = m_objSeq.locationId();
info.seq_type = m_objSeq.seqType();
CModuleDbAccessMngr& access = m_objSeq.getDbAccess();
return access.updateSeqRunningRecord(info, onlyState);
}
ESeqCtrl_NodeState CMethodSeq::getAsyncResultState(
ESeqCtrl_NodeState oldState,
ESeqCtrl_NodeState newState)
{
//失败优先级最高,一旦失败,就是失败
if (newState == SEQ_FAILED_STATUS || oldState == SEQ_FAILED_STATUS)
{
return SEQ_FAILED_STATUS;
}
//终止状态
if (newState == SEQ_STOP_STATUS || oldState == SEQ_STOP_STATUS)
{
return SEQ_STOP_STATUS;
}
if (newState == SEQ_SUCCESS_STATUS && oldState == SEQ_SUCCESS_STATUS)
{
return SEQ_SUCCESS_STATUS;
}
return newState;
}
bool CMethodSeq::updateSeqHistory()
{
CDbSaveCtrl db;
SSeqHistory info;
info.seq_name = m_objSeq.nodeName();
info.seq_desc = m_objSeq.description();
info.time = m_objSeq.getStartTime();//开始执行的时间
info.status = CNode::getStateStr(m_objSeq.getState());
info.location_id = m_objSeq.locationId();
SNodeSeqActor actor = m_objSeq.getSeqActor();
info.user_id = actor.user_id;
info.user_group = actor.user_grounp_id;
info.host_name = actor.host_name;
info.user_name = actor.user_name;
info.seq_type = m_objSeq.seqType();
bool bRet = db.updateSeqHistory(info);
return bRet;
}
//添加历史表,需要把功能 和 动作的一并写入
bool CMethodSeq::addSeqHistory()
{
CDbSaveCtrl db;
SSeqHistory seqInfo;
SSeqFunctionHistory funcInfo;
SSeqCtrlActionEvent actionInfo;
bool bRet = true;
CNodeFuncIterator funcIter(m_objSeq);
while (bRet && funcIter.hasNext())
{
CNodeFunc& func = funcIter.getNext();
CNodeActionIterator actionIter(func);
while (bRet && actionIter.hasNext())
{
CNodeAction& action = actionIter.getNext();
actionInfo.seq_name = m_objSeq.nodeName();
actionInfo.time = m_objSeq.getStartTime();//执行时间
BOOST_ASSERT(actionInfo.time != 0);
actionInfo.func_name = func.nodeName();
actionInfo.action_no = action.actionNo();
actionInfo.action_name = action.nodeName();
actionInfo.action_desc = action.description();
actionInfo.status = CNode::getStateStr(action.getState());
actionInfo.starttime = 0;
actionInfo.stoptime = 0;
actionInfo.key_id_tag = action.keyIdTag();
actionInfo.targetvalue = action.targetValue();
actionInfo.location_id = action.locationId();
actionInfo.discribe = "";
bRet = db.addActionEvent(actionInfo);
}
if (!bRet)
{
break;
}
funcInfo.seq_name = m_objSeq.nodeName();
funcInfo.time = m_objSeq.getStartTime();//开始执行的时间
funcInfo.func_name = func.nodeName();
funcInfo.func_desc = func.description();
funcInfo.func_no = func.funcNo();
funcInfo.relation = func.relation();
funcInfo.status = CNode::getStateStr(func.getState());
funcInfo.location_id = m_objSeq.locationId();
bRet = db.addSeqFuncHistory(funcInfo);
}
if (bRet)
{
seqInfo.seq_name = m_objSeq.nodeName();
seqInfo.seq_desc = m_objSeq.description();
seqInfo.time = m_objSeq.getStartTime();//开始执行的时间
seqInfo.status = CNode::getStateStr(SEQ_RUNNING_STATUS);
seqInfo.location_id = m_objSeq.locationId();
SNodeSeqActor actor = m_objSeq.getSeqActor();
seqInfo.user_id = actor.user_id;
seqInfo.user_group = actor.user_grounp_id;
seqInfo.host_name = actor.host_name;
seqInfo.user_name = actor.user_name;
seqInfo.seq_type = m_objSeq.seqType();
bRet = db.addSeqHistory(seqInfo);
}
return bRet;
}