Commit 9d917939 authored by kinaba@chromium.org's avatar kinaba@chromium.org

drive: Support authorizing third-party Drive apps for opening files.

Along the way, replace the official key check in DriveAppRegistry::IsUninstallSupported
by the new devoted function. (In fact, the macro is available
only during google_apis/ hence the previous code was not working well...)


BUG=332332

Review URL: https://codereview.chromium.org/140783006

git-svn-id: svn://svn.chromium.org/chrome/trunk/src@245565 0039d316-1c4b-4281-b951-d872f2087c98
parent c8868c8b
...@@ -21,6 +21,7 @@ ...@@ -21,6 +21,7 @@
#include "google_apis/drive/gdata_wapi_parser.h" #include "google_apis/drive/gdata_wapi_parser.h"
#include "google_apis/drive/gdata_wapi_requests.h" #include "google_apis/drive/gdata_wapi_requests.h"
#include "google_apis/drive/request_sender.h" #include "google_apis/drive/request_sender.h"
#include "google_apis/google_api_keys.h"
#include "net/url_request/url_request_context_getter.h" #include "net/url_request/url_request_context_getter.h"
using content::BrowserThread; using content::BrowserThread;
...@@ -784,12 +785,28 @@ CancelCallback DriveAPIService::AuthorizeApp( ...@@ -784,12 +785,28 @@ CancelCallback DriveAPIService::AuthorizeApp(
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
DCHECK(!callback.is_null()); DCHECK(!callback.is_null());
FilesGetRequest* request = new FilesGetRequest( // Files.Authorize is only available for whitelisted clients like official
sender_.get(), url_generator_, // Google Chrome. In other cases, we fall back to Files.Get that returns the
base::Bind(&ExtractOpenUrlAndRun, app_id, callback)); // same value as Files.Authorize without doing authorization. In that case,
request->set_file_id(resource_id); // the app can open if it was authorized by other means (from whitelisted
request->set_fields(kFileResourceOpenWithLinksFields); // clients or drive.google.com web UI.)
return sender_->StartRequestWithRetry(request); if (google_apis::IsGoogleChromeAPIKeyUsed()) {
google_apis::drive::FilesAuthorizeRequest* request =
new google_apis::drive::FilesAuthorizeRequest(
sender_.get(), url_generator_,
base::Bind(&ExtractOpenUrlAndRun, app_id, callback));
request->set_app_id(app_id);
request->set_file_id(resource_id);
request->set_fields(kFileResourceOpenWithLinksFields);
return sender_->StartRequestWithRetry(request);
} else {
FilesGetRequest* request = new FilesGetRequest(
sender_.get(), url_generator_,
base::Bind(&ExtractOpenUrlAndRun, app_id, callback));
request->set_file_id(resource_id);
request->set_fields(kFileResourceOpenWithLinksFields);
return sender_->StartRequestWithRetry(request);
}
} }
CancelCallback DriveAPIService::UninstallApp( CancelCallback DriveAPIService::UninstallApp(
......
...@@ -13,6 +13,7 @@ ...@@ -13,6 +13,7 @@
#include "chrome/browser/drive/drive_service_interface.h" #include "chrome/browser/drive/drive_service_interface.h"
#include "content/public/browser/browser_thread.h" #include "content/public/browser/browser_thread.h"
#include "google_apis/drive/drive_api_parser.h" #include "google_apis/drive/drive_api_parser.h"
#include "google_apis/google_api_keys.h"
using content::BrowserThread; using content::BrowserThread;
...@@ -205,11 +206,7 @@ void DriveAppRegistry::OnAppUninstalled(const std::string& app_id, ...@@ -205,11 +206,7 @@ void DriveAppRegistry::OnAppUninstalled(const std::string& app_id,
// static // static
bool DriveAppRegistry::IsAppUninstallSupported() { bool DriveAppRegistry::IsAppUninstallSupported() {
#ifdef USE_OFFICIAL_GOOGLE_API_KEYS return google_apis::IsGoogleChromeAPIKeyUsed();
return true;
#else
return false;
#endif
} }
namespace util { namespace util {
......
...@@ -162,6 +162,29 @@ GURL FilesGetRequest::GetURLInternal() const { ...@@ -162,6 +162,29 @@ GURL FilesGetRequest::GetURLInternal() const {
return url_generator_.GetFilesGetUrl(file_id_); return url_generator_.GetFilesGetUrl(file_id_);
} }
//============================ FilesAuthorizeRequest ===========================
FilesAuthorizeRequest::FilesAuthorizeRequest(
RequestSender* sender,
const DriveApiUrlGenerator& url_generator,
const FileResourceCallback& callback)
: DriveApiDataRequest(
sender,
base::Bind(&ParseJsonAndRun<FileResource>, callback)),
url_generator_(url_generator) {
DCHECK(!callback.is_null());
}
FilesAuthorizeRequest::~FilesAuthorizeRequest() {}
net::URLFetcher::RequestType FilesAuthorizeRequest::GetRequestType() const {
return net::URLFetcher::POST;
}
GURL FilesAuthorizeRequest::GetURLInternal() const {
return url_generator_.GetFilesAuthorizeUrl(file_id_, app_id_);
}
//============================ FilesInsertRequest ============================ //============================ FilesInsertRequest ============================
FilesInsertRequest::FilesInsertRequest( FilesInsertRequest::FilesInsertRequest(
......
...@@ -93,6 +93,38 @@ class FilesGetRequest : public DriveApiDataRequest { ...@@ -93,6 +93,38 @@ class FilesGetRequest : public DriveApiDataRequest {
DISALLOW_COPY_AND_ASSIGN(FilesGetRequest); DISALLOW_COPY_AND_ASSIGN(FilesGetRequest);
}; };
//============================ FilesAuthorizeRequest ===========================
// This class performs request for authorizing an app to access a file.
// This request is mapped to /drive/v2internal/file/authorize internal endpoint.
class FilesAuthorizeRequest : public DriveApiDataRequest {
public:
FilesAuthorizeRequest(RequestSender* sender,
const DriveApiUrlGenerator& url_generator,
const FileResourceCallback& callback);
virtual ~FilesAuthorizeRequest();
// Required parameter.
const std::string& file_id() const { return file_id_; }
void set_file_id(const std::string& file_id) { file_id_ = file_id; }
const std::string& app_id() const { return app_id_; }
void set_app_id(const std::string& app_id) { app_id_ = app_id; }
protected:
// Overridden from GetDataRequest.
virtual net::URLFetcher::RequestType GetRequestType() const OVERRIDE;
// Overridden from DriveApiDataRequest.
virtual GURL GetURLInternal() const OVERRIDE;
private:
const DriveApiUrlGenerator url_generator_;
std::string file_id_;
std::string app_id_;
DISALLOW_COPY_AND_ASSIGN(FilesAuthorizeRequest);
};
//============================ FilesInsertRequest ============================= //============================ FilesInsertRequest =============================
// This class performs the request for creating a resource. // This class performs the request for creating a resource.
......
...@@ -17,9 +17,6 @@ namespace { ...@@ -17,9 +17,6 @@ namespace {
// Hard coded URLs for communication with a google drive server. // Hard coded URLs for communication with a google drive server.
const char kDriveV2AboutUrl[] = "/drive/v2/about"; const char kDriveV2AboutUrl[] = "/drive/v2/about";
const char kDriveV2AppsUrl[] = "/drive/v2/apps"; const char kDriveV2AppsUrl[] = "/drive/v2/apps";
// apps.delete API is exposed through a special endpoint v2internal that
// is accessible only by the official API key for Chrome.
const char kDriveV2AppsDeleteUrlFormat[] = "/drive/v2internal/apps/%s";
const char kDriveV2ChangelistUrl[] = "/drive/v2/changes"; const char kDriveV2ChangelistUrl[] = "/drive/v2/changes";
const char kDriveV2FilesUrl[] = "/drive/v2/files"; const char kDriveV2FilesUrl[] = "/drive/v2/files";
const char kDriveV2FileUrlPrefix[] = "/drive/v2/files/"; const char kDriveV2FileUrlPrefix[] = "/drive/v2/files/";
...@@ -33,6 +30,12 @@ const char kDriveV2InitiateUploadNewFileUrl[] = "/upload/drive/v2/files"; ...@@ -33,6 +30,12 @@ const char kDriveV2InitiateUploadNewFileUrl[] = "/upload/drive/v2/files";
const char kDriveV2InitiateUploadExistingFileUrlPrefix[] = const char kDriveV2InitiateUploadExistingFileUrlPrefix[] =
"/upload/drive/v2/files/"; "/upload/drive/v2/files/";
// apps.delete and file.authorize API is exposed through a special endpoint
// v2internal that is accessible only by the official API key for Chrome.
const char kDriveV2AppsDeleteUrlFormat[] = "/drive/v2internal/apps/%s";
const char kDriveV2FilesAuthorizeUrlFormat[] =
"/drive/v2internal/files/%s/authorize?appId=%s";
GURL AddResumableUploadParam(const GURL& url) { GURL AddResumableUploadParam(const GURL& url) {
return net::AppendOrReplaceQueryParameter(url, "uploadType", "resumable"); return net::AppendOrReplaceQueryParameter(url, "uploadType", "resumable");
} }
...@@ -72,6 +75,14 @@ GURL DriveApiUrlGenerator::GetFilesGetUrl(const std::string& file_id) const { ...@@ -72,6 +75,14 @@ GURL DriveApiUrlGenerator::GetFilesGetUrl(const std::string& file_id) const {
return base_url_.Resolve(kDriveV2FileUrlPrefix + net::EscapePath(file_id)); return base_url_.Resolve(kDriveV2FileUrlPrefix + net::EscapePath(file_id));
} }
GURL DriveApiUrlGenerator::GetFilesAuthorizeUrl(
const std::string& file_id,
const std::string& app_id) const {
return base_url_.Resolve(base::StringPrintf(kDriveV2FilesAuthorizeUrlFormat,
net::EscapePath(file_id).c_str(),
net::EscapePath(app_id).c_str()));
}
GURL DriveApiUrlGenerator::GetFilesInsertUrl() const { GURL DriveApiUrlGenerator::GetFilesInsertUrl() const {
return base_url_.Resolve(kDriveV2FilesUrl); return base_url_.Resolve(kDriveV2FilesUrl);
} }
......
...@@ -38,6 +38,10 @@ class DriveApiUrlGenerator { ...@@ -38,6 +38,10 @@ class DriveApiUrlGenerator {
// Returns a URL to fetch a file metadata. // Returns a URL to fetch a file metadata.
GURL GetFilesGetUrl(const std::string& file_id) const; GURL GetFilesGetUrl(const std::string& file_id) const;
// Returns a URL to authorize an app to access a file.
GURL GetFilesAuthorizeUrl(const std::string& file_id,
const std::string& app_id) const;
// Returns a URL to create a resource. // Returns a URL to create a resource.
GURL GetFilesInsertUrl() const; GURL GetFilesInsertUrl() const;
......
...@@ -65,6 +65,15 @@ TEST_F(DriveApiUrlGeneratorTest, GetFilesGetUrl) { ...@@ -65,6 +65,15 @@ TEST_F(DriveApiUrlGeneratorTest, GetFilesGetUrl) {
test_url_generator_.GetFilesGetUrl("file:file_id").spec()); test_url_generator_.GetFilesGetUrl("file:file_id").spec());
} }
TEST_F(DriveApiUrlGeneratorTest, GetFilesAuthorizeUrl) {
EXPECT_EQ(
"https://www.googleapis.com/drive/v2internal/files/aa/authorize?appId=bb",
url_generator_.GetFilesAuthorizeUrl("aa", "bb").spec());
EXPECT_EQ(
"http://127.0.0.1:12345/drive/v2internal/files/foo/authorize?appId=bar",
test_url_generator_.GetFilesAuthorizeUrl("foo", "bar").spec());
}
TEST_F(DriveApiUrlGeneratorTest, GetFilesInsertUrl) { TEST_F(DriveApiUrlGeneratorTest, GetFilesInsertUrl) {
EXPECT_EQ("https://www.googleapis.com/drive/v2/files", EXPECT_EQ("https://www.googleapis.com/drive/v2/files",
url_generator_.GetFilesInsertUrl().spec()); url_generator_.GetFilesInsertUrl().spec());
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment