1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "google_apis/drive/drive_api_requests.h"
6
7 #include "base/bind.h"
8 #include "base/callback.h"
9 #include "base/json/json_writer.h"
10 #include "base/location.h"
11 #include "base/sequenced_task_runner.h"
12 #include "base/task_runner_util.h"
13 #include "base/values.h"
14 #include "google_apis/drive/request_sender.h"
15 #include "google_apis/drive/request_util.h"
16 #include "google_apis/drive/time_util.h"
17 #include "net/base/url_util.h"
18
19 namespace google_apis {
20 namespace {
21
22 const char kContentTypeApplicationJson[] = "application/json";
23 const char kParentLinkKind[] = "drive#fileLink";
24
25 // Parses the JSON value to FileResource instance and runs |callback| on the
26 // UI thread once parsing is done.
27 // This is customized version of ParseJsonAndRun defined above to adapt the
28 // remaining response type.
ParseFileResourceWithUploadRangeAndRun(const drive::UploadRangeCallback & callback,const UploadRangeResponse & response,scoped_ptr<base::Value> value)29 void ParseFileResourceWithUploadRangeAndRun(
30 const drive::UploadRangeCallback& callback,
31 const UploadRangeResponse& response,
32 scoped_ptr<base::Value> value) {
33 DCHECK(!callback.is_null());
34
35 scoped_ptr<FileResource> file_resource;
36 if (value) {
37 file_resource = FileResource::CreateFrom(*value);
38 if (!file_resource) {
39 callback.Run(
40 UploadRangeResponse(GDATA_PARSE_ERROR,
41 response.start_position_received,
42 response.end_position_received),
43 scoped_ptr<FileResource>());
44 return;
45 }
46 }
47
48 callback.Run(response, file_resource.Pass());
49 }
50
51 // Creates a Parents value which can be used as a part of request body.
CreateParentValue(const std::string & file_id)52 scoped_ptr<base::DictionaryValue> CreateParentValue(
53 const std::string& file_id) {
54 scoped_ptr<base::DictionaryValue> parent(new base::DictionaryValue);
55 parent->SetString("kind", kParentLinkKind);
56 parent->SetString("id", file_id);
57 return parent.Pass();
58 }
59
60 } // namespace
61
62 namespace drive {
63
64 //============================ DriveApiPartialFieldRequest ====================
65
DriveApiPartialFieldRequest(RequestSender * sender)66 DriveApiPartialFieldRequest::DriveApiPartialFieldRequest(
67 RequestSender* sender) : UrlFetchRequestBase(sender) {
68 }
69
~DriveApiPartialFieldRequest()70 DriveApiPartialFieldRequest::~DriveApiPartialFieldRequest() {
71 }
72
GetURL() const73 GURL DriveApiPartialFieldRequest::GetURL() const {
74 GURL url = GetURLInternal();
75 if (!fields_.empty())
76 url = net::AppendOrReplaceQueryParameter(url, "fields", fields_);
77 return url;
78 }
79
80 //=============================== FilesGetRequest =============================
81
FilesGetRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)82 FilesGetRequest::FilesGetRequest(
83 RequestSender* sender,
84 const DriveApiUrlGenerator& url_generator,
85 const FileResourceCallback& callback)
86 : DriveApiDataRequest<FileResource>(sender, callback),
87 url_generator_(url_generator) {
88 DCHECK(!callback.is_null());
89 }
90
~FilesGetRequest()91 FilesGetRequest::~FilesGetRequest() {}
92
GetURLInternal() const93 GURL FilesGetRequest::GetURLInternal() const {
94 return url_generator_.GetFilesGetUrl(file_id_);
95 }
96
97 //============================ FilesAuthorizeRequest ===========================
98
FilesAuthorizeRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)99 FilesAuthorizeRequest::FilesAuthorizeRequest(
100 RequestSender* sender,
101 const DriveApiUrlGenerator& url_generator,
102 const FileResourceCallback& callback)
103 : DriveApiDataRequest<FileResource>(sender, callback),
104 url_generator_(url_generator) {
105 DCHECK(!callback.is_null());
106 }
107
~FilesAuthorizeRequest()108 FilesAuthorizeRequest::~FilesAuthorizeRequest() {}
109
GetRequestType() const110 net::URLFetcher::RequestType FilesAuthorizeRequest::GetRequestType() const {
111 return net::URLFetcher::POST;
112 }
113
GetURLInternal() const114 GURL FilesAuthorizeRequest::GetURLInternal() const {
115 return url_generator_.GetFilesAuthorizeUrl(file_id_, app_id_);
116 }
117
118 //============================ FilesInsertRequest ============================
119
FilesInsertRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)120 FilesInsertRequest::FilesInsertRequest(
121 RequestSender* sender,
122 const DriveApiUrlGenerator& url_generator,
123 const FileResourceCallback& callback)
124 : DriveApiDataRequest<FileResource>(sender, callback),
125 url_generator_(url_generator) {
126 DCHECK(!callback.is_null());
127 }
128
~FilesInsertRequest()129 FilesInsertRequest::~FilesInsertRequest() {}
130
GetRequestType() const131 net::URLFetcher::RequestType FilesInsertRequest::GetRequestType() const {
132 return net::URLFetcher::POST;
133 }
134
GetContentData(std::string * upload_content_type,std::string * upload_content)135 bool FilesInsertRequest::GetContentData(std::string* upload_content_type,
136 std::string* upload_content) {
137 *upload_content_type = kContentTypeApplicationJson;
138
139 base::DictionaryValue root;
140
141 if (!last_viewed_by_me_date_.is_null()) {
142 root.SetString("lastViewedByMeDate",
143 util::FormatTimeAsString(last_viewed_by_me_date_));
144 }
145
146 if (!mime_type_.empty())
147 root.SetString("mimeType", mime_type_);
148
149 if (!modified_date_.is_null())
150 root.SetString("modifiedDate", util::FormatTimeAsString(modified_date_));
151
152 if (!parents_.empty()) {
153 base::ListValue* parents_value = new base::ListValue;
154 for (size_t i = 0; i < parents_.size(); ++i) {
155 base::DictionaryValue* parent = new base::DictionaryValue;
156 parent->SetString("id", parents_[i]);
157 parents_value->Append(parent);
158 }
159 root.Set("parents", parents_value);
160 }
161
162 if (!title_.empty())
163 root.SetString("title", title_);
164
165 base::JSONWriter::Write(&root, upload_content);
166 DVLOG(1) << "FilesInsert data: " << *upload_content_type << ", ["
167 << *upload_content << "]";
168 return true;
169 }
170
GetURLInternal() const171 GURL FilesInsertRequest::GetURLInternal() const {
172 return url_generator_.GetFilesInsertUrl();
173 }
174
175 //============================== FilesPatchRequest ============================
176
FilesPatchRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)177 FilesPatchRequest::FilesPatchRequest(
178 RequestSender* sender,
179 const DriveApiUrlGenerator& url_generator,
180 const FileResourceCallback& callback)
181 : DriveApiDataRequest<FileResource>(sender, callback),
182 url_generator_(url_generator),
183 set_modified_date_(false),
184 update_viewed_date_(true) {
185 DCHECK(!callback.is_null());
186 }
187
~FilesPatchRequest()188 FilesPatchRequest::~FilesPatchRequest() {}
189
GetRequestType() const190 net::URLFetcher::RequestType FilesPatchRequest::GetRequestType() const {
191 return net::URLFetcher::PATCH;
192 }
193
GetExtraRequestHeaders() const194 std::vector<std::string> FilesPatchRequest::GetExtraRequestHeaders() const {
195 std::vector<std::string> headers;
196 headers.push_back(util::kIfMatchAllHeader);
197 return headers;
198 }
199
GetURLInternal() const200 GURL FilesPatchRequest::GetURLInternal() const {
201 return url_generator_.GetFilesPatchUrl(
202 file_id_, set_modified_date_, update_viewed_date_);
203 }
204
GetContentData(std::string * upload_content_type,std::string * upload_content)205 bool FilesPatchRequest::GetContentData(std::string* upload_content_type,
206 std::string* upload_content) {
207 if (title_.empty() &&
208 modified_date_.is_null() &&
209 last_viewed_by_me_date_.is_null() &&
210 parents_.empty())
211 return false;
212
213 *upload_content_type = kContentTypeApplicationJson;
214
215 base::DictionaryValue root;
216 if (!title_.empty())
217 root.SetString("title", title_);
218
219 if (!modified_date_.is_null())
220 root.SetString("modifiedDate", util::FormatTimeAsString(modified_date_));
221
222 if (!last_viewed_by_me_date_.is_null()) {
223 root.SetString("lastViewedByMeDate",
224 util::FormatTimeAsString(last_viewed_by_me_date_));
225 }
226
227 if (!parents_.empty()) {
228 base::ListValue* parents_value = new base::ListValue;
229 for (size_t i = 0; i < parents_.size(); ++i) {
230 base::DictionaryValue* parent = new base::DictionaryValue;
231 parent->SetString("id", parents_[i]);
232 parents_value->Append(parent);
233 }
234 root.Set("parents", parents_value);
235 }
236
237 base::JSONWriter::Write(&root, upload_content);
238 DVLOG(1) << "FilesPatch data: " << *upload_content_type << ", ["
239 << *upload_content << "]";
240 return true;
241 }
242
243 //============================= FilesCopyRequest ==============================
244
FilesCopyRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)245 FilesCopyRequest::FilesCopyRequest(
246 RequestSender* sender,
247 const DriveApiUrlGenerator& url_generator,
248 const FileResourceCallback& callback)
249 : DriveApiDataRequest<FileResource>(sender, callback),
250 url_generator_(url_generator) {
251 DCHECK(!callback.is_null());
252 }
253
~FilesCopyRequest()254 FilesCopyRequest::~FilesCopyRequest() {
255 }
256
GetRequestType() const257 net::URLFetcher::RequestType FilesCopyRequest::GetRequestType() const {
258 return net::URLFetcher::POST;
259 }
260
GetURLInternal() const261 GURL FilesCopyRequest::GetURLInternal() const {
262 return url_generator_.GetFilesCopyUrl(file_id_);
263 }
264
GetContentData(std::string * upload_content_type,std::string * upload_content)265 bool FilesCopyRequest::GetContentData(std::string* upload_content_type,
266 std::string* upload_content) {
267 if (parents_.empty() && title_.empty())
268 return false;
269
270 *upload_content_type = kContentTypeApplicationJson;
271
272 base::DictionaryValue root;
273
274 if (!modified_date_.is_null())
275 root.SetString("modifiedDate", util::FormatTimeAsString(modified_date_));
276
277 if (!parents_.empty()) {
278 base::ListValue* parents_value = new base::ListValue;
279 for (size_t i = 0; i < parents_.size(); ++i) {
280 base::DictionaryValue* parent = new base::DictionaryValue;
281 parent->SetString("id", parents_[i]);
282 parents_value->Append(parent);
283 }
284 root.Set("parents", parents_value);
285 }
286
287 if (!title_.empty())
288 root.SetString("title", title_);
289
290 base::JSONWriter::Write(&root, upload_content);
291 DVLOG(1) << "FilesCopy data: " << *upload_content_type << ", ["
292 << *upload_content << "]";
293 return true;
294 }
295
296 //============================= FilesListRequest =============================
297
FilesListRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileListCallback & callback)298 FilesListRequest::FilesListRequest(
299 RequestSender* sender,
300 const DriveApiUrlGenerator& url_generator,
301 const FileListCallback& callback)
302 : DriveApiDataRequest<FileList>(sender, callback),
303 url_generator_(url_generator),
304 max_results_(100) {
305 DCHECK(!callback.is_null());
306 }
307
~FilesListRequest()308 FilesListRequest::~FilesListRequest() {}
309
GetURLInternal() const310 GURL FilesListRequest::GetURLInternal() const {
311 return url_generator_.GetFilesListUrl(max_results_, page_token_, q_);
312 }
313
314 //======================== FilesListNextPageRequest =========================
315
FilesListNextPageRequest(RequestSender * sender,const FileListCallback & callback)316 FilesListNextPageRequest::FilesListNextPageRequest(
317 RequestSender* sender,
318 const FileListCallback& callback)
319 : DriveApiDataRequest<FileList>(sender, callback) {
320 DCHECK(!callback.is_null());
321 }
322
~FilesListNextPageRequest()323 FilesListNextPageRequest::~FilesListNextPageRequest() {
324 }
325
GetURLInternal() const326 GURL FilesListNextPageRequest::GetURLInternal() const {
327 return next_link_;
328 }
329
330 //============================ FilesDeleteRequest =============================
331
FilesDeleteRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const EntryActionCallback & callback)332 FilesDeleteRequest::FilesDeleteRequest(
333 RequestSender* sender,
334 const DriveApiUrlGenerator& url_generator,
335 const EntryActionCallback& callback)
336 : EntryActionRequest(sender, callback),
337 url_generator_(url_generator) {
338 DCHECK(!callback.is_null());
339 }
340
~FilesDeleteRequest()341 FilesDeleteRequest::~FilesDeleteRequest() {}
342
GetRequestType() const343 net::URLFetcher::RequestType FilesDeleteRequest::GetRequestType() const {
344 return net::URLFetcher::DELETE_REQUEST;
345 }
346
GetURL() const347 GURL FilesDeleteRequest::GetURL() const {
348 return url_generator_.GetFilesDeleteUrl(file_id_);
349 }
350
GetExtraRequestHeaders() const351 std::vector<std::string> FilesDeleteRequest::GetExtraRequestHeaders() const {
352 std::vector<std::string> headers(
353 EntryActionRequest::GetExtraRequestHeaders());
354 headers.push_back(util::GenerateIfMatchHeader(etag_));
355 return headers;
356 }
357
358 //============================ FilesTrashRequest =============================
359
FilesTrashRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const FileResourceCallback & callback)360 FilesTrashRequest::FilesTrashRequest(
361 RequestSender* sender,
362 const DriveApiUrlGenerator& url_generator,
363 const FileResourceCallback& callback)
364 : DriveApiDataRequest<FileResource>(sender, callback),
365 url_generator_(url_generator) {
366 DCHECK(!callback.is_null());
367 }
368
~FilesTrashRequest()369 FilesTrashRequest::~FilesTrashRequest() {}
370
GetRequestType() const371 net::URLFetcher::RequestType FilesTrashRequest::GetRequestType() const {
372 return net::URLFetcher::POST;
373 }
374
GetURLInternal() const375 GURL FilesTrashRequest::GetURLInternal() const {
376 return url_generator_.GetFilesTrashUrl(file_id_);
377 }
378
379 //============================== AboutGetRequest =============================
380
AboutGetRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const AboutResourceCallback & callback)381 AboutGetRequest::AboutGetRequest(
382 RequestSender* sender,
383 const DriveApiUrlGenerator& url_generator,
384 const AboutResourceCallback& callback)
385 : DriveApiDataRequest<AboutResource>(sender, callback),
386 url_generator_(url_generator) {
387 DCHECK(!callback.is_null());
388 }
389
~AboutGetRequest()390 AboutGetRequest::~AboutGetRequest() {}
391
GetURLInternal() const392 GURL AboutGetRequest::GetURLInternal() const {
393 return url_generator_.GetAboutGetUrl();
394 }
395
396 //============================ ChangesListRequest ===========================
397
ChangesListRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const ChangeListCallback & callback)398 ChangesListRequest::ChangesListRequest(
399 RequestSender* sender,
400 const DriveApiUrlGenerator& url_generator,
401 const ChangeListCallback& callback)
402 : DriveApiDataRequest<ChangeList>(sender, callback),
403 url_generator_(url_generator),
404 include_deleted_(true),
405 max_results_(100),
406 start_change_id_(0) {
407 DCHECK(!callback.is_null());
408 }
409
~ChangesListRequest()410 ChangesListRequest::~ChangesListRequest() {}
411
GetURLInternal() const412 GURL ChangesListRequest::GetURLInternal() const {
413 return url_generator_.GetChangesListUrl(
414 include_deleted_, max_results_, page_token_, start_change_id_);
415 }
416
417 //======================== ChangesListNextPageRequest =========================
418
ChangesListNextPageRequest(RequestSender * sender,const ChangeListCallback & callback)419 ChangesListNextPageRequest::ChangesListNextPageRequest(
420 RequestSender* sender,
421 const ChangeListCallback& callback)
422 : DriveApiDataRequest<ChangeList>(sender, callback) {
423 DCHECK(!callback.is_null());
424 }
425
~ChangesListNextPageRequest()426 ChangesListNextPageRequest::~ChangesListNextPageRequest() {
427 }
428
GetURLInternal() const429 GURL ChangesListNextPageRequest::GetURLInternal() const {
430 return next_link_;
431 }
432
433 //============================== AppsListRequest ===========================
434
AppsListRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,bool use_internal_endpoint,const AppListCallback & callback)435 AppsListRequest::AppsListRequest(
436 RequestSender* sender,
437 const DriveApiUrlGenerator& url_generator,
438 bool use_internal_endpoint,
439 const AppListCallback& callback)
440 : DriveApiDataRequest<AppList>(sender, callback),
441 url_generator_(url_generator),
442 use_internal_endpoint_(use_internal_endpoint) {
443 DCHECK(!callback.is_null());
444 }
445
~AppsListRequest()446 AppsListRequest::~AppsListRequest() {}
447
GetURLInternal() const448 GURL AppsListRequest::GetURLInternal() const {
449 return url_generator_.GetAppsListUrl(use_internal_endpoint_);
450 }
451
452 //============================== AppsDeleteRequest ===========================
453
AppsDeleteRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const EntryActionCallback & callback)454 AppsDeleteRequest::AppsDeleteRequest(RequestSender* sender,
455 const DriveApiUrlGenerator& url_generator,
456 const EntryActionCallback& callback)
457 : EntryActionRequest(sender, callback),
458 url_generator_(url_generator) {
459 DCHECK(!callback.is_null());
460 }
461
~AppsDeleteRequest()462 AppsDeleteRequest::~AppsDeleteRequest() {}
463
GetRequestType() const464 net::URLFetcher::RequestType AppsDeleteRequest::GetRequestType() const {
465 return net::URLFetcher::DELETE_REQUEST;
466 }
467
GetURL() const468 GURL AppsDeleteRequest::GetURL() const {
469 return url_generator_.GetAppsDeleteUrl(app_id_);
470 }
471
472 //========================== ChildrenInsertRequest ============================
473
ChildrenInsertRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const EntryActionCallback & callback)474 ChildrenInsertRequest::ChildrenInsertRequest(
475 RequestSender* sender,
476 const DriveApiUrlGenerator& url_generator,
477 const EntryActionCallback& callback)
478 : EntryActionRequest(sender, callback),
479 url_generator_(url_generator) {
480 DCHECK(!callback.is_null());
481 }
482
~ChildrenInsertRequest()483 ChildrenInsertRequest::~ChildrenInsertRequest() {}
484
GetRequestType() const485 net::URLFetcher::RequestType ChildrenInsertRequest::GetRequestType() const {
486 return net::URLFetcher::POST;
487 }
488
GetURL() const489 GURL ChildrenInsertRequest::GetURL() const {
490 return url_generator_.GetChildrenInsertUrl(folder_id_);
491 }
492
GetContentData(std::string * upload_content_type,std::string * upload_content)493 bool ChildrenInsertRequest::GetContentData(std::string* upload_content_type,
494 std::string* upload_content) {
495 *upload_content_type = kContentTypeApplicationJson;
496
497 base::DictionaryValue root;
498 root.SetString("id", id_);
499
500 base::JSONWriter::Write(&root, upload_content);
501 DVLOG(1) << "InsertResource data: " << *upload_content_type << ", ["
502 << *upload_content << "]";
503 return true;
504 }
505
506 //========================== ChildrenDeleteRequest ============================
507
ChildrenDeleteRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const EntryActionCallback & callback)508 ChildrenDeleteRequest::ChildrenDeleteRequest(
509 RequestSender* sender,
510 const DriveApiUrlGenerator& url_generator,
511 const EntryActionCallback& callback)
512 : EntryActionRequest(sender, callback),
513 url_generator_(url_generator) {
514 DCHECK(!callback.is_null());
515 }
516
~ChildrenDeleteRequest()517 ChildrenDeleteRequest::~ChildrenDeleteRequest() {}
518
GetRequestType() const519 net::URLFetcher::RequestType ChildrenDeleteRequest::GetRequestType() const {
520 return net::URLFetcher::DELETE_REQUEST;
521 }
522
GetURL() const523 GURL ChildrenDeleteRequest::GetURL() const {
524 return url_generator_.GetChildrenDeleteUrl(child_id_, folder_id_);
525 }
526
527 //======================= InitiateUploadNewFileRequest =======================
528
InitiateUploadNewFileRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const std::string & content_type,int64 content_length,const std::string & parent_resource_id,const std::string & title,const InitiateUploadCallback & callback)529 InitiateUploadNewFileRequest::InitiateUploadNewFileRequest(
530 RequestSender* sender,
531 const DriveApiUrlGenerator& url_generator,
532 const std::string& content_type,
533 int64 content_length,
534 const std::string& parent_resource_id,
535 const std::string& title,
536 const InitiateUploadCallback& callback)
537 : InitiateUploadRequestBase(sender,
538 callback,
539 content_type,
540 content_length),
541 url_generator_(url_generator),
542 parent_resource_id_(parent_resource_id),
543 title_(title) {
544 }
545
~InitiateUploadNewFileRequest()546 InitiateUploadNewFileRequest::~InitiateUploadNewFileRequest() {}
547
GetURL() const548 GURL InitiateUploadNewFileRequest::GetURL() const {
549 return url_generator_.GetInitiateUploadNewFileUrl(!modified_date_.is_null());
550 }
551
552 net::URLFetcher::RequestType
GetRequestType() const553 InitiateUploadNewFileRequest::GetRequestType() const {
554 return net::URLFetcher::POST;
555 }
556
GetContentData(std::string * upload_content_type,std::string * upload_content)557 bool InitiateUploadNewFileRequest::GetContentData(
558 std::string* upload_content_type,
559 std::string* upload_content) {
560 *upload_content_type = kContentTypeApplicationJson;
561
562 base::DictionaryValue root;
563 root.SetString("title", title_);
564
565 // Fill parent link.
566 scoped_ptr<base::ListValue> parents(new base::ListValue);
567 parents->Append(CreateParentValue(parent_resource_id_).release());
568 root.Set("parents", parents.release());
569
570 if (!modified_date_.is_null())
571 root.SetString("modifiedDate", util::FormatTimeAsString(modified_date_));
572
573 if (!last_viewed_by_me_date_.is_null()) {
574 root.SetString("lastViewedByMeDate",
575 util::FormatTimeAsString(last_viewed_by_me_date_));
576 }
577
578 base::JSONWriter::Write(&root, upload_content);
579
580 DVLOG(1) << "InitiateUploadNewFile data: " << *upload_content_type << ", ["
581 << *upload_content << "]";
582 return true;
583 }
584
585 //===================== InitiateUploadExistingFileRequest ====================
586
InitiateUploadExistingFileRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const std::string & content_type,int64 content_length,const std::string & resource_id,const std::string & etag,const InitiateUploadCallback & callback)587 InitiateUploadExistingFileRequest::InitiateUploadExistingFileRequest(
588 RequestSender* sender,
589 const DriveApiUrlGenerator& url_generator,
590 const std::string& content_type,
591 int64 content_length,
592 const std::string& resource_id,
593 const std::string& etag,
594 const InitiateUploadCallback& callback)
595 : InitiateUploadRequestBase(sender,
596 callback,
597 content_type,
598 content_length),
599 url_generator_(url_generator),
600 resource_id_(resource_id),
601 etag_(etag) {
602 }
603
~InitiateUploadExistingFileRequest()604 InitiateUploadExistingFileRequest::~InitiateUploadExistingFileRequest() {}
605
GetURL() const606 GURL InitiateUploadExistingFileRequest::GetURL() const {
607 return url_generator_.GetInitiateUploadExistingFileUrl(
608 resource_id_, !modified_date_.is_null());
609 }
610
611 net::URLFetcher::RequestType
GetRequestType() const612 InitiateUploadExistingFileRequest::GetRequestType() const {
613 return net::URLFetcher::PUT;
614 }
615
616 std::vector<std::string>
GetExtraRequestHeaders() const617 InitiateUploadExistingFileRequest::GetExtraRequestHeaders() const {
618 std::vector<std::string> headers(
619 InitiateUploadRequestBase::GetExtraRequestHeaders());
620 headers.push_back(util::GenerateIfMatchHeader(etag_));
621 return headers;
622 }
623
GetContentData(std::string * upload_content_type,std::string * upload_content)624 bool InitiateUploadExistingFileRequest::GetContentData(
625 std::string* upload_content_type,
626 std::string* upload_content) {
627 base::DictionaryValue root;
628 if (!parent_resource_id_.empty()) {
629 scoped_ptr<base::ListValue> parents(new base::ListValue);
630 parents->Append(CreateParentValue(parent_resource_id_).release());
631 root.Set("parents", parents.release());
632 }
633
634 if (!title_.empty())
635 root.SetString("title", title_);
636
637 if (!modified_date_.is_null())
638 root.SetString("modifiedDate", util::FormatTimeAsString(modified_date_));
639
640 if (!last_viewed_by_me_date_.is_null()) {
641 root.SetString("lastViewedByMeDate",
642 util::FormatTimeAsString(last_viewed_by_me_date_));
643 }
644
645 if (root.empty())
646 return false;
647
648 *upload_content_type = kContentTypeApplicationJson;
649 base::JSONWriter::Write(&root, upload_content);
650 DVLOG(1) << "InitiateUploadExistingFile data: " << *upload_content_type
651 << ", [" << *upload_content << "]";
652 return true;
653 }
654
655 //============================ ResumeUploadRequest ===========================
656
ResumeUploadRequest(RequestSender * sender,const GURL & upload_location,int64 start_position,int64 end_position,int64 content_length,const std::string & content_type,const base::FilePath & local_file_path,const UploadRangeCallback & callback,const ProgressCallback & progress_callback)657 ResumeUploadRequest::ResumeUploadRequest(
658 RequestSender* sender,
659 const GURL& upload_location,
660 int64 start_position,
661 int64 end_position,
662 int64 content_length,
663 const std::string& content_type,
664 const base::FilePath& local_file_path,
665 const UploadRangeCallback& callback,
666 const ProgressCallback& progress_callback)
667 : ResumeUploadRequestBase(sender,
668 upload_location,
669 start_position,
670 end_position,
671 content_length,
672 content_type,
673 local_file_path),
674 callback_(callback),
675 progress_callback_(progress_callback) {
676 DCHECK(!callback_.is_null());
677 }
678
~ResumeUploadRequest()679 ResumeUploadRequest::~ResumeUploadRequest() {}
680
OnRangeRequestComplete(const UploadRangeResponse & response,scoped_ptr<base::Value> value)681 void ResumeUploadRequest::OnRangeRequestComplete(
682 const UploadRangeResponse& response,
683 scoped_ptr<base::Value> value) {
684 DCHECK(CalledOnValidThread());
685 ParseFileResourceWithUploadRangeAndRun(callback_, response, value.Pass());
686 }
687
OnURLFetchUploadProgress(const net::URLFetcher * source,int64 current,int64 total)688 void ResumeUploadRequest::OnURLFetchUploadProgress(
689 const net::URLFetcher* source, int64 current, int64 total) {
690 if (!progress_callback_.is_null())
691 progress_callback_.Run(current, total);
692 }
693
694 //========================== GetUploadStatusRequest ==========================
695
GetUploadStatusRequest(RequestSender * sender,const GURL & upload_url,int64 content_length,const UploadRangeCallback & callback)696 GetUploadStatusRequest::GetUploadStatusRequest(
697 RequestSender* sender,
698 const GURL& upload_url,
699 int64 content_length,
700 const UploadRangeCallback& callback)
701 : GetUploadStatusRequestBase(sender,
702 upload_url,
703 content_length),
704 callback_(callback) {
705 DCHECK(!callback.is_null());
706 }
707
~GetUploadStatusRequest()708 GetUploadStatusRequest::~GetUploadStatusRequest() {}
709
OnRangeRequestComplete(const UploadRangeResponse & response,scoped_ptr<base::Value> value)710 void GetUploadStatusRequest::OnRangeRequestComplete(
711 const UploadRangeResponse& response,
712 scoped_ptr<base::Value> value) {
713 DCHECK(CalledOnValidThread());
714 ParseFileResourceWithUploadRangeAndRun(callback_, response, value.Pass());
715 }
716
717 //========================== DownloadFileRequest ==========================
718
DownloadFileRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const std::string & resource_id,const base::FilePath & output_file_path,const DownloadActionCallback & download_action_callback,const GetContentCallback & get_content_callback,const ProgressCallback & progress_callback)719 DownloadFileRequest::DownloadFileRequest(
720 RequestSender* sender,
721 const DriveApiUrlGenerator& url_generator,
722 const std::string& resource_id,
723 const base::FilePath& output_file_path,
724 const DownloadActionCallback& download_action_callback,
725 const GetContentCallback& get_content_callback,
726 const ProgressCallback& progress_callback)
727 : DownloadFileRequestBase(
728 sender,
729 download_action_callback,
730 get_content_callback,
731 progress_callback,
732 url_generator.GenerateDownloadFileUrl(resource_id),
733 output_file_path) {
734 }
735
~DownloadFileRequest()736 DownloadFileRequest::~DownloadFileRequest() {
737 }
738
739 //========================== PermissionsInsertRequest ==========================
740
PermissionsInsertRequest(RequestSender * sender,const DriveApiUrlGenerator & url_generator,const EntryActionCallback & callback)741 PermissionsInsertRequest::PermissionsInsertRequest(
742 RequestSender* sender,
743 const DriveApiUrlGenerator& url_generator,
744 const EntryActionCallback& callback)
745 : EntryActionRequest(sender, callback),
746 url_generator_(url_generator),
747 type_(PERMISSION_TYPE_USER),
748 role_(PERMISSION_ROLE_READER) {
749 }
750
~PermissionsInsertRequest()751 PermissionsInsertRequest::~PermissionsInsertRequest() {
752 }
753
GetURL() const754 GURL PermissionsInsertRequest::GetURL() const {
755 return url_generator_.GetPermissionsInsertUrl(id_);
756 }
757
758 net::URLFetcher::RequestType
GetRequestType() const759 PermissionsInsertRequest::GetRequestType() const {
760 return net::URLFetcher::POST;
761 }
762
GetContentData(std::string * upload_content_type,std::string * upload_content)763 bool PermissionsInsertRequest::GetContentData(std::string* upload_content_type,
764 std::string* upload_content) {
765 *upload_content_type = kContentTypeApplicationJson;
766
767 base::DictionaryValue root;
768 switch (type_) {
769 case PERMISSION_TYPE_ANYONE:
770 root.SetString("type", "anyone");
771 break;
772 case PERMISSION_TYPE_DOMAIN:
773 root.SetString("type", "domain");
774 break;
775 case PERMISSION_TYPE_GROUP:
776 root.SetString("type", "group");
777 break;
778 case PERMISSION_TYPE_USER:
779 root.SetString("type", "user");
780 break;
781 }
782 switch (role_) {
783 case PERMISSION_ROLE_OWNER:
784 root.SetString("role", "owner");
785 break;
786 case PERMISSION_ROLE_READER:
787 root.SetString("role", "reader");
788 break;
789 case PERMISSION_ROLE_WRITER:
790 root.SetString("role", "writer");
791 break;
792 case PERMISSION_ROLE_COMMENTER:
793 root.SetString("role", "reader");
794 {
795 base::ListValue* list = new base::ListValue;
796 list->AppendString("commenter");
797 root.Set("additionalRoles", list);
798 }
799 break;
800 }
801 root.SetString("value", value_);
802 base::JSONWriter::Write(&root, upload_content);
803 return true;
804 }
805
806 } // namespace drive
807 } // namespace google_apis
808