Compare commits

...

44 Commits
dev ... v1.1

Author SHA1 Message Date
39d6f35ca7
<fix>(project): support static build. 2022-01-15 00:34:10 +08:00
Attila Tőkés
3fa4a0fe57
Merge pull request #101 from emkey08/v1.1
Fix incorrect date header when using Qt4
2021-03-20 18:52:56 +02:00
Mathias Kunter
152a3e7572 Fix incorrect date header when using Qt4
Fix the timezone offset string to comply with RFC 2822.

Use the "C" locale instead of the system locale for obtaining day
and month names. Day and month names must always be in English.
2021-02-25 15:06:33 +01:00
Attila Tőkés
f715bb9916
Merge pull request #73 from mabrand/fix2
remove stray space after colon following MAIL FROM and RCPT TO
2019-01-15 08:58:21 +02:00
Mark Brand
67c73c7c96 remove stray space after colon following MAIL FROM and RCPT TO
Quoth https://www.ietf.org/rfc/rfc5321.txt:

   Since it has been a common source of errors, it is worth noting that
   spaces are not permitted on either side of the colon following FROM
   in the MAIL command or TO in the RCPT command.  The syntax is exactly
   as given above.
2019-01-14 23:59:43 +01:00
Attila Tőkés
1f4f2e208b
Merge pull request #71 from mabrand/fix-date-field
fix Qt version check
2018-06-13 19:41:22 +03:00
Mark Brand
5bdfa6a5dd fix Qt version check
QT_VERSION_MAJOR, not QT_MAJOR_VERSION, and fixed stray #elif
2018-06-13 17:44:42 +02:00
Attila Tőkés
3d87c6306e
Merge pull request #69 from esilvia/v1.1
Fixed Qt4 compilation for version 1.1. Works with MSVC2013. (#62)
2018-04-24 07:28:33 +03:00
Evon Silvia
81c652dc73 Fixed Qt4 compilation for version 1.1. Works with MSVC2013. (#62) 2018-04-23 09:02:34 -07:00
Attila Tőkés
ca43f9d642
Merge pull request #63 from bluetiger9/master
Added Reply-To support
2017-12-22 10:47:43 +02:00
Attila Tőkés
12c810ada9 Merge pull request #43 from altaris/master
Added Reply-To support
2017-06-01 20:14:38 +03:00
Attila Tőkés
7633337dd6 Merge pull request #53 from ymuv/v1.1
Add In-Reply-To field.
2017-06-01 20:10:33 +03:00
Attila Tőkés
5fc59c0863 Issue #50 - fix memory leaks 2017-06-01 19:14:20 +03:00
Attila Tőkés
6b676827fe Issue #41 - remove extra space from MAIL FROM and RCPT TO commands 2017-06-01 18:20:49 +03:00
Attila Tőkés
cb04e35bed Merge pull request #56 from bryant1410/v1.1
Fix broken headings in Markdown files
2017-04-22 09:46:48 +03:00
Santiago Castro
96452106d8 Fix broken Markdown headings 2017-04-17 04:27:42 -03:00
ymuv
8623093e9b Add In-Reply-To field. 2017-01-23 01:56:44 +02:00
Attila Tőkés
800ff9cf69 Merge pull request #52 from kosmaz/v1.1
Caught SmtpClient::SendMessageTimeoutException
2017-01-14 09:16:28 +02:00
Ezenwanne I. Cosmas
ff2eb297c4 Caught SmtpClient::SendMessageTimeoutException
In Smtp::quit, SmtpClient::SendMessageTimeoutException is caught and if still connected to the smtp server, manually close
the connection.
2017-01-13 18:49:02 +01:00
Attila Tőkés
ef6194fb26 Merge pull request #48 from Spiek/v1.1
Add date header field in RFC2822 format to MimeMessage
2016-03-23 19:51:57 +02:00
Spiek
78bf2dac42 Add date header field in RFC2822 format to MimeMessage 2016-03-23 11:07:38 +01:00
Cedric HT
c2a734791a Added Reply-To support 2016-01-13 15:43:26 +01:00
Attila Tőkés
48c080b9ee Merge pull request #39 from ursfassler/v1.1
cleanup compiler errors/warnings
2015-10-26 20:21:14 +02:00
Urs Fässler
6de3493c92 cleanup compiler errors/warnings 2015-10-26 16:31:51 +01:00
Attila Tőkés
9afc349942 Fix typo in default host. 2015-09-05 18:22:58 +03:00
Attila Tőkés
c12f70b721 Fix memory leak 2015-06-03 23:27:54 +03:00
Attila Tőkés
6877ac8148 Small fixes. 2014-11-01 22:50:37 +02:00
Attila Tőkés
f8db82bae5 add demos/demo3/demo3.cpp 2014-10-30 23:09:18 +02:00
Attila Tőkés
7f8d11db2f Set up demo projects. 2014-10-30 23:04:04 +02:00
Attila Tőkés
06db4130d9 Add posibility to build as a shared library. 2014-10-30 22:17:44 +02:00
Tőkés Attila
235a350a34 Merge pull request #27 from DEgITx/patch-1
Update quotedprintable.cpp
2014-10-30 21:31:33 +02:00
Tőkés Attila
75f4bf385a Merge pull request #30 from amuetzel/master
added QT_DECL_EXPORT/QT_DECL_IMPORT to allow building DLLs
2014-10-30 21:30:31 +02:00
Andreas Mützel
a4f4235139 added necessary QT_DECL_EXPORT/QT_DECL_IMPORT to be able to build a DLL on windows 2014-09-01 09:59:57 +02:00
Alexey Kasyanchuk
649ea30336 Update quotedprintable.cpp
Some compilators can interpret this differently (gcc shows warning about this)
2014-07-20 10:27:23 +03:00
Tőkés Attila
076034a612 Merge pull request #17 from LascauxSRL/master
Added support for ByteArray Attachments and removed Memory Leak from MimeMessage class
2014-02-21 17:18:51 +02:00
Attila Tőkés
b1c640c39d Merge branch 'v1.1' 2014-02-21 17:17:42 +02:00
LascauxSRL
4f028793e1 - Added support for SendMessage Timeout (Doesn't rely on Reply Timeout)
- Solved small bug in emitting an error message
2014-02-20 11:41:21 +01:00
Attila Tőkés
f3da3b391c Qt5 compatibility. 2014-02-16 19:10:37 +02:00
LascauxSRL
93873f8b1c - Added support for ByteArray Attachments
- Removed memoryleak from MimeMessage
2013-08-08 10:45:39 +02:00
Tőkés Attila
dac7a04d6f Merge branch 'v1.1' 2012-10-25 18:17:30 +03:00
Tőkés Attila
8f6a67664f Added getters and setters for connection and response timeouts. 2012-10-25 18:06:16 +03:00
Attila Tőkés
3d3f9136af Bug fix (issue 2) 2012-09-05 19:36:52 +03:00
Attila
81e561c91b Merge branch 'v1.1'
Conflicts:
	README.md
2012-08-09 22:40:41 +03:00
bluetiger9
32b11e2351 Readme fixed. 2012-03-20 20:24:54 +02:00
30 changed files with 489 additions and 106 deletions

View File

@ -3,7 +3,7 @@ SMTP Client for Qt (C++) - Version 1.1
The SmtpClient for Qt is small library writen for Qt 4 (C++ version) that allows application to send complex emails (plain text, html, attachments, inline files, etc.) using the Simple Mail Transfer Protocol (SMTP). The SmtpClient for Qt is small library writen for Qt 4 (C++ version) that allows application to send complex emails (plain text, html, attachments, inline files, etc.) using the Simple Mail Transfer Protocol (SMTP).
##New in version 1.1: ## New in version 1.1:
- TLS (STARTTLS) connection is now supported - TLS (STARTTLS) connection is now supported

View File

@ -4,11 +4,17 @@
# #
#------------------------------------------------- #-------------------------------------------------
QT += core gui network QT += core network
TARGET = SMTPEmail TARGET = SMTPEmail
TEMPLATE = app
# Build as an application
#TEMPLATE = app
# Build as a library
TEMPLATE = lib
DEFINES += SMTP_BUILD
win32:CONFIG += dll
SOURCES += \ SOURCES += \
src/emailaddress.cpp \ src/emailaddress.cpp \
@ -22,7 +28,7 @@ SOURCES += \
src/smtpclient.cpp \ src/smtpclient.cpp \
src/quotedprintable.cpp \ src/quotedprintable.cpp \
src/mimemultipart.cpp \ src/mimemultipart.cpp \
src/mimecontentformatter.cpp src/mimecontentformatter.cpp \
HEADERS += \ HEADERS += \
src/emailaddress.h \ src/emailaddress.h \
@ -37,7 +43,8 @@ HEADERS += \
src/SmtpMime \ src/SmtpMime \
src/quotedprintable.h \ src/quotedprintable.h \
src/mimemultipart.h \ src/mimemultipart.h \
src/mimecontentformatter.h src/mimecontentformatter.h \
src/smtpexports.h
OTHER_FILES += \ OTHER_FILES += \
LICENSE \ LICENSE \

View File

@ -1,11 +1,10 @@
#include <QtGui/QApplication> #include <QtCore>
#include "../src/SmtpMime"
#include "../../src/SmtpMime"
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
QApplication a(argc, argv); QCoreApplication a(argc, argv);
// This is a first demo application of the SmtpClient for Qt project // This is a first demo application of the SmtpClient for Qt project
@ -18,17 +17,20 @@ int main(int argc, char *argv[])
// We need to set the username (your email address) and password // We need to set the username (your email address) and password
// for smtp authentification. // for smtp authentification.
smtp.setUser("your_email_address@gmail.com"); smtp.setUser("your_email_address@host.com");
smtp.setPassword("your_password"); smtp.setPassword("your_password");
// Now we create a MimeMessage object. This is the email. // Now we create a MimeMessage object. This is the email.
MimeMessage message; MimeMessage message;
message.setSender(new EmailAddress("your_email_address@gmail.com", "Your Name")); EmailAddress sender("your_email_address@host.com", "Your Name");
message.addRecipient(new EmailAddress("recipient@host.com", "Recipient's Name")); message.setSender(&sender);
message.setSubject("SmtpClient for Qt - Demo");
EmailAddress to("recipient@host.com", "Recipient's Name");
message.addRecipient(&to);
message.setSubject("SmtpClient for Qt - Demo");
// Now add some text to the email. // Now add some text to the email.
// First we create a MimeText object. // First we create a MimeText object.
@ -41,12 +43,23 @@ int main(int argc, char *argv[])
message.addPart(&text); message.addPart(&text);
// Now we can send the mail // Now we can send the mail
smtp.connectToHost(); if (!smtp.connectToHost()) {
smtp.login(); qDebug() << "Failed to connect to host!" << endl;
smtp.sendMail(message); return -1;
}
if (!smtp.login()) {
qDebug() << "Failed to login!" << endl;
return -2;
}
if (!smtp.sendMail(message)) {
qDebug() << "Failed to send mail!" << endl;
return -3;
}
smtp.quit(); smtp.quit();
} }

29
demos/demo1/demo1.pro Normal file
View File

@ -0,0 +1,29 @@
#-------------------------------------------------
#
# Project created by QtCreator 2014-10-30T22:19:03
#
#-------------------------------------------------
QT += core
QT -= gui
TARGET = demo1
CONFIG += console
CONFIG -= app_bundle
TEMPLATE = app
SOURCES += \
demo1.cpp
# Location of SMTP Library
SMTP_LIBRARY_LOCATION = $$PWD/../../../build/SMTPEmail-Desktop-Debug
win32:CONFIG(release, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/release/ -lSMTPEmail
else:win32:CONFIG(debug, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/debug/ -lSMTPEmail
else:unix: LIBS += -L$$SMTP_LIBRARY_LOCATION -lSMTPEmail
INCLUDEPATH += $$SMTP_LIBRARY_LOCATION
DEPENDPATH += $$SMTP_LIBRARY_LOCATION

View File

@ -14,12 +14,11 @@
See the LICENSE file for more details. See the LICENSE file for more details.
*/ */
#include <QtGui/QApplication> #include <QtWidgets>
#include "sendemail.h" #include "sendemail.h"
#include "../../src/SmtpMime" #include "../../src/SmtpMime"
#include <iostream> #include <iostream>
using namespace std; using namespace std;

32
demos/demo2/demo2.pro Normal file
View File

@ -0,0 +1,32 @@
#-------------------------------------------------
#
# Project created by QtCreator 2014-10-30T22:48:32
#
#-------------------------------------------------
QT += core gui
greaterThan(QT_MAJOR_VERSION, 4): QT += widgets
TARGET = demo2
TEMPLATE = app
SOURCES += \
demo2.cpp \
sendemail.cpp
# Location of SMTP Library
SMTP_LIBRARY_LOCATION = $$PWD/../../../build/SMTPEmail-Desktop-Debug
win32:CONFIG(release, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/release/ -lSMTPEmail
else:win32:CONFIG(debug, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/debug/ -lSMTPEmail
else:unix: LIBS += -L$$SMTP_LIBRARY_LOCATION -lSMTPEmail
INCLUDEPATH += $$SMTP_LIBRARY_LOCATION
DEPENDPATH += $$SMTP_LIBRARY_LOCATION
HEADERS += \
sendemail.h
FORMS += \
sendemail.ui

View File

@ -123,7 +123,7 @@ void SendEmail::on_sendEmail_clicked()
else else
{ {
QMessageBox okMessage (this); QMessageBox okMessage (this);
okMessage.setText("The email was succesfully sended."); okMessage.setText("The email was succesfully sent.");
okMessage.exec(); okMessage.exec();
} }

View File

@ -14,26 +14,31 @@
See the LICENSE file for more details. See the LICENSE file for more details.
*/ */
#include <QtGui/QApplication> #include <QtCore>
#include "../src/SmtpMime"
#include "../../src/SmtpMime"
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
QApplication a(argc, argv); QCoreApplication a(argc, argv);
// First create the SmtpClient object and set the user and the password. // First create the SmtpClient object and set the user and the password.
SmtpClient smtp("smtp.gmail.com", 465, SmtpClient::SslConnection); SmtpClient smtp("smtp.gmail.com", 465, SmtpClient::SslConnection);
smtp.setUser("your_email@gmail.com"); smtp.setUser("your_email@host.com");
smtp.setPassword("your_password"); smtp.setPassword("your_password");
// Create a MimeMessage // Create a MimeMessage
MimeMessage message; MimeMessage message;
message.setSender(new EmailAddress("your_email@gmail.com", "Your Name")); EmailAddress sender("your_email_address@host.com", "Your Name");
message.addRecipient(new EmailAddress("recipient@host.com", "Recipient's Name")); message.setSender(&sender);
EmailAddress to("recipient@host.com", "Recipient's Name");
message.addRecipient(&to);
message.setSubject("SmtpClient for Qt - Demo"); message.setSubject("SmtpClient for Qt - Demo");
// Add some text // Add some text
@ -51,13 +56,26 @@ int main(int argc, char *argv[])
message.addPart(&attachment); message.addPart(&attachment);
// Add an another attachment // Add an another attachment
message.addPart(new MimeAttachment(new QFile("document.pdf"))); MimeAttachment document(new QFile("document.pdf"));
message.addPart(&document);
// Now we can send the mail // Now we can send the mail
smtp.connectToHost(); if (!smtp.connectToHost()) {
smtp.login(); qDebug() << "Failed to connect to host!" << endl;
smtp.sendMail(message); return -1;
}
if (!smtp.login()) {
qDebug() << "Failed to login!" << endl;
return -2;
}
if (!smtp.sendMail(message)) {
qDebug() << "Failed to send mail!" << endl;
return -3;
}
smtp.quit(); smtp.quit();
} }

28
demos/demo3/demo3.pro Normal file
View File

@ -0,0 +1,28 @@
#-------------------------------------------------
#
# Project created by QtCreator 2014-10-30T22:20:42
#
#-------------------------------------------------
QT += core
QT -= gui
TARGET = demo3
CONFIG += console
CONFIG -= app_bundle
TEMPLATE = app
SOURCES += \
demo3.cpp
# Location of SMTP Library
SMTP_LIBRARY_LOCATION = $$PWD/../../../build/SMTPEmail-Desktop-Debug
win32:CONFIG(release, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/release/ -lSMTPEmail
else:win32:CONFIG(debug, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/debug/ -lSMTPEmail
else:unix: LIBS += -L$$SMTP_LIBRARY_LOCATION -lSMTPEmail
INCLUDEPATH += $$SMTP_LIBRARY_LOCATION
DEPENDPATH += $$SMTP_LIBRARY_LOCATION

View File

@ -14,28 +14,32 @@
See the LICENSE file for more details. See the LICENSE file for more details.
*/ */
#include <QtGui/QApplication> #include <QtCore>
#include "../src/SmtpMime"
#include "../../src/SmtpMime"
int main(int argc, char *argv[]) int main(int argc, char *argv[])
{ {
QApplication a(argc, argv); QCoreApplication a(argc, argv);
// First create the SmtpClient object and set the user and the password. // First create the SmtpClient object and set the user and the password.
SmtpClient smtp("smtp.gmail.com", 465, SmtpClient::SslConnection); SmtpClient smtp("smtp.gmail.com", 465, SmtpClient::SslConnection);
smtp.setUser("your_email@gmail.com"); smtp.setUser("your_email@host.com");
smtp.setPassword("your_password"); smtp.setPassword("your_password");
// Create a MimeMessage // Create a MimeMessage
MimeMessage message; MimeMessage message;
message.setSender(new EmailAddress("your_email@gmail.com", "Your Name")); EmailAddress sender("your_email_address@host.com", "Your Name");
message.addRecipient(new EmailAddress("recipient@host.com", "Recipient's Name")); message.setSender(&sender);
message.setSubject("SmtpClient for Qt - Example 3 - Html email with images");
EmailAddress to("recipient@host.com", "Recipient's Name");
message.addRecipient(&to);
message.setSubject("SmtpClient for Qt - Example 3 - Html email with images");
// Now we need to create a MimeHtml object for HTML content // Now we need to create a MimeHtml object for HTML content
MimeHtml html; MimeHtml html;
@ -63,10 +67,21 @@ int main(int argc, char *argv[])
message.addPart(&image2); message.addPart(&image2);
// Now the email can be sended // Now the email can be sended
if (!smtp.connectToHost()) {
qDebug() << "Failed to connect to host!" << endl;
return -1;
}
if (!smtp.login()) {
qDebug() << "Failed to login!" << endl;
return -2;
}
if (!smtp.sendMail(message)) {
qDebug() << "Failed to send mail!" << endl;
return -3;
}
smtp.connectToHost();
smtp.login();
smtp.sendMail(message);
smtp.quit(); smtp.quit();
} }

28
demos/demo4/demo4.pro Normal file
View File

@ -0,0 +1,28 @@
#-------------------------------------------------
#
# Project created by QtCreator 2014-10-30T22:20:54
#
#-------------------------------------------------
QT += core
QT -= gui
TARGET = demo4
CONFIG += console
CONFIG -= app_bundle
TEMPLATE = app
SOURCES += \
demo4.cpp
# Location of SMTP Library
SMTP_LIBRARY_LOCATION = $$PWD/../../../build/SMTPEmail-Desktop-Debug
win32:CONFIG(release, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/release/ -lSMTPEmail
else:win32:CONFIG(debug, debug|release): LIBS += -L$$SMTP_LIBRARY_LOCATION/debug/ -lSMTPEmail
else:unix: LIBS += -L$$SMTP_LIBRARY_LOCATION -lSMTPEmail
INCLUDEPATH += $$SMTP_LIBRARY_LOCATION
DEPENDPATH += $$SMTP_LIBRARY_LOCATION

View File

@ -21,7 +21,9 @@
#include <QObject> #include <QObject>
class EmailAddress : public QObject #include "smtpexports.h"
class SMTP_EXPORT EmailAddress : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -24,6 +24,10 @@
MimeAttachment::MimeAttachment(QFile *file) MimeAttachment::MimeAttachment(QFile *file)
: MimeFile(file) : MimeFile(file)
{ {
}
MimeAttachment::MimeAttachment(const QByteArray& stream, const QString& fileName): MimeFile(stream, fileName)
{
} }
MimeAttachment::~MimeAttachment() MimeAttachment::~MimeAttachment()

View File

@ -23,7 +23,9 @@
#include "mimepart.h" #include "mimepart.h"
#include "mimefile.h" #include "mimefile.h"
class MimeAttachment : public MimeFile #include "smtpexports.h"
class SMTP_EXPORT MimeAttachment : public MimeFile
{ {
Q_OBJECT Q_OBJECT
public: public:
@ -31,6 +33,8 @@ public:
/* [1] Constructors and Destructors */ /* [1] Constructors and Destructors */
MimeAttachment(QFile* file); MimeAttachment(QFile* file);
MimeAttachment(const QByteArray& stream, const QString& fileName);
~MimeAttachment(); ~MimeAttachment();
/* [1] --- */ /* [1] --- */

View File

@ -22,7 +22,9 @@
#include <QObject> #include <QObject>
#include <QByteArray> #include <QByteArray>
class MimeContentFormatter : public QObject #include "smtpexports.h"
class SMTP_EXPORT MimeContentFormatter : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -29,8 +29,18 @@ MimeFile::MimeFile(QFile *file)
this->cEncoding = Base64; this->cEncoding = Base64;
} }
MimeFile::MimeFile(const QByteArray& stream, const QString& fileName)
{
this->cEncoding = Base64;
this->cType = "application/octet-stream";
this->file = 0;
this->cName = fileName;
this->content = stream;
}
MimeFile::~MimeFile() MimeFile::~MimeFile()
{ {
if (file)
delete file; delete file;
} }
@ -46,10 +56,12 @@ MimeFile::~MimeFile()
void MimeFile::prepare() void MimeFile::prepare()
{ {
if (this->file)
{
file->open(QIODevice::ReadOnly); file->open(QIODevice::ReadOnly);
this->content = file->readAll(); this->content = file->readAll();
file->close(); file->close();
}
/* !!! IMPORTANT !!!! */ /* !!! IMPORTANT !!!! */
MimePart::prepare(); MimePart::prepare();
} }

View File

@ -22,13 +22,16 @@
#include "mimepart.h" #include "mimepart.h"
#include <QFile> #include <QFile>
class MimeFile : public MimePart #include "smtpexports.h"
class SMTP_EXPORT MimeFile : public MimePart
{ {
Q_OBJECT Q_OBJECT
public: public:
/* [1] Constructors and Destructors */ /* [1] Constructors and Destructors */
MimeFile(const QByteArray& stream, const QString& fileName);
MimeFile(QFile *f); MimeFile(QFile *f);
~MimeFile(); ~MimeFile();

View File

@ -21,7 +21,9 @@
#include "mimetext.h" #include "mimetext.h"
class MimeHtml : public MimeText #include "smtpexports.h"
class SMTP_EXPORT MimeHtml : public MimeText
{ {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -21,7 +21,9 @@
#include "mimefile.h" #include "mimefile.h"
class MimeInlineFile : public MimeFile #include "smtpexports.h"
class SMTP_EXPORT MimeInlineFile : public MimeFile
{ {
public: public:

View File

@ -19,20 +19,28 @@
#include "mimemessage.h" #include "mimemessage.h"
#include <QDateTime> #include <QDateTime>
#include <QLocale>
#include "quotedprintable.h" #include "quotedprintable.h"
#include <typeinfo> #include <typeinfo>
/* [1] Constructors and Destructors */ /* [1] Constructors and Destructors */
MimeMessage::MimeMessage(bool createAutoMimeContent) : MimeMessage::MimeMessage(bool createAutoMimeContent) :
replyTo(nullptr),
hEncoding(MimePart::_8Bit) hEncoding(MimePart::_8Bit)
{ {
if (createAutoMimeContent) if (createAutoMimeContent)
this->content = new MimeMultiPart(); this->content = new MimeMultiPart();
autoMimeContentCreated = createAutoMimeContent;
} }
MimeMessage::~MimeMessage() MimeMessage::~MimeMessage()
{ {
if (this->autoMimeContentCreated)
{
this->autoMimeContentCreated = false;
delete (this->content);
}
} }
/* [1] --- */ /* [1] --- */
@ -44,12 +52,22 @@ MimePart& MimeMessage::getContent() {
} }
void MimeMessage::setContent(MimePart *content) { void MimeMessage::setContent(MimePart *content) {
if (this->autoMimeContentCreated)
{
this->autoMimeContentCreated = false;
delete (this->content);
}
this->content = content; this->content = content;
} }
void MimeMessage::setReplyTo(EmailAddress* rto) {
replyTo = rto;
}
void MimeMessage::setSender(EmailAddress* e) void MimeMessage::setSender(EmailAddress* e)
{ {
this->sender = e; this->sender = e;
e->setParent(this);
} }
void MimeMessage::addRecipient(EmailAddress* rcpt, RecipientType type) void MimeMessage::addRecipient(EmailAddress* rcpt, RecipientType type)
@ -66,6 +84,8 @@ void MimeMessage::addRecipient(EmailAddress* rcpt, RecipientType type)
recipientsBcc << rcpt; recipientsBcc << rcpt;
break; break;
} }
rcpt->setParent(this);
} }
void MimeMessage::addTo(EmailAddress* rcpt) { void MimeMessage::addTo(EmailAddress* rcpt) {
@ -92,6 +112,11 @@ void MimeMessage::addPart(MimePart *part)
}; };
} }
void MimeMessage::setInReplyTo(const QString& inReplyTo)
{
mInReplyTo = inReplyTo;
}
void MimeMessage::setHeaderEncoding(MimePart::Encoding hEnc) void MimeMessage::setHeaderEncoding(MimePart::Encoding hEnc)
{ {
this->hEncoding = hEnc; this->hEncoding = hEnc;
@ -116,6 +141,10 @@ const QList<EmailAddress*> & MimeMessage::getRecipients(RecipientType type) cons
} }
} }
const EmailAddress* MimeMessage::getReplyTo() const {
return replyTo;
}
const QString & MimeMessage::getSubject() const const QString & MimeMessage::getSubject() const
{ {
return subject; return subject;
@ -234,10 +263,50 @@ QString MimeMessage::toString()
default: default:
mime += subject; mime += subject;
} }
mime += "\r\n";
/* ---------------------------------- */
/* ---------- Reply-To -------------- */
if (replyTo) {
mime += "Reply-To: ";
if (replyTo->getName() != "")
{
switch (hEncoding)
{
case MimePart::Base64:
mime += " =?utf-8?B?" + QByteArray().append(replyTo->getName()).toBase64() + "?=";
break;
case MimePart::QuotedPrintable:
mime += " =?utf-8?Q?" + QuotedPrintable::encode(QByteArray().append(replyTo->getName())).replace(' ', "_").replace(':',"=3A") + "?=";
break;
default:
mime += " " + replyTo->getName();
}
}
mime += " <" + replyTo->getAddress() + ">\r\n";
}
/* ---------------------------------- */ /* ---------------------------------- */
mime += "\r\n";
mime += "MIME-Version: 1.0\r\n"; mime += "MIME-Version: 1.0\r\n";
if (!mInReplyTo.isEmpty())
{
mime += "In-Reply-To: <" + mInReplyTo + ">\r\n";
mime += "References: <" + mInReplyTo + ">\r\n";
}
QDateTime now = QDateTime::currentDateTime();
#if QT_VERSION_MAJOR < 5 //Qt4 workaround since RFC2822Date isn't defined
QString shortDayName = QLocale::c().dayName(now.date().dayOfWeek(), QLocale::ShortFormat);
QString shortMonthName = QLocale::c().monthName(now.date().month(), QLocale::ShortFormat);
int utcOffset = now.secsTo(QDateTime(now.date(), now.time(), Qt::UTC)) / 60;
char timezoneSign = utcOffset >= 0 ? '+' : '-';
utcOffset = utcOffset >= 0 ? utcOffset : -utcOffset;
QString timezone = QString("%1%2%3").arg(timezoneSign).arg(utcOffset / 60, 2, 10, QChar('0')).arg(utcOffset % 60, 2, 10, QChar('0'));
mime += QString("Date: %1\r\n").arg(now.toString("%1, dd %2 yyyy hh:mm:ss %3").arg(shortDayName).arg(shortMonthName).arg(timezone));
#else //Qt5 supported
mime += QString("Date: %1\r\n").arg(now.toString(Qt::RFC2822Date));
#endif //support RFC2822Date
mime += content->toString(); mime += content->toString();
return mime; return mime;

View File

@ -24,7 +24,9 @@
#include "emailaddress.h" #include "emailaddress.h"
#include <QList> #include <QList>
class MimeMessage : public QObject #include "smtpexports.h"
class SMTP_EXPORT MimeMessage : public QObject
{ {
public: public:
@ -51,6 +53,9 @@ public:
void addBcc(EmailAddress* rcpt); void addBcc(EmailAddress* rcpt);
void setSubject(const QString & subject); void setSubject(const QString & subject);
void addPart(MimePart* part); void addPart(MimePart* part);
void setReplyTo(EmailAddress* rto);
void setInReplyTo(const QString& inReplyTo);
void setHeaderEncoding(MimePart::Encoding); void setHeaderEncoding(MimePart::Encoding);
@ -58,6 +63,7 @@ public:
const QList<EmailAddress*> & getRecipients(RecipientType type = To) const; const QList<EmailAddress*> & getRecipients(RecipientType type = To) const;
const QString & getSubject() const; const QString & getSubject() const;
const QList<MimePart*> & getParts() const; const QList<MimePart*> & getParts() const;
const EmailAddress* getReplyTo() const;
MimePart& getContent(); MimePart& getContent();
void setContent(MimePart *content); void setContent(MimePart *content);
@ -75,9 +81,12 @@ protected:
/* [4] Protected members */ /* [4] Protected members */
EmailAddress* sender; EmailAddress* sender;
EmailAddress* replyTo;
QList<EmailAddress*> recipientsTo, recipientsCc, recipientsBcc; QList<EmailAddress*> recipientsTo, recipientsCc, recipientsBcc;
QString subject; QString subject;
QString mInReplyTo;
MimePart *content; MimePart *content;
bool autoMimeContentCreated;
MimePart::Encoding hEncoding; MimePart::Encoding hEncoding;

View File

@ -21,7 +21,9 @@
#include "mimepart.h" #include "mimepart.h"
class MimeMultiPart : public MimePart #include "smtpexports.h"
class SMTP_EXPORT MimeMultiPart : public MimePart
{ {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -193,7 +193,7 @@ void MimePart::prepare()
switch (cEncoding) switch (cEncoding)
{ {
case _7Bit: case _7Bit:
mimeString.append(QString(content).toAscii()); mimeString.append(QString(content).toLatin1());
break; break;
case _8Bit: case _8Bit:
mimeString.append(content); mimeString.append(content);

View File

@ -22,7 +22,9 @@
#include <QObject> #include <QObject>
#include "mimecontentformatter.h" #include "mimecontentformatter.h"
class MimePart : public QObject #include "smtpexports.h"
class SMTP_EXPORT MimePart : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:

View File

@ -21,7 +21,9 @@
#include "mimepart.h" #include "mimepart.h"
class MimeText : public MimePart #include "smtpexports.h"
class SMTP_EXPORT MimeText : public MimePart
{ {
public: public:

View File

@ -18,9 +18,9 @@
#include "quotedprintable.h" #include "quotedprintable.h"
QString& QuotedPrintable::encode(const QByteArray &input) QString QuotedPrintable::encode(const QByteArray &input)
{ {
QString *output = new QString(); QString output;
char byte; char byte;
const char hex[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'}; const char hex[] = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'A', 'B', 'C', 'D', 'E', 'F'};
@ -29,40 +29,41 @@ QString& QuotedPrintable::encode(const QByteArray &input)
{ {
byte = input[i]; byte = input[i];
if ((byte == 0x20) || (byte >= 33) && (byte <= 126) && (byte != 61)) if ((byte == 0x20) || ((byte >= 33) && (byte <= 126) && (byte != 61)))
{ {
output->append(byte); output.append(byte);
} }
else else
{ {
output->append('='); output.append('=');
output->append(hex[((byte >> 4) & 0x0F)]); output.append(hex[((byte >> 4) & 0x0F)]);
output->append(hex[(byte & 0x0F)]); output.append(hex[(byte & 0x0F)]);
} }
} }
return *output; return output;
} }
QByteArray& QuotedPrintable::decode(const QString &input) QByteArray QuotedPrintable::decode(const QString &input)
{ {
// 0 1 2 3 4 5 6 7 8 9 : ; < = > ? @ A B C D E F // 0 1 2 3 4 5 6 7 8 9 : ; < = > ? @ A B C D E F
const int hexVal[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 0, 0, 0, 0, 0, 0, 10, 11, 12, 13, 14, 15}; const int hexVal[] = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 0, 0, 0, 0, 0, 0, 10, 11, 12, 13, 14, 15};
QByteArray *output = new QByteArray(); QByteArray output;
for (int i = 0; i < input.length(); ++i) for (int i = 0; i < input.length(); ++i)
{ {
if (input.at(i).toAscii() == '=') if (input.at(i).toLatin1() == '=')
{ {
output->append((hexVal[input.at(++i).toAscii() - '0'] << 4) + hexVal[input.at(++i).toAscii() - '0']); output.append((hexVal[input.at(i + 1).toLatin1() - '0'] << 4) + hexVal[input.at(i + 2).toLatin1() - '0']);
i += 2;
} }
else else
{ {
output->append(input.at(i).toAscii()); output.append(input.at(i).toLatin1());
} }
} }
return *output; return output;
} }

View File

@ -22,13 +22,15 @@
#include <QObject> #include <QObject>
#include <QByteArray> #include <QByteArray>
class QuotedPrintable : public QObject #include "smtpexports.h"
class SMTP_EXPORT QuotedPrintable : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:
static QString& encode(const QByteArray &input); static QString encode(const QByteArray &input);
static QByteArray& decode(const QString &input); static QByteArray decode(const QString &input);
private: private:
QuotedPrintable(); QuotedPrintable();

View File

@ -25,10 +25,12 @@
/* [1] Constructors and destructors */ /* [1] Constructors and destructors */
SmtpClient::SmtpClient(const QString & host, int port, ConnectionType connectionType) : SmtpClient::SmtpClient(const QString & host, int port, ConnectionType connectionType) :
socket(NULL),
name("localhost"), name("localhost"),
authMethod(AuthPlain), authMethod(AuthPlain),
connectionTimeout(5000), connectionTimeout(5000),
responseTimeout(5000) responseTimeout(5000),
sendMessageTimeout(60000)
{ {
setConnectionType(connectionType); setConnectionType(connectionType);
@ -43,7 +45,10 @@ SmtpClient::SmtpClient(const QString & host, int port, ConnectionType connection
this, SLOT(socketReadyRead())); this, SLOT(socketReadyRead()));
} }
SmtpClient::~SmtpClient() {} SmtpClient::~SmtpClient() {
if (socket)
delete socket;
}
/* [1] --- */ /* [1] --- */
@ -65,7 +70,7 @@ void SmtpClient::setAuthMethod(AuthMethod method)
this->authMethod = method; this->authMethod = method;
} }
void SmtpClient::setHost(QString &host) void SmtpClient::setHost(const QString &host)
{ {
this->host = host; this->host = host;
} }
@ -79,6 +84,9 @@ void SmtpClient::setConnectionType(ConnectionType ct)
{ {
this->connectionType = ct; this->connectionType = ct;
if (socket)
delete socket;
switch (connectionType) switch (connectionType)
{ {
case TcpConnection: case TcpConnection:
@ -144,6 +152,34 @@ QTcpSocket* SmtpClient::getSocket() {
return socket; return socket;
} }
int SmtpClient::getConnectionTimeout() const
{
return connectionTimeout;
}
void SmtpClient::setConnectionTimeout(int msec)
{
connectionTimeout = msec;
}
int SmtpClient::getResponseTimeout() const
{
return responseTimeout;
}
void SmtpClient::setResponseTimeout(int msec)
{
responseTimeout = msec;
}
int SmtpClient::getSendMessageTimeout() const
{
return sendMessageTimeout;
}
void SmtpClient::setSendMessageTimeout(int msec)
{
sendMessageTimeout = msec;
}
/* [2] --- */ /* [2] --- */
@ -213,7 +249,7 @@ bool SmtpClient::connectToHost()
if (!((QSslSocket*) socket)->waitForEncrypted(connectionTimeout)) { if (!((QSslSocket*) socket)->waitForEncrypted(connectionTimeout)) {
qDebug() << ((QSslSocket*) socket)->errorString(); qDebug() << ((QSslSocket*) socket)->errorString();
emit SmtpError(ConnectionTimeoutError); emit smtpError(ConnectionTimeoutError);
return false; return false;
} }
@ -234,6 +270,10 @@ bool SmtpClient::connectToHost()
{ {
return false; return false;
} }
catch (SendMessageTimeoutException)
{
return false;
}
// If no errors occured the function returns true. // If no errors occured the function returns true.
return true; return true;
@ -292,12 +332,18 @@ bool SmtpClient::login(const QString &user, const QString &password, AuthMethod
} }
} }
} }
catch (ResponseTimeoutException e) catch (ResponseTimeoutException)
{ {
// Responce Timeout exceeded // Responce Timeout exceeded
emit smtpError(AuthenticationFailedError); emit smtpError(AuthenticationFailedError);
return false; return false;
} }
catch (SendMessageTimeoutException)
{
// Send Timeout exceeded
emit smtpError(AuthenticationFailedError);
return false;
}
return true; return true;
} }
@ -307,7 +353,7 @@ bool SmtpClient::sendMail(MimeMessage& email)
try try
{ {
// Send the MAIL command with the sender // Send the MAIL command with the sender
sendMessage("MAIL FROM: <" + email.getSender().getAddress() + ">"); sendMessage("MAIL FROM:<" + email.getSender().getAddress() + ">");
waitForResponse(); waitForResponse();
@ -319,7 +365,8 @@ bool SmtpClient::sendMail(MimeMessage& email)
for (it = email.getRecipients().begin(), itEnd = email.getRecipients().end(); for (it = email.getRecipients().begin(), itEnd = email.getRecipients().end();
it != itEnd; ++it) it != itEnd; ++it)
{ {
sendMessage("RCPT TO: <" + (*it)->getAddress() + ">");
sendMessage("RCPT TO:<" + (*it)->getAddress() + ">");
waitForResponse(); waitForResponse();
if (responseCode != 250) return false; if (responseCode != 250) return false;
@ -329,7 +376,7 @@ bool SmtpClient::sendMail(MimeMessage& email)
for (it = email.getRecipients(MimeMessage::Cc).begin(), itEnd = email.getRecipients(MimeMessage::Cc).end(); for (it = email.getRecipients(MimeMessage::Cc).begin(), itEnd = email.getRecipients(MimeMessage::Cc).end();
it != itEnd; ++it) it != itEnd; ++it)
{ {
sendMessage("RCPT TO: <" + (*it)->getAddress() + ">"); sendMessage("RCPT TO:<" + (*it)->getAddress() + ">");
waitForResponse(); waitForResponse();
if (responseCode != 250) return false; if (responseCode != 250) return false;
@ -339,7 +386,7 @@ bool SmtpClient::sendMail(MimeMessage& email)
for (it = email.getRecipients(MimeMessage::Bcc).begin(), itEnd = email.getRecipients(MimeMessage::Bcc).end(); for (it = email.getRecipients(MimeMessage::Bcc).begin(), itEnd = email.getRecipients(MimeMessage::Bcc).end();
it != itEnd; ++it) it != itEnd; ++it)
{ {
sendMessage("RCPT TO: <" + (*it)->getAddress() + ">"); sendMessage("RCPT TO:<" + (*it)->getAddress() + ">");
waitForResponse(); waitForResponse();
if (responseCode != 250) return false; if (responseCode != 250) return false;
@ -364,13 +411,26 @@ bool SmtpClient::sendMail(MimeMessage& email)
{ {
return false; return false;
} }
catch (SendMessageTimeoutException)
{
return false;
}
return true; return true;
} }
void SmtpClient::quit() void SmtpClient::quit()
{ {
sendMessage("QUIT"); try
{
sendMessage("QUIT");
}
catch(SmtpClient::SendMessageTimeoutException)
{
//Manually close the connection to the smtp server if message "QUIT" wasn't received by the smtp server
if(socket->state() == QAbstractSocket::ConnectedState || socket->state() == QAbstractSocket::ConnectingState || socket->state() == QAbstractSocket::HostLookupState)
socket->disconnectFromHost();
}
} }
/* [3] --- */ /* [3] --- */
@ -378,30 +438,41 @@ void SmtpClient::quit()
/* [4] Protected methods */ /* [4] Protected methods */
void SmtpClient::waitForResponse() throw (ResponseTimeoutException) void SmtpClient::waitForResponse()
{ {
if (!socket->waitForReadyRead(responseTimeout)) do {
{ if (!socket->waitForReadyRead(responseTimeout))
emit smtpError(ResponseTimeoutError); {
throw ResponseTimeoutException(); emit smtpError(ResponseTimeoutError);
} throw ResponseTimeoutException();
}
// Save the server's response while (socket->canReadLine()) {
responseText = socket->readAll(); // Save the server's response
responseText = socket->readLine();
// Extract the respose code from the server's responce (first 3 digits) // Extract the respose code from the server's responce (first 3 digits)
responseCode = responseText.left(3).toInt(); responseCode = responseText.left(3).toInt();
if (responseCode / 100 == 4) if (responseCode / 100 == 4)
emit smtpError(ServerError); emit smtpError(ServerError);
if (responseCode / 100 == 5) if (responseCode / 100 == 5)
emit smtpError(ClientError); emit smtpError(ClientError);
if (responseText[3] == ' ') { return; }
}
} while (true);
} }
void SmtpClient::sendMessage(const QString &text) void SmtpClient::sendMessage(const QString &text)
{ {
socket->write(text.toUtf8() + "\r\n"); socket->write(text.toUtf8() + "\r\n");
if (! socket->waitForBytesWritten(sendMessageTimeout))
{
emit smtpError(SendDataTimeoutError);
throw SendMessageTimeoutException();
}
} }
/* [4] --- */ /* [4] --- */
@ -409,11 +480,11 @@ void SmtpClient::sendMessage(const QString &text)
/* [5] Slots for the socket's signals */ /* [5] Slots for the socket's signals */
void SmtpClient::socketStateChanged(QAbstractSocket::SocketState state) void SmtpClient::socketStateChanged(QAbstractSocket::SocketState /*state*/)
{ {
} }
void SmtpClient::socketError(QAbstractSocket::SocketError socketError) void SmtpClient::socketError(QAbstractSocket::SocketError /*socketError*/)
{ {
} }

View File

@ -23,9 +23,9 @@
#include <QtNetwork/QSslSocket> #include <QtNetwork/QSslSocket>
#include "mimemessage.h" #include "mimemessage.h"
#include "smtpexports.h"
class SMTP_EXPORT SmtpClient : public QObject
class SmtpClient : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:
@ -42,6 +42,7 @@ public:
{ {
ConnectionTimeoutError, ConnectionTimeoutError,
ResponseTimeoutError, ResponseTimeoutError,
SendDataTimeoutError,
AuthenticationFailedError, AuthenticationFailedError,
ServerError, // 4xx smtp error ServerError, // 4xx smtp error
ClientError // 5xx smtp error ClientError // 5xx smtp error
@ -59,7 +60,7 @@ public:
/* [1] Constructors and Destructors */ /* [1] Constructors and Destructors */
SmtpClient(const QString & host = "locahost", int port = 25, ConnectionType ct = TcpConnection); SmtpClient(const QString & host = "localhost", int port = 25, ConnectionType ct = TcpConnection);
~SmtpClient(); ~SmtpClient();
@ -69,7 +70,7 @@ public:
/* [2] Getters and Setters */ /* [2] Getters and Setters */
const QString& getHost() const; const QString& getHost() const;
void setHost(QString &host); void setHost(const QString &host);
int getPort() const; int getPort() const;
void setPort(int port); void setPort(int port);
@ -81,7 +82,7 @@ public:
void setConnectionType(ConnectionType ct); void setConnectionType(ConnectionType ct);
const QString & getUser() const; const QString & getUser() const;
void setUser(const QString &host); void setUser(const QString &user);
const QString & getPassword() const; const QString & getPassword() const;
void setPassword(const QString &password); void setPassword(const QString &password);
@ -92,6 +93,15 @@ public:
const QString & getResponseText() const; const QString & getResponseText() const;
int getResponseCode() const; int getResponseCode() const;
int getConnectionTimeout() const;
void setConnectionTimeout(int msec);
int getResponseTimeout() const;
void setResponseTimeout(int msec);
int getSendMessageTimeout() const;
void setSendMessageTimeout(int msec);
QTcpSocket* getSocket(); QTcpSocket* getSocket();
@ -129,19 +139,22 @@ protected:
int connectionTimeout; int connectionTimeout;
int responseTimeout; int responseTimeout;
int sendMessageTimeout;
QString responseText; QString responseText;
int responseCode; int responseCode;
class ResponseTimeoutException {}; class ResponseTimeoutException {};
class SendMessageTimeoutException {};
/* [4] --- */ /* [4] --- */
/* [5] Protected methods */ /* [5] Protected methods */
void waitForResponse() throw (ResponseTimeoutException); void waitForResponse();
void sendMessage(const QString &text); void sendMessage(const QString &text);
@ -162,7 +175,7 @@ signals:
/* [7] Signals */ /* [7] Signals */
void smtpError(SmtpError e); void smtpError(SmtpClient::SmtpError e);
/* [7] --- */ /* [7] --- */

12
src/smtpexports.h Normal file
View File

@ -0,0 +1,12 @@
#ifndef SMTPEXPORTS_H
#define SMTPEXPORTS_H
#ifdef SMTP_BUILD
#define SMTP_EXPORT Q_DECL_EXPORT
#elseif SMTP_USE
#define SMTP_EXPORT Q_DECL_IMPORT
#else
#define SMTP_EXPORT
#endif
#endif // SMTPEXPORTS_H