Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(159)

Side by Side Diff: chrome/browser/chromeos/gdata/gdata_operations.cc

Issue 10749015: gdrive: Get JSON feeds parsing off the UI thread (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: sync Created 8 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/chromeos/gdata/gdata_operations.h" 5 #include "chrome/browser/chromeos/gdata/gdata_operations.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/json/json_reader.h" 8 #include "base/json/json_reader.h"
9 #include "base/metrics/histogram.h" 9 #include "base/metrics/histogram.h"
10 #include "base/string_number_conversions.h" 10 #include "base/string_number_conversions.h"
(...skipping 141 matching lines...) Expand 10 before | Expand all | Expand 10 after
152 // URL for fetching documents in a particular directory. 152 // URL for fetching documents in a particular directory.
153 GURL FormatDocumentListURL(const std::string& directory_resource_id) { 153 GURL FormatDocumentListURL(const std::string& directory_resource_id) {
154 if (directory_resource_id.empty()) 154 if (directory_resource_id.empty())
155 return GURL(kGetDocumentListURLForAllDocuments); 155 return GURL(kGetDocumentListURLForAllDocuments);
156 156
157 return GURL(base::StringPrintf(kGetDocumentListURLForDirectoryFormat, 157 return GURL(base::StringPrintf(kGetDocumentListURLForDirectoryFormat,
158 net::EscapePath( 158 net::EscapePath(
159 directory_resource_id).c_str())); 159 directory_resource_id).c_str()));
160 } 160 }
161 161
162 // Parse JSON string to base::Value object.
163 void ParseJsonOnBlockingPool(const std::string& data,
164 scoped_ptr<base::Value>* value) {
165 DCHECK(!BrowserThread::CurrentlyOn(BrowserThread::UI));
166
167 int error_code = -1;
168 std::string error_message;
169 value->reset(base::JSONReader::ReadAndReturnError(data,
170 base::JSON_PARSE_RFC,
171 &error_code,
172 &error_message));
173
174 if (!value->get()) {
175 LOG(ERROR) << "Error while parsing entry response: "
176 << error_message
177 << ", code: "
178 << error_code
179 << ", data:\n"
180 << data;
181 }
182 }
183
162 } // namespace 184 } // namespace
163 185
164 namespace gdata { 186 namespace gdata {
165 187
166 //================================ AuthOperation =============================== 188 //================================ AuthOperation ===============================
167 189
168 AuthOperation::AuthOperation(GDataOperationRegistry* registry, 190 AuthOperation::AuthOperation(GDataOperationRegistry* registry,
169 Profile* profile, 191 Profile* profile,
170 const AuthStatusCallback& callback, 192 const AuthStatusCallback& callback,
171 const std::string& refresh_token) 193 const std::string& refresh_token)
(...skipping 268 matching lines...) Expand 10 before | Expand all | Expand 10 after
440 void EntryActionOperation::RunCallbackOnPrematureFailure(GDataErrorCode code) { 462 void EntryActionOperation::RunCallbackOnPrematureFailure(GDataErrorCode code) {
441 if (!callback_.is_null()) 463 if (!callback_.is_null())
442 callback_.Run(code, document_url_); 464 callback_.Run(code, document_url_);
443 } 465 }
444 466
445 //============================== GetDataOperation ============================== 467 //============================== GetDataOperation ==============================
446 468
447 GetDataOperation::GetDataOperation(GDataOperationRegistry* registry, 469 GetDataOperation::GetDataOperation(GDataOperationRegistry* registry,
448 Profile* profile, 470 Profile* profile,
449 const GetDataCallback& callback) 471 const GetDataCallback& callback)
450 : UrlFetchOperationBase(registry, profile), callback_(callback) { 472 : UrlFetchOperationBase(registry, profile),
473 callback_(callback),
474 weak_ptr_factory_(this) {
451 } 475 }
452 476
453 GetDataOperation::~GetDataOperation() {} 477 GetDataOperation::~GetDataOperation() {}
454 478
455 bool GetDataOperation::ProcessURLFetchResults(const net::URLFetcher* source) { 479 bool GetDataOperation::ProcessURLFetchResults(const net::URLFetcher* source) {
456 std::string data; 480 std::string data;
457 source->GetResponseAsString(&data); 481 source->GetResponseAsString(&data);
458 scoped_ptr<base::Value> root_value; 482 GDataErrorCode fetch_error_code = GetErrorCode(source);
459 GDataErrorCode code = GetErrorCode(source); 483 bool ret = false;
460 484
461 switch (code) { 485 switch (fetch_error_code) {
462 case HTTP_SUCCESS: 486 case HTTP_SUCCESS:
463 case HTTP_CREATED: { 487 case HTTP_CREATED:
464 root_value.reset(ParseResponse(data)); 488 ret = ParseResponse(fetch_error_code, data);
465 if (!root_value.get())
466 code = GDATA_PARSE_ERROR;
467
468 break; 489 break;
469 }
470 default: 490 default:
491 RunCallback(fetch_error_code, scoped_ptr<base::Value>());
471 break; 492 break;
472 } 493 }
473 494
474 if (!callback_.is_null()) 495 return ret;
475 callback_.Run(code, root_value.Pass());
476 return root_value.get() != NULL;
477 } 496 }
478 497
479 void GetDataOperation::RunCallbackOnPrematureFailure(GDataErrorCode code) { 498 void GetDataOperation::RunCallbackOnPrematureFailure(
499 GDataErrorCode fetch_error_code) {
480 if (!callback_.is_null()) { 500 if (!callback_.is_null()) {
481 scoped_ptr<base::Value> root_value; 501 scoped_ptr<base::Value> root_value;
482 callback_.Run(code, root_value.Pass()); 502 callback_.Run(fetch_error_code, root_value.Pass());
483 } 503 }
484 } 504 }
485 505
486 base::Value* GetDataOperation::ParseResponse(const std::string& data) { 506 bool GetDataOperation::ParseResponse(GDataErrorCode fetch_error_code,
487 int error_code = -1; 507 const std::string& data) {
488 std::string error_message; 508 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
489 scoped_ptr<base::Value> root_value(base::JSONReader::ReadAndReturnError( 509
490 data, base::JSON_PARSE_RFC, &error_code, &error_message)); 510 // Uses this hack to avoid deep-copy of json object because json might be so
491 if (!root_value.get()) { 511 // big.
492 LOG(ERROR) << "Error while parsing entry response: " 512 // This pointer of scped_ptr is to ensure a deletion of the parsed json value
493 << error_message 513 // object, even when OnDataParsed() is not called.
494 << ", code: " 514 scoped_ptr<base::Value>* parsed_value = new scoped_ptr<base::Value>();
495 << error_code 515
496 << ", data:\n" 516 return BrowserThread::PostBlockingPoolTaskAndReply(
497 << data; 517 FROM_HERE,
498 return NULL; 518 base::Bind(&ParseJsonOnBlockingPool,
499 } 519 data,
500 return root_value.release(); 520 parsed_value),
521 base::Bind(&GetDataOperation::OnDataParsed,
522 weak_ptr_factory_.GetWeakPtr(),
523 fetch_error_code,
524 base::Owned(parsed_value)));
525 }
526
527 void GetDataOperation::RunCallback(GDataErrorCode fetch_error_code,
528 scoped_ptr<base::Value> value) {
529 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
530 if (!callback_.is_null())
531 callback_.Run(fetch_error_code, value.Pass());
532 }
533
534 void GetDataOperation::OnDataParsed(GDataErrorCode fetch_error_code,
535 scoped_ptr<base::Value>* value) {
536 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
537 if (!value->get())
538 fetch_error_code = GDATA_PARSE_ERROR;
539
540 // The ownership of the parsed json object is transfered to RunCallBack(),
541 // keeping the ownership of the |value| here.
542 RunCallback(fetch_error_code, value->Pass());
543 DCHECK(!value->get());
544
545 // |value| will be deleted after return beause it is base::Owned()'d.
501 } 546 }
502 547
503 //============================ GetDocumentsOperation =========================== 548 //============================ GetDocumentsOperation ===========================
504 549
505 GetDocumentsOperation::GetDocumentsOperation( 550 GetDocumentsOperation::GetDocumentsOperation(
506 GDataOperationRegistry* registry, 551 GDataOperationRegistry* registry,
507 Profile* profile, 552 Profile* profile,
508 int start_changestamp, 553 int start_changestamp,
509 const std::string& search_string, 554 const std::string& search_string,
510 const std::string& directory_resource_id, 555 const std::string& directory_resource_id,
(...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after
851 xml_writer.WriteElement("docs:authorizedApp", app_id_); 896 xml_writer.WriteElement("docs:authorizedApp", app_id_);
852 897
853 xml_writer.EndElement(); // Ends "entry" element. 898 xml_writer.EndElement(); // Ends "entry" element.
854 xml_writer.StopWriting(); 899 xml_writer.StopWriting();
855 upload_content->assign(xml_writer.GetWrittenString()); 900 upload_content->assign(xml_writer.GetWrittenString());
856 DVLOG(1) << "AuthorizeAppOperation data: " << *upload_content_type << ", [" 901 DVLOG(1) << "AuthorizeAppOperation data: " << *upload_content_type << ", ["
857 << *upload_content << "]"; 902 << *upload_content << "]";
858 return true; 903 return true;
859 } 904 }
860 905
861 base::Value* AuthorizeAppsOperation::ParseResponse(const std::string& data) { 906 bool AuthorizeAppsOperation::ParseResponse(GDataErrorCode code,
907 const std::string& data) {
862 // Parse entry XML. 908 // Parse entry XML.
863 XmlReader xml_reader; 909 XmlReader xml_reader;
864 scoped_ptr<DocumentEntry> entry; 910 scoped_ptr<DocumentEntry> entry;
865 if (xml_reader.Load(data)) { 911 if (xml_reader.Load(data)) {
866 while (xml_reader.Read()) { 912 while (xml_reader.Read()) {
867 if (xml_reader.NodeName() == DocumentEntry::GetEntryNodeName()) { 913 if (xml_reader.NodeName() == DocumentEntry::GetEntryNodeName()) {
868 entry.reset(DocumentEntry::CreateFromXml(&xml_reader)); 914 entry.reset(DocumentEntry::CreateFromXml(&xml_reader));
869 break; 915 break;
870 } 916 }
871 } 917 }
872 } 918 }
873 919
874 // From the response, we create a list of the links returned, since those 920 // From the response, we create a list of the links returned, since those
875 // are the only things we are interested in. 921 // are the only things we are interested in.
876 scoped_ptr<base::ListValue> link_list(new ListValue); 922 scoped_ptr<base::ListValue> link_list(new ListValue);
877 const ScopedVector<Link>& feed_links = entry->links(); 923 const ScopedVector<Link>& feed_links = entry->links();
878 for (ScopedVector<Link>::const_iterator iter = feed_links.begin(); 924 for (ScopedVector<Link>::const_iterator iter = feed_links.begin();
879 iter != feed_links.end(); ++iter) { 925 iter != feed_links.end(); ++iter) {
880 if ((*iter)->type() == Link::OPEN_WITH) { 926 if ((*iter)->type() == Link::OPEN_WITH) {
881 base::DictionaryValue* link = new DictionaryValue; 927 base::DictionaryValue* link = new DictionaryValue;
882 link->SetString(std::string("href"), (*iter)->href().spec()); 928 link->SetString(std::string("href"), (*iter)->href().spec());
883 link->SetString(std::string("mime_type"), (*iter)->mime_type()); 929 link->SetString(std::string("mime_type"), (*iter)->mime_type());
884 link->SetString(std::string("title"), (*iter)->title()); 930 link->SetString(std::string("title"), (*iter)->title());
885 link->SetString(std::string("app_id"), (*iter)->app_id()); 931 link->SetString(std::string("app_id"), (*iter)->app_id());
886 link_list->Append(link); 932 link_list->Append(link);
887 } 933 }
888 } 934 }
889 935
890 return link_list.release(); 936 RunCallback(code, link_list.PassAs<base::Value>());
937
938 return true;
891 } 939 }
892 940
893 GURL AuthorizeAppsOperation::GetURL() const { 941 GURL AuthorizeAppsOperation::GetURL() const {
894 return document_url_; 942 return document_url_;
895 } 943 }
896 944
897 //======================= AddResourceToDirectoryOperation ====================== 945 //======================= AddResourceToDirectoryOperation ======================
898 946
899 AddResourceToDirectoryOperation::AddResourceToDirectoryOperation( 947 AddResourceToDirectoryOperation::AddResourceToDirectoryOperation(
900 GDataOperationRegistry* registry, 948 GDataOperationRegistry* registry,
(...skipping 324 matching lines...) Expand 10 before | Expand all | Expand 10 after
1225 return true; 1273 return true;
1226 } 1274 }
1227 1275
1228 void ResumeUploadOperation::OnURLFetchUploadProgress( 1276 void ResumeUploadOperation::OnURLFetchUploadProgress(
1229 const net::URLFetcher* source, int64 current, int64 total) { 1277 const net::URLFetcher* source, int64 current, int64 total) {
1230 // Adjust the progress values according to the range currently uploaded. 1278 // Adjust the progress values according to the range currently uploaded.
1231 NotifyProgress(params_.start_range + current, params_.content_length); 1279 NotifyProgress(params_.start_range + current, params_.content_length);
1232 } 1280 }
1233 1281
1234 } // namespace gdata 1282 } // namespace gdata
OLDNEW
« no previous file with comments | « chrome/browser/chromeos/gdata/gdata_operations.h ('k') | chrome/browser/chromeos/gdata/gdata_operations_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698