File indexing completed on 2023-10-01 05:03:15
0001 /* 0002 * Copyright (C) 2011 Collabora Ltd. <http://www.collabora.co.uk/> 0003 * @author Andre Moreira Magalhaes <andre.magalhaes@collabora.co.uk> 0004 * Copyright (C) 2011 David Edmundson <kde@davidedmundson.co.uk> 0005 * 0006 * This library is free software; you can redistribute it and/or 0007 * modify it under the terms of the GNU Lesser General Public 0008 * License as published by the Free Software Foundation; either 0009 * version 2.1 of the License, or (at your option) any later version. 0010 * 0011 * This library is distributed in the hope that it will be useful, 0012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 0013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 0014 * Lesser General Public License for more details. 0015 * 0016 * You should have received a copy of the GNU Lesser General Public 0017 * License along with this library; if not, write to the Free Software 0018 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA 0019 */ 0020 0021 #include "sasl-auth-op.h" 0022 0023 #include "x-telepathy-password-auth-operation.h" 0024 #include "x-telepathy-sso-google-operation.h" 0025 0026 #include <QtCore/QScopedPointer> 0027 0028 #include <TelepathyQt/PendingVariantMap> 0029 0030 #include <QDebug> 0031 #include <KLocalizedString> 0032 0033 SaslAuthOp::SaslAuthOp(const Tp::AccountPtr &account, 0034 const Tp::ChannelPtr &channel) 0035 : Tp::PendingOperation(channel), 0036 m_account(account), 0037 m_channel(channel), 0038 m_saslIface(channel->interface<Tp::Client::ChannelInterfaceSASLAuthenticationInterface>()) 0039 { 0040 //Check if the account has any StorageIdentifier, in which case we will 0041 //prioritize those mechanism related with KDE Accounts integration 0042 QScopedPointer<Tp::Client::AccountInterfaceStorageInterface> accountStorageInterface( 0043 new Tp::Client::AccountInterfaceStorageInterface(m_account->busName(), m_account->objectPath())); 0044 0045 Tp::PendingVariantMap *pendingMap = accountStorageInterface->requestAllProperties(); 0046 connect(pendingMap, SIGNAL(finished(Tp::PendingOperation*)), SLOT(onGetAccountStorageFetched(Tp::PendingOperation*))); 0047 } 0048 0049 SaslAuthOp::~SaslAuthOp() 0050 { 0051 } 0052 0053 void SaslAuthOp::gotProperties(Tp::PendingOperation *op) 0054 { 0055 if (m_mechanisms.isEmpty()) { 0056 if (op->isError()) { 0057 qWarning() << "Unable to retrieve available SASL mechanisms"; 0058 m_channel->requestClose(); 0059 setFinishedWithError(op->errorName(), op->errorMessage()); 0060 return; 0061 } 0062 0063 Tp::PendingVariantMap *pvm = qobject_cast<Tp::PendingVariantMap*>(op); 0064 m_properties = qdbus_cast<QVariantMap>(pvm->result()); 0065 m_mechanisms = qdbus_cast<QStringList>(m_properties.value(QLatin1String("AvailableMechanisms"))); 0066 qDebug() << m_mechanisms; 0067 } 0068 0069 uint status = qdbus_cast<uint>(m_properties.value(QLatin1String("SASLStatus"))); 0070 QString error = qdbus_cast<QString>(m_properties.value(QLatin1String("SASLError"))); 0071 QVariantMap errorDetails = qdbus_cast<QVariantMap>(m_properties.value(QLatin1String("SASLErrorDetails"))); 0072 0073 if (m_mechanisms.contains(QLatin1String("X-OAUTH2"))) { 0074 qDebug() << "Starting X-OAuth2 auth"; 0075 m_mechanisms.removeAll(QStringLiteral("X-OAUTH2")); 0076 XTelepathySSOGoogleOperation *authop = new XTelepathySSOGoogleOperation(m_account, m_accountStorageId, m_saslIface); 0077 connect(authop, 0078 SIGNAL(finished(Tp::PendingOperation*)), 0079 SLOT(onAuthOperationFinished(Tp::PendingOperation*))); 0080 0081 authop->onSASLStatusChanged(status, error, errorDetails); 0082 } else if (m_mechanisms.contains(QLatin1String("X-TELEPATHY-PASSWORD"))) { 0083 qDebug() << "Starting Password auth"; 0084 m_mechanisms.removeAll(QStringLiteral("X-TELEPATHY-PASSWORD")); 0085 Q_EMIT ready(this); 0086 XTelepathyPasswordAuthOperation *authop = new XTelepathyPasswordAuthOperation(m_account, m_accountStorageId, m_saslIface, qdbus_cast<bool>(m_properties.value(QLatin1String("CanTryAgain")))); 0087 connect(authop, 0088 SIGNAL(finished(Tp::PendingOperation*)), 0089 SLOT(onAuthOperationFinished(Tp::PendingOperation*))); 0090 0091 authop->onSASLStatusChanged(status, error, errorDetails); 0092 } else { 0093 qWarning() << "X-TELEPATHY-PASSWORD, X-OAUTH2 are the only supported SASL mechanism and are not available:" << m_mechanisms; 0094 m_channel->requestClose(); 0095 setFinishedWithError(TP_QT_ERROR_NOT_IMPLEMENTED, 0096 QLatin1String("X-TELEPATHY-PASSWORD, X-OAUTH2 are the only supported SASL mechanism and are not available:")); 0097 return; 0098 } 0099 } 0100 0101 void SaslAuthOp::onAuthOperationFinished(Tp::PendingOperation *op) 0102 { 0103 if (op->isError()) { 0104 if (!m_mechanisms.isEmpty()) { 0105 // if we have other mechanisms left, try again with different one 0106 gotProperties(0); 0107 } else { 0108 setFinishedWithError(op->errorName(), op->errorMessage()); 0109 m_channel->requestClose(); 0110 } 0111 } else { 0112 setFinished(); 0113 m_channel->requestClose(); 0114 } 0115 } 0116 0117 void SaslAuthOp::setReady() 0118 { 0119 connect(m_saslIface->requestAllProperties(), 0120 SIGNAL(finished(Tp::PendingOperation*)), 0121 SLOT(gotProperties(Tp::PendingOperation*))); 0122 } 0123 0124 void SaslAuthOp::onGetAccountStorageFetched(Tp::PendingOperation* op) 0125 { 0126 Tp::PendingVariantMap *pendingMap = qobject_cast<Tp::PendingVariantMap*>(op); 0127 0128 m_accountStorageId = pendingMap->result()["StorageIdentifier"].value<QDBusVariant>().variant().toInt(); 0129 qDebug() << m_accountStorageId; 0130 0131 setReady(); 0132 }