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

Side by Side Diff: content/browser/service_worker/service_worker_storage.cc

Issue 380093002: Update installed ServiceWorkers. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: rebase Created 6 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 2013 The Chromium Authors. All rights reserved. 1 // Copyright 2013 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 "content/browser/service_worker/service_worker_storage.h" 5 #include "content/browser/service_worker/service_worker_storage.h"
6 6
7 #include <string> 7 #include <string>
8 8
9 #include "base/bind_helpers.h" 9 #include "base/bind_helpers.h"
10 #include "base/file_util.h" 10 #include "base/file_util.h"
11 #include "base/message_loop/message_loop.h" 11 #include "base/message_loop/message_loop.h"
12 #include "base/sequenced_task_runner.h" 12 #include "base/sequenced_task_runner.h"
13 #include "base/task_runner_util.h" 13 #include "base/task_runner_util.h"
14 #include "content/browser/service_worker/service_worker_context_core.h" 14 #include "content/browser/service_worker/service_worker_context_core.h"
15 #include "content/browser/service_worker/service_worker_disk_cache.h" 15 #include "content/browser/service_worker/service_worker_disk_cache.h"
16 #include "content/browser/service_worker/service_worker_info.h" 16 #include "content/browser/service_worker/service_worker_info.h"
17 #include "content/browser/service_worker/service_worker_metrics.h" 17 #include "content/browser/service_worker/service_worker_metrics.h"
18 #include "content/browser/service_worker/service_worker_registration.h" 18 #include "content/browser/service_worker/service_worker_registration.h"
19 #include "content/browser/service_worker/service_worker_utils.h" 19 #include "content/browser/service_worker/service_worker_utils.h"
20 #include "content/browser/service_worker/service_worker_version.h" 20 #include "content/browser/service_worker/service_worker_version.h"
21 #include "content/common/service_worker/service_worker_types.h" 21 #include "content/common/service_worker/service_worker_types.h"
22 #include "content/public/browser/browser_thread.h" 22 #include "content/public/browser/browser_thread.h"
23 #include "net/base/completion_callback.h" 23 #include "net/base/completion_callback.h"
24 #include "net/base/io_buffer.h"
24 #include "net/base/net_errors.h" 25 #include "net/base/net_errors.h"
25 #include "webkit/browser/quota/quota_manager_proxy.h" 26 #include "webkit/browser/quota/quota_manager_proxy.h"
26 27
27 namespace content { 28 namespace content {
28 29
29 namespace { 30 namespace {
30 31
31 void RunSoon(const tracked_objects::Location& from_here, 32 void RunSoon(const tracked_objects::Location& from_here,
32 const base::Closure& closure) { 33 const base::Closure& closure) {
33 base::MessageLoop::current()->PostTask(from_here, closure); 34 base::MessageLoop::current()->PostTask(from_here, closure);
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
65 return SERVICE_WORKER_OK; 66 return SERVICE_WORKER_OK;
66 case ServiceWorkerDatabase::STATUS_ERROR_NOT_FOUND: 67 case ServiceWorkerDatabase::STATUS_ERROR_NOT_FOUND:
67 return SERVICE_WORKER_ERROR_NOT_FOUND; 68 return SERVICE_WORKER_ERROR_NOT_FOUND;
68 case ServiceWorkerDatabase::STATUS_ERROR_MAX: 69 case ServiceWorkerDatabase::STATUS_ERROR_MAX:
69 NOTREACHED(); 70 NOTREACHED();
70 default: 71 default:
71 return SERVICE_WORKER_ERROR_FAILED; 72 return SERVICE_WORKER_ERROR_FAILED;
72 } 73 }
73 } 74 }
74 75
76 class ResponseComparer : public base::RefCounted<ResponseComparer> {
77 public:
78 ResponseComparer(
79 base::WeakPtr<ServiceWorkerStorage> owner,
80 scoped_ptr<ServiceWorkerResponseReader> lhs,
81 scoped_ptr<ServiceWorkerResponseReader> rhs,
82 const ServiceWorkerStorage::CompareCallback& callback)
83 : owner_(owner),
84 completion_callback_(callback),
85 lhs_reader_(lhs.release()),
86 rhs_reader_(rhs.release()),
87 completion_count_(0),
88 previous_result_(0) {
89 }
90
91 void Start();
92
93 private:
94 friend class base::RefCounted<ResponseComparer>;
95
96 static const int kBufferSize = 16 * 1024;
97
98 ~ResponseComparer() {}
99 void ReadInfos();
100 void OnReadInfoComplete(int result);
101 void ReadSomeData();
102 void OnReadDataComplete(int result);
103
104 base::WeakPtr<ServiceWorkerStorage> owner_;
105 ServiceWorkerStorage::CompareCallback completion_callback_;
106 scoped_ptr<ServiceWorkerResponseReader> lhs_reader_;
107 scoped_refptr<HttpResponseInfoIOBuffer> lhs_info_;
108 scoped_refptr<net::IOBuffer> lhs_buffer_;
109 scoped_ptr<ServiceWorkerResponseReader> rhs_reader_;
110 scoped_refptr<HttpResponseInfoIOBuffer> rhs_info_;
111 scoped_refptr<net::IOBuffer> rhs_buffer_;
112 int completion_count_;
113 int previous_result_;
114 DISALLOW_COPY_AND_ASSIGN(ResponseComparer);
115 };
116
117 void ResponseComparer::Start() {
118 lhs_buffer_ = new net::IOBuffer(kBufferSize);
119 lhs_info_ = new HttpResponseInfoIOBuffer();
120 rhs_buffer_ = new net::IOBuffer(kBufferSize);
121 rhs_info_ = new HttpResponseInfoIOBuffer();
122
123 ReadInfos();
124 }
125
126 void ResponseComparer::ReadInfos() {
127 lhs_reader_->ReadInfo(
128 lhs_info_,
129 base::Bind(&ResponseComparer::OnReadInfoComplete,
130 this));
131 rhs_reader_->ReadInfo(
132 rhs_info_,
133 base::Bind(&ResponseComparer::OnReadInfoComplete,
134 this));
135 }
136
137 void ResponseComparer::OnReadInfoComplete(int result) {
138 if (completion_callback_.is_null() || !owner_)
139 return;
140 if (result < 0) {
141 completion_callback_.Run(SERVICE_WORKER_ERROR_FAILED, false);
142 completion_callback_.Reset();
143 return;
144 }
145 if (++completion_count_ != 2)
146 return;
147
148 if (lhs_info_->response_data_size != rhs_info_->response_data_size) {
149 completion_callback_.Run(SERVICE_WORKER_OK, false);
150 return;
151 }
152 ReadSomeData();
153 }
154
155 void ResponseComparer::ReadSomeData() {
156 completion_count_ = 0;
157 lhs_reader_->ReadData(
158 lhs_buffer_,
159 kBufferSize,
160 base::Bind(&ResponseComparer::OnReadDataComplete, this));
161 rhs_reader_->ReadData(
162 rhs_buffer_,
163 kBufferSize,
164 base::Bind(&ResponseComparer::OnReadDataComplete, this));
165 }
166
167 void ResponseComparer::OnReadDataComplete(int result) {
168 if (completion_callback_.is_null() || !owner_)
169 return;
170 if (result < 0) {
171 completion_callback_.Run(SERVICE_WORKER_ERROR_FAILED, false);
172 completion_callback_.Reset();
173 return;
174 }
175 if (++completion_count_ != 2) {
176 previous_result_ = result;
177 return;
178 }
179
180 // TODO(michaeln): Probably shouldn't assume that the amounts read from
181 // each reader will always be the same. This would wrongly signal false
182 // in that case.
183 if (result != previous_result_) {
184 completion_callback_.Run(SERVICE_WORKER_OK, false);
185 return;
186 }
187
188 if (result == 0) {
189 completion_callback_.Run(SERVICE_WORKER_OK, true);
190 return;
191 }
192
193 int compare_result =
194 memcmp(lhs_buffer_->data(), rhs_buffer_->data(), result);
195 if (compare_result != 0) {
196 completion_callback_.Run(SERVICE_WORKER_OK, false);
197 return;
198 }
199
200 ReadSomeData();
201 }
202
75 } // namespace 203 } // namespace
76 204
77 ServiceWorkerStorage::InitialData::InitialData() 205 ServiceWorkerStorage::InitialData::InitialData()
78 : next_registration_id(kInvalidServiceWorkerRegistrationId), 206 : next_registration_id(kInvalidServiceWorkerRegistrationId),
79 next_version_id(kInvalidServiceWorkerVersionId), 207 next_version_id(kInvalidServiceWorkerVersionId),
80 next_resource_id(kInvalidServiceWorkerResourceId) { 208 next_resource_id(kInvalidServiceWorkerResourceId) {
81 } 209 }
82 210
83 ServiceWorkerStorage::InitialData::~InitialData() { 211 ServiceWorkerStorage::InitialData::~InitialData() {
84 } 212 }
(...skipping 299 matching lines...) Expand 10 before | Expand all | Expand 10 after
384 DCHECK_NE(kInvalidServiceWorkerResponseId, id); 512 DCHECK_NE(kInvalidServiceWorkerResponseId, id);
385 database_task_runner_->PostTask( 513 database_task_runner_->PostTask(
386 FROM_HERE, 514 FROM_HERE,
387 base::Bind(base::IgnoreResult( 515 base::Bind(base::IgnoreResult(
388 &ServiceWorkerDatabase::PurgeUncommittedResourceIds), 516 &ServiceWorkerDatabase::PurgeUncommittedResourceIds),
389 base::Unretained(database_.get()), 517 base::Unretained(database_.get()),
390 std::set<int64>(&id, &id + 1))); 518 std::set<int64>(&id, &id + 1)));
391 StartPurgingResources(std::vector<int64>(1, id)); 519 StartPurgingResources(std::vector<int64>(1, id));
392 } 520 }
393 521
522 void ServiceWorkerStorage::CompareScriptResources(
523 int64 lhs_id, int64 rhs_id,
524 const CompareCallback& callback) {
525 DCHECK(!callback.is_null());
526 scoped_refptr<ResponseComparer> comparer =
527 new ResponseComparer(weak_factory_.GetWeakPtr(),
528 CreateResponseReader(lhs_id),
529 CreateResponseReader(rhs_id),
530 callback);
531 comparer->Start(); // It deletes itself when done.
532 }
533
394 void ServiceWorkerStorage::DeleteAndStartOver(const StatusCallback& callback) { 534 void ServiceWorkerStorage::DeleteAndStartOver(const StatusCallback& callback) {
395 Disable(); 535 Disable();
396 536
397 // Delete the database on the database thread. 537 // Delete the database on the database thread.
398 PostTaskAndReplyWithResult( 538 PostTaskAndReplyWithResult(
399 database_task_runner_, 539 database_task_runner_,
400 FROM_HERE, 540 FROM_HERE,
401 base::Bind(&ServiceWorkerDatabase::DestroyDatabase, 541 base::Bind(&ServiceWorkerDatabase::DestroyDatabase,
402 base::Unretained(database_.get())), 542 base::Unretained(database_.get())),
403 base::Bind(&ServiceWorkerStorage::DidDeleteDatabase, 543 base::Bind(&ServiceWorkerStorage::DidDeleteDatabase,
(...skipping 349 matching lines...) Expand 10 before | Expand all | Expand 10 after
753 893
754 registration = new ServiceWorkerRegistration( 894 registration = new ServiceWorkerRegistration(
755 data.scope, data.script, data.registration_id, context_); 895 data.scope, data.script, data.registration_id, context_);
756 scoped_refptr<ServiceWorkerVersion> version = 896 scoped_refptr<ServiceWorkerVersion> version =
757 context_->GetLiveVersion(data.version_id); 897 context_->GetLiveVersion(data.version_id);
758 if (!version) { 898 if (!version) {
759 version = new ServiceWorkerVersion(registration, data.version_id, context_); 899 version = new ServiceWorkerVersion(registration, data.version_id, context_);
760 version->SetStatus(data.is_active ? 900 version->SetStatus(data.is_active ?
761 ServiceWorkerVersion::ACTIVATED : ServiceWorkerVersion::INSTALLED); 901 ServiceWorkerVersion::ACTIVATED : ServiceWorkerVersion::INSTALLED);
762 version->script_cache_map()->SetResources(resources); 902 version->script_cache_map()->SetResources(resources);
903
904 // TODO(michaeln): need to activate a waiting version that wasn't
905 // actrivated in an earlier session, maybe test for this condition
906 // (waitingversion and no activeversion) when navigating to a page?
763 } 907 }
764 908
765 if (version->status() == ServiceWorkerVersion::ACTIVATED) 909 if (version->status() == ServiceWorkerVersion::ACTIVATED)
766 registration->SetActiveVersion(version); 910 registration->SetActiveVersion(version);
767 else if (version->status() == ServiceWorkerVersion::INSTALLED) 911 else if (version->status() == ServiceWorkerVersion::INSTALLED)
768 registration->SetWaitingVersion(version); 912 registration->SetWaitingVersion(version);
769 else 913 else
770 NOTREACHED(); 914 NOTREACHED();
771 // TODO(michaeln): Hmmm, what if DeleteReg was invoked after 915
772 // the Find result we're returning here? NOTREACHED condition?
773 return registration; 916 return registration;
774 } 917 }
775 918
776 ServiceWorkerRegistration* 919 ServiceWorkerRegistration*
777 ServiceWorkerStorage::FindInstallingRegistrationForDocument( 920 ServiceWorkerStorage::FindInstallingRegistrationForDocument(
778 const GURL& document_url) { 921 const GURL& document_url) {
779 DCHECK(!document_url.has_ref()); 922 DCHECK(!document_url.has_ref());
780 923
781 LongestScopeMatcher matcher(document_url); 924 LongestScopeMatcher matcher(document_url);
782 ServiceWorkerRegistration* match = NULL; 925 ServiceWorkerRegistration* match = NULL;
(...skipping 391 matching lines...) Expand 10 before | Expand all | Expand 10 after
1174 // Give up the corruption recovery until the browser restarts. 1317 // Give up the corruption recovery until the browser restarts.
1175 LOG(ERROR) << "Failed to delete the diskcache."; 1318 LOG(ERROR) << "Failed to delete the diskcache.";
1176 callback.Run(SERVICE_WORKER_ERROR_FAILED); 1319 callback.Run(SERVICE_WORKER_ERROR_FAILED);
1177 return; 1320 return;
1178 } 1321 }
1179 DVLOG(1) << "Deleted ServiceWorkerDiskCache successfully."; 1322 DVLOG(1) << "Deleted ServiceWorkerDiskCache successfully.";
1180 callback.Run(SERVICE_WORKER_OK); 1323 callback.Run(SERVICE_WORKER_OK);
1181 } 1324 }
1182 1325
1183 } // namespace content 1326 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698