Factor out Google Drive specific code from OAuthenticator.
This commit is contained in:
parent
14c07cbaed
commit
8eea98ba66
|
@ -29,8 +29,23 @@ using namespace google_drive;
|
|||
const char* File::kFolderMimeType = "application/vnd.google-apps.folder";
|
||||
|
||||
namespace {
|
||||
static const char* kGoogleDriveFile = "https://www.googleapis.com/drive/v2/files/%1";
|
||||
static const char* kGoogleDriveChanges = "https://www.googleapis.com/drive/v2/changes";
|
||||
static const char* kGoogleDriveFile =
|
||||
"https://www.googleapis.com/drive/v2/files/%1";
|
||||
static const char* kGoogleDriveChanges =
|
||||
"https://www.googleapis.com/drive/v2/changes";
|
||||
static const char* kGoogleOAuthUserInfoEndpoint =
|
||||
"https://www.googleapis.com/oauth2/v1/userinfo";
|
||||
|
||||
static const char* kOAuthEndpoint = "https://accounts.google.com/o/oauth2/auth";
|
||||
static const char* kOAuthTokenEndpoint =
|
||||
"https://accounts.google.com/o/oauth2/token";
|
||||
static const char* kOAuthScope =
|
||||
"https://www.googleapis.com/auth/drive.readonly "
|
||||
"https://www.googleapis.com/auth/userinfo.email";
|
||||
static const char* kClientId =
|
||||
"679260893280.apps.googleusercontent.com";
|
||||
static const char* kClientSecret =
|
||||
"l3cWb8efUZsrBI4wmY3uKl6i";
|
||||
}
|
||||
|
||||
QStringList File::parent_ids() const {
|
||||
|
@ -74,12 +89,15 @@ Client::Client(QObject* parent)
|
|||
|
||||
ConnectResponse* Client::Connect(const QString& refresh_token) {
|
||||
ConnectResponse* ret = new ConnectResponse(this);
|
||||
OAuthenticator* oauth = new OAuthenticator(this);
|
||||
OAuthenticator* oauth = new OAuthenticator(kClientId, kClientSecret, this);
|
||||
|
||||
if (refresh_token.isEmpty()) {
|
||||
oauth->StartAuthorisation();
|
||||
oauth->StartAuthorisation(
|
||||
kOAuthEndpoint,
|
||||
kOAuthTokenEndpoint,
|
||||
kOAuthScope);
|
||||
} else {
|
||||
oauth->RefreshAuthorisation(refresh_token);
|
||||
oauth->RefreshAuthorisation(kOAuthTokenEndpoint, refresh_token);
|
||||
}
|
||||
|
||||
NewClosure(oauth, SIGNAL(Finished()),
|
||||
|
@ -93,9 +111,36 @@ void Client::ConnectFinished(ConnectResponse* response, OAuthenticator* oauth) {
|
|||
access_token_ = oauth->access_token();
|
||||
expiry_time_ = oauth->expiry_time();
|
||||
response->refresh_token_ = oauth->refresh_token();
|
||||
response->user_email_ = oauth->user_email();
|
||||
emit response->Finished();
|
||||
|
||||
// Fetch user email.
|
||||
QUrl url(kGoogleOAuthUserInfoEndpoint);
|
||||
QNetworkRequest request(url);
|
||||
AddAuthorizationHeader(&request);
|
||||
QNetworkReply* reply = network_->get(request);
|
||||
NewClosure(reply, SIGNAL(finished()),
|
||||
this, SLOT(FetchUserInfoFinished(ConnectResponse*, QNetworkReply*)),
|
||||
response, reply);
|
||||
}
|
||||
|
||||
void Client::FetchUserInfoFinished(
|
||||
ConnectResponse* response, QNetworkReply* reply) {
|
||||
reply->deleteLater();
|
||||
if (reply->attribute(QNetworkRequest::HttpStatusCodeAttribute) != 200) {
|
||||
qLog(Warning) << "Failed to get user info" << reply->readAll();
|
||||
} else {
|
||||
QJson::Parser parser;
|
||||
bool ok = false;
|
||||
QVariantMap result = parser.parse(reply, &ok).toMap();
|
||||
if (!ok) {
|
||||
qLog(Error) << "Failed to parse user info reply";
|
||||
return;
|
||||
}
|
||||
|
||||
qLog(Debug) << result;
|
||||
response->user_email_ = result["email"].toString();
|
||||
qLog(Debug) << response->user_email_;
|
||||
}
|
||||
emit response->Finished();
|
||||
emit Authenticated();
|
||||
}
|
||||
|
||||
|
|
|
@ -155,6 +155,7 @@ signals:
|
|||
|
||||
private slots:
|
||||
void ConnectFinished(ConnectResponse* response, OAuthenticator* oauth);
|
||||
void FetchUserInfoFinished(ConnectResponse* response, QNetworkReply* reply);
|
||||
void GetFileFinished(GetFileResponse* response, QNetworkReply* reply);
|
||||
void ListChangesFinished(ListChangesResponse* response, QNetworkReply* reply);
|
||||
|
||||
|
|
|
@ -10,38 +10,31 @@
|
|||
#include "core/logging.h"
|
||||
#include "internet/localredirectserver.h"
|
||||
|
||||
namespace {
|
||||
|
||||
const char* kGoogleOAuthEndpoint = "https://accounts.google.com/o/oauth2/auth";
|
||||
const char* kGoogleOAuthTokenEndpoint =
|
||||
"https://accounts.google.com/o/oauth2/token";
|
||||
const char* kGoogleOAuthScope =
|
||||
"https://www.googleapis.com/auth/drive.readonly "
|
||||
"https://www.googleapis.com/auth/userinfo.email";
|
||||
const char* kGoogleOAuthUserInfoEndpoint =
|
||||
"https://www.googleapis.com/oauth2/v1/userinfo";
|
||||
|
||||
const char* kClientId = "679260893280.apps.googleusercontent.com";
|
||||
const char* kClientSecret = "l3cWb8efUZsrBI4wmY3uKl6i";
|
||||
|
||||
} // namespace
|
||||
|
||||
OAuthenticator::OAuthenticator(QObject* parent)
|
||||
: QObject(parent) {
|
||||
OAuthenticator::OAuthenticator(
|
||||
const QString& client_id,
|
||||
const QString& client_secret,
|
||||
QObject* parent)
|
||||
: QObject(parent),
|
||||
client_id_(client_id),
|
||||
client_secret_(client_secret) {
|
||||
}
|
||||
|
||||
void OAuthenticator::StartAuthorisation() {
|
||||
void OAuthenticator::StartAuthorisation(
|
||||
const QString& oauth_endpoint,
|
||||
const QString& token_endpoint,
|
||||
const QString& scope) {
|
||||
token_endpoint_ = QUrl(token_endpoint);
|
||||
LocalRedirectServer* server = new LocalRedirectServer(this);
|
||||
server->Listen();
|
||||
|
||||
NewClosure(server, SIGNAL(Finished()),
|
||||
this, SLOT(RedirectArrived(LocalRedirectServer*)), server);
|
||||
|
||||
QUrl url = QUrl(kGoogleOAuthEndpoint);
|
||||
QUrl url = QUrl(oauth_endpoint);
|
||||
url.addQueryItem("response_type", "code");
|
||||
url.addQueryItem("client_id", kClientId);
|
||||
url.addQueryItem("client_id", client_id_);
|
||||
url.addQueryItem("redirect_uri", server->url().toString());
|
||||
url.addQueryItem("scope", kGoogleOAuthScope);
|
||||
url.addQueryItem("scope", scope);
|
||||
|
||||
QDesktopServices::openUrl(url);
|
||||
}
|
||||
|
@ -68,8 +61,8 @@ void OAuthenticator::RequestAccessToken(const QByteArray& code, const QUrl& url)
|
|||
typedef QPair<QString, QString> Param;
|
||||
QList<Param> parameters;
|
||||
parameters << Param("code", code)
|
||||
<< Param("client_id", kClientId)
|
||||
<< Param("client_secret", kClientSecret)
|
||||
<< Param("client_id", client_id_)
|
||||
<< Param("client_secret", client_secret_)
|
||||
<< Param("grant_type", "authorization_code")
|
||||
// Even though we don't use this URI anymore, it must match the
|
||||
// original one.
|
||||
|
@ -82,7 +75,7 @@ void OAuthenticator::RequestAccessToken(const QByteArray& code, const QUrl& url)
|
|||
QString post_data = params.join("&");
|
||||
qLog(Debug) << post_data;
|
||||
|
||||
QNetworkRequest request = QNetworkRequest(QUrl(kGoogleOAuthTokenEndpoint));
|
||||
QNetworkRequest request = QNetworkRequest(QUrl(token_endpoint_));
|
||||
request.setHeader(QNetworkRequest::ContentTypeHeader,
|
||||
"application/x-www-form-urlencoded");
|
||||
|
||||
|
@ -114,49 +107,20 @@ void OAuthenticator::FetchAccessTokenFinished(QNetworkReply* reply) {
|
|||
refresh_token_ = result["refresh_token"].toString();
|
||||
SetExpiryTime(result["expires_in"].toInt());
|
||||
|
||||
// Fetch some basic user information
|
||||
QUrl url = QUrl(kGoogleOAuthUserInfoEndpoint);
|
||||
QNetworkRequest request(url);
|
||||
request.setRawHeader(
|
||||
"Authorization", QString("Bearer %1").arg(access_token_).toUtf8());
|
||||
|
||||
QNetworkReply* user_info_reply = network_.get(request);
|
||||
NewClosure(user_info_reply, SIGNAL(finished()), this,
|
||||
SLOT(FetchUserInfoFinished(QNetworkReply*)), user_info_reply);
|
||||
}
|
||||
|
||||
void OAuthenticator::FetchUserInfoFinished(QNetworkReply* reply) {
|
||||
reply->deleteLater();
|
||||
|
||||
if (reply->attribute(QNetworkRequest::HttpStatusCodeAttribute) != 200) {
|
||||
qLog(Warning) << "Failed to get user info" << reply->readAll();
|
||||
} else {
|
||||
QJson::Parser parser;
|
||||
bool ok = false;
|
||||
QVariantMap result = parser.parse(reply, &ok).toMap();
|
||||
if (!ok) {
|
||||
qLog(Error) << "Failed to parse user info reply";
|
||||
return;
|
||||
}
|
||||
|
||||
qLog(Debug) << result;
|
||||
|
||||
user_email_ = result["email"].toString();
|
||||
qLog(Debug) << user_email_;
|
||||
}
|
||||
|
||||
emit Finished();
|
||||
}
|
||||
|
||||
void OAuthenticator::RefreshAuthorisation(const QString& refresh_token) {
|
||||
void OAuthenticator::RefreshAuthorisation(
|
||||
const QString& token_endpoint,
|
||||
const QString& refresh_token) {
|
||||
refresh_token_ = refresh_token;
|
||||
|
||||
QUrl url = QUrl(kGoogleOAuthTokenEndpoint);
|
||||
QUrl url(token_endpoint);
|
||||
|
||||
typedef QPair<QString, QString> Param;
|
||||
QList<Param> parameters;
|
||||
parameters << Param("client_id", kClientId)
|
||||
<< Param("client_secret", kClientSecret)
|
||||
parameters << Param("client_id", client_id_)
|
||||
<< Param("client_secret", client_secret_)
|
||||
<< Param("grant_type", "refresh_token")
|
||||
<< Param("refresh_token", refresh_token);
|
||||
QStringList params;
|
||||
|
|
|
@ -12,9 +12,17 @@ class QTcpSocket;
|
|||
class OAuthenticator : public QObject {
|
||||
Q_OBJECT
|
||||
public:
|
||||
explicit OAuthenticator(QObject* parent = 0);
|
||||
void StartAuthorisation();
|
||||
void RefreshAuthorisation(const QString& refresh_token);
|
||||
OAuthenticator(
|
||||
const QString& client_id,
|
||||
const QString& client_secret,
|
||||
QObject* parent = 0);
|
||||
void StartAuthorisation(
|
||||
const QString& oauth_endpoint,
|
||||
const QString& token_endpoint,
|
||||
const QString& scope);
|
||||
void RefreshAuthorisation(
|
||||
const QString& token_endpoint,
|
||||
const QString& refresh_token);
|
||||
|
||||
// Token to use now.
|
||||
const QString& access_token() const { return access_token_; }
|
||||
|
@ -32,7 +40,6 @@ class OAuthenticator : public QObject {
|
|||
void RedirectArrived(LocalRedirectServer* server);
|
||||
void FetchAccessTokenFinished(QNetworkReply* reply);
|
||||
void RefreshAccessTokenFinished(QNetworkReply* reply);
|
||||
void FetchUserInfoFinished(QNetworkReply* reply);
|
||||
|
||||
private:
|
||||
QByteArray ParseHttpRequest(const QByteArray& request) const;
|
||||
|
@ -45,6 +52,10 @@ class OAuthenticator : public QObject {
|
|||
QString refresh_token_;
|
||||
QDateTime expiry_time_;
|
||||
QString user_email_;
|
||||
|
||||
const QString client_id_;
|
||||
const QString client_secret_;
|
||||
QUrl token_endpoint_;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
Loading…
Reference in New Issue