Fix authentication reply crash if client already disconnected

authenticator-crash
Simon Stürz 2022-04-04 08:59:10 +02:00
parent 6c6013665f
commit 8f8e660eb9
4 changed files with 33 additions and 61 deletions

View File

@ -51,28 +51,10 @@ QString AwsAuthenticator::name() const
return "AWS authenticator";
}
void AwsAuthenticator::onAuthenticationProcessFinished(Authenticator::AuthenticationError error, const UserInformation &userInformation)
{
AuthenticationProcess *process = static_cast<AuthenticationProcess *>(sender());
AuthenticationReply *reply = m_runningProcesses.take(process);
if (error == AuthenticationErrorNoError) {
qCDebug(dcAuthentication()) << name() << reply->proxyClient() << "finished successfully." << userInformation;
} else {
qCDebug(dcAuthentication()) << name() << reply->proxyClient() << "finished with error" << error;
}
reply->proxyClient()->setUserName(userInformation.email());
setReplyError(reply, error);
setReplyFinished(reply);
}
AuthenticationReply *AwsAuthenticator::authenticate(ProxyClient *proxyClient)
{
qCDebug(dcAuthentication()) << name() << "Start authenticating" << proxyClient;
AuthenticationReply *reply = createAuthenticationReply(proxyClient, this);
AuthenticationReply *reply = createAuthenticationReply(proxyClient, proxyClient);
if (!m_credentialsProvider->isValid()) {
qCWarning(dcAuthentication()) << name() << "There are no credentials for authenticating.";
setReplyError(reply, AuthenticationErrorProxyError);
@ -83,12 +65,21 @@ AuthenticationReply *AwsAuthenticator::authenticate(ProxyClient *proxyClient)
AuthenticationProcess *process = new AuthenticationProcess(m_manager,
m_credentialsProvider->accessKey(),
m_credentialsProvider->secretAccessKey(),
m_credentialsProvider->sessionToken(), this);
m_credentialsProvider->sessionToken(), reply);
connect(process, &AuthenticationProcess::authenticationFinished, this, &AwsAuthenticator::onAuthenticationProcessFinished);
connect(process, &AuthenticationProcess::authenticationFinished, proxyClient, [=](Authenticator::AuthenticationError error, const UserInformation &userInformation = UserInformation()){
if (error == AuthenticationErrorNoError) {
qCDebug(dcAuthentication()) << name() << proxyClient << "finished successfully." << userInformation;
} else {
qCDebug(dcAuthentication()) << name() << proxyClient << "finished with error" << error;
}
proxyClient->setUserName(userInformation.email());
setReplyError(reply, error);
setReplyFinished(reply);
});
// Configure process
m_runningProcesses.insert(process, reply);
// Start authentication process
process->authenticate(proxyClient->token());

View File

@ -50,10 +50,6 @@ public:
private:
QNetworkAccessManager *m_manager = nullptr;
AwsCredentialProvider *m_credentialsProvider = nullptr;
QHash<AuthenticationProcess *, AuthenticationReply *> m_runningProcesses;
private slots:
void onAuthenticationProcessFinished(Authenticator::AuthenticationError error, const UserInformation &userInformation);
public slots:
AuthenticationReply *authenticate(ProxyClient *proxyClient) override;

View File

@ -79,36 +79,28 @@ JsonReply *AuthenticationHandler::Authenticate(const QVariantMap &params, Transp
proxyClient->setNonce(nonce);
AuthenticationReply *authReply = Engine::instance()->authenticator()->authenticate(proxyClient);
connect(authReply, &AuthenticationReply::finished, this, &AuthenticationHandler::onAuthenticationFinished);
connect(authReply, &AuthenticationReply::finished, jsonReply, [=](){
authReply->deleteLater();
m_runningAuthentications.insert(authReply, jsonReply);
qCDebug(dcJsonRpc()) << "Authentication reply finished";
if (authReply->error() != Authenticator::AuthenticationErrorNoError) {
qCWarning(dcJsonRpc()) << "Authentication error occurred" << authReply->error();
jsonReply->setSuccess(false);
} else {
// Successfully authenticated
jsonReply->setSuccess(true);
}
// Set client authenticated if still there
if (!authReply->proxyClient().isNull()) {
authReply->proxyClient()->setAuthenticated(authReply->error() == Authenticator::AuthenticationErrorNoError);
jsonReply->setData(errorToReply(authReply->error()));
}
emit jsonReply->finished();
});
return jsonReply;
}
void AuthenticationHandler::onAuthenticationFinished()
{
AuthenticationReply *authenticationReply = static_cast<AuthenticationReply *>(sender());
authenticationReply->deleteLater();
qCDebug(dcJsonRpc()) << "Authentication reply finished";
JsonReply *jsonReply = m_runningAuthentications.take(authenticationReply);
if (authenticationReply->error() != Authenticator::AuthenticationErrorNoError) {
qCWarning(dcJsonRpc()) << "Authentication error occurred" << authenticationReply->error();
jsonReply->setSuccess(false);
} else {
// Successfully authenticated
jsonReply->setSuccess(true);
}
// Set client authenticated if still there
if (!authenticationReply->proxyClient().isNull()) {
authenticationReply->proxyClient()->setAuthenticated(authenticationReply->error() == Authenticator::AuthenticationErrorNoError);
jsonReply->setData(errorToReply(authenticationReply->error()));
}
emit jsonReply->finished();
}
}

View File

@ -48,13 +48,6 @@ public:
Q_INVOKABLE JsonReply *Authenticate(const QVariantMap &params, TransportClient *transportClient);
private:
QHash<AuthenticationReply *, JsonReply *> m_runningAuthentications;
private slots:
void onAuthenticationFinished();
};
}