mirror of https://github.com/nymea/nymea.git
387 lines
16 KiB
C++
387 lines
16 KiB
C++
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
|
|
*
|
|
* Copyright 2013 - 2022, nymea GmbH
|
|
* Contact: contact@nymea.io
|
|
*
|
|
* This file is part of nymea.
|
|
* This project including source code and documentation is protected by
|
|
* copyright law, and remains the property of nymea GmbH. All rights, including
|
|
* reproduction, publication, editing and translation, are reserved. The use of
|
|
* this project is subject to the terms of a license agreement to be concluded
|
|
* with nymea GmbH in accordance with the terms of use of nymea GmbH, available
|
|
* under https://nymea.io/license
|
|
*
|
|
* GNU General Public License Usage
|
|
* Alternatively, this project may be redistributed and/or modified under the
|
|
* terms of the GNU General Public License as published by the Free Software
|
|
* Foundation, GNU version 3. This project is distributed in the hope that it
|
|
* will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty
|
|
* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
|
|
* Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License along with
|
|
* this project. If not, see <https://www.gnu.org/licenses/>.
|
|
*
|
|
* For any further details and any questions please contact us under
|
|
* contact@nymea.io or see our FAQ/Licensing Information on
|
|
* https://nymea.io/license/faq
|
|
*
|
|
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
|
|
|
|
#include "zwavehandler.h"
|
|
|
|
namespace nymeaserver
|
|
{
|
|
|
|
ZWaveHandler::ZWaveHandler(ZWaveManager *zwaveManager, QObject *parent):
|
|
JsonHandler(parent),
|
|
m_zwaveManager(zwaveManager)
|
|
{
|
|
|
|
registerEnum<ZWave::ZWaveError>();
|
|
registerObject<SerialPort, SerialPorts>();
|
|
registerEnum<ZWaveNetwork::ZWaveNetworkState>();
|
|
registerEnum<ZWaveNode::ZWaveNodeType>();
|
|
registerEnum<ZWaveNode::ZWaveNodeRole>();
|
|
registerEnum<ZWaveNode::ZWaveDeviceType>();
|
|
|
|
QVariantMap networkDescription;
|
|
networkDescription.insert("networkUuid", enumValueName(Uuid));
|
|
networkDescription.insert("serialPort", enumValueName(String));
|
|
networkDescription.insert("networkState", enumRef<ZWaveNetwork::ZWaveNetworkState>());
|
|
networkDescription.insert("homeId", enumValueName(Uint));
|
|
networkDescription.insert("isZWavePlus", enumValueName(Bool));
|
|
networkDescription.insert("isStaticUpdateController", enumValueName(Bool));
|
|
networkDescription.insert("isPrimaryController", enumValueName(Bool));
|
|
networkDescription.insert("isBridgeController", enumValueName(Bool));
|
|
networkDescription.insert("waitingForNodeAddition", enumValueName(Bool));
|
|
networkDescription.insert("waitingForNodeRemoval", enumValueName(Bool));
|
|
registerObject("ZWaveNetwork", networkDescription);
|
|
|
|
QVariantMap nodeDescription;
|
|
nodeDescription.insert("nodeId", enumValueName(Uint));
|
|
nodeDescription.insert("networkUuid", enumValueName(Uuid));
|
|
nodeDescription.insert("initialized", enumValueName(Bool));
|
|
nodeDescription.insert("reachable", enumValueName(Bool));
|
|
nodeDescription.insert("failed", enumValueName(Bool));
|
|
nodeDescription.insert("sleeping", enumValueName(Bool));
|
|
nodeDescription.insert("linkQuality", enumValueName(Uint));
|
|
nodeDescription.insert("securityMode", enumValueName(Uint));
|
|
nodeDescription.insert("nodeType", enumRef<ZWaveNode::ZWaveNodeType>());
|
|
nodeDescription.insert("role", enumRef<ZWaveNode::ZWaveNodeRole>());
|
|
nodeDescription.insert("deviceType", enumRef<ZWaveNode::ZWaveDeviceType>());
|
|
nodeDescription.insert("productType", enumValueName(Uint));
|
|
nodeDescription.insert("productId", enumValueName(Uint));
|
|
nodeDescription.insert("productName", enumValueName(String));
|
|
nodeDescription.insert("manufacturerId", enumValueName(Uint));
|
|
nodeDescription.insert("manufacturerName", enumValueName(String));
|
|
nodeDescription.insert("version", enumValueName(String));
|
|
nodeDescription.insert("isZWavePlusDevice", enumValueName(Bool));
|
|
nodeDescription.insert("isSecurityDevice", enumValueName(Bool));
|
|
nodeDescription.insert("isBeamingDevice", enumValueName(Bool));
|
|
|
|
registerObject("ZWaveNode", nodeDescription);
|
|
|
|
QVariantMap params, returns;
|
|
QString description;
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Query if the Z-Wave subsystem is available at all.";
|
|
returns.insert("available", enumValueName(Bool));
|
|
registerMethod("IsZWaveAvailable", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Get the list of available serial ports from the host system.";
|
|
returns.insert("serialPorts", objectRef<SerialPorts>());
|
|
registerMethod("GetSerialPorts", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Get all the Z-Wave networks in the system.";
|
|
returns.insert("networks", QVariantList() << objectRef("ZWaveNetwork"));
|
|
registerMethod("GetNetworks", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Add a new Z-Wave network with the given serial port.";
|
|
params.insert("serialPort", enumValueName(String));
|
|
returns.insert("o:networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("AddNetwork", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Remove the given Z-Wave network from the system.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("RemoveNetwork", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Start the node inclusion procedure for the given Z-Wave network.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("AddNode", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Start the node removal procedure for the given Z-Wave network.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("RemoveNode", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Cancel any running node inclusion or removal procedure for the given Z-Wave network.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("CancelPendingOperation", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Remove the given failed node from the given Z-Wave network. This will not work if node is not marked as failed.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
params.insert("nodeId", enumValueName(Uint));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("RemoveFailedNode", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Factory reset the controller for the given Z-Wave network.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
registerMethod("FactoryResetNetwork", description, params, returns);
|
|
|
|
params.clear(); returns.clear();
|
|
description = "Get the list of nodes in a network";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
returns.insert("zwaveError", enumRef<ZWave::ZWaveError>());
|
|
returns.insert("o:nodes", QVariantList() << objectRef("ZWaveNode"));
|
|
registerMethod("GetNodes", description, params, returns);
|
|
|
|
// Notifications
|
|
params.clear();
|
|
description = "Emitted whenever a new Z-Wave network has been added to the system.";
|
|
params.insert("network", objectRef("ZWaveNetwork"));
|
|
registerNotification("NetworkAdded", description, params);
|
|
|
|
params.clear();
|
|
description = "Emitted whenever a Z-Wave network has been removed from the system.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
registerNotification("NetworkRemoved", description, params);
|
|
|
|
params.clear();
|
|
description = "Emitted whenever a Z-Wave network changes.";
|
|
params.insert("network", objectRef("ZWaveNetwork"));
|
|
registerNotification("NetworkChanged", description, params);
|
|
|
|
params.clear();
|
|
description = "Emitted whenever a Z-Wave node is added.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
params.insert("node", objectRef("ZWaveNode"));
|
|
registerNotification("NodeAdded", description, params);
|
|
|
|
params.clear();
|
|
description = "Emitted whenever a Z-Wave node has changed.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
params.insert("node", objectRef("ZWaveNode"));
|
|
registerNotification("NodeChanged", description, params);
|
|
|
|
params.clear();
|
|
description = "Emitted whenever a Z-Wave node is removed.";
|
|
params.insert("networkUuid", enumValueName(Uuid));
|
|
params.insert("nodeId", enumValueName(Uint));
|
|
registerNotification("NodeRemoved", description, params);
|
|
|
|
connect(m_zwaveManager, &ZWaveManager::networkAdded, this, &ZWaveHandler::onNetworkAdded);
|
|
connect(m_zwaveManager, &ZWaveManager::networkChanged, this, &ZWaveHandler::onNetworkChanged);
|
|
connect(m_zwaveManager, &ZWaveManager::networkStateChanged, this, &ZWaveHandler::onNetworkChanged);
|
|
connect(m_zwaveManager, &ZWaveManager::networkRemoved, this, &ZWaveHandler::onNetworkRemoved);
|
|
connect(m_zwaveManager, &ZWaveManager::nodeAdded, this, &ZWaveHandler::onNodeAdded);
|
|
connect(m_zwaveManager, &ZWaveManager::nodeChanged, this, &ZWaveHandler::onNodeChanged);
|
|
connect(m_zwaveManager, &ZWaveManager::nodeRemoved, this, &ZWaveHandler::onNodeRemoved);
|
|
}
|
|
|
|
QString ZWaveHandler::name() const
|
|
{
|
|
return "ZWave";
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::IsZWaveAvailable(const QVariantMap ¶ms)
|
|
{
|
|
Q_UNUSED(params)
|
|
return createReply({{"available", m_zwaveManager->available()}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::GetSerialPorts(const QVariantMap ¶ms)
|
|
{
|
|
Q_UNUSED(params)
|
|
|
|
QVariantList portList;
|
|
foreach (const SerialPort &serialPort, m_zwaveManager->serialPorts()) {
|
|
portList << pack(serialPort);
|
|
}
|
|
return createReply({{"serialPorts", portList}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::GetNetworks(const QVariantMap ¶ms)
|
|
{
|
|
Q_UNUSED(params)
|
|
|
|
QVariantList networkList;
|
|
foreach (ZWaveNetwork *network, m_zwaveManager->networks()) {
|
|
networkList.append(packNetwork(network));
|
|
}
|
|
return createReply({{"networks", networkList}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::AddNetwork(const QVariantMap ¶ms)
|
|
{
|
|
QPair<ZWave::ZWaveError, QUuid> status = m_zwaveManager->createNetwork(params.value("serialPort").toString());
|
|
|
|
QVariantMap returns;
|
|
returns.insert("zwaveError", enumValueName(status.first));
|
|
if (status.first == ZWave::ZWaveErrorNoError) {
|
|
returns.insert("networkUuid", status.second);
|
|
}
|
|
return createReply(returns);
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::RemoveNetwork(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
ZWave::ZWaveError status = m_zwaveManager->removeNetwork(networkUuid);
|
|
return createReply({{"zwaveError", enumValueName(status)}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::FactoryResetNetwork(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
ZWave::ZWaveError status = m_zwaveManager->factoryResetNetwork(networkUuid);
|
|
return createReply({{"zwaveError", enumValueName(status)}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::AddNode(const QVariantMap ¶ms)
|
|
{
|
|
ZWaveReply *zwaveReply = m_zwaveManager->addNode(params.value("networkUuid").toUuid());
|
|
JsonReply *jsonReply = createAsyncReply("AddNode");
|
|
connect(zwaveReply, &ZWaveReply::finished, jsonReply, [jsonReply](ZWave::ZWaveError status) {
|
|
jsonReply->setData({{"zwaveError", enumValueName(status)}});
|
|
jsonReply->finished();
|
|
});
|
|
return jsonReply;
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::GetNodes(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
ZWaveNetwork *network = m_zwaveManager->network(networkUuid);
|
|
if (!network) {
|
|
return createReply({{"zwaveError", enumValueName(ZWave::ZWaveErrorNetworkUuidNotFound)}});
|
|
}
|
|
ZWaveNodes nodes = m_zwaveManager->network(networkUuid)->nodes();
|
|
QVariantList nodeList;
|
|
foreach (ZWaveNode *node, nodes) {
|
|
nodeList.append(packNode(node));
|
|
}
|
|
return createReply({
|
|
{"zwaveError", enumValueName(ZWave::ZWaveErrorNoError)},
|
|
{"nodes", nodeList}
|
|
});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::RemoveNode(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
|
|
JsonReply *jsonReply = createAsyncReply("RemoveNode");
|
|
ZWaveReply *zwaveReply = m_zwaveManager->removeNode(networkUuid);
|
|
connect(zwaveReply, &ZWaveReply::finished, jsonReply, [jsonReply](ZWave::ZWaveError status) {
|
|
jsonReply->setData({{"zwaveError", enumValueName(status)}});
|
|
jsonReply->finished();
|
|
});
|
|
return jsonReply;
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::RemoveFailedNode(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
quint8 nodeId = params.value("nodeId").toUInt();
|
|
|
|
m_zwaveManager->removeFailedNode(networkUuid, nodeId);
|
|
return createReply({{"zwaveError", enumValueName(ZWave::ZWaveErrorNoError)}});
|
|
}
|
|
|
|
JsonReply *ZWaveHandler::CancelPendingOperation(const QVariantMap ¶ms)
|
|
{
|
|
QUuid networkUuid = params.value("networkUuid").toUuid();
|
|
m_zwaveManager->cancelPendingOperation(networkUuid);
|
|
return createReply({{"zwaveError", enumValueName(ZWave::ZWaveErrorNoError)}});
|
|
}
|
|
|
|
void ZWaveHandler::onNetworkAdded(ZWaveNetwork *network)
|
|
{
|
|
emit NetworkAdded({{"network", packNetwork(network)}});
|
|
}
|
|
|
|
void ZWaveHandler::onNetworkChanged(ZWaveNetwork *network)
|
|
{
|
|
emit NetworkChanged({{"network", packNetwork(network)}});
|
|
}
|
|
|
|
void ZWaveHandler::onNetworkRemoved(const QUuid &networkUuid)
|
|
{
|
|
emit NetworkRemoved({{"networkUuid", networkUuid.toString()}});
|
|
}
|
|
|
|
void ZWaveHandler::onNodeAdded(ZWaveNode *node)
|
|
{
|
|
emit NodeAdded({{"networkUuid", node->networkUuid()}, {"node", packNode(node)}});
|
|
}
|
|
|
|
void ZWaveHandler::onNodeChanged(ZWaveNode *node)
|
|
{
|
|
emit NodeChanged({{"networkUuid", node->networkUuid()}, {"node", packNode(node)}});
|
|
}
|
|
|
|
void ZWaveHandler::onNodeRemoved(ZWaveNode *node)
|
|
{
|
|
emit NodeRemoved({{"networkUuid", node->networkUuid()}, {"nodeId", node->nodeId()}});
|
|
}
|
|
|
|
QVariantMap ZWaveHandler::packNetwork(ZWaveNetwork *network)
|
|
{
|
|
return {
|
|
{"networkUuid", network->networkUuid()},
|
|
{"serialPort", network->serialPort()},
|
|
{"networkState", enumValueName(network->networkState())},
|
|
{"homeId", network->homeId()},
|
|
{"isZWavePlus", network->isZWavePlus()},
|
|
{"isPrimaryController", network->isPrimaryController()},
|
|
{"isStaticUpdateController", network->isStaticUpdateController()},
|
|
{"isBridgeController", network->isBridgeController()},
|
|
{"waitingForNodeAddition", network->waitingForNodeAddition()},
|
|
{"waitingForNodeRemoval", network->waitingForNodeRemoval()}
|
|
};
|
|
}
|
|
|
|
QVariantMap ZWaveHandler::packNode(ZWaveNode *node)
|
|
{
|
|
return {
|
|
{"nodeId", node->nodeId()},
|
|
{"networkUuid", node->networkUuid()},
|
|
{"initialized", node->initialized()},
|
|
{"reachable", node->reachable()},
|
|
{"failed", node->failed()},
|
|
{"sleeping", node->sleeping()},
|
|
{"linkQuality", node->linkQuality()},
|
|
{"securityMode", node->securityMode()},
|
|
{"nodeType", enumValueName(node->nodeType())},
|
|
{"role", enumValueName(node->role())},
|
|
{"deviceType", enumValueName(node->deviceType())},
|
|
{"productType", node->productType()},
|
|
{"productId", node->productId()},
|
|
{"productName", node->productName()},
|
|
{"manufacturerId", node->manufacturerId()},
|
|
{"manufacturerName", node->manufacturerName()},
|
|
{"version", node->version()},
|
|
{"isZWavePlusDevice", node->isZWavePlusDevice()},
|
|
{"isSecurityDevice", node->isSecurityDevice()},
|
|
{"isBeamingDevice", node->isBeamingDevice()}
|
|
};
|
|
}
|
|
|
|
}
|