Update mailnotification plugin
parent
efa2f26b26
commit
68ddae487b
|
|
@ -38,24 +38,40 @@ DevicePluginMailNotification::~DevicePluginMailNotification()
|
|||
{
|
||||
}
|
||||
|
||||
Device::DeviceSetupStatus DevicePluginMailNotification::setupDevice(Device *device)
|
||||
void DevicePluginMailNotification::startPairing(DevicePairingInfo *info)
|
||||
{
|
||||
info->finish(Device::DeviceErrorNoError, QT_TR_NOOP("Please enter your username and password for the e-mail account."));
|
||||
}
|
||||
|
||||
void DevicePluginMailNotification::confirmPairing(DevicePairingInfo *info, const QString &username, const QString &secret)
|
||||
{
|
||||
// Just store details, we'll do a test login in setupDevice anyways
|
||||
pluginStorage()->beginGroup(info->deviceId().toString());
|
||||
pluginStorage()->setValue("username", username);
|
||||
pluginStorage()->setValue("password", secret);
|
||||
pluginStorage()->endGroup();
|
||||
info->finish(Device::DeviceErrorNoError);
|
||||
}
|
||||
|
||||
void DevicePluginMailNotification::setupDevice(DeviceSetupInfo *info)
|
||||
{
|
||||
Device *device = info->device();
|
||||
|
||||
// Custom mail
|
||||
if(device->deviceClassId() == customMailDeviceClassId) {
|
||||
SmtpClient *smtpClient = new SmtpClient(this);
|
||||
smtpClient->setHost(device->paramValue(customMailDeviceSmtpParamTypeId).toString());
|
||||
smtpClient->setPort(static_cast<quint16>(device->paramValue(customMailDevicePortParamTypeId).toUInt()));
|
||||
smtpClient->setUser(device->paramValue(customMailDeviceCustomUserParamTypeId).toString());
|
||||
|
||||
// TODO: use cryptography to save password not as plain text
|
||||
smtpClient->setPassword(device->paramValue(customMailDeviceCustomPasswordParamTypeId).toString());
|
||||
pluginStorage()->beginGroup(device->id().toString());
|
||||
smtpClient->setUser(pluginStorage()->value("username").toString());
|
||||
smtpClient->setPassword(pluginStorage()->value("password").toString());
|
||||
pluginStorage()->endGroup();
|
||||
|
||||
if(device->paramValue(customMailDeviceAuthenticationParamTypeId).toString() == "PLAIN") {
|
||||
smtpClient->setAuthenticationMethod(SmtpClient::AuthenticationMethodPlain);
|
||||
} else if(device->paramValue(customMailDeviceAuthenticationParamTypeId).toString() == "LOGIN") {
|
||||
smtpClient->setAuthenticationMethod(SmtpClient::AuthenticationMethodLogin);
|
||||
} else {
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
}
|
||||
|
||||
if(device->paramValue(customMailDeviceEncryptionParamTypeId).toString() == "NONE") {
|
||||
|
|
@ -64,45 +80,64 @@ Device::DeviceSetupStatus DevicePluginMailNotification::setupDevice(Device *devi
|
|||
smtpClient->setEncryptionType(SmtpClient::EncryptionTypeSSL);
|
||||
} else if(device->paramValue(customMailDeviceEncryptionParamTypeId).toString() == "TLS") {
|
||||
smtpClient->setEncryptionType(SmtpClient::EncryptionTypeTLS);
|
||||
} else {
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
}
|
||||
|
||||
QString recipientsString = device->paramValue(customMailDeviceCustomRecipientParamTypeId).toString();
|
||||
QString recipientsString = device->paramValue(customMailDeviceRecipientParamTypeId).toString();
|
||||
QStringList recipients = recipientsString.split(",");
|
||||
|
||||
smtpClient->setRecipients(recipients);
|
||||
smtpClient->setSender(device->paramValue(customMailDeviceCustomSenderParamTypeId).toString());
|
||||
|
||||
connect(smtpClient, &SmtpClient::testLoginFinished, this, &DevicePluginMailNotification::testLoginFinished);
|
||||
connect(smtpClient, &SmtpClient::sendMailFinished, this, &DevicePluginMailNotification::sendMailFinished);
|
||||
m_clients.insert(smtpClient,device);
|
||||
smtpClient->setSender(device->paramValue(customMailDeviceSenderParamTypeId).toString());
|
||||
|
||||
smtpClient->testLogin();
|
||||
connect(smtpClient, &SmtpClient::testLoginFinished, info, [this, smtpClient, info, device](bool success){
|
||||
if (!success) {
|
||||
qCWarning(dcMailNotification()) << "Email login test failed";
|
||||
info->finish(Device::DeviceErrorAuthenticationFailure, QT_TR_NOOP("The email account cannot be accessed. Wrong username or password?"));
|
||||
smtpClient->deleteLater();
|
||||
return;
|
||||
}
|
||||
|
||||
return Device::DeviceSetupStatusAsync;
|
||||
qCDebug(dcMailNotification()) << "Email login test successful.";
|
||||
m_clients.insert(smtpClient,device);
|
||||
info->finish(Device::DeviceErrorNoError);
|
||||
});
|
||||
|
||||
return;
|
||||
}
|
||||
return Device::DeviceSetupStatusFailure;
|
||||
|
||||
info->finish(Device::DeviceErrorDeviceClassNotFound);
|
||||
}
|
||||
|
||||
Device::DeviceError DevicePluginMailNotification::executeAction(Device *device, const Action &action)
|
||||
void DevicePluginMailNotification::executeAction(DeviceActionInfo *info)
|
||||
{
|
||||
Device *device = info->device();
|
||||
Action action = info->action();
|
||||
|
||||
if (device->deviceClassId() == customMailDeviceClassId) {
|
||||
if(action.actionTypeId() == customMailNotifyActionTypeId) {
|
||||
SmtpClient *smtpClient = m_clients.key(device);
|
||||
if (!smtpClient) {
|
||||
qCWarning(dcMailNotification()) << "Could not find SMTP client for " << device;
|
||||
return Device::DeviceErrorHardwareNotAvailable;
|
||||
return info->finish(Device::DeviceErrorHardwareNotAvailable);
|
||||
}
|
||||
|
||||
smtpClient->sendMail(action.param(customMailNotifyActionTitleParamTypeId).value().toString(),
|
||||
action.param(customMailNotifyActionBodyParamTypeId).value().toString(),
|
||||
action.id());
|
||||
return Device::DeviceErrorAsync;
|
||||
int id = smtpClient->sendMail(action.param(customMailNotifyActionTitleParamTypeId).value().toString(),
|
||||
action.param(customMailNotifyActionBodyParamTypeId).value().toString());
|
||||
connect(smtpClient, &SmtpClient::sendMailFinished, info, [info, id](bool success, int resultId){
|
||||
if (id != resultId) {
|
||||
return; // Not the process we were waiting for
|
||||
}
|
||||
if (!success) {
|
||||
info->finish(Device::DeviceErrorHardwareFailure, QT_TR_NOOP("Error sending email."));
|
||||
return;
|
||||
}
|
||||
info->finish(Device::DeviceErrorNoError);
|
||||
});
|
||||
return;
|
||||
}
|
||||
return Device::DeviceErrorActionTypeNotFound;
|
||||
return info->finish(Device::DeviceErrorActionTypeNotFound);
|
||||
}
|
||||
return Device::DeviceErrorDeviceClassNotFound;
|
||||
return info->finish(Device::DeviceErrorDeviceClassNotFound);
|
||||
}
|
||||
|
||||
void DevicePluginMailNotification::deviceRemoved(Device *device)
|
||||
|
|
@ -111,31 +146,3 @@ void DevicePluginMailNotification::deviceRemoved(Device *device)
|
|||
m_clients.remove(smtpClient);
|
||||
delete smtpClient;
|
||||
}
|
||||
|
||||
void DevicePluginMailNotification::testLoginFinished(const bool &success)
|
||||
{
|
||||
SmtpClient *smtpClient = static_cast<SmtpClient*>(sender());
|
||||
Device *device = m_clients.value(smtpClient);
|
||||
if (success) {
|
||||
qCDebug(dcMailNotification()) << "Email login test successfull";
|
||||
emit deviceSetupFinished(device, Device::DeviceSetupStatusSuccess);
|
||||
} else {
|
||||
qCWarning(dcMailNotification()) << "Email login test failed";
|
||||
emit deviceSetupFinished(device, Device::DeviceSetupStatusFailure);
|
||||
if(m_clients.contains(smtpClient)) {
|
||||
m_clients.remove(smtpClient);
|
||||
}
|
||||
smtpClient->deleteLater();
|
||||
}
|
||||
}
|
||||
|
||||
void DevicePluginMailNotification::sendMailFinished(const bool &success, const ActionId &actionId)
|
||||
{
|
||||
if (success) {
|
||||
qCDebug(dcMailNotification()) << "Email sent successfully";
|
||||
emit actionExecutionFinished(actionId, Device::DeviceErrorNoError);
|
||||
} else {
|
||||
qCWarning(dcMailNotification()) << "Email sending failed";
|
||||
emit actionExecutionFinished(actionId, Device::DeviceErrorDeviceNotFound);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -37,17 +37,15 @@ public:
|
|||
explicit DevicePluginMailNotification();
|
||||
~DevicePluginMailNotification();
|
||||
|
||||
Device::DeviceSetupStatus setupDevice(Device *device) override;
|
||||
Device::DeviceError executeAction(Device *device, const Action &action) override;
|
||||
void startPairing(DevicePairingInfo *info) override;
|
||||
void confirmPairing(DevicePairingInfo *info, const QString &username, const QString &secret) override;
|
||||
void setupDevice(DeviceSetupInfo *info) override;
|
||||
void executeAction(DeviceActionInfo *info) override;
|
||||
void deviceRemoved(Device *device) override;
|
||||
|
||||
private:
|
||||
QHash <SmtpClient*, Device*> m_clients;
|
||||
|
||||
private slots:
|
||||
void testLoginFinished(const bool &success);
|
||||
void sendMailFinished(const bool &success, const ActionId &actionId);
|
||||
|
||||
};
|
||||
|
||||
#endif // DEVICEPLUGINMAILNOTIFICATION_H
|
||||
|
|
|
|||
|
|
@ -11,34 +11,21 @@
|
|||
{
|
||||
"id": "f4844c97-7ca6-4349-904e-ff9749a9fe74",
|
||||
"name": "customMail",
|
||||
"displayName": "Custom mail",
|
||||
"displayName": "E-mail notifications",
|
||||
"createMethods": [ "user" ],
|
||||
"setupMethod": "userandpassword",
|
||||
"interfaces": [ "notifications" ],
|
||||
"paramTypes": [
|
||||
{
|
||||
"id": "af30ce7b-fb6b-42f0-889d-20b32f8b8fa4",
|
||||
"name": "customSender",
|
||||
"name": "sender",
|
||||
"displayName": "Sender mail",
|
||||
"type": "QString",
|
||||
"inputType": "Mail"
|
||||
},
|
||||
{
|
||||
"id": "b91d0ecc-6903-4991-ae8d-f36757ce40a7",
|
||||
"name": "customUser",
|
||||
"displayName": "User",
|
||||
"type": "QString",
|
||||
"inputType": "TextLine"
|
||||
},
|
||||
{
|
||||
"id": "ac29e643-1d18-4612-8d2f-65fb07a67182",
|
||||
"name": "customPassword",
|
||||
"displayName": "Password",
|
||||
"type": "QString",
|
||||
"inputType": "Password"
|
||||
},
|
||||
{
|
||||
"id": "d657f002-9741-42e1-9fef-32eae96dacdb",
|
||||
"name": "customRecipient",
|
||||
"name": "recipient",
|
||||
"displayName": "Recipient",
|
||||
"type": "QString",
|
||||
"inputType": "Mail"
|
||||
|
|
|
|||
|
|
@ -25,8 +25,6 @@
|
|||
|
||||
#include <QDateTime>
|
||||
|
||||
Q_LOGGING_CATEGORY(dcSmtpClient, "SmtpClient")
|
||||
|
||||
SmtpClient::SmtpClient(QObject *parent):
|
||||
QObject(parent)
|
||||
{
|
||||
|
|
@ -55,6 +53,7 @@ void SmtpClient::connectToHost()
|
|||
|
||||
void SmtpClient::testLogin()
|
||||
{
|
||||
qCDebug(dcMailNotification()) << "Starting test login";
|
||||
m_testLogin = true;
|
||||
setState(StateInitialize);
|
||||
m_socket->close();
|
||||
|
|
@ -63,19 +62,19 @@ void SmtpClient::testLogin()
|
|||
|
||||
void SmtpClient::connected()
|
||||
{
|
||||
qCDebug(dcSmtpClient()) << "Connected";
|
||||
qCDebug(dcMailNotification()) << "Connected";
|
||||
}
|
||||
|
||||
void SmtpClient::disconnected()
|
||||
{
|
||||
qCDebug(dcSmtpClient()) << "Disconnected";
|
||||
qCDebug(dcMailNotification()) << "Disconnected";
|
||||
setState(StateIdle);
|
||||
sendNextMail();
|
||||
}
|
||||
|
||||
void SmtpClient::onEncrypted()
|
||||
{
|
||||
qCDebug(dcSmtpClient()) << "Socket encrypted";
|
||||
qCDebug(dcMailNotification()) << "Socket encrypted";
|
||||
send("EHLO localhost");
|
||||
setState(StateAuthentification);
|
||||
}
|
||||
|
|
@ -86,12 +85,12 @@ void SmtpClient::readData()
|
|||
QString responseLine;
|
||||
responseLine = m_socket->readLine();
|
||||
|
||||
qCDebug(dcSmtpClient()) << "<--" << responseLine;
|
||||
qCDebug(dcMailNotification()) << "<--" << responseLine;
|
||||
|
||||
bool responseCodeParseSuccess = false;
|
||||
int responseCode = responseLine.left(3).toInt(&responseCodeParseSuccess);
|
||||
if (!responseCodeParseSuccess) {
|
||||
qCWarning(dcSmtpClient()) << "Could not convert status code to a valid integer" << responseLine;
|
||||
qCWarning(dcMailNotification()) << "Could not convert status code to a valid integer" << responseLine;
|
||||
if (m_state != StateIdle) {
|
||||
handleSmtpFailure();
|
||||
continue;
|
||||
|
|
@ -102,15 +101,17 @@ void SmtpClient::readData()
|
|||
}
|
||||
}
|
||||
|
||||
void SmtpClient::sendMail(const QString &subject, const QString &body, const ActionId &actionId)
|
||||
int SmtpClient::sendMail(const QString &subject, const QString &body)
|
||||
{
|
||||
static int ids = 0;
|
||||
Message message;
|
||||
message.subject = subject;
|
||||
message.body = body;
|
||||
message.actionId = actionId;
|
||||
message.id = ids++;
|
||||
|
||||
m_messageQueue.enqueue(message);
|
||||
sendNextMail();
|
||||
return message.id;
|
||||
}
|
||||
|
||||
void SmtpClient::setHost(const QString &host)
|
||||
|
|
@ -163,12 +164,13 @@ void SmtpClient::setState(SmtpClient::State state)
|
|||
if (m_state == state)
|
||||
return;
|
||||
|
||||
qCDebug(dcSmtpClient()) << state;
|
||||
qCDebug(dcMailNotification()) << state;
|
||||
m_state = state;
|
||||
}
|
||||
|
||||
void SmtpClient::processServerResponse(int responseCode, const QString &response)
|
||||
{
|
||||
qCDebug(dcMailNotification()) << "Server response:" << responseCode << response;
|
||||
switch (m_state) {
|
||||
case StateIdle:
|
||||
// Check if we have to send an other email, otherwise we are done and remain in idle
|
||||
|
|
@ -203,7 +205,7 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
// We need a 220 befor continue
|
||||
if (responseCode == 220) {
|
||||
if (!m_socket->isEncrypted() && m_encryptionType != EncryptionTypeNone) {
|
||||
qCDebug(dcSmtpClient()) << "Start client encryption...";
|
||||
qCDebug(dcMailNotification()) << "Start client encryption...";
|
||||
m_socket->startClientEncryption();
|
||||
}
|
||||
} else {
|
||||
|
|
@ -223,12 +225,12 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
}
|
||||
break;
|
||||
case StateAuthentification:
|
||||
// Ignore server information messages until we get a '250 ...' instead of '250-....'
|
||||
// Ignore server information messages of '250-....' (with dash), we need a clear "250 ..."
|
||||
if (responseCode == 250 && response.at(3) != ' ') {
|
||||
break;
|
||||
}
|
||||
|
||||
if (responseCode == 250) {
|
||||
if (responseCode == 250 || responseCode == 220) {
|
||||
if (m_authenticationMethod == AuthenticationMethodLogin) {
|
||||
send("AUTH LOGIN");
|
||||
setState(StateUser);
|
||||
|
|
@ -277,6 +279,11 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
}
|
||||
break;
|
||||
case StateTestLoginFinished:
|
||||
// Ignore server information messages
|
||||
if (responseCode == 250) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (responseCode == 235) {
|
||||
emit testLoginFinished(true);
|
||||
} else {
|
||||
|
|
@ -286,12 +293,17 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
m_testLogin = false;
|
||||
break;
|
||||
case StateMail:
|
||||
// Ignore server information messages
|
||||
if (responseCode == 250) {
|
||||
break;
|
||||
}
|
||||
|
||||
if (responseCode == 235) {
|
||||
send("MAIL FROM:<" + m_sender + ">");
|
||||
|
||||
// Prepare queue for recipients
|
||||
m_recipientsQueue.clear();
|
||||
qCDebug(dcSmtpClient()) << "Prepare recipients list" << m_recipients;
|
||||
qCDebug(dcMailNotification()) << "Prepare recipients list" << m_recipients;
|
||||
foreach (const QString &recipient, m_recipients) {
|
||||
m_recipientsQueue.enqueue(recipient.trimmed());
|
||||
}
|
||||
|
|
@ -344,7 +356,7 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
}
|
||||
|
||||
if (responseCode == 250) {
|
||||
emit sendMailFinished(true, m_message.actionId);
|
||||
emit sendMailFinished(true, m_message.id);
|
||||
send("QUIT");
|
||||
setState(StateClose);
|
||||
} else {
|
||||
|
|
@ -355,7 +367,7 @@ void SmtpClient::processServerResponse(int responseCode, const QString &response
|
|||
if (responseCode == 221) {
|
||||
m_socket->close();
|
||||
} else {
|
||||
qCDebug(dcSmtpClient()) << "The server does not handle the QUIT command. This is ok, we close the socket either way.";
|
||||
qCDebug(dcMailNotification()) << "The server does not handle the QUIT command. This is ok, we close the socket either way.";
|
||||
}
|
||||
|
||||
// some mail server does not recognize the QUIT command...so close the connection either way
|
||||
|
|
@ -410,7 +422,7 @@ void SmtpClient::handleSmtpFailure()
|
|||
if (m_testLogin) {
|
||||
emit testLoginFinished(false);
|
||||
} else {
|
||||
emit sendMailFinished(false, m_message.actionId);
|
||||
emit sendMailFinished(false, m_message.id);
|
||||
}
|
||||
|
||||
// Clean up
|
||||
|
|
@ -438,7 +450,7 @@ void SmtpClient::onSocketError(QAbstractSocket::SocketError error)
|
|||
|
||||
void SmtpClient::send(const QString &data)
|
||||
{
|
||||
qCDebug(dcSmtpClient()) << "-->" << data;
|
||||
qCDebug(dcMailNotification()) << "-->" << data;
|
||||
m_socket->write(data.toUtf8() + "\r\n");
|
||||
m_socket->flush();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -31,14 +31,14 @@
|
|||
#include <QStringList>
|
||||
#include <QLoggingCategory>
|
||||
|
||||
#include "devices/deviceplugin.h"
|
||||
//#include "devices/deviceplugin.h"
|
||||
|
||||
Q_DECLARE_LOGGING_CATEGORY(dcSmtpClient)
|
||||
|
||||
struct Message {
|
||||
QString subject;
|
||||
QString body;
|
||||
ActionId actionId;
|
||||
int id;
|
||||
};
|
||||
|
||||
|
||||
|
|
@ -82,7 +82,7 @@ public:
|
|||
|
||||
void connectToHost();
|
||||
void testLogin();
|
||||
void sendMail(const QString &subject, const QString &body, const ActionId &actionId);
|
||||
int sendMail(const QString &subject, const QString &body);
|
||||
|
||||
void setHost(const QString &host);
|
||||
void setPort(const quint16 &port);
|
||||
|
|
@ -127,8 +127,8 @@ private:
|
|||
void handleUnexpectedSmtpCode(int responseCode, const QString &serverMessage);
|
||||
|
||||
signals:
|
||||
void sendMailFinished(const bool &success, const ActionId &actionId);
|
||||
void testLoginFinished(const bool &success);
|
||||
void sendMailFinished(bool success, int &id);
|
||||
void testLoginFinished(bool success);
|
||||
|
||||
private slots:
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue