Made device names constant and fixed duplicates

This commit is contained in:
0xFEEDC0DE64
2018-06-01 10:49:09 +02:00
parent bf71582aaf
commit eb0ad52ad6
6 changed files with 76 additions and 68 deletions

View File

@@ -8,11 +8,19 @@ RelaisClient::RelaisClient(QTcpSocket *socket, RelaisServer *server) :
QObject(server), QObject(server),
m_socket(socket), m_socket(socket),
m_server(server), m_server(server),
m_state(Name) m_waitingForName(true)
{ {
m_socket->setParent(this); m_socket->setParent(this);
connect(m_socket, &QIODevice::readyRead, this, &RelaisClient::readyRead); connect(m_socket, &QIODevice::readyRead, this, &RelaisClient::readyRead);
connect(m_socket, &QAbstractSocket::disconnected, this, &QObject::deleteLater); connect(m_socket, &QAbstractSocket::disconnected, this, &QObject::deleteLater);
m_server->m_clients.insert(this);
}
RelaisClient::~RelaisClient()
{
m_server->m_clients.remove(this);
} }
quint16 RelaisClient::localPort() const quint16 RelaisClient::localPort() const
@@ -90,10 +98,19 @@ void RelaisClient::readyRead()
QString line(m_buffer.left(index)); QString line(m_buffer.left(index));
m_buffer.remove(0, index + 2); m_buffer.remove(0, index + 2);
switch(m_state) if(m_waitingForName)
{ {
case Name: m_name = line; m_state = Status; break; auto iter = std::find_if(m_server->m_clients.constBegin(), m_server->m_clients.constEnd(),
case Status: m_status = line; break; [&line](RelaisClient *client) {
} return client->name() == line;
});
if(iter != m_server->m_clients.constEnd())
delete *iter;
m_name = line;
m_waitingForName = false;
}
else
m_status = line;
} }
} }

View File

@@ -13,6 +13,7 @@ class RelaisClient : public QObject
public: public:
explicit RelaisClient(QTcpSocket *socket, RelaisServer *server); explicit RelaisClient(QTcpSocket *socket, RelaisServer *server);
virtual ~RelaisClient();
quint16 localPort() const; quint16 localPort() const;
QHostAddress localAddress() const; QHostAddress localAddress() const;
@@ -37,7 +38,7 @@ private:
QTcpSocket *m_socket; QTcpSocket *m_socket;
RelaisServer *m_server; RelaisServer *m_server;
QByteArray m_buffer; QByteArray m_buffer;
enum { Name, Status } m_state; bool m_waitingForName;
QString m_name; QString m_name;
QString m_status; QString m_status;

View File

@@ -105,9 +105,5 @@ void RelaisServer::newConnection()
if(!connection) if(!connection)
return; return;
auto client = new RelaisClient(connection, this); new RelaisClient(connection, this);
m_clients.insert(client);
connect(client, &QObject::destroyed, this, [=](){
m_clients.remove(client);
});
} }

View File

@@ -15,6 +15,8 @@ class RelaisServer : public QObject
{ {
Q_OBJECT Q_OBJECT
friend class RelaisClient;
public: public:
explicit RelaisServer(QObject *parent = Q_NULLPTR); explicit RelaisServer(QObject *parent = Q_NULLPTR);

View File

@@ -33,6 +33,12 @@ void RelaisWebserver::handleRequest(HttpClientConnection *connection, const Http
{ {
handleRoot(connection, request); handleRoot(connection, request);
} }
else if(request.path == QStringLiteral("/refresh"))
{
for(auto client : m_relaisServer->clients())
client->requestStatus();
redirectRoot(connection, request);
}
else if(request.path.startsWith("/devices/")) else if(request.path.startsWith("/devices/"))
{ {
auto parts = request.path.split('/'); auto parts = request.path.split('/');
@@ -42,57 +48,41 @@ void RelaisWebserver::handleRequest(HttpClientConnection *connection, const Http
return; return;
} }
RelaisClient *client = Q_NULLPTR; RelaisClient *client;
for(auto _client : m_relaisServer->clients())
{ {
if(clientId(_client) == parts.at(2)) auto iter = std::find_if(m_relaisServer->clients().constBegin(), m_relaisServer->clients().constEnd(),
{ [&parts](const RelaisClient *client){
client = _client; return clientId(client) == parts.at(2);
break; });
}
}
if(!client) if(iter == m_relaisServer->clients().constEnd())
{ {
handle404(connection, request); handle404(connection, request);
return; return;
} }
if(parts.at(3) == "on") client = *iter;
{
client->on();
redirectRoot(connection, request);
return;
} }
else if(parts.at(3) == "off")
static const QHash<QString, std::function<void(RelaisClient*)> > actions {
{ QStringLiteral("toggle"), [](RelaisClient *client){ client->toggle(); } },
{ QStringLiteral("on"), [](RelaisClient *client){ client->on(); } },
{ QStringLiteral("off"), [](RelaisClient *client){ client->off(); } },
{ QStringLiteral("refresh"), [](RelaisClient *client){ client->requestStatus(); } },
{ QStringLiteral("reboot"), [](RelaisClient *client){ client->reboot(); } },
{ QStringLiteral("delete"), [](RelaisClient *client){ client->deleteLater(); } }
};
{ {
client->off(); auto iter = actions.find(parts.at(3));
redirectRoot(connection, request); if(iter == actions.constEnd())
return; handle404(connection, request);
}
else if(parts.at(3) == "toggle")
{
client->toggle();
redirectRoot(connection, request);
return;
}
else if(parts.at(3) == "delete")
{
client->deleteLater();
redirectRoot(connection, request);
return;
}
else if(parts.at(3) == "reboot")
{
client->reboot();
redirectRoot(connection, request);
return;
}
else else
{ {
handle404(connection, request); (*iter)(client);
return; redirectRoot(connection, request);
}
} }
} }
else else
@@ -103,7 +93,9 @@ void RelaisWebserver::handleRequest(HttpClientConnection *connection, const Http
void RelaisWebserver::handleRoot(HttpClientConnection *connection, const HttpRequest &request) void RelaisWebserver::handleRoot(HttpClientConnection *connection, const HttpRequest &request)
{ {
QString output = "<p>" % tr("%0 clients").arg(m_relaisServer->clients().count()) % "</p>"; QString output = "<h1>Lampen-Steuerung</h1>";
output.append("<a href=\"/refresh\">Alle aktualisieren</a>");
output.append("<table border=\"1\">"); output.append("<table border=\"1\">");
output.append("<thead>"); output.append("<thead>");
@@ -112,29 +104,27 @@ void RelaisWebserver::handleRoot(HttpClientConnection *connection, const HttpReq
output.append("<th>Name</th>"); output.append("<th>Name</th>");
output.append("<th>Status</th>"); output.append("<th>Status</th>");
output.append("<th>Actions</th>"); output.append("<th>Actions</th>");
output.append("<th>Administration</th>");
output.append("</tr>"); output.append("</tr>");
output.append("</thead>"); output.append("</thead>");
output.append("<tbody>"); output.append("<tbody>");
for(auto client : m_relaisServer->clients()) for(auto client : m_relaisServer->clients())
{ {
output.append("<tr>"); output.append("<tr>");
output.append("<td>" % clientId(client).toHtmlEscaped() % "</td>"); output.append("<td>" % clientId(client, true).toHtmlEscaped() % "</td>");
output.append("<td>" % client->name().toHtmlEscaped() % "</td>"); output.append("<td>" % client->name().toHtmlEscaped() % "</td>");
output.append("<td>" % client->status().toHtmlEscaped() % "</td>"); output.append("<td>" % client->status().toHtmlEscaped() % "</td>");
output.append("<td><a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/toggle\">" % tr("toggle") % "</a> "); output.append("<td>");
output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/toggle\">" % tr("Toggle") % "</a> ");
if(client->status() != QStringLiteral("on")) output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/on\">" % tr("On") % "</a> ");
output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/on\">" % tr("on") % "</a> "); output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/off\">" % tr("Off") % "</a> ");
output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/refresh\">" % tr("Refresh") % "</a> ");
if(client->status() != QStringLiteral("off")) output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/reboot\">" % tr("Reboot") % "</a> ");
output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/off\">" % tr("off") % "</a> "); output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/delete\">" % tr("Delete") % "</a> ");
output.append("<a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/reboot\">" % tr("reboot") % "</a> ");
output.append("</td>"); output.append("</td>");
output.append("<td><a href=\"/devices/" % clientId(client).toHtmlEscaped() % "/delete\">" % tr("Delete") % "</a></td>");
output.append("</tr>"); output.append("</tr>");
} }
output.append("</tbody>"); output.append("</tbody>");
output.append("</table>"); output.append("</table>");
@@ -171,7 +161,9 @@ void RelaisWebserver::handle404(HttpClientConnection *connection, const HttpRequ
connection->sendResponse(response, tr("Not Found")); connection->sendResponse(response, tr("Not Found"));
} }
QString RelaisWebserver::clientId(RelaisClient *client) QString RelaisWebserver::clientId(const RelaisClient *client, bool forceIp)
{ {
if(!client->name().isEmpty() && !forceIp)
return client->name();
return client->peerAddress().toString() % ':' % QString::number(client->peerPort()); return client->peerAddress().toString() % ':' % QString::number(client->peerPort());
} }

View File

@@ -23,7 +23,7 @@ private:
void handleRoot(HttpClientConnection *connection, const HttpRequest &request); void handleRoot(HttpClientConnection *connection, const HttpRequest &request);
void redirectRoot(HttpClientConnection *connection, const HttpRequest &request); void redirectRoot(HttpClientConnection *connection, const HttpRequest &request);
void handle404(HttpClientConnection *connection, const HttpRequest &request); void handle404(HttpClientConnection *connection, const HttpRequest &request);
static QString clientId(RelaisClient *client); static QString clientId(const RelaisClient *client, bool forceIp = false);
RelaisServer *m_relaisServer; RelaisServer *m_relaisServer;
}; };