Merge PR #85: Add support nymea's MQTT broker configuration
This commit is contained in:
commit
05efea3d5f
@ -1,237 +0,0 @@
|
||||
#include "basicconfiguration.h"
|
||||
#include "serverconfiguration.h"
|
||||
|
||||
#include "jsonrpc/jsonrpcclient.h"
|
||||
|
||||
BasicConfiguration::BasicConfiguration(JsonRpcClient* client, QObject *parent) :
|
||||
JsonHandler(parent),
|
||||
m_client(client),
|
||||
m_tcpServerConfigurations(new ServerConfigurations(this)),
|
||||
m_websocketServerConfigurations(new ServerConfigurations(this))
|
||||
{
|
||||
client->registerNotificationHandler(this, "notificationReceived");
|
||||
}
|
||||
|
||||
QString BasicConfiguration::nameSpace() const
|
||||
{
|
||||
return "Configuration";
|
||||
}
|
||||
|
||||
bool BasicConfiguration::debugServerEnabled() const
|
||||
{
|
||||
return m_debugServerEnabled;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setDebugServerEnabled(bool debugServerEnabled)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("enabled", debugServerEnabled);
|
||||
m_client->sendCommand("Configuration.SetDebugServerEnabled", params, this, "setDebugServerEnabledResponse");
|
||||
}
|
||||
|
||||
QString BasicConfiguration::serverName() const
|
||||
{
|
||||
return m_serverName;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setServerName(const QString &serverName)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("serverName", serverName);
|
||||
m_client->sendCommand("Configuration.SetServerName", params, this, "setServerNameResponse");
|
||||
}
|
||||
|
||||
bool BasicConfiguration::cloudEnabled() const
|
||||
{
|
||||
return m_cloudEnabled;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setCloudEnabled(bool cloudEnabled)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("enabled", cloudEnabled);
|
||||
m_client->sendCommand("Configuration.SetCloudEnabled", params, this, "setCloudEnabledResponse");
|
||||
}
|
||||
|
||||
QString BasicConfiguration::language() const
|
||||
{
|
||||
return m_language;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setLanguage(const QString &language)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("language", language);
|
||||
m_client->sendCommand("Configuration.SetLanguage", params);
|
||||
}
|
||||
|
||||
QString BasicConfiguration::timezone() const
|
||||
{
|
||||
return m_timezone;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setTimezone(const QString &timezone)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("timeZone", timezone);
|
||||
m_client->sendCommand("Configuration.SetTimeZone", params, this, "setTimezoneResponse");
|
||||
}
|
||||
|
||||
QStringList BasicConfiguration::timezones() const
|
||||
{
|
||||
return m_timezones;
|
||||
}
|
||||
|
||||
ServerConfigurations *BasicConfiguration::tcpServerConfigurations() const
|
||||
{
|
||||
return m_tcpServerConfigurations;
|
||||
}
|
||||
|
||||
ServerConfigurations *BasicConfiguration::websocketServerConfigurations() const
|
||||
{
|
||||
return m_websocketServerConfigurations;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setTcpServerConfiguration(ServerConfiguration *configuration) const
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", configuration->id());
|
||||
params.insert("address", configuration->address());
|
||||
params.insert("port", configuration->address());
|
||||
params.insert("authentiactionEnabled", configuration->authenticationEnabled());
|
||||
params.insert("sslEnabled", configuration->sslEnabled());
|
||||
m_client->sendCommand("Configuration.SetTcpServerConfiguration", params);
|
||||
}
|
||||
|
||||
void BasicConfiguration::deleteTcpServerConfiguration(const QString &id)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", id);
|
||||
m_client->sendCommand("Configuration.DeleteTcpServerConfiguration", params, this, "deleteTcpConfigReply");
|
||||
}
|
||||
|
||||
void BasicConfiguration::deleteWebsocketServerConfiguration(const QString &id)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", id);
|
||||
m_client->sendCommand("Configuration.DeleteWebSocketServerConfiguration", params, this, "deleteWebSocketConfigReply");
|
||||
}
|
||||
|
||||
QStringList BasicConfiguration::availableLanguages() const
|
||||
{
|
||||
return m_availableLanguages;
|
||||
}
|
||||
|
||||
void BasicConfiguration::init()
|
||||
{
|
||||
m_client->sendCommand("Configuration.GetConfigurations", this, "getConfigurationsResponse");
|
||||
m_client->sendCommand("Configuration.GetAvailableLanguages", this, "getAvailableLanguagesResponse");
|
||||
m_client->sendCommand("Configuration.GetTimeZones", this, "getTimezonesResponse");
|
||||
}
|
||||
|
||||
void BasicConfiguration::getConfigurationsResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "have config reply" << params;
|
||||
QVariantMap basicConfig = params.value("params").toMap().value("basicConfiguration").toMap();
|
||||
m_debugServerEnabled = basicConfig.value("debugServerEnabled").toBool();
|
||||
emit debugServerEnabledChanged();
|
||||
m_serverName = basicConfig.value("serverName").toString();
|
||||
emit serverNameChanged();
|
||||
m_language = basicConfig.value("language").toString();
|
||||
emit languageChanged();
|
||||
m_timezone = basicConfig.value("timeZone").toString();
|
||||
emit timezoneChanged();
|
||||
QVariantMap cloudConfig = params.value("params").toMap().value("cloud").toMap();
|
||||
m_cloudEnabled = cloudConfig.value("enabled").toBool();
|
||||
emit cloudEnabledChanged();
|
||||
|
||||
tcpServerConfigurations()->clear();
|
||||
foreach (const QVariant &tcpServerVariant, params.value("params").toMap().value("tcpServerConfigurations").toList()) {
|
||||
qDebug() << "tcp server config:" << tcpServerVariant;
|
||||
QVariantMap tcpConfigMap = tcpServerVariant.toMap();
|
||||
ServerConfiguration *config = new ServerConfiguration(tcpConfigMap.value("id").toString(), QHostAddress(tcpConfigMap.value("address").toString()), tcpConfigMap.value("port").toInt(), tcpConfigMap.value("authenticationEnabled").toBool(), tcpConfigMap.value("sslEnabled").toBool());
|
||||
m_tcpServerConfigurations->addConfiguration(config);
|
||||
}
|
||||
websocketServerConfigurations()->clear();
|
||||
foreach (const QVariant &websocketServerVariant, params.value("params").toMap().value("webSocketServerConfigurations").toList()) {
|
||||
QVariantMap websocketConfigMap = websocketServerVariant.toMap();
|
||||
ServerConfiguration *config = new ServerConfiguration(websocketConfigMap.value("id").toString(), QHostAddress(websocketConfigMap.value("address").toString()), websocketConfigMap.value("port").toInt(), websocketConfigMap.value("authenticationEnabled").toBool(), websocketConfigMap.value("sslEnabled").toBool());
|
||||
m_websocketServerConfigurations->addConfiguration(config);
|
||||
}
|
||||
}
|
||||
|
||||
void BasicConfiguration::getCloudConfigurationResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Cloud config reply" << params;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setDebugServerEnabledResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Debug server set:" << params;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setServerNameResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Server name set:" << params;
|
||||
}
|
||||
|
||||
void BasicConfiguration::setCloudEnabledResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set cloud enabled:" << params;
|
||||
}
|
||||
|
||||
void BasicConfiguration::getAvailableLanguagesResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
// qDebug() << "Get available languages response" << params;
|
||||
m_availableLanguages = params.value("params").toMap().value("languages").toStringList();
|
||||
emit availableLanguagesChanged();
|
||||
}
|
||||
|
||||
void BasicConfiguration::getTimezonesResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
// qDebug() << "Get timezones response" << params;
|
||||
m_timezones = params.value("params").toMap().value("timeZones").toStringList();
|
||||
emit timezonesChanged();
|
||||
}
|
||||
|
||||
void BasicConfiguration::setTimezoneResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set timezones response" << params;
|
||||
}
|
||||
|
||||
void BasicConfiguration::deleteTcpConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
if (params.value("params").toMap().value("configurationError").toString() == "ConfigurationErrorNoError") {
|
||||
}
|
||||
}
|
||||
|
||||
void BasicConfiguration::deleteWebSocketConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void BasicConfiguration::notificationReceived(const QVariantMap ¬ification)
|
||||
{
|
||||
QString notif = notification.value("notification").toString();
|
||||
if (notif == "Configuration.BasicConfigurationChanged") {
|
||||
QVariantMap params = notification.value("params").toMap().value("basicConfiguration").toMap();
|
||||
qDebug() << "notif" << params;
|
||||
m_debugServerEnabled = params.value("debugServerEnabled").toBool();
|
||||
emit debugServerEnabledChanged();
|
||||
m_serverName = params.value("serverName").toString();
|
||||
emit serverNameChanged();
|
||||
m_language = params.value("language").toString();
|
||||
emit languageChanged();
|
||||
m_timezone = params.value("timeZone").toString();
|
||||
emit timezoneChanged();
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.CloudConfigurationChanged") {
|
||||
QVariantMap params = notification.value("params").toMap().value("cloudConfiguration").toMap();
|
||||
qDebug() << "notif" << params;
|
||||
m_cloudEnabled = params.value("enabled").toBool();
|
||||
emit cloudEnabledChanged();
|
||||
return;
|
||||
}
|
||||
qDebug() << "Unhandled Configuration notification" << notif;
|
||||
}
|
||||
109
libnymea-app-core/configuration/mqttpolicies.cpp
Normal file
109
libnymea-app-core/configuration/mqttpolicies.cpp
Normal file
@ -0,0 +1,109 @@
|
||||
#include "mqttpolicies.h"
|
||||
#include "mqttpolicy.h"
|
||||
|
||||
MqttPolicies::MqttPolicies(QObject *parent) : QAbstractListModel(parent)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
int MqttPolicies::rowCount(const QModelIndex &index) const
|
||||
{
|
||||
Q_UNUSED(index)
|
||||
return m_list.count();
|
||||
}
|
||||
|
||||
QVariant MqttPolicies::data(const QModelIndex &index, int role) const
|
||||
{
|
||||
switch (role) {
|
||||
case RoleClientId:
|
||||
return m_list.at(index.row())->clientId();
|
||||
case RoleUsername:
|
||||
return m_list.at(index.row())->username();
|
||||
case RolePassword:
|
||||
return m_list.at(index.row())->password();
|
||||
case RoleAllowedPublishTopicFilters:
|
||||
return m_list.at(index.row())->allowedPublishTopicFilters();
|
||||
case RoleAllowedSubscribeTopicFilters:
|
||||
return m_list.at(index.row())->allowedSubscribeTopicFilters();
|
||||
}
|
||||
return QVariant();
|
||||
}
|
||||
|
||||
QHash<int, QByteArray> MqttPolicies::roleNames() const
|
||||
{
|
||||
QHash<int, QByteArray> roles;
|
||||
roles.insert(RoleClientId, "clientId");
|
||||
roles.insert(RoleUsername, "username");
|
||||
roles.insert(RolePassword, "password");
|
||||
roles.insert(RoleAllowedPublishTopicFilters, "allowedPublishTopicFilters");
|
||||
roles.insert(RoleAllowedSubscribeTopicFilters, "allowedSubscribeTopicFilters");
|
||||
return roles;
|
||||
}
|
||||
|
||||
void MqttPolicies::addPolicy(MqttPolicy *policy)
|
||||
{
|
||||
policy->setParent(this);
|
||||
beginInsertRows(QModelIndex(), m_list.count(), m_list.count());
|
||||
m_list.append(policy);
|
||||
|
||||
connect(policy, &MqttPolicy::clientIdChanged, this, [this, policy]() {
|
||||
QModelIndex index = this->index(m_list.indexOf(policy));
|
||||
emit dataChanged(index, index, {RoleClientId});
|
||||
});
|
||||
connect(policy, &MqttPolicy::usernameChanged, this, [this, policy]() {
|
||||
QModelIndex index = this->index(m_list.indexOf(policy));
|
||||
emit dataChanged(index, index, {RoleUsername});
|
||||
});
|
||||
connect(policy, &MqttPolicy::passwordChanged, this, [this, policy]() {
|
||||
QModelIndex index = this->index(m_list.indexOf(policy));
|
||||
emit dataChanged(index, index, {RolePassword});
|
||||
});
|
||||
connect(policy, &MqttPolicy::allowedPublishTopicFiltersChanged, this, [this, policy]() {
|
||||
QModelIndex index = this->index(m_list.indexOf(policy));
|
||||
emit dataChanged(index, index, {RoleAllowedPublishTopicFilters});
|
||||
});
|
||||
connect(policy, &MqttPolicy::allowedSubscribeTopicFiltersChanged, this, [this, policy]() {
|
||||
QModelIndex index = this->index(m_list.indexOf(policy));
|
||||
emit dataChanged(index, index, {RoleAllowedSubscribeTopicFilters});
|
||||
});
|
||||
|
||||
endInsertRows();
|
||||
emit countChanged();
|
||||
}
|
||||
|
||||
void MqttPolicies::removePolicy(MqttPolicy *policy)
|
||||
{
|
||||
int idx = m_list.indexOf(policy);
|
||||
if (idx < 0) {
|
||||
return;
|
||||
}
|
||||
beginRemoveRows(QModelIndex(), idx, idx);
|
||||
m_list.takeAt(idx)->deleteLater();
|
||||
endRemoveRows();
|
||||
}
|
||||
|
||||
MqttPolicy *MqttPolicies::getPolicy(const QString &clientId) const
|
||||
{
|
||||
foreach (MqttPolicy* policy, m_list) {
|
||||
if (policy->clientId() == clientId) {
|
||||
return policy;
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
MqttPolicy *MqttPolicies::get(int index) const
|
||||
{
|
||||
if (index < 0 || index >= m_list.count()){
|
||||
return nullptr;
|
||||
}
|
||||
return m_list.at(index);
|
||||
}
|
||||
|
||||
void MqttPolicies::clear()
|
||||
{
|
||||
beginResetModel();
|
||||
qDeleteAll(m_list);
|
||||
m_list.clear();
|
||||
endResetModel();
|
||||
}
|
||||
42
libnymea-app-core/configuration/mqttpolicies.h
Normal file
42
libnymea-app-core/configuration/mqttpolicies.h
Normal file
@ -0,0 +1,42 @@
|
||||
#ifndef MQTTPOLICIES_H
|
||||
#define MQTTPOLICIES_H
|
||||
|
||||
#include <QObject>
|
||||
#include <QAbstractListModel>
|
||||
|
||||
class MqttPolicy;
|
||||
|
||||
class MqttPolicies : public QAbstractListModel
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(int count READ rowCount NOTIFY countChanged)
|
||||
public:
|
||||
enum Roles {
|
||||
RoleClientId,
|
||||
RoleUsername,
|
||||
RolePassword,
|
||||
RoleAllowedPublishTopicFilters,
|
||||
RoleAllowedSubscribeTopicFilters
|
||||
};
|
||||
|
||||
explicit MqttPolicies(QObject *parent = nullptr);
|
||||
|
||||
int rowCount(const QModelIndex &index = QModelIndex()) const override;
|
||||
QVariant data(const QModelIndex &index, int role) const override;
|
||||
QHash<int, QByteArray> roleNames() const override;
|
||||
|
||||
void addPolicy(MqttPolicy *policy);
|
||||
void removePolicy(MqttPolicy *policy);
|
||||
|
||||
Q_INVOKABLE MqttPolicy* getPolicy(const QString &clientId) const;
|
||||
Q_INVOKABLE MqttPolicy* get(int index) const;
|
||||
|
||||
void clear();
|
||||
signals:
|
||||
void countChanged();
|
||||
|
||||
private:
|
||||
QList<MqttPolicy*> m_list;
|
||||
};
|
||||
|
||||
#endif // MQTTPOLICIES_H
|
||||
82
libnymea-app-core/configuration/mqttpolicy.cpp
Normal file
82
libnymea-app-core/configuration/mqttpolicy.cpp
Normal file
@ -0,0 +1,82 @@
|
||||
#include "mqttpolicy.h"
|
||||
|
||||
MqttPolicy::MqttPolicy(const QString &clientId, const QString &username, const QString &password, const QStringList &allowedPublishTopicFilters, const QStringList &allowedSubscribeTopicFilters, QObject *parent):
|
||||
QObject(parent),
|
||||
m_clientId(clientId),
|
||||
m_username(username),
|
||||
m_password(password),
|
||||
m_allowedPublishTopicFilters(allowedPublishTopicFilters),
|
||||
m_allowedSubscribeTopicFilters(allowedSubscribeTopicFilters)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
QString MqttPolicy::clientId() const
|
||||
{
|
||||
return m_clientId;
|
||||
}
|
||||
|
||||
void MqttPolicy::setClientId(const QString &clientId)
|
||||
{
|
||||
if (m_clientId != clientId) {
|
||||
m_clientId = clientId;
|
||||
emit clientIdChanged();
|
||||
}
|
||||
}
|
||||
|
||||
QString MqttPolicy::username() const
|
||||
{
|
||||
return m_username;
|
||||
}
|
||||
|
||||
void MqttPolicy::setUsername(const QString &username)
|
||||
{
|
||||
if (m_username != username) {
|
||||
m_username = username;
|
||||
emit usernameChanged();
|
||||
}
|
||||
}
|
||||
|
||||
QString MqttPolicy::password() const
|
||||
{
|
||||
return m_password;
|
||||
}
|
||||
|
||||
void MqttPolicy::setPassword(const QString &password)
|
||||
{
|
||||
if (m_password != password) {
|
||||
m_password = password;
|
||||
emit passwordChanged();
|
||||
}
|
||||
}
|
||||
|
||||
QStringList MqttPolicy::allowedPublishTopicFilters() const
|
||||
{
|
||||
return m_allowedPublishTopicFilters;
|
||||
}
|
||||
|
||||
void MqttPolicy::setAllowedPublishTopicFilters(const QStringList &allowedPublishTopicFilters)
|
||||
{
|
||||
if (m_allowedPublishTopicFilters != allowedPublishTopicFilters) {
|
||||
m_allowedPublishTopicFilters = allowedPublishTopicFilters;
|
||||
emit allowedPublishTopicFiltersChanged();
|
||||
}
|
||||
}
|
||||
|
||||
QStringList MqttPolicy::allowedSubscribeTopicFilters() const
|
||||
{
|
||||
return m_allowedSubscribeTopicFilters;
|
||||
}
|
||||
|
||||
void MqttPolicy::setAllowedSubscribeTopicFilters(const QStringList &allowedSubscribeTopicFilters)
|
||||
{
|
||||
if (m_allowedSubscribeTopicFilters != allowedSubscribeTopicFilters) {
|
||||
m_allowedSubscribeTopicFilters = allowedSubscribeTopicFilters;
|
||||
emit allowedSubscribeTopicFiltersChanged();
|
||||
}
|
||||
}
|
||||
|
||||
MqttPolicy *MqttPolicy::clone()
|
||||
{
|
||||
return new MqttPolicy(m_clientId, m_username, m_password, m_allowedPublishTopicFilters, m_allowedSubscribeTopicFilters, this);
|
||||
}
|
||||
54
libnymea-app-core/configuration/mqttpolicy.h
Normal file
54
libnymea-app-core/configuration/mqttpolicy.h
Normal file
@ -0,0 +1,54 @@
|
||||
#ifndef MQTTPOLICY_H
|
||||
#define MQTTPOLICY_H
|
||||
|
||||
#include <QObject>
|
||||
|
||||
class MqttPolicy : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString clientId READ clientId WRITE setClientId NOTIFY clientIdChanged)
|
||||
Q_PROPERTY(QString username READ username WRITE setUsername NOTIFY usernameChanged)
|
||||
Q_PROPERTY(QString password READ password WRITE setPassword NOTIFY passwordChanged)
|
||||
Q_PROPERTY(QStringList allowedPublishTopicFilters READ allowedPublishTopicFilters WRITE setAllowedPublishTopicFilters NOTIFY allowedPublishTopicFiltersChanged)
|
||||
Q_PROPERTY(QStringList allowedSubscribeTopicFilters READ allowedSubscribeTopicFilters WRITE setAllowedSubscribeTopicFilters NOTIFY allowedSubscribeTopicFiltersChanged)
|
||||
|
||||
public:
|
||||
explicit MqttPolicy(const QString &clientId = QString(),
|
||||
const QString &username = QString(),
|
||||
const QString &password = QString(),
|
||||
const QStringList &allowedPublishTopicFilters = QStringList(),
|
||||
const QStringList &allowedSubscribeTopicFilters = QStringList(),
|
||||
QObject *parent = nullptr);
|
||||
|
||||
QString clientId() const;
|
||||
void setClientId(const QString &clientId);
|
||||
|
||||
QString username() const;
|
||||
void setUsername(const QString &username);
|
||||
|
||||
QString password() const;
|
||||
void setPassword(const QString &password);
|
||||
|
||||
QStringList allowedPublishTopicFilters() const;
|
||||
void setAllowedPublishTopicFilters(const QStringList &allowedPublishTopicFilters);
|
||||
|
||||
QStringList allowedSubscribeTopicFilters() const;
|
||||
void setAllowedSubscribeTopicFilters(const QStringList &allowedSubscribeTopicFilters);
|
||||
|
||||
Q_INVOKABLE MqttPolicy* clone();
|
||||
signals:
|
||||
void clientIdChanged();
|
||||
void usernameChanged();
|
||||
void passwordChanged();
|
||||
void allowedPublishTopicFiltersChanged();
|
||||
void allowedSubscribeTopicFiltersChanged();
|
||||
|
||||
private:
|
||||
QString m_clientId;
|
||||
QString m_username;
|
||||
QString m_password;
|
||||
QStringList m_allowedPublishTopicFilters;
|
||||
QStringList m_allowedSubscribeTopicFilters;
|
||||
};
|
||||
|
||||
#endif // MQTTPOLICY_H
|
||||
457
libnymea-app-core/configuration/nymeaconfiguration.cpp
Normal file
457
libnymea-app-core/configuration/nymeaconfiguration.cpp
Normal file
@ -0,0 +1,457 @@
|
||||
#include "nymeaconfiguration.h"
|
||||
|
||||
#include "serverconfiguration.h"
|
||||
#include "serverconfigurations.h"
|
||||
#include "mqttpolicy.h"
|
||||
#include "mqttpolicies.h"
|
||||
|
||||
#include "jsonrpc/jsonrpcclient.h"
|
||||
|
||||
#include <QUuid>
|
||||
|
||||
NymeaConfiguration::NymeaConfiguration(JsonRpcClient *client, QObject *parent):
|
||||
JsonHandler(parent),
|
||||
m_client(client),
|
||||
m_tcpServerConfigurations(new ServerConfigurations(this)),
|
||||
m_webSocketServerConfigurations(new ServerConfigurations(this)),
|
||||
m_mqttServerConfigurations(new ServerConfigurations(this)),
|
||||
m_mqttPolicies(new MqttPolicies(this))
|
||||
{
|
||||
client->registerNotificationHandler(this, "notificationReceived");
|
||||
}
|
||||
|
||||
QString NymeaConfiguration::nameSpace() const
|
||||
{
|
||||
return "Configuration";
|
||||
}
|
||||
|
||||
void NymeaConfiguration::init()
|
||||
{
|
||||
m_tcpServerConfigurations->clear();
|
||||
m_webSocketServerConfigurations->clear();
|
||||
m_mqttServerConfigurations->clear();
|
||||
m_client->sendCommand("Configuration.GetConfigurations", this, "getConfigurationsResponse");
|
||||
m_client->sendCommand("Configuration.GetAvailableLanguages", this, "getAvailableLanguagesResponse");
|
||||
m_client->sendCommand("Configuration.GetTimeZones", this, "getTimezonesResponse");
|
||||
m_client->sendCommand("Configuration.GetMqttServerConfigurations", this, "getMqttServerConfigsReply");
|
||||
m_client->sendCommand("Configuration.GetMqttPolicies", this, "getMqttPoliciesReply");
|
||||
}
|
||||
|
||||
QString NymeaConfiguration::serverName() const
|
||||
{
|
||||
return m_serverName;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setServerName(const QString &serverName)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("serverName", serverName);
|
||||
m_client->sendCommand("Configuration.SetServerName", params, this, "setServerNameResponse");
|
||||
}
|
||||
|
||||
QString NymeaConfiguration::language() const
|
||||
{
|
||||
return m_language;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setLanguage(const QString &language)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("language", language);
|
||||
m_client->sendCommand("Configuration.SetLanguage", params);
|
||||
}
|
||||
|
||||
QStringList NymeaConfiguration::availableLanguages() const
|
||||
{
|
||||
return m_availableLanguages;
|
||||
}
|
||||
|
||||
QString NymeaConfiguration::timezone() const
|
||||
{
|
||||
return m_timezone;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setTimezone(const QString &timezone)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("timeZone", timezone);
|
||||
m_client->sendCommand("Configuration.SetTimeZone", params, this, "setTimezoneResponse");
|
||||
}
|
||||
|
||||
QStringList NymeaConfiguration::timezones() const
|
||||
{
|
||||
return m_timezones;
|
||||
}
|
||||
|
||||
bool NymeaConfiguration::debugServerEnabled() const
|
||||
{
|
||||
return m_debugServerEnabled;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setDebugServerEnabled(bool debugServerEnabled)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("enabled", debugServerEnabled);
|
||||
m_client->sendCommand("Configuration.SetDebugServerEnabled", params, this, "setDebugServerEnabledResponse");
|
||||
}
|
||||
|
||||
bool NymeaConfiguration::cloudEnabled() const
|
||||
{
|
||||
return m_cloudEnabled;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setCloudEnabled(bool cloudEnabled)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("enabled", cloudEnabled);
|
||||
m_client->sendCommand("Configuration.SetCloudEnabled", params, this, "setCloudEnabledResponse");
|
||||
}
|
||||
|
||||
ServerConfigurations *NymeaConfiguration::tcpServerConfigurations() const
|
||||
{
|
||||
return m_tcpServerConfigurations;
|
||||
}
|
||||
|
||||
ServerConfigurations *NymeaConfiguration::webSocketServerConfigurations() const
|
||||
{
|
||||
return m_webSocketServerConfigurations;
|
||||
}
|
||||
|
||||
ServerConfigurations *NymeaConfiguration::mqttServerConfigurations() const
|
||||
{
|
||||
return m_mqttServerConfigurations;
|
||||
}
|
||||
|
||||
MqttPolicies *NymeaConfiguration::mqttPolicies() const
|
||||
{
|
||||
return m_mqttPolicies;
|
||||
}
|
||||
|
||||
ServerConfiguration *NymeaConfiguration::createServerConfiguration(const QString &address, int port, bool authEnabled, bool sslEnabled)
|
||||
{
|
||||
return new ServerConfiguration(QUuid::createUuid().toString(), QHostAddress(address), port, authEnabled, sslEnabled);
|
||||
}
|
||||
|
||||
MqttPolicy *NymeaConfiguration::createMqttPolicy() const
|
||||
{
|
||||
return new MqttPolicy(QString(), QString(), QString(), {"#"}, {"#"});
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setTcpServerConfiguration(ServerConfiguration *configuration)
|
||||
{
|
||||
QVariantMap params;
|
||||
QVariantMap configurationMap;
|
||||
configurationMap.insert("id", configuration->id());
|
||||
configurationMap.insert("address", configuration->address());
|
||||
configurationMap.insert("port", configuration->port());
|
||||
configurationMap.insert("authenticationEnabled", configuration->authenticationEnabled());
|
||||
configurationMap.insert("sslEnabled", configuration->sslEnabled());
|
||||
params.insert("configuration", configurationMap);
|
||||
m_client->sendCommand("Configuration.SetTcpServerConfiguration", params, this, "setTcpConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setWebSocketServerConfiguration(ServerConfiguration *configuration)
|
||||
{
|
||||
QVariantMap params;
|
||||
QVariantMap configurationMap;
|
||||
configurationMap.insert("id", configuration->id());
|
||||
configurationMap.insert("address", configuration->address());
|
||||
configurationMap.insert("port", configuration->port());
|
||||
configurationMap.insert("authenticationEnabled", configuration->authenticationEnabled());
|
||||
configurationMap.insert("sslEnabled", configuration->sslEnabled());
|
||||
params.insert("configuration", configurationMap);
|
||||
m_client->sendCommand("Configuration.SetWebSocketServerConfiguration", params, this, "setWebSocketConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setMqttServerConfiguration(ServerConfiguration *configuration)
|
||||
{
|
||||
QVariantMap params;
|
||||
QVariantMap configurationMap;
|
||||
configurationMap.insert("id", configuration->id());
|
||||
configurationMap.insert("address", configuration->address());
|
||||
configurationMap.insert("port", configuration->port());
|
||||
configurationMap.insert("authenticationEnabled", configuration->authenticationEnabled());
|
||||
configurationMap.insert("sslEnabled", configuration->sslEnabled());
|
||||
params.insert("configuration", configurationMap);
|
||||
m_client->sendCommand("Configuration.SetMqttServerConfiguration", params, this, "setMqttConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteTcpServerConfiguration(const QString &id)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", id);
|
||||
m_client->sendCommand("Configuration.DeleteTcpServerConfiguration", params, this, "deleteTcpConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteWebSocketServerConfiguration(const QString &id)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", id);
|
||||
m_client->sendCommand("Configuration.DeleteWebSocketServerConfiguration", params, this, "deleteWebSocketConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteMqttServerConfiguration(const QString &id)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("id", id);
|
||||
m_client->sendCommand("Configuration.DeleteMqttServerConfiguration", params, this, "deleteMqttConfigReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::updateMqttPolicy(MqttPolicy *policy)
|
||||
{
|
||||
QVariantMap params;
|
||||
QVariantMap policyMap;
|
||||
policyMap.insert("clientId", policy->clientId());
|
||||
policyMap.insert("username", policy->username());
|
||||
policyMap.insert("password", policy->password());
|
||||
policyMap.insert("allowedPublishTopicFilters", policy->allowedPublishTopicFilters());
|
||||
policyMap.insert("allowedSubscribeTopicFilters", policy->allowedSubscribeTopicFilters());
|
||||
params.insert("policy", policyMap);
|
||||
m_client->sendCommand("Configuration.SetMqttPolicy", params, this, "setMqttPolicyReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteMqttPolicy(const QString &clientId)
|
||||
{
|
||||
QVariantMap params;
|
||||
params.insert("clientId", clientId);
|
||||
m_client->sendCommand("Configuration.DeleteMqttPolicy", params, this, "deleteMqttPolicyReply");
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getConfigurationsResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "have config reply" << params;
|
||||
QVariantMap basicConfig = params.value("params").toMap().value("basicConfiguration").toMap();
|
||||
m_debugServerEnabled = basicConfig.value("debugServerEnabled").toBool();
|
||||
emit debugServerEnabledChanged();
|
||||
m_serverName = basicConfig.value("serverName").toString();
|
||||
emit serverNameChanged();
|
||||
m_language = basicConfig.value("language").toString();
|
||||
emit languageChanged();
|
||||
m_timezone = basicConfig.value("timeZone").toString();
|
||||
emit timezoneChanged();
|
||||
QVariantMap cloudConfig = params.value("params").toMap().value("cloud").toMap();
|
||||
m_cloudEnabled = cloudConfig.value("enabled").toBool();
|
||||
emit cloudEnabledChanged();
|
||||
|
||||
tcpServerConfigurations()->clear();
|
||||
foreach (const QVariant &tcpServerVariant, params.value("params").toMap().value("tcpServerConfigurations").toList()) {
|
||||
qDebug() << "tcp server config:" << tcpServerVariant;
|
||||
QVariantMap tcpConfigMap = tcpServerVariant.toMap();
|
||||
ServerConfiguration *config = new ServerConfiguration(tcpConfigMap.value("id").toString(), QHostAddress(tcpConfigMap.value("address").toString()), tcpConfigMap.value("port").toInt(), tcpConfigMap.value("authenticationEnabled").toBool(), tcpConfigMap.value("sslEnabled").toBool());
|
||||
m_tcpServerConfigurations->addConfiguration(config);
|
||||
}
|
||||
webSocketServerConfigurations()->clear();
|
||||
foreach (const QVariant &websocketServerVariant, params.value("params").toMap().value("webSocketServerConfigurations").toList()) {
|
||||
QVariantMap websocketConfigMap = websocketServerVariant.toMap();
|
||||
ServerConfiguration *config = new ServerConfiguration(websocketConfigMap.value("id").toString(), QHostAddress(websocketConfigMap.value("address").toString()), websocketConfigMap.value("port").toInt(), websocketConfigMap.value("authenticationEnabled").toBool(), websocketConfigMap.value("sslEnabled").toBool());
|
||||
m_webSocketServerConfigurations->addConfiguration(config);
|
||||
}
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getAvailableLanguagesResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "available languages" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getTimezonesResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
// qDebug() << "Get timezones response" << params;
|
||||
m_timezones = params.value("params").toMap().value("timeZones").toStringList();
|
||||
emit timezonesChanged();
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setTimezoneResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set timezones response" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setServerNameResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Server name set:" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getCloudConfigurationResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Cloud config reply" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setCloudEnabledResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set cloud enabled:" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setDebugServerEnabledResponse(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Debug server set:" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setTcpConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteTcpConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
if (params.value("params").toMap().value("configurationError").toString() == "ConfigurationErrorNoError") {
|
||||
}
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setWebSocketConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "set weboscket config reply" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteWebSocketConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getMqttServerConfigsReply(const QVariantMap ¶ms)
|
||||
{
|
||||
m_mqttServerConfigurations->clear();
|
||||
foreach (const QVariant &mqttServerVariant, params.value("params").toMap().value("mqttServerConfigurations").toList()) {
|
||||
QVariantMap mqttConfigMap = mqttServerVariant.toMap();
|
||||
ServerConfiguration *config = new ServerConfiguration(mqttConfigMap.value("id").toString(), QHostAddress(mqttConfigMap.value("address").toString()), mqttConfigMap.value("port").toInt(), mqttConfigMap.value("authenticationEnabled").toBool(), mqttConfigMap.value("sslEnabled").toBool());
|
||||
m_mqttServerConfigurations->addConfiguration(config);
|
||||
}
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setMqttConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set mqtt config reply" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteMqttConfigReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Delete Mqtt Broker config reply:" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::getMqttPoliciesReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Mqtt polices:" << params;
|
||||
m_mqttPolicies->clear();
|
||||
foreach (const QVariant &policyVariant, params.value("params").toMap().value("mqttPolicies").toList()) {
|
||||
QVariantMap policyMap = policyVariant.toMap();
|
||||
MqttPolicy *policy = new MqttPolicy(
|
||||
policyMap.value("clientId").toString(),
|
||||
policyMap.value("username").toString(),
|
||||
policyMap.value("password").toString(),
|
||||
policyMap.value("allowedPublishTopicFilters").toStringList(),
|
||||
policyMap.value("allowedSubscribeTopicFilters").toStringList());
|
||||
m_mqttPolicies->addPolicy(policy);
|
||||
}
|
||||
}
|
||||
|
||||
void NymeaConfiguration::setMqttPolicyReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Set MQTT policy reply" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::deleteMqttPolicyReply(const QVariantMap ¶ms)
|
||||
{
|
||||
qDebug() << "Delete MQTT policy reply" << params;
|
||||
}
|
||||
|
||||
void NymeaConfiguration::notificationReceived(const QVariantMap ¬ification)
|
||||
{
|
||||
QString notif = notification.value("notification").toString();
|
||||
if (notif == "Configuration.BasicConfigurationChanged") {
|
||||
QVariantMap params = notification.value("params").toMap().value("basicConfiguration").toMap();
|
||||
qDebug() << "notif" << params;
|
||||
m_debugServerEnabled = params.value("debugServerEnabled").toBool();
|
||||
emit debugServerEnabledChanged();
|
||||
m_serverName = params.value("serverName").toString();
|
||||
emit serverNameChanged();
|
||||
m_language = params.value("language").toString();
|
||||
emit languageChanged();
|
||||
m_timezone = params.value("timeZone").toString();
|
||||
emit timezoneChanged();
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.CloudConfigurationChanged") {
|
||||
QVariantMap params = notification.value("params").toMap().value("cloudConfiguration").toMap();
|
||||
qDebug() << "notif" << params;
|
||||
m_cloudEnabled = params.value("enabled").toBool();
|
||||
emit cloudEnabledChanged();
|
||||
return;
|
||||
}
|
||||
if (notif.endsWith("ServerConfigurationChanged")) {
|
||||
ServerConfigurations *configModel = nullptr;
|
||||
QVariantMap params;
|
||||
if (notif == "Configuration.TcpServerConfigurationChanged") {
|
||||
configModel = m_tcpServerConfigurations;
|
||||
params = notification.value("params").toMap().value("tcpServerConfiguration").toMap();
|
||||
}
|
||||
if (notif == "Configuration.WebSocketServerConfigurationChanged") {
|
||||
configModel = m_webSocketServerConfigurations;
|
||||
params = notification.value("params").toMap().value("webSocketServerConfiguration").toMap();
|
||||
}
|
||||
if (notif == "Configuration.MqttServerConfigurationChanged") {
|
||||
configModel = m_mqttServerConfigurations;
|
||||
params = notification.value("params").toMap().value("mqttServerConfiguration").toMap();
|
||||
}
|
||||
if (!configModel) {
|
||||
return;
|
||||
}
|
||||
|
||||
ServerConfiguration *serverConfig = nullptr;
|
||||
for (int i = 0; i < configModel->rowCount(); i++) {
|
||||
ServerConfiguration* config = configModel->get(i);
|
||||
if (config->id() == params.value("id").toString()) {
|
||||
serverConfig = config;
|
||||
}
|
||||
}
|
||||
|
||||
if (!serverConfig) {
|
||||
serverConfig = new ServerConfiguration(params.value("id").toString());
|
||||
configModel->addConfiguration(serverConfig);
|
||||
}
|
||||
serverConfig->setAddress(params.value("address").toString());
|
||||
serverConfig->setPort(params.value("port").toInt());
|
||||
serverConfig->setAuthenticationEnabled(params.value("authenticationEnabled").toBool());
|
||||
serverConfig->setSslEnabled(params.value("sslEnabled").toBool());
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.TcpServerConfigurationRemoved") {
|
||||
m_tcpServerConfigurations->removeConfiguration(notification.value("params").toMap().value("id").toString());
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.WebSocketServerConfigurationRemoved") {
|
||||
m_webSocketServerConfigurations->removeConfiguration(notification.value("params").toMap().value("id").toString());
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.MqttServerConfigurationRemoved") {
|
||||
m_mqttServerConfigurations->removeConfiguration(notification.value("params").toMap().value("id").toString());
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.MqttPolicyChanged") {
|
||||
MqttPolicy *policy = nullptr;
|
||||
QVariantMap policyMap = notification.value("params").toMap().value("policy").toMap();
|
||||
for (int i = 0; i < m_mqttPolicies->rowCount(); i++) {
|
||||
if (m_mqttPolicies->get(i)->clientId() == policyMap.value("clientId").toString()) {
|
||||
policy = m_mqttPolicies->get(i);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (!policy) {
|
||||
policy = new MqttPolicy(policyMap.value("clientId").toString());
|
||||
m_mqttPolicies->addPolicy(policy);
|
||||
}
|
||||
policy->setUsername(policyMap.value("username").toString());
|
||||
policy->setPassword(policyMap.value("password").toString());
|
||||
policy->setAllowedPublishTopicFilters(policyMap.value("allowedPublishTopicFilters").toStringList());
|
||||
policy->setAllowedSubscribeTopicFilters(policyMap.value("allowedSubscribeTopicFilters").toStringList());
|
||||
qDebug() << "MQTT policy added" << policy->clientId() << policy->username() << policy->password();
|
||||
return;
|
||||
}
|
||||
if (notif == "Configuration.MqttPolicyRemoved") {
|
||||
MqttPolicy* policy = m_mqttPolicies->getPolicy(notification.value("params").toMap().value("clientId").toString());
|
||||
if (!policy) {
|
||||
qWarning() << "Reveived a policy removed notification for apolicy we don't know";
|
||||
return;
|
||||
}
|
||||
m_mqttPolicies->removePolicy(policy);
|
||||
}
|
||||
|
||||
qDebug() << "Unhandled Configuration notification" << notif << notification;
|
||||
}
|
||||
@ -1,61 +1,77 @@
|
||||
#ifndef BASICCONFIGURATION_H
|
||||
#define BASICCONFIGURATION_H
|
||||
#ifndef NYMEACONFIGURATION_H
|
||||
#define NYMEACONFIGURATION_H
|
||||
|
||||
#include <QObject>
|
||||
|
||||
#include "jsonrpc/jsonhandler.h"
|
||||
#include "serverconfigurations.h"
|
||||
|
||||
class JsonRpcClient;
|
||||
class ServerConfiguration;
|
||||
class ServerConfigurations;
|
||||
class MqttPolicy;
|
||||
class MqttPolicies;
|
||||
|
||||
class BasicConfiguration : public JsonHandler
|
||||
class NymeaConfiguration : public JsonHandler
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(bool debugServerEnabled READ debugServerEnabled WRITE setDebugServerEnabled NOTIFY debugServerEnabledChanged)
|
||||
|
||||
Q_PROPERTY(QString serverName READ serverName WRITE setServerName NOTIFY serverNameChanged)
|
||||
|
||||
Q_PROPERTY(QString language READ language WRITE setLanguage NOTIFY languageChanged)
|
||||
Q_PROPERTY(QString timezone READ timezone WRITE setTimezone NOTIFY timezoneChanged)
|
||||
|
||||
Q_PROPERTY(bool cloudEnabled READ cloudEnabled WRITE setCloudEnabled NOTIFY cloudEnabledChanged)
|
||||
|
||||
Q_PROPERTY(QStringList availableLanguages READ availableLanguages NOTIFY availableLanguagesChanged)
|
||||
|
||||
Q_PROPERTY(QString timezone READ timezone WRITE setTimezone NOTIFY timezoneChanged)
|
||||
Q_PROPERTY(QStringList timezones READ timezones NOTIFY timezonesChanged)
|
||||
|
||||
Q_PROPERTY(bool cloudEnabled READ cloudEnabled WRITE setCloudEnabled NOTIFY cloudEnabledChanged)
|
||||
Q_PROPERTY(bool debugServerEnabled READ debugServerEnabled WRITE setDebugServerEnabled NOTIFY debugServerEnabledChanged)
|
||||
|
||||
Q_PROPERTY(ServerConfigurations* tcpServerConfigurations READ tcpServerConfigurations CONSTANT)
|
||||
Q_PROPERTY(ServerConfigurations* websocketServerConfigurations READ websocketServerConfigurations CONSTANT)
|
||||
Q_PROPERTY(ServerConfigurations* webSocketServerConfigurations READ webSocketServerConfigurations CONSTANT)
|
||||
Q_PROPERTY(ServerConfigurations* mqttServerConfigurations READ mqttServerConfigurations CONSTANT)
|
||||
|
||||
Q_PROPERTY(MqttPolicies* mqttPolicies READ mqttPolicies CONSTANT)
|
||||
|
||||
public:
|
||||
explicit BasicConfiguration(JsonRpcClient* client, QObject *parent = nullptr);
|
||||
explicit NymeaConfiguration(JsonRpcClient* client, QObject *parent = nullptr);
|
||||
|
||||
QString nameSpace() const override;
|
||||
|
||||
bool debugServerEnabled() const;
|
||||
void setDebugServerEnabled(bool debugServerEnabled);
|
||||
|
||||
QString serverName() const;
|
||||
void setServerName(const QString &serverName);
|
||||
|
||||
bool cloudEnabled() const;
|
||||
void setCloudEnabled(bool cloudEnabled);
|
||||
|
||||
QString language() const;
|
||||
void setLanguage(const QString &language);
|
||||
|
||||
QStringList availableLanguages() const;
|
||||
|
||||
QString timezone() const;
|
||||
void setTimezone(const QString &timezone);
|
||||
|
||||
QStringList timezones() const;
|
||||
|
||||
ServerConfigurations *tcpServerConfigurations() const;
|
||||
ServerConfigurations *websocketServerConfigurations() const;
|
||||
bool debugServerEnabled() const;
|
||||
void setDebugServerEnabled(bool debugServerEnabled);
|
||||
|
||||
void setTcpServerConfiguration(ServerConfiguration *configuration) const;
|
||||
void setWebsocketServerConfiguration(ServerConfiguration *configuration) const;
|
||||
bool cloudEnabled() const;
|
||||
void setCloudEnabled(bool cloudEnabled);
|
||||
|
||||
ServerConfigurations *tcpServerConfigurations() const;
|
||||
ServerConfigurations *webSocketServerConfigurations() const;
|
||||
ServerConfigurations *mqttServerConfigurations() const;
|
||||
MqttPolicies *mqttPolicies() const;
|
||||
|
||||
Q_INVOKABLE ServerConfiguration* createServerConfiguration(const QString &address = "0.0.0.0", int port = 0, bool authEnabled = false, bool sslEnabled = false);
|
||||
Q_INVOKABLE MqttPolicy* createMqttPolicy() const;
|
||||
|
||||
Q_INVOKABLE void setTcpServerConfiguration(ServerConfiguration *configuration);
|
||||
Q_INVOKABLE void setWebSocketServerConfiguration(ServerConfiguration *configuration);
|
||||
Q_INVOKABLE void setMqttServerConfiguration(ServerConfiguration *configuration);
|
||||
|
||||
Q_INVOKABLE void deleteTcpServerConfiguration(const QString &id);
|
||||
Q_INVOKABLE void deleteWebsocketServerConfiguration(const QString &id);
|
||||
Q_INVOKABLE void deleteWebSocketServerConfiguration(const QString &id);
|
||||
Q_INVOKABLE void deleteMqttServerConfiguration(const QString &id);
|
||||
|
||||
Q_INVOKABLE void updateMqttPolicy(MqttPolicy* policy);
|
||||
Q_INVOKABLE void deleteMqttPolicy(const QString &clientId);
|
||||
void init();
|
||||
|
||||
private:
|
||||
@ -67,8 +83,16 @@ private:
|
||||
Q_INVOKABLE void getAvailableLanguagesResponse(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void getTimezonesResponse(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void setTimezoneResponse(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void setTcpConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void deleteTcpConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void setWebSocketConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void deleteWebSocketConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void getMqttServerConfigsReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void setMqttConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void deleteMqttConfigReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void getMqttPoliciesReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void setMqttPolicyReply(const QVariantMap ¶ms);
|
||||
Q_INVOKABLE void deleteMqttPolicyReply(const QVariantMap ¶ms);
|
||||
|
||||
Q_INVOKABLE void notificationReceived(const QVariantMap ¬ification);
|
||||
|
||||
@ -83,6 +107,7 @@ signals:
|
||||
|
||||
private:
|
||||
JsonRpcClient* m_client = nullptr;
|
||||
|
||||
bool m_debugServerEnabled = false;
|
||||
QString m_serverName;
|
||||
QString m_language;
|
||||
@ -92,7 +117,10 @@ private:
|
||||
bool m_cloudEnabled = false;
|
||||
|
||||
ServerConfigurations *m_tcpServerConfigurations = nullptr;
|
||||
ServerConfigurations *m_websocketServerConfigurations = nullptr;
|
||||
ServerConfigurations *m_webSocketServerConfigurations = nullptr;
|
||||
ServerConfigurations *m_mqttServerConfigurations = nullptr;
|
||||
MqttPolicies *m_mqttPolicies = nullptr;
|
||||
|
||||
};
|
||||
|
||||
#endif // BASICCONFIGURATION_H
|
||||
#endif // NYMEACONFIGURATION_H
|
||||
@ -21,17 +21,55 @@ QString ServerConfiguration::address() const
|
||||
return m_hostAddress.toString();
|
||||
}
|
||||
|
||||
void ServerConfiguration::setAddress(const QString &address)
|
||||
{
|
||||
if (m_hostAddress != QHostAddress(address)) {
|
||||
m_hostAddress = QHostAddress(address);
|
||||
emit addressChanged();
|
||||
}
|
||||
}
|
||||
|
||||
int ServerConfiguration::port() const
|
||||
{
|
||||
return m_port;
|
||||
}
|
||||
|
||||
void ServerConfiguration::setPort(int port)
|
||||
{
|
||||
if (m_port != port) {
|
||||
m_port = port;
|
||||
emit portChanged();
|
||||
}
|
||||
}
|
||||
|
||||
bool ServerConfiguration::authenticationEnabled() const
|
||||
{
|
||||
return m_authEnabled;
|
||||
}
|
||||
|
||||
void ServerConfiguration::setAuthenticationEnabled(bool authenticationEnabled)
|
||||
{
|
||||
if (m_authEnabled != authenticationEnabled) {
|
||||
m_authEnabled = authenticationEnabled;
|
||||
emit authenticationEnabledChanged();
|
||||
}
|
||||
}
|
||||
|
||||
bool ServerConfiguration::sslEnabled() const
|
||||
{
|
||||
return m_sslEnabled;
|
||||
}
|
||||
|
||||
void ServerConfiguration::setSslEnabled(bool sslEnabled)
|
||||
{
|
||||
if (m_sslEnabled != sslEnabled) {
|
||||
m_sslEnabled = sslEnabled;
|
||||
emit sslEnabledChanged();
|
||||
}
|
||||
}
|
||||
|
||||
ServerConfiguration *ServerConfiguration::clone() const
|
||||
{
|
||||
ServerConfiguration *ret = new ServerConfiguration(m_id, m_hostAddress, m_port, m_authEnabled, m_sslEnabled);
|
||||
return ret;
|
||||
}
|
||||
|
||||
@ -9,18 +9,35 @@ class ServerConfiguration : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
Q_PROPERTY(QString id READ id CONSTANT)
|
||||
Q_PROPERTY(QString address READ address CONSTANT)
|
||||
Q_PROPERTY(int port READ port CONSTANT)
|
||||
Q_PROPERTY(bool authenticationEnabled READ authenticationEnabled CONSTANT)
|
||||
Q_PROPERTY(bool sslEnabled READ sslEnabled CONSTANT)
|
||||
Q_PROPERTY(QString address READ address WRITE setAddress NOTIFY addressChanged)
|
||||
Q_PROPERTY(int port READ port WRITE setPort NOTIFY portChanged)
|
||||
Q_PROPERTY(bool authenticationEnabled READ authenticationEnabled WRITE setAuthenticationEnabled NOTIFY authenticationEnabledChanged)
|
||||
Q_PROPERTY(bool sslEnabled READ sslEnabled WRITE setSslEnabled NOTIFY sslEnabledChanged)
|
||||
|
||||
public:
|
||||
explicit ServerConfiguration(const QString &id, const QHostAddress &address, int port, bool authEnabled, bool sslEnabled, QObject *parent = nullptr);
|
||||
explicit ServerConfiguration(const QString &id, const QHostAddress &address = QHostAddress(), int port = 0, bool authEnabled = false, bool sslEnabled = false, QObject *parent = nullptr);
|
||||
|
||||
QString id() const;
|
||||
|
||||
QString address() const;
|
||||
void setAddress(const QString &address);
|
||||
|
||||
int port() const;
|
||||
void setPort(int port);
|
||||
|
||||
bool authenticationEnabled() const;
|
||||
void setAuthenticationEnabled(bool authenticationEnabled);
|
||||
|
||||
bool sslEnabled() const;
|
||||
void setSslEnabled(bool sslEnabled);
|
||||
|
||||
Q_INVOKABLE ServerConfiguration* clone() const;
|
||||
|
||||
signals:
|
||||
void addressChanged();
|
||||
void portChanged();
|
||||
void authenticationEnabledChanged();
|
||||
void sslEnabledChanged();
|
||||
|
||||
private:
|
||||
QString m_id;
|
||||
|
||||
@ -45,10 +45,40 @@ void ServerConfigurations::addConfiguration(ServerConfiguration *configuration)
|
||||
configuration->setParent(this);
|
||||
beginInsertRows(QModelIndex(), m_list.count(), m_list.count());
|
||||
m_list.append(configuration);
|
||||
|
||||
connect(configuration, &ServerConfiguration::addressChanged, this, [this, configuration]() {
|
||||
QModelIndex idx = index(m_list.indexOf(configuration), 0);
|
||||
emit dataChanged(idx, idx, {RoleAddress});
|
||||
});
|
||||
connect(configuration, &ServerConfiguration::portChanged, this, [this, configuration]() {
|
||||
QModelIndex idx = index(m_list.indexOf(configuration), 0);
|
||||
emit dataChanged(idx, idx, {RolePort});
|
||||
});
|
||||
connect(configuration, &ServerConfiguration::authenticationEnabledChanged, this, [this, configuration]() {
|
||||
QModelIndex idx = index(m_list.indexOf(configuration), 0);
|
||||
emit dataChanged(idx, idx, {RoleAuthenticationEnabled});
|
||||
});
|
||||
connect(configuration, &ServerConfiguration::sslEnabledChanged, this, [this, configuration]() {
|
||||
QModelIndex idx = index(m_list.indexOf(configuration), 0);
|
||||
emit dataChanged(idx, idx, {RoleSslEnabled});
|
||||
});
|
||||
|
||||
endInsertRows();
|
||||
emit countChanged();
|
||||
}
|
||||
|
||||
void ServerConfigurations::removeConfiguration(const QString &id)
|
||||
{
|
||||
for (int i = 0; i < m_list.count(); i++) {
|
||||
if (m_list.at(i)->id() == id) {
|
||||
beginRemoveRows(QModelIndex(), i, i);
|
||||
m_list.takeAt(i)->deleteLater();
|
||||
endRemoveRows();
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void ServerConfigurations::clear()
|
||||
{
|
||||
beginResetModel();
|
||||
@ -57,3 +87,11 @@ void ServerConfigurations::clear()
|
||||
endResetModel();
|
||||
emit countChanged();
|
||||
}
|
||||
|
||||
ServerConfiguration *ServerConfigurations::get(int index) const
|
||||
{
|
||||
if (index < 0 || index > m_list.count() - 1) {
|
||||
return nullptr;
|
||||
}
|
||||
return m_list.at(index);
|
||||
}
|
||||
|
||||
@ -28,9 +28,12 @@ public:
|
||||
QHash<int, QByteArray> roleNames() const override;
|
||||
|
||||
void addConfiguration(ServerConfiguration *configuration);
|
||||
void removeConfiguration(const QString &id);
|
||||
|
||||
void clear();
|
||||
|
||||
Q_INVOKABLE ServerConfiguration* get(int index) const;
|
||||
|
||||
signals:
|
||||
void countChanged();
|
||||
|
||||
|
||||
@ -23,7 +23,7 @@
|
||||
#include "rulemanager.h"
|
||||
#include "logmanager.h"
|
||||
#include "tagsmanager.h"
|
||||
#include "configuration/basicconfiguration.h"
|
||||
#include "configuration/nymeaconfiguration.h"
|
||||
#include "connection/awsclient.h"
|
||||
|
||||
#include "connection/tcpsockettransport.h"
|
||||
@ -39,7 +39,7 @@ Engine::Engine(QObject *parent) :
|
||||
m_ruleManager(new RuleManager(m_jsonRpcClient, this)),
|
||||
m_logManager(new LogManager(m_jsonRpcClient, this)),
|
||||
m_tagsManager(new TagsManager(m_jsonRpcClient, this)),
|
||||
m_basicConfiguration(new BasicConfiguration(m_jsonRpcClient, this))
|
||||
m_nymeaConfiguration(new NymeaConfiguration(m_jsonRpcClient, this))
|
||||
{
|
||||
m_connection->registerTransport(new TcpSocketTransportFactory());
|
||||
m_connection->registerTransport(new WebsocketTransportFactory());
|
||||
@ -92,16 +92,11 @@ LogManager *Engine::logManager() const
|
||||
return m_logManager;
|
||||
}
|
||||
|
||||
BasicConfiguration *Engine::basicConfiguration() const
|
||||
NymeaConfiguration *Engine::nymeaConfiguration() const
|
||||
{
|
||||
return m_basicConfiguration;
|
||||
return m_nymeaConfiguration;
|
||||
}
|
||||
|
||||
//AWSClient *Engine::awsClient() const
|
||||
//{
|
||||
// return m_aws;
|
||||
//}
|
||||
|
||||
void Engine::deployCertificate()
|
||||
{
|
||||
if (!m_jsonRpcClient->connected()) {
|
||||
@ -133,7 +128,7 @@ void Engine::onConnectedChanged()
|
||||
if (!m_jsonRpcClient->initialSetupRequired() && !m_jsonRpcClient->authenticationRequired()) {
|
||||
m_deviceManager->init();
|
||||
m_ruleManager->init();
|
||||
m_basicConfiguration->init();
|
||||
m_nymeaConfiguration->init();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -31,8 +31,7 @@
|
||||
class RuleManager;
|
||||
class LogManager;
|
||||
class TagsManager;
|
||||
class BasicConfiguration;
|
||||
class AWSClient;
|
||||
class NymeaConfiguration;
|
||||
|
||||
class Engine : public QObject
|
||||
{
|
||||
@ -42,8 +41,7 @@ class Engine : public QObject
|
||||
Q_PROPERTY(RuleManager* ruleManager READ ruleManager CONSTANT)
|
||||
Q_PROPERTY(TagsManager* tagsManager READ tagsManager CONSTANT)
|
||||
Q_PROPERTY(JsonRpcClient* jsonRpcClient READ jsonRpcClient CONSTANT)
|
||||
Q_PROPERTY(BasicConfiguration* basicConfiguration READ basicConfiguration CONSTANT)
|
||||
// Q_PROPERTY(AWSClient* awsClient READ awsClient CONSTANT)
|
||||
Q_PROPERTY(NymeaConfiguration* nymeaConfiguration READ nymeaConfiguration CONSTANT)
|
||||
|
||||
public:
|
||||
explicit Engine(QObject *parent = nullptr);
|
||||
@ -57,8 +55,7 @@ public:
|
||||
TagsManager *tagsManager() const;
|
||||
JsonRpcClient *jsonRpcClient() const;
|
||||
LogManager *logManager() const;
|
||||
BasicConfiguration *basicConfiguration() const;
|
||||
// AWSClient* awsClient() const;
|
||||
NymeaConfiguration *nymeaConfiguration() const;
|
||||
|
||||
Q_INVOKABLE void deployCertificate();
|
||||
|
||||
@ -69,8 +66,7 @@ private:
|
||||
RuleManager *m_ruleManager;
|
||||
LogManager *m_logManager;
|
||||
TagsManager *m_tagsManager;
|
||||
BasicConfiguration *m_basicConfiguration;
|
||||
// AWSClient *m_aws;
|
||||
NymeaConfiguration *m_nymeaConfiguration;
|
||||
|
||||
private slots:
|
||||
void onConnectedChanged();
|
||||
|
||||
@ -356,7 +356,6 @@ void JsonRpcClient::dataReceived(const QByteArray &data)
|
||||
m_pushButtonAuthAvailable = dataMap.value("pushButtonAuthAvailable").toBool();
|
||||
emit pushButtonAuthAvailableChanged();
|
||||
|
||||
qDebug() << "Handshake received" << "initRequired:" << m_initialSetupRequired << "authRequired:" << m_authenticationRequired << "pushButtonAvailable:" << m_pushButtonAuthAvailable;;
|
||||
m_serverUuid = dataMap.value("uuid").toString();
|
||||
m_serverVersion = dataMap.value("version").toString();
|
||||
|
||||
@ -366,6 +365,8 @@ void JsonRpcClient::dataReceived(const QByteArray &data)
|
||||
}
|
||||
m_jsonRpcVersion = QVersionNumber::fromString(protoVersionString);
|
||||
|
||||
qDebug() << "Handshake reply:" << "Protocol version:" << protoVersionString << "InitRequired:" << m_initialSetupRequired << "AuthRequired:" << m_authenticationRequired << "PushButtonAvailable:" << m_pushButtonAuthAvailable;;
|
||||
|
||||
QVersionNumber minimumRequiredVersion = QVersionNumber(1, 0);
|
||||
if (m_jsonRpcVersion < minimumRequiredVersion) {
|
||||
qWarning() << "Nymea box doesn't support minimum required version. Required:" << minimumRequiredVersion << "Found:" << m_jsonRpcVersion;
|
||||
|
||||
@ -35,7 +35,11 @@
|
||||
#include "models/logsmodelng.h"
|
||||
#include "models/valuelogsproxymodel.h"
|
||||
#include "models/interfacesproxy.h"
|
||||
#include "configuration/basicconfiguration.h"
|
||||
#include "configuration/nymeaconfiguration.h"
|
||||
#include "configuration/serverconfiguration.h"
|
||||
#include "configuration/serverconfigurations.h"
|
||||
#include "configuration/mqttpolicy.h"
|
||||
#include "configuration/mqttpolicies.h"
|
||||
#include "wifisetup/networkmanagercontroller.h"
|
||||
#include "wifisetup/wirelessaccesspoint.h"
|
||||
#include "wifisetup/wirelessaccesspoints.h"
|
||||
@ -143,14 +147,17 @@ void registerQmlTypes() {
|
||||
qmlRegisterUncreatableType<Plugins>(uri, 1, 0, "Plugins", "Can't create this in QML. Get it from the DeviceManager.");
|
||||
qmlRegisterType<PluginsProxy>(uri, 1, 0, "PluginsProxy");
|
||||
|
||||
qmlRegisterUncreatableType<BasicConfiguration>(uri, 1, 0, "BasicConfiguration", "Uncreatable");
|
||||
qmlRegisterUncreatableType<NymeaConfiguration>(uri, 1, 0, "NymeaConfiguration", "Get it from Engine");
|
||||
qmlRegisterUncreatableType<ServerConfiguration>(uri, 1, 0, "ServerConfiguration", "Get it from NymeaConfiguration");
|
||||
qmlRegisterUncreatableType<ServerConfigurations>(uri, 1, 0, "ServerConfigurations", "Get it from NymeaConfiguration");
|
||||
qmlRegisterUncreatableType<MqttPolicy>(uri, 1, 0, "MqttPolicy", "Get it from NymeaConfiguration");
|
||||
qmlRegisterUncreatableType<MqttPolicies>(uri, 1, 0, "MqttPolicies", "Get it from NymeaConfiguration");
|
||||
|
||||
qmlRegisterType<NymeaDiscovery>(uri, 1, 0, "NymeaDiscovery");
|
||||
qmlRegisterUncreatableType<DiscoveryModel>(uri, 1, 0, "DiscoveryModel", "Get it from NymeaDiscovery");
|
||||
qmlRegisterUncreatableType<DiscoveryDevice>(uri, 1, 0, "DiscoveryDevice", "Get it from DiscoveryModel");
|
||||
qmlRegisterUncreatableType<Connection>(uri, 1, 0, "Connection", "Get it from DiscoveryDevice");
|
||||
|
||||
|
||||
qmlRegisterType<LogsModel>(uri, 1, 0, "LogsModel");
|
||||
qmlRegisterType<LogsModelNg>(uri, 1, 0, "LogsModelNg");
|
||||
qmlRegisterType<ValueLogsProxyModel>(uri, 1, 0, "ValueLogsProxyModel");
|
||||
|
||||
@ -55,7 +55,6 @@ SOURCES += \
|
||||
models/valuelogsproxymodel.cpp \
|
||||
discovery/nymeadiscovery.cpp \
|
||||
logmanager.cpp \
|
||||
configuration/basicconfiguration.cpp \
|
||||
wifisetup/bluetoothdevice.cpp \
|
||||
wifisetup/bluetoothdeviceinfo.cpp \
|
||||
wifisetup/bluetoothdeviceinfos.cpp \
|
||||
@ -80,7 +79,11 @@ SOURCES += \
|
||||
connection/sigv4utils.cpp \
|
||||
ruletemplates/ruleactionparamtemplate.cpp \
|
||||
configuration/serverconfiguration.cpp \
|
||||
configuration/serverconfigurations.cpp
|
||||
configuration/serverconfigurations.cpp \
|
||||
configuration/nymeaconfiguration.cpp \
|
||||
models/mqttpolicies.cpp \
|
||||
configuration/mqttpolicy.cpp \
|
||||
configuration/mqttpolicies.cpp
|
||||
|
||||
HEADERS += \
|
||||
engine.h \
|
||||
@ -115,7 +118,6 @@ HEADERS += \
|
||||
models/valuelogsproxymodel.h \
|
||||
discovery/nymeadiscovery.h \
|
||||
logmanager.h \
|
||||
configuration/basicconfiguration.h \
|
||||
wifisetup/bluetoothdevice.h \
|
||||
wifisetup/bluetoothdeviceinfo.h \
|
||||
wifisetup/bluetoothdeviceinfos.h \
|
||||
@ -140,7 +142,10 @@ HEADERS += \
|
||||
connection/cloudtransport.h \
|
||||
ruletemplates/ruleactionparamtemplate.h \
|
||||
configuration/serverconfiguration.h \
|
||||
configuration/serverconfigurations.h
|
||||
configuration/serverconfigurations.h \
|
||||
configuration/nymeaconfiguration.h \
|
||||
configuration/mqttpolicy.h \
|
||||
configuration/mqttpolicies.h
|
||||
|
||||
unix {
|
||||
target.path = /usr/lib
|
||||
|
||||
6
libnymea-app-core/models/mqttpolicies.cpp
Normal file
6
libnymea-app-core/models/mqttpolicies.cpp
Normal file
@ -0,0 +1,6 @@
|
||||
#include "mqttpolicies.h"
|
||||
|
||||
MqttPolicies::MqttPolicies(QObject *parent) : QObject(parent)
|
||||
{
|
||||
|
||||
}
|
||||
@ -157,5 +157,7 @@
|
||||
<file>ui/images/lighting/concentrate.svg</file>
|
||||
<file>ui/images/lighting/reading.svg</file>
|
||||
<file>ui/images/lighting/relax.svg</file>
|
||||
<file>ui/images/messaging-app-symbolic.svg</file>
|
||||
<file>ui/images/mqtt.svg</file>
|
||||
</qresource>
|
||||
</RCC>
|
||||
|
||||
@ -136,5 +136,8 @@
|
||||
<file>ui/customviews/GenericTypeGraph.qml</file>
|
||||
<file>ui/devicepages/SmartMeterDevicePage.qml</file>
|
||||
<file>ui/devicelistpages/SmartMeterDeviceListPage.qml</file>
|
||||
<file>ui/system/MqttBrokerSettingsPage.qml</file>
|
||||
<file>ui/system/ServerConfigurationDialog.qml</file>
|
||||
<file>ui/system/MqttPolicyPage.qml</file>
|
||||
</qresource>
|
||||
</RCC>
|
||||
|
||||
@ -322,7 +322,7 @@ Page {
|
||||
id: paramRepeater
|
||||
model: d.deviceDescriptorId == null ? d.deviceClass.paramTypes : null
|
||||
delegate: ParamDelegate {
|
||||
Layout.preferredHeight: 60
|
||||
// Layout.preferredHeight: 60
|
||||
Layout.fillWidth: true
|
||||
paramType: d.deviceClass.paramTypes.get(index)
|
||||
}
|
||||
|
||||
@ -158,7 +158,7 @@ ApplicationWindow {
|
||||
case "gateway":
|
||||
return Qt.resolvedUrl("images/network-wired-symbolic.svg")
|
||||
case "notifications":
|
||||
return Qt.resolvedUrl("images/notification.svg")
|
||||
return Qt.resolvedUrl("images/messaging-app-symbolic.svg")
|
||||
case "inputtrigger":
|
||||
return Qt.resolvedUrl("images/attention.svg")
|
||||
case "outputtrigger":
|
||||
|
||||
@ -276,7 +276,7 @@ Item {
|
||||
delegate: TabButton {
|
||||
id: hostTabButton
|
||||
property var engine: mainRepeater.itemAt(index)._engine
|
||||
property string serverName: engine.basicConfiguration.serverName
|
||||
property string serverName: engine.nymeaConfiguration.serverName
|
||||
Material.elevation: index
|
||||
|
||||
contentItem: RowLayout {
|
||||
|
||||
@ -62,12 +62,12 @@ Page {
|
||||
TextField {
|
||||
id: nameTextField
|
||||
Layout.fillWidth: true
|
||||
text: engine.basicConfiguration.serverName
|
||||
text: engine.nymeaConfiguration.serverName
|
||||
}
|
||||
Button {
|
||||
text: qsTr("OK")
|
||||
visible: nameTextField.displayText !== engine.basicConfiguration.serverName
|
||||
onClicked: engine.basicConfiguration.serverName = nameTextField.displayText
|
||||
visible: nameTextField.displayText !== engine.nymeaConfiguration.serverName
|
||||
onClicked: engine.nymeaConfiguration.serverName = nameTextField.displayText
|
||||
}
|
||||
}
|
||||
|
||||
@ -81,10 +81,10 @@ Page {
|
||||
text: qsTr("Language")
|
||||
}
|
||||
ComboBox {
|
||||
model: engine.basicConfiguration.availableLanguages
|
||||
currentIndex: model.indexOf(engine.basicConfiguration.language)
|
||||
model: engine.nymeaConfiguration.availableLanguages
|
||||
currentIndex: model.indexOf(engine.nymeaConfiguration.language)
|
||||
onActivated: {
|
||||
engine.basicConfiguration.language = currentText;
|
||||
engine.nymeaConfiguration.language = currentText;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -100,10 +100,10 @@ Page {
|
||||
}
|
||||
ComboBox {
|
||||
Layout.minimumWidth: 200
|
||||
model: engine.basicConfiguration.timezones
|
||||
currentIndex: model.indexOf(engine.basicConfiguration.timezone)
|
||||
model: engine.nymeaConfiguration.timezones
|
||||
currentIndex: model.indexOf(engine.nymeaConfiguration.timezone)
|
||||
onActivated: {
|
||||
engine.basicConfiguration.timezone = currentText;
|
||||
engine.nymeaConfiguration.timezone = currentText;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -122,8 +122,8 @@ Page {
|
||||
}
|
||||
Switch {
|
||||
id: debugServerEnabledSwitch
|
||||
checked: engine.basicConfiguration.debugServerEnabled
|
||||
onClicked: engine.basicConfiguration.debugServerEnabled = checked
|
||||
checked: engine.nymeaConfiguration.debugServerEnabled
|
||||
onClicked: engine.nymeaConfiguration.debugServerEnabled = checked
|
||||
}
|
||||
}
|
||||
|
||||
@ -138,6 +138,12 @@ Page {
|
||||
|
||||
}
|
||||
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/logs.svg"
|
||||
text: qsTr("Log viewer")
|
||||
onClicked: pageStack.push(Qt.resolvedUrl("system/LogViewerPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/cloud.svg"
|
||||
@ -145,24 +151,25 @@ Page {
|
||||
visible: engine.jsonRpcClient.ensureServerVersion("1.9")
|
||||
onClicked: pageStack.push(Qt.resolvedUrl("system/CloudSettingsPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/plugin.svg"
|
||||
text: qsTr("Plugins")
|
||||
onClicked:pageStack.push(Qt.resolvedUrl("system/PluginsPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/logs.svg"
|
||||
text: qsTr("Log viewer")
|
||||
onClicked: pageStack.push(Qt.resolvedUrl("system/LogViewerPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/network-vpn.svg"
|
||||
text: qsTr("Server interfaces")
|
||||
onClicked: pageStack.push(Qt.resolvedUrl("system/ConnectionInterfacesPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/mqtt.svg"
|
||||
text: qsTr("MQTT broker")
|
||||
visible: engine.jsonRpcClient.ensureServerVersion("1.11")
|
||||
onClicked: pageStack.push(Qt.resolvedUrl("system/MqttBrokerSettingsPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/plugin.svg"
|
||||
text: qsTr("Plugins")
|
||||
onClicked:pageStack.push(Qt.resolvedUrl("system/PluginsPage.qml"))
|
||||
}
|
||||
MeaListItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
iconName: "../images/info.svg"
|
||||
|
||||
@ -5,6 +5,7 @@ import QtQuick.Controls.Material 2.2
|
||||
|
||||
SwipeDelegate {
|
||||
id: root
|
||||
implicitWidth: 200
|
||||
|
||||
property string subText
|
||||
property bool progressive: true
|
||||
|
||||
@ -8,11 +8,13 @@ import "../components"
|
||||
ItemDelegate {
|
||||
id: root
|
||||
|
||||
property var actionType: null
|
||||
property ActionType actionType: null
|
||||
property var actionState: null
|
||||
|
||||
signal executeAction(var params)
|
||||
|
||||
readonly property bool multiParam: actionType.paramTypes.count > 1
|
||||
|
||||
contentItem: ColumnLayout {
|
||||
RowLayout {
|
||||
Label {
|
||||
@ -25,7 +27,7 @@ ItemDelegate {
|
||||
id: loader
|
||||
Layout.fillWidth: sourceComponent == textFieldComponent || sourceComponent == buttonComponent
|
||||
sourceComponent: {
|
||||
if (root.actionType.paramTypes.count !== 1) {
|
||||
if (root.multiParam || root.actionType.paramTypes.count === 0) {
|
||||
return buttonComponent
|
||||
}
|
||||
|
||||
@ -68,16 +70,21 @@ ItemDelegate {
|
||||
}
|
||||
Repeater {
|
||||
id: paramRepeater
|
||||
|
||||
model: root.actionType.paramTypes
|
||||
delegate: Loader {
|
||||
id: bottomLoader
|
||||
property var paramType: root.actionType.paramTypes.get(index)
|
||||
|
||||
Layout.fillWidth: true
|
||||
sourceComponent: {
|
||||
switch (paramType.type.toLowerCase()) {
|
||||
case "int":
|
||||
case "double":
|
||||
if (paramType.minValue !== undefined && paramType.maxValue !== undefined) {
|
||||
if (root.multiParam) {
|
||||
return labelledSpinnerComponent;
|
||||
}
|
||||
return sliderComponent
|
||||
}
|
||||
return textFieldComponent;
|
||||
@ -87,7 +94,7 @@ ItemDelegate {
|
||||
return paramType.allowedValues.length === 0 ? textFieldComponent :
|
||||
root.actionType.paramTypes.count === 1 ? null : comboBoxComponent
|
||||
case "bool":
|
||||
if (root.actionType.paramTypes.count > 1) {
|
||||
if (root.multiParam) {
|
||||
return labeledBoolComponent;
|
||||
}
|
||||
return null
|
||||
@ -104,9 +111,9 @@ ItemDelegate {
|
||||
}
|
||||
Binding {
|
||||
target: bottomLoader.item
|
||||
when: bottomLoader.item && root.actionState
|
||||
when: bottomLoader.item
|
||||
property: "value"
|
||||
value: root.actionState
|
||||
value: (root.actionState && index == 0) ? root.actionState : root.actionType.paramTypes.get(index).defaultValue
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -147,8 +154,10 @@ ItemDelegate {
|
||||
id: switchRow
|
||||
property var paramType: null
|
||||
property var value
|
||||
|
||||
Label {
|
||||
text: paramType.displayName
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
Switch {
|
||||
checked: paramType.defaultValue
|
||||
@ -196,7 +205,28 @@ ItemDelegate {
|
||||
text: sliderRow.paramType.maxValue
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: labelledSpinnerComponent
|
||||
RowLayout {
|
||||
id: sliderRow
|
||||
property var paramType: null
|
||||
property var value: null
|
||||
Label {
|
||||
text: sliderRow.paramType.displayName
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
SpinBox {
|
||||
from: sliderRow.paramType.minValue
|
||||
to: sliderRow.paramType.maxValue
|
||||
value: sliderRow.value
|
||||
editable: true
|
||||
onValueModified: {
|
||||
sliderRow.value = value
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
|
||||
@ -8,7 +8,7 @@ import "../components"
|
||||
ItemDelegate {
|
||||
id: root
|
||||
|
||||
property var paramType: null
|
||||
property ParamType paramType: null
|
||||
property alias value: d.value
|
||||
property var param: Param {
|
||||
id: d
|
||||
@ -17,7 +17,10 @@ ItemDelegate {
|
||||
}
|
||||
property bool writable: true
|
||||
|
||||
topPadding: 0
|
||||
bottomPadding: 0
|
||||
contentItem: ColumnLayout {
|
||||
id: contentItemColumn
|
||||
RowLayout {
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
@ -36,10 +39,7 @@ ItemDelegate {
|
||||
case "bool":
|
||||
return boolComponent;
|
||||
case "int":
|
||||
if (root.paramType.minimumValue !== undefined && root.paramType.maximumValue !== undefined) {
|
||||
return sliderComponent;
|
||||
}
|
||||
return textFieldComponent;
|
||||
return spinnerComponent;
|
||||
case "string":
|
||||
case "qstring":
|
||||
if (root.paramType.allowedValues.length > 0) {
|
||||
@ -58,12 +58,12 @@ ItemDelegate {
|
||||
Layout.fillWidth: true
|
||||
sourceComponent: {
|
||||
switch (root.paramType.type.toLowerCase()) {
|
||||
case "int":
|
||||
case "double":
|
||||
if (root.paramType.minValue !== undefined && root.paramType.maxValue !== undefined) {
|
||||
return sliderComponent
|
||||
}
|
||||
break;
|
||||
// case "int":
|
||||
// case "double":
|
||||
// if (root.paramType.minValue !== undefined && root.paramType.maxValue !== undefined) {
|
||||
// return sliderComponent
|
||||
// }
|
||||
// break;
|
||||
case "color":
|
||||
return colorPickerComponent
|
||||
}
|
||||
@ -140,6 +140,20 @@ ItemDelegate {
|
||||
|
||||
}
|
||||
|
||||
Component {
|
||||
id: spinnerComponent
|
||||
SpinBox {
|
||||
value: root.param.value
|
||||
from: root.paramType.minValue
|
||||
to: root.paramType.maxValue
|
||||
editable: true
|
||||
onValueModified: root.param.value = value
|
||||
textFromValue: function(value) {
|
||||
return value
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Component {
|
||||
id: textFieldComponent
|
||||
TextField {
|
||||
@ -167,7 +181,7 @@ ItemDelegate {
|
||||
ColorPicker {
|
||||
id: colorPicker
|
||||
implicitHeight: 200
|
||||
// color: root.param.value
|
||||
// color: root.param.value
|
||||
|
||||
Binding {
|
||||
target: colorPicker
|
||||
|
||||
@ -22,7 +22,8 @@ Page {
|
||||
function enterPage(index, replace) {
|
||||
var device = devicesProxy.get(index);
|
||||
var deviceClass = engine.deviceManager.deviceClasses.getDeviceClass(device.deviceClassId);
|
||||
var page = app.interfaceListToDevicePage(deviceClass.interfaces);
|
||||
var page = app.interfaceListToDevicePage(root.shownInterfaces);
|
||||
// var page = "GenericDevicePage.qml";
|
||||
if (replace) {
|
||||
pageStack.replace(Qt.resolvedUrl("../devicepages/" + page), {device: devicesProxy.get(index)})
|
||||
} else {
|
||||
|
||||
@ -101,7 +101,7 @@ DeviceListPageBase {
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
text: sensorValueDelegate.stateValue
|
||||
? "%1 %2".arg(sensorValueDelegate.stateValue.value).arg(sensorValueDelegate.stateType.unitString)
|
||||
? "%1 %2".arg(Math.round(sensorValueDelegate.stateValue.value * 100) / 100).arg(sensorValueDelegate.stateType.unitString)
|
||||
: ""
|
||||
elide: Text.ElideRight
|
||||
verticalAlignment: Text.AlignVCenter
|
||||
|
||||
@ -9,6 +9,7 @@ DevicePageBase {
|
||||
id: root
|
||||
|
||||
GenericTypeLogView {
|
||||
id: logView
|
||||
anchors.fill: parent
|
||||
|
||||
logsModel: engine.jsonRpcClient.ensureServerVersion("1.10") ? logsModelNg : logsModel
|
||||
@ -28,6 +29,22 @@ DevicePageBase {
|
||||
typeIds: [root.deviceClass.eventTypes.findByName("triggered").id];
|
||||
}
|
||||
|
||||
// delegate: MeaListItemDelegate {
|
||||
// width: parent.width
|
||||
// iconName: app.interfaceToIcon("inputtrigger")
|
||||
// text: model.value.trim()
|
||||
// subText: Qt.formatDateTime(model.timestamp)
|
||||
// progressive: false
|
||||
|
||||
// onClicked: {
|
||||
// print("a", model.value.trim())
|
||||
// var parts = model.value.trim().split(', ')
|
||||
// print("b", parts)
|
||||
// var popup = detailsPopup.createObject(root, {timestamp: model.timestamp, notificationTitle: parts[1], notificationBody: parts[0]});
|
||||
// popup.open();
|
||||
// }
|
||||
// }
|
||||
|
||||
onAddRuleClicked: {
|
||||
var value = logView.logsModel.get(index).value
|
||||
var typeId = logView.logsModel.get(index).typeId
|
||||
|
||||
@ -88,6 +88,7 @@ DevicePageBase {
|
||||
id: logsModelNg
|
||||
deviceId: root.device.id
|
||||
engine: _engine
|
||||
live: true
|
||||
typeIds: [root.deviceClass.actionTypes.findByName("notify").id];
|
||||
}
|
||||
|
||||
@ -102,7 +103,7 @@ DevicePageBase {
|
||||
|
||||
delegate: MeaListItemDelegate {
|
||||
width: parent.width
|
||||
iconName: "../images/notification.svg"
|
||||
iconName: app.interfaceToIcon("notifications")
|
||||
text: model.value.trim()
|
||||
subText: Qt.formatDateTime(model.timestamp)
|
||||
progressive: false
|
||||
|
||||
176
nymea-app/ui/images/messaging-app-symbolic.svg
Normal file
176
nymea-app/ui/images/messaging-app-symbolic.svg
Normal file
@ -0,0 +1,176 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<!-- Created with Inkscape (http://www.inkscape.org/) -->
|
||||
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
|
||||
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
|
||||
width="96"
|
||||
height="96"
|
||||
id="svg4874"
|
||||
version="1.1"
|
||||
inkscape:version="0.91+devel r"
|
||||
viewBox="0 0 96 96.000001"
|
||||
sodipodi:docname="message.svg">
|
||||
<defs
|
||||
id="defs4876" />
|
||||
<sodipodi:namedview
|
||||
id="base"
|
||||
pagecolor="#ffffff"
|
||||
bordercolor="#666666"
|
||||
borderopacity="1.0"
|
||||
inkscape:pageopacity="0.0"
|
||||
inkscape:pageshadow="2"
|
||||
inkscape:zoom="5.6199993"
|
||||
inkscape:cx="-40.729549"
|
||||
inkscape:cy="50.693934"
|
||||
inkscape:document-units="px"
|
||||
inkscape:current-layer="g4780"
|
||||
showgrid="true"
|
||||
showborder="true"
|
||||
fit-margin-top="0"
|
||||
fit-margin-left="0"
|
||||
fit-margin-right="0"
|
||||
fit-margin-bottom="0"
|
||||
inkscape:snap-bbox="true"
|
||||
inkscape:bbox-paths="true"
|
||||
inkscape:bbox-nodes="true"
|
||||
inkscape:snap-bbox-edge-midpoints="true"
|
||||
inkscape:snap-bbox-midpoints="true"
|
||||
inkscape:object-paths="true"
|
||||
inkscape:snap-intersection-paths="true"
|
||||
inkscape:object-nodes="true"
|
||||
inkscape:snap-smooth-nodes="true"
|
||||
inkscape:snap-midpoints="true"
|
||||
inkscape:snap-object-midpoints="true"
|
||||
inkscape:snap-center="true"
|
||||
showguides="true"
|
||||
inkscape:guide-bbox="true"
|
||||
inkscape:snap-global="true">
|
||||
<inkscape:grid
|
||||
type="xygrid"
|
||||
id="grid5451"
|
||||
empspacing="8" />
|
||||
<sodipodi:guide
|
||||
orientation="1,0"
|
||||
position="8,-8.0000001"
|
||||
id="guide4063" />
|
||||
<sodipodi:guide
|
||||
orientation="1,0"
|
||||
position="4,-8.0000001"
|
||||
id="guide4065" />
|
||||
<sodipodi:guide
|
||||
orientation="0,1"
|
||||
position="-8,88.000001"
|
||||
id="guide4067" />
|
||||
<sodipodi:guide
|
||||
orientation="0,1"
|
||||
position="-8,92.000001"
|
||||
id="guide4069" />
|
||||
<sodipodi:guide
|
||||
orientation="0,1"
|
||||
position="104,4"
|
||||
id="guide4071" />
|
||||
<sodipodi:guide
|
||||
orientation="0,1"
|
||||
position="-5,8.0000001"
|
||||
id="guide4073" />
|
||||
<sodipodi:guide
|
||||
orientation="1,0"
|
||||
position="88,-8.0000001"
|
||||
id="guide4077" />
|
||||
<sodipodi:guide
|
||||
orientation="0,1"
|
||||
position="-8,84.000001"
|
||||
id="guide4074" />
|
||||
<sodipodi:guide
|
||||
orientation="1,0"
|
||||
position="12,-8.0000001"
|
||||
id="guide4076" />
|
||||
<sodipodi:guide
|
||||
orientation="1,0"
|
||||
position="84,-8.0000001"
|
||||
id="guide4080" />
|
||||
<sodipodi:guide
|
||||
position="48,-8.0000001"
|
||||
orientation="1,0"
|
||||
id="guide4170" />
|
||||
<sodipodi:guide
|
||||
position="-8,48"
|
||||
orientation="0,1"
|
||||
id="guide4172" />
|
||||
<sodipodi:guide
|
||||
position="92,-8.0000001"
|
||||
orientation="1,0"
|
||||
id="guide4760" />
|
||||
</sodipodi:namedview>
|
||||
<metadata
|
||||
id="metadata4879">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
inkscape:label="Layer 1"
|
||||
inkscape:groupmode="layer"
|
||||
id="layer1"
|
||||
transform="translate(67.857146,-78.50504)">
|
||||
<g
|
||||
transform="matrix(0,-1,-1,0,373.50506,516.50504)"
|
||||
id="g4845"
|
||||
style="display:inline">
|
||||
<g
|
||||
inkscape:export-ydpi="90"
|
||||
inkscape:export-xdpi="90"
|
||||
inkscape:export-filename="next01.png"
|
||||
transform="matrix(-0.9996045,0,0,1,575.94296,-611.00001)"
|
||||
id="g4778"
|
||||
inkscape:label="Layer 1">
|
||||
<g
|
||||
transform="matrix(-1,0,0,1,575.99999,611)"
|
||||
id="g4780"
|
||||
style="display:inline">
|
||||
<rect
|
||||
style="color:#000000;display:inline;overflow:visible;visibility:visible;fill:none;stroke:none;stroke-width:4;marker:none;enable-background:accumulate"
|
||||
id="rect4782"
|
||||
width="96.037987"
|
||||
height="96"
|
||||
x="-438.00244"
|
||||
y="345.36221"
|
||||
transform="scale(-1,1)" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:15px;line-height:125%;font-family:Ubuntu;-inkscape-font-specification:Ubuntu;text-align:center;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:middle;display:inline;fill:#808080;fill-opacity:1;stroke:none"
|
||||
d="m 353.96924,406.36222 10.10306,-13 2.20883,2.05882 0,21.88236 -2.20883,2.05882 z"
|
||||
id="path1652"
|
||||
inkscape:connector-curvature="0"
|
||||
sodipodi:nodetypes="cccccc" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:15px;line-height:125%;font-family:Ubuntu;-inkscape-font-specification:Ubuntu;text-align:center;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:middle;display:inline;fill:#808080;fill-opacity:1;stroke:none"
|
||||
d="m 401.98822,419.36222 0,-25 -4.0016,0 0,25 z"
|
||||
id="path4215"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:15px;line-height:125%;font-family:Ubuntu;-inkscape-font-specification:Ubuntu;text-align:center;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:middle;display:inline;fill:#808080;fill-opacity:1;stroke:none"
|
||||
d="m 389.98346,419.36222 0,-52 -4.00156,0 0,52 z"
|
||||
id="path4237"
|
||||
inkscape:connector-curvature="0" />
|
||||
<path
|
||||
style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:medium;line-height:normal;font-family:sans-serif;font-variant-ligatures:none;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-feature-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#808080;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:4.00079155;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;marker:none;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate"
|
||||
d="m 375.97656,349.36133 c -2.6314,0 -4.71356,0.23788 -6.46875,0.89648 -1.75519,0.6586 -3.16114,1.84985 -3.99219,3.35547 -1.66208,3.01124 -1.48476,6.6938 -1.54296,11.72656 l 0,0.0117 0,56.02149 0,0.0117 c 0.0582,5.03276 -0.11912,8.71532 1.54296,11.72656 0.83105,1.50562 2.237,2.69686 3.99219,3.35547 1.75519,0.6586 3.83735,0.89648 6.46875,0.89648 l 36.01563,0 c 2.6314,0 4.71551,-0.23788 6.4707,-0.89648 1.75519,-0.65861 3.15919,-1.84985 3.99023,-3.35547 1.66209,-3.01124 1.48477,-6.6938 1.54297,-11.72656 l 0,-0.0117 0,-56.02149 0,-0.0117 c -0.0582,-5.03276 0.11912,-8.71532 -1.54297,-11.72656 -0.83104,-1.50562 -2.23504,-2.69687 -3.99023,-3.35547 -1.75519,-0.6586 -3.8393,-0.89648 -6.4707,-0.89648 l -36.01563,0 z m 0,4.00195 36.01563,0 c 2.37058,0 4.02426,0.25031 5.06445,0.64063 1.0402,0.39031 1.48966,0.80945 1.89453,1.54297 0.80823,1.46429 0.98613,4.77814 1.04492,9.8164 l 0,55.97656 c -0.0584,5.05418 -0.23518,8.37086 -1.04492,9.83789 -0.40487,0.73352 -0.85433,1.15266 -1.89453,1.54297 -1.04019,0.39032 -2.69387,0.64063 -5.06445,0.64063 l -36.01563,0 c -2.37058,0 -4.0223,-0.25031 -5.0625,-0.64063 -1.04019,-0.39031 -1.48966,-0.80945 -1.89453,-1.54297 -0.80835,-1.46451 -0.98616,-4.77682 -1.04492,-9.8164 l 0,-0.0215 0,-55.95312 0,-0.0234 c 0.0588,-5.03826 0.23669,-8.35211 1.04492,-9.8164 0.40487,-0.73352 0.85434,-1.15266 1.89453,-1.54297 1.0402,-0.39032 2.69192,-0.64063 5.0625,-0.64063 z"
|
||||
id="path4211"
|
||||
inkscape:connector-curvature="0" />
|
||||
</g>
|
||||
</g>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 8.5 KiB |
72
nymea-app/ui/images/mqtt.svg
Normal file
72
nymea-app/ui/images/mqtt.svg
Normal file
@ -0,0 +1,72 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<svg
|
||||
xmlns:dc="http://purl.org/dc/elements/1.1/"
|
||||
xmlns:cc="http://creativecommons.org/ns#"
|
||||
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
|
||||
xmlns:svg="http://www.w3.org/2000/svg"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
viewBox="0 0 96 96.000001"
|
||||
version="1.1"
|
||||
id="svg4874"
|
||||
height="96"
|
||||
width="96">
|
||||
<defs
|
||||
id="defs4876" />
|
||||
<metadata
|
||||
id="metadata4879">
|
||||
<rdf:RDF>
|
||||
<cc:Work
|
||||
rdf:about="">
|
||||
<dc:format>image/svg+xml</dc:format>
|
||||
<dc:type
|
||||
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
|
||||
<dc:title></dc:title>
|
||||
</cc:Work>
|
||||
</rdf:RDF>
|
||||
</metadata>
|
||||
<g
|
||||
transform="translate(67.857146,-78.50504)"
|
||||
id="layer1">
|
||||
<g
|
||||
style="display:inline"
|
||||
id="g4845"
|
||||
transform="matrix(0,-1,-1,0,373.50506,516.50504)">
|
||||
<g
|
||||
id="g4778"
|
||||
transform="matrix(-0.9996045,0,0,1,575.94296,-611.00001)">
|
||||
<g
|
||||
style="display:inline"
|
||||
id="g4780"
|
||||
transform="matrix(-1,0,0,1,575.99999,611)">
|
||||
<rect
|
||||
transform="scale(-1,1)"
|
||||
y="345.36221"
|
||||
x="-438.00244"
|
||||
height="96"
|
||||
width="96.037987"
|
||||
id="rect4782"
|
||||
style="color:#000000;display:inline;overflow:visible;visibility:visible;fill:none;stroke:none;stroke-width:4;marker:none;enable-background:accumulate" />
|
||||
<path
|
||||
id="path1652"
|
||||
d="m 353.96924,406.36222 10.10306,-13 2.20883,2.05882 0,21.88236 -2.20883,2.05882 z"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:15px;line-height:125%;font-family:Ubuntu;-inkscape-font-specification:Ubuntu;text-align:center;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:middle;display:inline;fill:#808080;fill-opacity:1;stroke:none" />
|
||||
<path
|
||||
id="path4211"
|
||||
d="m 375.97656,349.36133 c -2.6314,0 -4.71356,0.23788 -6.46875,0.89648 -1.75519,0.6586 -3.16114,1.84985 -3.99219,3.35547 -1.66208,3.01124 -1.48476,6.6938 -1.54296,11.72656 l 0,0.0117 0,56.02149 0,0.0117 c 0.0582,5.03276 -0.11912,8.71532 1.54296,11.72656 0.83105,1.50562 2.237,2.69686 3.99219,3.35547 1.75519,0.6586 3.83735,0.89648 6.46875,0.89648 l 36.01563,0 c 2.6314,0 4.71551,-0.23788 6.4707,-0.89648 1.75519,-0.65861 3.15919,-1.84985 3.99023,-3.35547 1.66209,-3.01124 1.48477,-6.6938 1.54297,-11.72656 l 0,-0.0117 0,-56.02149 0,-0.0117 c -0.0582,-5.03276 0.11912,-8.71532 -1.54297,-11.72656 -0.83104,-1.50562 -2.23504,-2.69687 -3.99023,-3.35547 -1.75519,-0.6586 -3.8393,-0.89648 -6.4707,-0.89648 l -36.01563,0 z m 0,4.00195 36.01563,0 c 2.37058,0 4.02426,0.25031 5.06445,0.64063 1.0402,0.39031 1.48966,0.80945 1.89453,1.54297 0.80823,1.46429 0.98613,4.77814 1.04492,9.8164 l 0,55.97656 c -0.0584,5.05418 -0.23518,8.37086 -1.04492,9.83789 -0.40487,0.73352 -0.85433,1.15266 -1.89453,1.54297 -1.04019,0.39032 -2.69387,0.64063 -5.06445,0.64063 l -36.01563,0 c -2.37058,0 -4.0223,-0.25031 -5.0625,-0.64063 -1.04019,-0.39031 -1.48966,-0.80945 -1.89453,-1.54297 -0.80835,-1.46451 -0.98616,-4.77682 -1.04492,-9.8164 l 0,-0.0215 0,-55.95312 0,-0.0234 c 0.0588,-5.03826 0.23669,-8.35211 1.04492,-9.8164 0.40487,-0.73352 0.85434,-1.15266 1.89453,-1.54297 1.0402,-0.39032 2.69192,-0.64063 5.0625,-0.64063 z"
|
||||
style="color:#000000;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:medium;line-height:normal;font-family:sans-serif;font-variant-ligatures:none;font-variant-position:normal;font-variant-caps:normal;font-variant-numeric:normal;font-variant-alternates:normal;font-feature-settings:normal;text-indent:0;text-align:start;text-decoration:none;text-decoration-line:none;text-decoration-style:solid;text-decoration-color:#000000;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;baseline-shift:baseline;text-anchor:start;white-space:normal;shape-padding:0;clip-rule:nonzero;display:inline;overflow:visible;visibility:visible;opacity:1;isolation:auto;mix-blend-mode:normal;color-interpolation:sRGB;color-interpolation-filters:linearRGB;solid-color:#000000;solid-opacity:1;fill:#808080;fill-opacity:1;fill-rule:nonzero;stroke:none;stroke-width:4.00079155;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-dasharray:none;stroke-dashoffset:0;stroke-opacity:1;marker:none;color-rendering:auto;image-rendering:auto;shape-rendering:auto;text-rendering:auto;enable-background:accumulate" />
|
||||
<text
|
||||
transform="matrix(0,-0.99980223,-1.0001978,0,0,0)"
|
||||
id="text1615"
|
||||
y="-388.20221"
|
||||
x="-427.9313"
|
||||
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:21.33755493px;line-height:1.25;font-family:Verdana;-inkscape-font-specification:Verdana;letter-spacing:0px;word-spacing:0px;fill:#000000;fill-opacity:1;stroke:none;stroke-width:1.00019789"
|
||||
xml:space="preserve"><tspan
|
||||
style="font-style:normal;font-variant:normal;font-weight:bold;font-stretch:normal;font-size:21.33755302px;font-family:Verdana;-inkscape-font-specification:'Verdana Bold';fill:#808080;fill-opacity:1;stroke-width:1.00019789"
|
||||
y="-388.20221"
|
||||
x="-427.9313"
|
||||
id="tspan1613">MQTT</tspan></text>
|
||||
</g>
|
||||
</g>
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 5.4 KiB |
@ -389,7 +389,7 @@ MainPageTile {
|
||||
// switch (model.name) {
|
||||
// case "sensor":
|
||||
// }
|
||||
return parent.state.value + "°C";
|
||||
return (Math.round(parent.state.value * 100) / 100) + " °C";
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -49,9 +49,9 @@ Page {
|
||||
SwitchDelegate {
|
||||
Layout.fillWidth: true
|
||||
text: qsTr("Cloud connection enabled")
|
||||
checked: engine.basicConfiguration.cloudEnabled
|
||||
checked: engine.nymeaConfiguration.cloudEnabled
|
||||
onToggled: {
|
||||
engine.basicConfiguration.cloudEnabled = checked;
|
||||
engine.nymeaConfiguration.cloudEnabled = checked;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -5,9 +5,9 @@ import Nymea 1.0
|
||||
import "../components"
|
||||
|
||||
MeaListItemDelegate {
|
||||
text: model.address
|
||||
subText: model.port
|
||||
iconName: "../images/network-wifi-symbolic.svg"
|
||||
text: qsTr("Interface: %1").arg(model.address === "0.0.0.0" ? qsTr("Any") : model.address === "127.0.0.1" ? qsTr("localhost") : model.address)
|
||||
subText: qsTr("Port: %1").arg(model.port)
|
||||
iconName: "../images/network-vpn.svg"
|
||||
progressive: false
|
||||
iconColor: {
|
||||
if ((engine.connection.hostAddress === model.address || model.address === "0.0.0.0")
|
||||
|
||||
@ -27,18 +27,52 @@ Page {
|
||||
Layout.topMargin: app.margins
|
||||
text: qsTr("TCP Server Interfaces")
|
||||
wrapMode: Text.WordWrap
|
||||
color: app.accentColor
|
||||
}
|
||||
|
||||
Repeater {
|
||||
model: engine.basicConfiguration.tcpServerConfigurations
|
||||
model: engine.nymeaConfiguration.tcpServerConfigurations
|
||||
delegate: ConnectionInterfaceDelegate {
|
||||
Layout.fillWidth: true
|
||||
canDelete: true
|
||||
onClicked: {
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: engine.nymeaConfiguration.tcpServerConfigurations.get(index).clone() });
|
||||
popup.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.setTcpServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
onDeleteClicked: {
|
||||
print("should delete")
|
||||
engine.basicConfiguration.deleteTcpServerConfiguration(model.id)
|
||||
engine.nymeaConfiguration.deleteTcpServerConfiguration(model.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
Button {
|
||||
Layout.fillWidth: true
|
||||
Layout.margins: app.margins
|
||||
text: qsTr("Add")
|
||||
onClicked: {
|
||||
var config = engine.nymeaConfiguration.createServerConfiguration("0.0.0.0", 2222 + engine.nymeaConfiguration.tcpServerConfigurations.count, false, false);
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: config });
|
||||
popup.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.setTcpServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
}
|
||||
|
||||
ThinDivider {}
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins
|
||||
@ -46,18 +80,51 @@ Page {
|
||||
Layout.topMargin: app.margins
|
||||
text: qsTr("WebSocket Server Interfaces")
|
||||
wrapMode: Text.WordWrap
|
||||
color: app.accentColor
|
||||
}
|
||||
|
||||
Repeater {
|
||||
model: engine.basicConfiguration.websocketServerConfigurations
|
||||
model: engine.nymeaConfiguration.webSocketServerConfigurations
|
||||
delegate: ConnectionInterfaceDelegate {
|
||||
Layout.fillWidth: true
|
||||
canDelete: true
|
||||
onClicked: {
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: engine.nymeaConfiguration.webSocketServerConfigurations.get(index).clone() });
|
||||
popup.accepted.connect(function() {
|
||||
print("configuring:", popup.serverConfiguration.port)
|
||||
engine.nymeaConfiguration.setWebSocketServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
onDeleteClicked: {
|
||||
print("should delete", model.id)
|
||||
engine.basicConfiguration.deleteWebsocketServerConfiguration(model.id)
|
||||
engine.nymeaConfiguration.deleteWebSocketServerConfiguration(model.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
Button {
|
||||
Layout.fillWidth: true
|
||||
Layout.margins: app.margins
|
||||
text: qsTr("Add")
|
||||
onClicked: {
|
||||
var config = engine.nymeaConfiguration.createServerConfiguration("0.0.0.0", 4444 + engine.nymeaConfiguration.webSocketServerConfigurations.count, false, false);
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: config });
|
||||
popup.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.setWebSocketServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
143
nymea-app/ui/system/MqttBrokerSettingsPage.qml
Normal file
143
nymea-app/ui/system/MqttBrokerSettingsPage.qml
Normal file
@ -0,0 +1,143 @@
|
||||
import QtQuick 2.9
|
||||
import QtQuick.Controls 2.2
|
||||
import QtQuick.Layouts 1.3
|
||||
import Nymea 1.0
|
||||
import "../components"
|
||||
|
||||
Page {
|
||||
id: root
|
||||
header: GuhHeader {
|
||||
text: qsTr("MQTT broker")
|
||||
onBackPressed: pageStack.pop();
|
||||
}
|
||||
|
||||
// Flickable {
|
||||
// anchors.fill: parent
|
||||
// contentHeight: connectionsColumn.implicitHeight
|
||||
// interactive: contentHeight > height
|
||||
|
||||
ColumnLayout {
|
||||
id: connectionsColumn
|
||||
// anchors { left: parent.left; top: parent.top; right: parent.right }
|
||||
anchors.fill: parent
|
||||
// layoutDirection: Qt.
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins
|
||||
Layout.rightMargin: app.margins
|
||||
Layout.topMargin: app.margins
|
||||
text: qsTr("MQTT Server Interfaces")
|
||||
wrapMode: Text.WordWrap
|
||||
color: app.accentColor
|
||||
}
|
||||
|
||||
ListView {
|
||||
Layout.fillWidth: true
|
||||
Layout.minimumHeight: 0
|
||||
Layout.preferredHeight: Math.min(contentHeight, 120)
|
||||
model: engine.nymeaConfiguration.mqttServerConfigurations
|
||||
clip: true
|
||||
ScrollBar.vertical: ScrollBar {}
|
||||
|
||||
delegate: ConnectionInterfaceDelegate {
|
||||
width: parent.width
|
||||
canDelete: true
|
||||
onClicked: {
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: engine.nymeaConfiguration.mqttServerConfigurations.get(index).clone() });
|
||||
popup.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.setMqttServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
|
||||
onDeleteClicked: {
|
||||
engine.nymeaConfiguration.deleteMqttServerConfiguration(model.id)
|
||||
}
|
||||
}
|
||||
}
|
||||
Button {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
text: qsTr("Add")
|
||||
onClicked: {
|
||||
var config = engine.nymeaConfiguration.createServerConfiguration("0.0.0.0", 1883 + engine.nymeaConfiguration.mqttServerConfigurations.count, false, false);
|
||||
var component = Qt.createComponent(Qt.resolvedUrl("ServerConfigurationDialog.qml"));
|
||||
var popup = component.createObject(root, { serverConfiguration: config });
|
||||
popup.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.setMqttServerConfiguration(popup.serverConfiguration)
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.rejected.connect(function() {
|
||||
popup.serverConfiguration.destroy();
|
||||
})
|
||||
popup.open()
|
||||
}
|
||||
}
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.topMargin: app.margins; Layout.rightMargin: app.margins
|
||||
text: qsTr("MQTT permissions")
|
||||
wrapMode: Text.WordWrap
|
||||
color: app.accentColor
|
||||
}
|
||||
|
||||
ListView {
|
||||
Layout.fillWidth: true
|
||||
Layout.preferredHeight: Math.min(contentHeight, parent.height * .4)
|
||||
model: engine.nymeaConfiguration.mqttPolicies
|
||||
clip: true
|
||||
ScrollBar.vertical: ScrollBar {}
|
||||
delegate: MeaListItemDelegate {
|
||||
width: parent.width
|
||||
iconName: "../images/account.svg"
|
||||
text: qsTr("Client ID: %1").arg(model.clientId)
|
||||
subText: qsTr("Username: %1").arg(model.username)
|
||||
progressive: false
|
||||
canDelete: true
|
||||
onClicked: {
|
||||
var page = pageStack.push(Qt.resolvedUrl("MqttPolicyPage.qml"), { policy: engine.nymeaConfiguration.mqttPolicies.get(index).clone() });
|
||||
page.accepted.connect(function() {
|
||||
if (page.policy.clientId !== model.clientId) {
|
||||
engine.nymeaConfiguration.deleteMqttPolicy(model.clientId);
|
||||
}
|
||||
engine.nymeaConfiguration.updateMqttPolicy(page.policy)
|
||||
page.policy.destroy();
|
||||
})
|
||||
page.rejected.connect(function() {
|
||||
page.policy.destroy();
|
||||
})
|
||||
}
|
||||
onDeleteClicked: {
|
||||
engine.nymeaConfiguration.deleteMqttPolicy(model.clientId)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Button {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
text: qsTr("Add")
|
||||
onClicked: {
|
||||
var page = pageStack.push(Qt.resolvedUrl("MqttPolicyPage.qml"), { policy: engine.nymeaConfiguration.createMqttPolicy() });
|
||||
page.accepted.connect(function() {
|
||||
engine.nymeaConfiguration.updateMqttPolicy(page.policy)
|
||||
page.policy.destroy();
|
||||
})
|
||||
page.rejected.connect(function() {
|
||||
page.policy.destroy();
|
||||
})
|
||||
}
|
||||
}
|
||||
Item {
|
||||
Layout.fillWidth: true
|
||||
Layout.fillHeight: true
|
||||
Layout.minimumHeight: 0
|
||||
}
|
||||
}
|
||||
// }
|
||||
}
|
||||
201
nymea-app/ui/system/MqttPolicyPage.qml
Normal file
201
nymea-app/ui/system/MqttPolicyPage.qml
Normal file
@ -0,0 +1,201 @@
|
||||
import QtQuick 2.9
|
||||
import QtQuick.Controls 2.1
|
||||
import QtQuick.Controls.Material 2.1
|
||||
import QtQuick.Layouts 1.1
|
||||
import Nymea 1.0
|
||||
import "../components"
|
||||
|
||||
Page {
|
||||
id: root
|
||||
header: GuhHeader {
|
||||
text: qsTr("Mqtt permission")
|
||||
onBackPressed: {
|
||||
root.rejected();
|
||||
pageStack.pop();
|
||||
}
|
||||
HeaderButton {
|
||||
imageSource: "../images/tick.svg"
|
||||
enabled: clientIdTextField.isValid
|
||||
onClicked: {
|
||||
root.accepted();
|
||||
pageStack.pop();
|
||||
}
|
||||
}
|
||||
}
|
||||
property MqttPolicy policy: null
|
||||
|
||||
signal accepted();
|
||||
signal rejected()
|
||||
|
||||
ColumnLayout {
|
||||
anchors { left: parent.left; top: parent.top; right: parent.right; bottom: parent.bottom }
|
||||
RowLayout {
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins; Layout.topMargin: app.margins
|
||||
spacing: app.margins
|
||||
Label {
|
||||
text: qsTr("Client ID:")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
TextField {
|
||||
id: clientIdTextField
|
||||
Layout.fillWidth: true
|
||||
text: root.policy ? root.policy.clientId : ""
|
||||
onEditingFinished: root.policy.clientId = text
|
||||
placeholderText: qsTr("E.g. Sensor_1")
|
||||
property bool isEmpty: displayText.length === 0
|
||||
property bool isDuplicate: clientIdTextField.displayText != root.policy.clientId && engine.nymeaConfiguration.mqttPolicies.getPolicy(clientIdTextField.displayText) !== null
|
||||
property bool isValid: !isEmpty && !isDuplicate
|
||||
}
|
||||
}
|
||||
Label {
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
text: clientIdTextField.isDuplicate ? qsTr("%1 is already used").arg(clientIdTextField.displayText) : qsTr("Can't be blank")
|
||||
font.pixelSize: app.smallFont
|
||||
Layout.alignment: Qt.AlignRight
|
||||
color: "red"
|
||||
visible: !clientIdTextField.isValid
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
Label {
|
||||
text: qsTr("Username:")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
TextField {
|
||||
id: usernameTextField
|
||||
Layout.fillWidth: true
|
||||
text: root.policy ? root.policy.username : ""
|
||||
onEditingFinished: root.policy.username = text
|
||||
placeholderText: qsTr("Optional")
|
||||
}
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
Label {
|
||||
text: qsTr("Password:")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
RowLayout {
|
||||
TextField {
|
||||
id: passwordTextField
|
||||
Layout.fillWidth: true
|
||||
text: root.policy ? root.policy.password : ""
|
||||
onEditingFinished: root.policy.password = text
|
||||
placeholderText: qsTr("Optional")
|
||||
echoMode: hiddenPassword ? TextInput.Password : TextInput.Normal
|
||||
property bool hiddenPassword: true
|
||||
}
|
||||
ColorIcon {
|
||||
Layout.preferredHeight: app.iconSize
|
||||
Layout.preferredWidth: height
|
||||
name: "../images/eye.svg"
|
||||
color: passwordTextField.hiddenPassword ? keyColor : app.accentColor
|
||||
MouseArea {
|
||||
anchors.fill: parent
|
||||
onClicked: passwordTextField.hiddenPassword = !passwordTextField.hiddenPassword
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ThinDivider {}
|
||||
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins; Layout.topMargin: app.margins
|
||||
text: qsTr("Allowed publish topics")
|
||||
}
|
||||
ListView {
|
||||
Layout.fillWidth: true
|
||||
Layout.fillHeight: true
|
||||
model: root.policy.allowedPublishTopicFilters
|
||||
ScrollBar.vertical: ScrollBar {}
|
||||
clip: true
|
||||
delegate: MeaListItemDelegate {
|
||||
width: parent.width
|
||||
text: modelData
|
||||
canDelete: true
|
||||
progressive: false
|
||||
onDeleteClicked: {
|
||||
root.policy.allowedPublishTopicFilters.splice(index, 1)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins
|
||||
property bool add: false
|
||||
TextField {
|
||||
id: pubField
|
||||
Layout.fillWidth: parent.add
|
||||
Layout.preferredWidth: parent.add ? undefined : 0
|
||||
Behavior on width {
|
||||
NumberAnimation {}
|
||||
}
|
||||
}
|
||||
Button {
|
||||
Layout.fillWidth: !parent.add
|
||||
text: parent.add ? qsTr("OK") : qsTr("Add")
|
||||
enabled: !parent.add || pubField.displayText.length > 0
|
||||
onClicked: {
|
||||
if (parent.add) {
|
||||
root.policy.allowedPublishTopicFilters.push(pubField.displayText)
|
||||
pubField.clear();
|
||||
}
|
||||
parent.add = !parent.add;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ThinDivider {}
|
||||
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins; Layout.topMargin: app.margins
|
||||
text: qsTr("Allowed subscribe filters")
|
||||
}
|
||||
ListView {
|
||||
Layout.fillWidth: true
|
||||
Layout.fillHeight: true
|
||||
model: root.policy.allowedSubscribeTopicFilters
|
||||
ScrollBar.vertical: ScrollBar {}
|
||||
clip: true
|
||||
delegate: MeaListItemDelegate {
|
||||
width: parent.width
|
||||
text: modelData
|
||||
canDelete: true
|
||||
progressive: false
|
||||
onDeleteClicked: {
|
||||
root.policy.allowedSubscribeTopicFilters.splice(index, 1)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Layout.fillWidth: true
|
||||
Layout.leftMargin: app.margins; Layout.rightMargin: app.margins; Layout.bottomMargin: app.margins
|
||||
property bool add: false
|
||||
TextField {
|
||||
id: subField
|
||||
Layout.fillWidth: parent.add
|
||||
Layout.preferredWidth: parent.add ? undefined : 0
|
||||
}
|
||||
Button {
|
||||
Layout.fillWidth: !parent.add;
|
||||
Behavior on width { NumberAnimation {} }
|
||||
text: parent.add ? qsTr("OK") : qsTr("Add")
|
||||
enabled: !parent.add || subField.displayText.length > 0
|
||||
onClicked: {
|
||||
if (parent.add) {
|
||||
root.policy.allowedSubscribeTopicFilters.push(subField.displayText)
|
||||
subField.clear();
|
||||
}
|
||||
parent.add = !parent.add;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
95
nymea-app/ui/system/ServerConfigurationDialog.qml
Normal file
95
nymea-app/ui/system/ServerConfigurationDialog.qml
Normal file
@ -0,0 +1,95 @@
|
||||
import QtQuick 2.9
|
||||
import QtQuick.Controls 2.1
|
||||
import QtQuick.Controls.Material 2.1
|
||||
import QtQuick.Layouts 1.1
|
||||
import Nymea 1.0
|
||||
|
||||
Dialog {
|
||||
id: root
|
||||
title: qsTr("Server configuration")
|
||||
width: parent.width * .8
|
||||
x: (parent.width - width) / 2
|
||||
y: (parent.height - height) / 2
|
||||
|
||||
property ServerConfiguration serverConfiguration: null
|
||||
standardButtons: Dialog.Ok | Dialog.Cancel
|
||||
|
||||
ColumnLayout {
|
||||
anchors { left: parent.left; top: parent.top; right: parent.right }
|
||||
RowLayout {
|
||||
Label {
|
||||
text: qsTr("Interface")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
ComboBox {
|
||||
id: interfaceCombobox
|
||||
model: [qsTr("Any"), qsTr("Localhost"), qsTr("Custom")]
|
||||
Layout.fillWidth: true
|
||||
currentIndex: !root.serverConfiguration
|
||||
? 0 : root.serverConfiguration.address === "0.0.0.0"
|
||||
? 0
|
||||
: root.serverConfiguration.address === "127.0.0.1"
|
||||
? 1 : 2
|
||||
onActivated: {
|
||||
switch (index) {
|
||||
case 0:
|
||||
root.serverConfiguration.address = "0.0.0.0";
|
||||
break;
|
||||
case 1:
|
||||
root.serverConfiguration.address = "127.0.0.1";
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
RowLayout {
|
||||
visible: interfaceCombobox.currentIndex === 2
|
||||
Label {
|
||||
text: qsTr("Address:")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
TextField {
|
||||
id: addressTextField
|
||||
Layout.fillWidth: true
|
||||
inputMethodHints: Qt.ImhPreferNumbers
|
||||
inputMask: "000.000.000.000"
|
||||
text: root.serverConfiguration ? root.serverConfiguration.address : ""
|
||||
onEditingFinished: root.serverConfiguration.address = text
|
||||
}
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Label {
|
||||
text: qsTr("Port:")
|
||||
Layout.fillWidth: true
|
||||
}
|
||||
TextField {
|
||||
inputMethodHints: Qt.ImhDigitsOnly
|
||||
text: root.serverConfiguration ? root.serverConfiguration.port : 0
|
||||
validator: IntValidator { bottom: 0; top: 65535 }
|
||||
onEditingFinished: root.serverConfiguration.port = text
|
||||
}
|
||||
}
|
||||
|
||||
RowLayout {
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
text: qsTr("SSL enabled")
|
||||
}
|
||||
CheckBox {
|
||||
checkState: root.serverConfiguration && root.serverConfiguration.sslEnabled ? Qt.Checked : Qt.Unchecked
|
||||
onClicked: root.serverConfiguration.sslEnabled = checked
|
||||
}
|
||||
}
|
||||
RowLayout {
|
||||
Label {
|
||||
Layout.fillWidth: true
|
||||
text: qsTr("Login required")
|
||||
}
|
||||
CheckBox {
|
||||
checkState: root.serverConfiguration && root.serverConfiguration.authenticationEnabled ? Qt.Checked : Qt.Unchecked
|
||||
onClicked: root.serverConfiguration.authenticationEnabled = checked
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user