lundi 19 novembre 2018

Signal not catched by QSignalSpy

I'm currently coding some unit tests for one of my classes. However, I quickly ran into an issue. It seems that QSignalSpy sometimes does not catch the disconnected() signal emitted by my Client class. Here's my unit test:

void ClientTest::test_disconnectFromHost()
{
    QTcpServer server;
    server.listen(QHostAddress::Any, 65000);

    QTcpSocket* clientSocket = new QTcpSocket();
    QSignalSpy connectedSpy(clientSocket, SIGNAL(connected()));

    clientSocket->connectToHost(QHostAddress::Any, 65000);
    if (!connectedSpy.wait()) {
        QFAIL("Client socket connection failed.");
    }

    Chat::Client client(clientSocket);
    QSignalSpy disconnectedSpy(clientSocket, SIGNAL(disconnected()));

    // Return true if disconnection succeded
    QVERIFY(client.disconnectFromHost());
    QVERIFY(disconnectedSpy.wait(500));  // RETURNS FALSE!

    // Return false if client was not connected
    QVERIFY(!client.disconnectFromHost());
    QCOMPARE(client.getLastError(), 
       Chat::Client::Error::NotConnected);

    clientSocket->connectToHost(QHostAddress::Any, 65000);
    if (!connectedSpy.wait()) {
        QFAIL("Client socket connection failed.");
    }

    QTcpSocket* serverSocket = server.nextPendingConnection();
    serverSocket->disconnectFromHost(); // RETURNS FALSE!

    // Emit disconnected if the server closed the connection
    QVERIFY(disconnectedSpy.wait(500));

    delete serverSocket;
}

And here are the related class methods:

Client::Client(QTcpSocket* socket, QObject* parent)
    : QObject(parent)
{
    this->socket = socket;
    messageSize = -1;

    lastError = None;
    lastErrorString = "";

    connect(socket, SIGNAL(connected()), this, SLOT(onSocketConnected()));
    connect(socket, SIGNAL(disconnected()), this, SLOT(onSocketDisconnected()));
    connect(socket, SIGNAL(error(QAbstractSocket::SocketError)), this, SLOT(onSocketError(QAbstractSocket::SocketError)));
    connect(socket, SIGNAL(readyRead()), this, SLOT(onDataReceived()));
}

bool Client::connectToHost(const QHostAddress& serverAddress, quint16 serverPort)
{
    if (socket->state() != QTcpSocket::SocketState::UnconnectedState) {
        lastError = AlreadyConnected;
        return false;
    }

    messageSize = -1;

    socket->connectToHost(serverAddress, serverPort);
    return true;
}

bool Client::disconnectFromHost()
{
    if (socket->state() != QTcpSocket::SocketState::ConnectedState) {
        lastError = NotConnected;
        return false;
    }

    socket->disconnectFromHost();
    return true;
}

void Client::onSocketConnected()
{
    emit connected();
}

void Client::onSocketDisconnected()
{
    emit disconnected();
}

[...]

Does anyone have an explanation as to why the QSignalSpy.wait() method returns false even if, by debugging the unit test, I know that the disconnected() signal is emitted?

Thanks!

Aucun commentaire:

Enregistrer un commentaire