/** * Handler emergency call from tetra radio * $Id$ * $HeadURL$ * $Author$ * Created by Astrid Müller, SGAS, 2018-02-23 */ #include "handler_emergency_call.h" #include "initialization.h" #include "handler_configure_alarms.h" #include "object_emergency_call.h" #include "alm_db.h" #include #include #include #include namespace AlarmManagement { HandlerEmergencyCall::HandlerEmergencyCall(const std::shared_ptr &configAlarmHandler, Initialization *mainHandler) : QObject() , EmergencyCallAcknowledgeRequestHandler(mainHandler->dds()->ftsAlm()) , m_mainHandler(mainHandler) , m_configAlarmHandler(configAlarmHandler) , m_logger(getLogger("HandlerEmergencyCall")) { } HandlerEmergencyCall::~HandlerEmergencyCall() { } bool HandlerEmergencyCall::init() { INFO_LOG(m_logger) << "Start HandlerEmergencyCall."; auto dtcTab = m_mainHandler->dds()->dtcTab(); connect(dtcTab.get(), &TrainingAreaBase::Interface::Dtc::emergencyCallChanged, this, &HandlerEmergencyCall::onEmergencyCallChanged); connect(m_mainHandler->dds()->dtcAlm().get(), &AlarmManagement::Interface::Dtc::acknowledgeSOSInAllExercisesChanged, this, &HandlerEmergencyCall::onAcknowledgeSOSInExercises); // create and init Object bool bRet = true; auto cbEmergencyCall = [this, &bRet](const Database::AlmEmergencyCall &data) { WARNING_LOG(m_logger)<<" ALM_EMERGENCY " << "Reading from DB AlmEmergencyCall with id = " << data.id; if (!this->isExerciseValidForEmergencyCall() && !data.expired) return; ObjectEmergencyCall *ifs(new ObjectEmergencyCall(m_mainHandler)); Core::FunctionReplyObject ret = ifs->createObject(data); if (ret.error()) { delete ifs; ERROR_LOG(m_logger) << ret(); bRet = false; return; } m_emergencyObjMap.insert(ifs->getId(), ifs); }; if (!m_mainHandler->db()->select(cbEmergencyCall) || !bRet) { ERROR_LOG(m_logger) <<"Error reading data from database 'alm_emergency_call!"; return false; } return true; } bool HandlerEmergencyCall::createEmergencyCallObject(const AlarmManagement::AlmEmergencyCall &data) { if (!isNewEmergencyCall(data) || std::isnan(data.position().lat())) return false; Database::AlmEmergencyCall newData; newData.id = 0; newData.operatorId = 0; newData.sampleTime = data.sampleTime(); newData.incomingTime = data.sampleTime(); newData.expired = false; newData.issi = data.issi(); newData.position.setX(data.position().lon()); newData.position.setY(data.position().lat()); newData.comment = QStringLiteral(""); newData.name = QStringLiteral(""); ObjectEmergencyCall *ifs(new ObjectEmergencyCall(m_mainHandler, this)); Core::FunctionReplyObject ret = ifs->createObject(newData); if (ret.error()) { delete ifs; ERROR_LOG(m_logger)<< ret(); return false; } WARNING_LOG(m_logger)<< "Entry createEmergencyCallObject in the DB id: "<getData().id<<" issi: "<getData().issi<<" expired: "<getData().expired; m_emergencyObjMap.insert(ifs->getId(), ifs); return true; } void HandlerEmergencyCall::onEmergencyCallAcknowledgeRequest(const rti::core::SampleIdentity &cookie, const EmergencyCallAcknowledgeRequest &request) { WARNING_LOG(m_logger) << "[onEmergencyCallAcknowledgeRequest] request: " << request; Core::FunctionReplyObject ret = emergencyCallAcknowledgeRequest(request); if (ret.error()) WARNING_LOG(m_logger)<< ret(); if (request.expired()) { AcknowledgeSOSInAllExercises ackInEx; ackInEx.id(request.id()); ackInEx.timestamp(request.timestamp()); ackInEx.incomingTime(request.incomingTime()); ackInEx.name(request.name()); ackInEx.issi(request.issi()); ackInEx.operatorId(request.operatorId()); ackInEx.comment(request.comment()); ackInEx.expired(request.expired()); WARNING_LOG(m_logger) << "onEmergencyCallAcknowledgeRequest: issi: "<dds()->publishSOS()->write(ackInEx); } m_mainHandler->dds()->ftsAlm()->emergencyCallAcknowledgeReply(cookie,ret); } Core::FunctionReplyObject HandlerEmergencyCall::emergencyCallAcknowledgeRequest(const EmergencyCallAcknowledgeRequest &request) { ObjectEmergencyCall *ifs = nullptr; for(auto _ifs : qAsConst(m_emergencyObjMap)) { auto data = _ifs->getData(); if (data.issi == request.issi() && data.incomingTime == request.incomingTime() && !data.expired) { ifs = _ifs; break; } } if (ifs == nullptr) { WARNING_LOG(m_logger)<<" Couldn't acknowledge SOS with issi: " <getData().expired) // if already expired do nothing { WARNING_LOG(m_logger) << "SOS Already expired do nothing"; return Core::FunctionReplyObject(ifs->getData().id); } WARNING_LOG(m_logger) << "emergencyCallAcknowledgeRequest: issi found!: "<state: "<getData().expired; Database::AlmEmergencyCall newData(ifs->getData()); newData.expired = true; newData.issi = request.issi(); newData.sampleTime = request.timestamp(); newData.deleted = request.timestamp(); newData.operatorId = request.operatorId(); newData.name = QString::fromStdString(request.name()); newData.comment = QString::fromStdString(request.comment()); return ifs->updateObject(newData); } bool HandlerEmergencyCall::isExerciseValidForEmergencyCall() const { const auto &exmDtc = m_mainHandler->dds()->dtcExm(); exmDtc->waitForHistoricalDataExercise(); const ExerciseManagement::Exercise exercise = exmDtc->exercise(m_mainHandler->dds()->exerciseId()); if (exercise.state() != ExerciseManagement::ExerciseState::Started && exercise.state() != ExerciseManagement::ExerciseState::Paused) return false; return true; } bool HandlerEmergencyCall::isNewEmergencyCall(const AlmEmergencyCall &newdata) { for(const auto &ifs : qAsConst(m_emergencyObjMap)) { const auto &data = ifs->getData(); if (data.issi == newdata.issi() && data.incomingTime == newdata.incomingTime() && !data.expired) { WARNING_LOG(m_logger)<<" SOS EXISTS and not yet quit! issi: "<