added sunspec plugin

This commit is contained in:
Boernsman 2020-06-19 11:52:22 +02:00
parent a6d41012e4
commit c1cdaac571
13 changed files with 499 additions and 3 deletions

19
debian/control vendored
View File

@ -35,6 +35,7 @@ Section: libs
Depends: ${shlibs:Depends},
${misc:Depends},
nymea-plugins-modbus-translations
nymea-plugins-translations
Description: nymea.io plugin to send and receive generic modbus commands
The nymea daemon is a plugin based IoT (Internet of Things) server. The
server works like a translator for devices, things and services and
@ -50,7 +51,7 @@ Architecture: any
Section: libs
Depends: ${shlibs:Depends},
${misc:Depends},
nymea-plugins-modbus-translations,
nymea-plugins-modbus-translations
Description: nymea.io plugin for my-pv heating rods
The nymea daemon is a plugin based IoT (Internet of Things) server. The
server works like a translator for devices, things and services and
@ -61,6 +62,21 @@ Description: nymea.io plugin for my-pv heating rods
This package will install the nymea.io plugin for my-pv
Package: nymea-plugin-sunspec
Architecture: any
Depends: ${shlibs:Depends},
${misc:Depends},
nymea-plugins-modbus-translations
Description: nymea.io plugin for SunSpec Modbus devices.
The nymea daemon is a plugin based IoT (Internet of Things) server. The
server works like a translator for devices, things and services and
allows them to interact.
With the powerful rule engine you are able to connect any device available
in the system and create individual scenes and behaviors for your environment.
.
This package will install the nymea.io plugin for manufactor independent sunspec devices.
Package: nymea-plugin-wallbe
Architecture: any
Section: libs
@ -89,4 +105,3 @@ Description: Translation files for nymea modbus plugins - translations
in the system and create individual scenes and behaviors for your environment.
.
This package provides the translation files for all nymea modbus plugins.

View File

@ -0,0 +1 @@
usr/lib/@DEB_HOST_MULTIARCH@/nymea/plugins/libnymea_devicepluginsunspec.so

View File

@ -195,7 +195,6 @@ void IntegrationPluginMyPv::executeAction(ThingActionInfo *info)
void IntegrationPluginMyPv::onRefreshTimer()
{
foreach (Thing *thing, myThings()) {
update(thing);
}

View File

@ -4,6 +4,7 @@ PLUGIN_DIRS = \
drexelundweiss \
modbuscommander \
mypv \
sunspec \
wallbe \
message(============================================)

16
sunspec/README.md Normal file
View File

@ -0,0 +1,16 @@
# SunSpec
## Supported Things
* SunSpec Inverter
* SunSpec PV Modules
* SunSpec Meter
* SunSpec Tracker
* SunSpec Storage
## Requirements
* The package 'nymea-plugin-sunspec' must be installed.
## More
https://sunspec.org

View File

@ -0,0 +1,119 @@
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* Copyright 2013 - 2020, 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 Lesser General Public License Usage
* Alternatively, this project may be redistributed and/or modified under the
* terms of the GNU Lesser General Public License as published by the Free
* Software Foundation; 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser 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 "plugininfo.h"
#include "integrationpluginsunspec.h"
#include <QHostAddress>
IntegrationPluginSunSpec::IntegrationPluginSunSpec()
{
}
void IntegrationPluginSunSpec::discoverThings(ThingDiscoveryInfo *info)
{
// Discovery possible?
Q_ASSERT_X(false, "discoverThing", QString("Unhandled thingClassId: %1").arg(info->thingClassId().toString()).toUtf8());
}
void IntegrationPluginSunSpec::setupThing(ThingSetupInfo *info)
{
if (info->thing()->thingClassId() == sunspecInverterThingClassId) {
} else if (info->thing()->thingClassId() == sunspecPvModuleThingClassId) {
} else if (info->thing()->thingClassId() == sunspecMeterThingClassId) {
} else if (info->thing()->thingClassId() == sunspecTrackerThingClassId) {
} else if (info->thing()->thingClassId() == sunspecStorageThingClassId) {
} else {
Q_ASSERT_X(false, "setupThing", QString("Unhandled thingClassId: %1").arg(info->thing()->thingClassId().toString()).toUtf8());
}
}
void IntegrationPluginSunSpec::postSetupThing(Thing *thing)
{
Q_UNUSED(thing)
if (!m_refreshTimer) {
int refreshTime = configValue(sunSpecPluginUpdateIntervalParamTypeId).toInt();
m_refreshTimer = hardwareManager()->pluginTimerManager()->registerTimer(refreshTime);
connect(m_refreshTimer, &PluginTimer::timeout, this, &IntegrationPluginSunSpec::onRefreshTimer);
}
}
void IntegrationPluginSunSpec::thingRemoved(Thing *thing)
{
Q_UNUSED(thing)
if (myThings().isEmpty()) {
hardwareManager()->pluginTimerManager()->unregisterTimer(m_refreshTimer);
m_refreshTimer = nullptr;
}
}
void IntegrationPluginSunSpec::executeAction(ThingActionInfo *info)
{
Thing *thing = info->thing();
//Action action = info->action();
if (thing->thingClassId() == sunspecInverterThingClassId) {
info->finish(Thing::ThingErrorActionTypeNotFound);
} else if (thing->thingClassId() == sunspecMeterThingClassId) {
info->finish(Thing::ThingErrorActionTypeNotFound);
} else if (thing->thingClassId() == sunspecTrackerThingClassId) {
info->finish(Thing::ThingErrorActionTypeNotFound);
} else if (thing->thingClassId() == sunspecPvModuleThingClassId) {
info->finish(Thing::ThingErrorActionTypeNotFound);
} else if (thing->thingClassId() == sunspecStorageThingClassId) {
info->finish(Thing::ThingErrorActionTypeNotFound);
} else {
Q_ASSERT_X(false, "executeAction", QString("Unhandled thingClassId: %1").arg(info->thing()->thingClassId().toString()).toUtf8());
}
}
void IntegrationPluginSunSpec::onRefreshTimer()
{
//get data
}
void IntegrationPluginSunSpec::onPluginConfigurationChanged(const ParamTypeId &paramTypeId, const QVariant &value)
{
// Check refresh schedule
if (paramTypeId == sunSpecPluginUpdateIntervalParamTypeId) {
if (m_refreshTimer) {
int refreshTime = value.toInt();
m_refreshTimer->stop();
m_refreshTimer->startTimer(refreshTime);
}
}
}

View File

@ -0,0 +1,80 @@
/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *
*
* Copyright 2013 - 2020, 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 Lesser General Public License Usage
* Alternatively, this project may be redistributed and/or modified under the
* terms of the GNU Lesser General Public License as published by the Free
* Software Foundation; 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
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser 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
*
* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
#ifndef INTEGRATIONPLUGINSUNSPEC_H
#define INTEGRATIONPLUGINSUNSPEC_H
#include "integrations/integrationplugin.h"
#include "plugintimer.h"
#include "../modbus/modbustcpmaster.h"
#include <QUuid>
class IntegrationPluginSunSpec: public IntegrationPlugin
{
Q_OBJECT
Q_PLUGIN_METADATA(IID "io.nymea.IntegrationPlugin" FILE "integrationpluginsunspec.json")
Q_INTERFACES(IntegrationPlugin)
public:
explicit IntegrationPluginSunSpec();
void discoverThings(ThingDiscoveryInfo *info) override;
void setupThing(ThingSetupInfo *info) override;
void postSetupThing(Thing *thing) override;
void thingRemoved(Thing *thing) override;
void executeAction(ThingActionInfo *info) override;
private:
PluginTimer *m_refreshTimer = nullptr;
QHash<Thing *, ModbusTCPMaster *> m_modbusTcpMasters;
QHash<QUuid, ThingActionInfo *> m_asyncActions;
void update(Thing *thing);
private slots:
void onRefreshTimer();
void onPluginConfigurationChanged(const ParamTypeId &paramTypeId, const QVariant &value);
void onConnectionStateChanged(bool status);
void onWriteRequestExecuted(QUuid requestId, bool success);
void onWriteRequestError(QUuid requestId, const QString &error);
void onReceivedHoldingRegister(quint32 slaveAddress, quint32 modbusRegister, const QVector<quint16> &values);
void onReceivedInputRegister(quint32 slaveAddress, quint32 modbusRegister, const QVector<quint16> &values);
};
#endif // INTEGRATIONPLUGINSUNSPEC_H

View File

@ -0,0 +1,238 @@
{
"name": "SunSpec",
"displayName": "sunspec",
"id": "73c7efcc-80d5-4166-ad97-2cbbeb129d91",
"paramTypes":[
{
"id": "52da5222-9a94-47a2-9adc-004541d2f5ed",
"name": "updateInterval",
"displayName": "Update interval",
"type": "int",
"unit": "Seconds",
"defaultValue": 15
}
],
"vendors": [
{
"name": "sunspec",
"displayName": "SunSpec",
"id": "c143a7b4-a16c-4fff-86a3-9ffab3d6841d",
"thingClasses": [
{
"name": "sunspecInverter",
"displayName": "SunSpec Inverter",
"id": "2e4122ea-96a5-415c-b5e2-7d6012265a83",
"createMethods": [ "User" ],
"interfaces": ["connectable"],
"paramTypes": [
{
"id": "6ffaa694-a4f2-4936-b043-37679449a34b",
"name":"ipAddress",
"displayName": "IP address",
"type": "QString"
},
{
"id": "08bf6597-976d-4fb9-8fc2-4372c07961d4",
"name":"serialNumber",
"displayName": "Serial number",
"type": "QString"
}
],
"stateTypes":[
{
"id": "4401468c-0385-40a9-b436-daf7ed6a50d5",
"name": "connected",
"displayName": "Connected",
"displayNameEvent": "Connected changed",
"type": "bool",
"defaultValue": false,
"cached": false
},
{
"id": "9bdcc785-4738-437e-88a0-fc231095c2dd",
"name": "power",
"displayName": "Power",
"displayNameEvent": "Power changed",
"displayNameAction": "Change power",
"type": "bool",
"defaultValue": 0,
"writable": true
}
]
},
{
"name": "sunspecPvModule",
"displayName": "SunSpec PV Module",
"id": "fb7ff0df-a745-4313-83e4-1e5007b06fe2",
"createMethods": [ "User" ],
"interfaces": ["connectable"],
"paramTypes": [
{
"id": "890e468b-fc76-4641-9569-93cd45e6bb8d",
"name":"ipAddress",
"displayName": "IP address",
"type": "QString"
},
{
"id": "d5a9510d-720f-4a28-9d91-977eedd022bd",
"name":"serialNumber",
"displayName": "Serial number",
"type": "QString"
}
],
"stateTypes":[
{
"id": "edc032d2-022f-43f7-9131-831ad23ee62a",
"name": "connected",
"displayName": "Connected",
"displayNameEvent": "Connected changed",
"type": "bool",
"defaultValue": false,
"cached": false
},
{
"id": "0b7485eb-3cf7-45b2-87cf-9ec85366b197",
"name": "power",
"displayName": "Power",
"displayNameEvent": "Power changed",
"displayNameAction": "Change power",
"type": "bool",
"defaultValue": 0,
"writable": true
}
]
},
{
"name": "sunspecMeter",
"displayName": "SunSpec Meter",
"id": "68f822f9-ff30-4275-b229-39a3674fead7",
"createMethods": [ "User" ],
"interfaces": ["connectable"],
"paramTypes": [
{
"id": "66bdb89b-bbd4-4edf-96df-649014d94c42",
"name":"ipAddress",
"displayName": "IP address",
"type": "QString"
},
{
"id": "89af6d27-4b81-42ef-9883-1e2ba2067884",
"name":"serialNumber",
"displayName": "Serial number",
"type": "QString"
}
],
"stateTypes":[
{
"id": "36f861c7-afc1-4725-b41f-67113200d78f",
"name": "connected",
"displayName": "Connected",
"displayNameEvent": "Connected changed",
"type": "bool",
"defaultValue": false,
"cached": false
},
{
"id": "36f18720-69ca-4021-9328-262d87397f1b",
"name": "power",
"displayName": "Power",
"displayNameEvent": "Power changed",
"displayNameAction": "Change power",
"type": "bool",
"defaultValue": 0,
"writable": true
}
]
},
{
"name": "sunspecTracker",
"displayName": "SunSpec Tracker",
"id": "9941da30-a6d6-475d-8244-3c2145b419e6",
"createMethods": [ "User" ],
"interfaces": ["connectable"],
"paramTypes": [
{
"id": "ccdcca78-7efa-4253-8fdb-8731e6880e9b",
"name":"ipAddress",
"displayName": "IP address",
"type": "QString"
},
{
"id": "67ce05ff-14bf-4d43-94ba-d5f290278514",
"name":"serialNumber",
"displayName": "Serial number",
"type": "QString"
}
],
"stateTypes":[
{
"id": "fe57e465-e49e-4d50-b880-6d9a243783ff",
"name": "connected",
"displayName": "Connected",
"displayNameEvent": "Connected changed",
"type": "bool",
"defaultValue": false,
"cached": false
},
{
"id": "d2bbba4b-998f-444e-935f-f958927afddd",
"name": "power",
"displayName": "Power",
"displayNameEvent": "Power changed",
"displayNameAction": "Change power",
"type": "bool",
"defaultValue": 0,
"writable": true
}
]
},
{
"name": "sunspecStorage",
"displayName": "SunSpec Storage",
"id": "9a643ba8-346c-4127-a2f8-956a7133d75e",
"createMethods": [ "User" ],
"interfaces": ["connectable"],
"paramTypes": [
{
"id": "421cacb9-a94d-4ba9-923c-3bc30d8b94c8",
"name":"ipAddress",
"displayName": "IP address",
"type": "QString"
},
{
"id": "ae76db81-7969-440f-85f0-28ed46d772db",
"name":"serialNumber",
"displayName": "Serial number",
"type": "QString"
}
],
"stateTypes":[
{
"id": "25a1fb10-a6b9-4037-b7cf-ad481a65beb4",
"name": "connected",
"displayName": "Connected",
"displayNameEvent": "Connected changed",
"type": "bool",
"defaultValue": false,
"cached": false
},
{
"id": "9c0e0b08-4461-4e54-aaf3-cab9155028da",
"name": "power",
"displayName": "Power",
"displayNameEvent": "Power changed",
"displayNameAction": "Change power",
"type": "bool",
"defaultValue": 0,
"writable": true
}
]
}
]
}
]
}

12
sunspec/meta.json Normal file
View File

@ -0,0 +1,12 @@
{
"title": "SunSpec",
"tagline": "Connect to SunSpec devices.",
"icon": "sunspec.png",
"stability": "consumer",
"offline": true,
"technologies": [
"network"
],
"categories": [
]
}

0
sunspec/sunspec.cpp Normal file
View File

0
sunspec/sunspec.h Normal file
View File

BIN
sunspec/sunspec.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 8.6 KiB

15
sunspec/sunspec.pro Normal file
View File

@ -0,0 +1,15 @@
include(../plugins.pri)
QT += \
network \
serialbus \
SOURCES += \
integrationpluginsunspec.cpp \
sunspec.cpp \
../modbus/modbustcpmaster.cpp \
HEADERS += \
integrationpluginsunspec.h \
sunspec.h \
../modbus/modbustcpmaster.h \