File indexing completed on 2024-11-24 04:44:31

0001 /*
0002    SPDX-FileCopyrightText: 2008 Omat Holding B.V. <info@omat.nl>
0003    SPDX-FileCopyrightText: 2009 Thomas McGuire <mcguire@kde.org>
0004 
0005    SPDX-License-Identifier: GPL-2.0-or-later
0006 */
0007 
0008 #pragma once
0009 
0010 #include <QMutex>
0011 #include <QThread>
0012 
0013 class QTcpServer;
0014 class QTcpSocket;
0015 class FakeServer : public QObject
0016 {
0017     Q_OBJECT
0018 
0019 public:
0020     explicit FakeServer(QObject *parent = nullptr);
0021     ~FakeServer() override;
0022 
0023     void setNextConversation(const QString &conversation, const QList<int> &exceptions = QList<int>());
0024     void setAllowedDeletions(const QString &deleteIds);
0025     void setAllowedRetrieves(const QString &retrieveIds);
0026     void setMails(const QList<QByteArray> &mails);
0027 
0028     // This is kind of a hack: The POP3 test needs to know when the POP3 client
0029     // disconnects from the server. Normally, we could just use a QSignalSpy on the
0030     // disconnected() signal, but that is not thread-safe. Therefore this hack with the
0031     // state variable mGotDisconnected
0032     bool gotDisconnected() const;
0033 
0034     // Returns an integer that is incremented each time the POP3 server receives some
0035     // data
0036     int progress() const;
0037 
0038 Q_SIGNALS:
0039     void disconnected();
0040 
0041 private Q_SLOTS:
0042 
0043     void newConnection();
0044     void dataAvailable();
0045     void slotDisconnected();
0046 
0047 private:
0048     QByteArray parseDeleteMark(const QByteArray &expectedData, const QByteArray &dataReceived);
0049     QByteArray parseRetrMark(const QByteArray &expectedData, const QByteArray &dataReceived);
0050     QByteArray parseResponse(const QByteArray &expectedData, const QByteArray &dataReceived);
0051 
0052     QList<QByteArray> mReadData;
0053     QList<QByteArray> mWriteData;
0054     QList<QByteArray> mAllowedDeletions;
0055     QList<QByteArray> mAllowedRetrieves;
0056     QList<QByteArray> mMails;
0057     QTcpServer *mTcpServer = nullptr;
0058     QTcpSocket *mTcpServerConnection = nullptr;
0059     int mConnections = 0;
0060     int mProgress = 0;
0061     bool mGotDisconnected = false;
0062 
0063     // We use one big mutex to protect everything
0064     // There shouldn't be deadlocks, as there are only 2 places where the functions
0065     // are called: From the KTcpSocket (or QSslSocket with KIO >= 5.65) signals, which
0066     // are triggered by the POP3 ioslave, and from the actual test.
0067     mutable QMutex mMutex;
0068 };
0069 
0070 class FakeServerThread : public QThread
0071 {
0072     Q_OBJECT
0073 
0074 public:
0075     explicit FakeServerThread(QObject *parent);
0076     void run() override;
0077 
0078     // Returns the FakeServer use. Be careful when using this and make sure
0079     // the methods you use are actually thread-safe!!
0080     // This should however be the case because the FakeServer uses one big mutex
0081     // to protect everything.
0082     FakeServer *server() const;
0083 
0084 private:
0085     FakeServer *mServer = nullptr;
0086 };