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

Side by Side Diff: chrome/browser/android/offline_pages/recent_tab_helper.cc

Issue 2655673005: RecentTabHelper won't accept overlapping requests from Downloads anymore. (Closed)
Patch Set: Minor changes from addressing dewittj@ comments. Created 3 years, 10 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
OLDNEW
1 // Copyright (c) 2016 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2016 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/android/offline_pages/recent_tab_helper.h" 5 #include "chrome/browser/android/offline_pages/recent_tab_helper.h"
6 6
7 #include <queue> 7 #include <queue>
8 #include <vector> 8 #include <vector>
9 9
10 #include "base/bind.h" 10 #include "base/bind.h"
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
49 bool GetTabId(content::WebContents* web_contents, int* tab_id) override { 49 bool GetTabId(content::WebContents* web_contents, int* tab_id) override {
50 return offline_pages::OfflinePageUtils::GetTabId(web_contents, tab_id); 50 return offline_pages::OfflinePageUtils::GetTabId(web_contents, tab_id);
51 } 51 }
52 }; 52 };
53 } // namespace 53 } // namespace
54 54
55 namespace offline_pages { 55 namespace offline_pages {
56 56
57 using PageQuality = SnapshotController::PageQuality; 57 using PageQuality = SnapshotController::PageQuality;
58 58
59 bool RecentTabHelper::SnapshotProgressInfo::IsForLastN() { 59 // Keeps client_id/request_id that will be used for the offline snapshot.
60 // A last_n snapshot always has an invalid request id. 60 struct RecentTabHelper::SnapshotProgressInfo {
61 return request_id == OfflinePageModel::kInvalidOfflineId; 61 public:
62 } 62 // For a downloads snapshot request, where the |request_id| is defined.
63 SnapshotProgressInfo(const ClientId& client_id, int64_t request_id)
64 : client_id(client_id), request_id(request_id) {}
65
66 // For a last_n snapshot request.
67 explicit SnapshotProgressInfo(const ClientId& client_id)
68 : client_id(client_id) {}
69
70 bool IsForLastN() { return client_id.name_space == kLastNNamespace; }
71
72 // The ClientID to go with the offline page.
73 ClientId client_id;
74
75 // Id of the suspended request in Background Offliner. Used to un-suspend
76 // the request if the capture of the current page was not possible (e.g.
77 // the user navigated to another page before current one was loaded).
78 // 0 if this is a "last_n" info.
79 int64_t request_id = OfflinePageModel::kInvalidOfflineId;
80
81 // Expected snapshot quality should the saving succeed. This value is only
82 // valid for successfully saved snapshots.
83 SnapshotController::PageQuality expected_page_quality =
84 SnapshotController::PageQuality::POOR;
85 };
63 86
64 RecentTabHelper::RecentTabHelper(content::WebContents* web_contents) 87 RecentTabHelper::RecentTabHelper(content::WebContents* web_contents)
65 : content::WebContentsObserver(web_contents), 88 : content::WebContentsObserver(web_contents),
66 delegate_(new DefaultDelegate()), 89 delegate_(new DefaultDelegate()),
67 weak_ptr_factory_(this) { 90 weak_ptr_factory_(this) {
68 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); 91 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
69 } 92 }
70 93
71 RecentTabHelper::~RecentTabHelper() { 94 RecentTabHelper::~RecentTabHelper() {
72 } 95 }
73 96
74 void RecentTabHelper::SetDelegate( 97 void RecentTabHelper::SetDelegate(
75 std::unique_ptr<RecentTabHelper::Delegate> delegate) { 98 std::unique_ptr<RecentTabHelper::Delegate> delegate) {
76 DCHECK(delegate); 99 DCHECK(delegate);
77 delegate_ = std::move(delegate); 100 delegate_ = std::move(delegate);
78 } 101 }
79 102
80 void RecentTabHelper::ObserveAndDownloadCurrentPage( 103 void RecentTabHelper::ObserveAndDownloadCurrentPage(
81 const ClientId& client_id, int64_t request_id) { 104 const ClientId& client_id, int64_t request_id) {
105 // Note: as this implementation only supports one client namespace, enforce
106 // that the call is from Downloads.
107 DCHECK_EQ(kDownloadNamespace, client_id.name_space);
82 auto new_downloads_snapshot_info = 108 auto new_downloads_snapshot_info =
83 base::MakeUnique<SnapshotProgressInfo>(client_id, request_id); 109 base::MakeUnique<SnapshotProgressInfo>(client_id, request_id);
84 110
85 // If this tab helper is not enabled, immediately give the job back to 111 // If this tab helper is not enabled, immediately give the job back to
86 // RequestCoordinator. 112 // RequestCoordinator.
87 if (!EnsureInitialized()) { 113 if (!EnsureInitialized()) {
88 ReportDownloadStatusToRequestCoordinator(new_downloads_snapshot_info.get()); 114 ReportDownloadStatusToRequestCoordinator(new_downloads_snapshot_info.get(),
115 false);
89 return; 116 return;
90 } 117 }
91 118
92 // TODO(carlosk): This is a good moment check if a snapshot is currently being 119 // If there is an ongoing snapshot request, completely ignore this one and
93 // generated. This would allow the early cancellation of this request (without 120 // cancel the Background Offliner request.
94 // incurring in scheduling a background download). 121 // TODO(carlosk): it might be better to make the decision to schedule or not
122 // the background request here. See https://crbug.com/686165.
123 // TODO(carlosk): there is an edge case that happens when the ongoing request
124 // was automatically and transparently scheduled by a navigation event and
125 // this call happens due to the user pressing the download button. The user's
126 // request to download the page will be immediately dismissed. See
127 // https://crbug.com/686283.
128 if (downloads_ongoing_snapshot_info_) {
129 ReportDownloadStatusToRequestCoordinator(new_downloads_snapshot_info.get(),
130 true);
131 return;
132 }
95 133
96 // Stores the new snapshot info. 134 // Stores the new snapshot info.
97 downloads_latest_snapshot_info_ = std::move(new_downloads_snapshot_info); 135 downloads_ongoing_snapshot_info_ = std::move(new_downloads_snapshot_info);
98 136
99 // If the page is not yet ready for a snapshot return now as it will be 137 // If the page is not yet ready for a snapshot return now as it will be
100 // started later, once page loading advances. 138 // started later, once page loading advances.
101 if (PageQuality::POOR == snapshot_controller_->current_page_quality()) 139 if (PageQuality::POOR == snapshot_controller_->current_page_quality()) {
140 downloads_snapshot_on_hold_ = true;
102 return; 141 return;
142 }
103 143
104 // Otherwise start saving the snapshot now. 144 // Otherwise start saving the snapshot now.
105 SaveSnapshotForDownloads(); 145 SaveSnapshotForDownloads(false);
106 } 146 }
107 147
108 // Initialize lazily. It needs TabAndroid for initialization, which is also a 148 // Initialize lazily. It needs TabAndroid for initialization, which is also a
109 // TabHelper - so can't initialize in constructor because of uncertain order 149 // TabHelper - so can't initialize in constructor because of uncertain order
110 // of creation of TabHelpers. 150 // of creation of TabHelpers.
111 bool RecentTabHelper::EnsureInitialized() { 151 bool RecentTabHelper::EnsureInitialized() {
112 if (snapshot_controller_) // Initialized already. 152 if (snapshot_controller_) // Initialized already.
113 return snapshots_enabled_; 153 return snapshots_enabled_;
114 154
115 snapshot_controller_.reset( 155 snapshot_controller_.reset(
(...skipping 22 matching lines...) Expand all
138 void RecentTabHelper::DidFinishNavigation( 178 void RecentTabHelper::DidFinishNavigation(
139 content::NavigationHandle* navigation_handle) { 179 content::NavigationHandle* navigation_handle) {
140 if (!navigation_handle->IsInMainFrame() || 180 if (!navigation_handle->IsInMainFrame() ||
141 !navigation_handle->HasCommitted()) { 181 !navigation_handle->HasCommitted()) {
142 return; 182 return;
143 } 183 }
144 184
145 if (!EnsureInitialized()) 185 if (!EnsureInitialized())
146 return; 186 return;
147 187
148 // We navigated to a different page, lets report progress to Background 188 // If there is an ongoing downloads request, lets allow Background Offliner to
149 // Offliner. 189 // continue downloading this page.
150 if (downloads_latest_snapshot_info_) 190 if (downloads_ongoing_snapshot_info_) {
151 ReportDownloadStatusToRequestCoordinator( 191 ReportDownloadStatusToRequestCoordinator(
152 downloads_latest_snapshot_info_.get()); 192 downloads_ongoing_snapshot_info_.get(), false);
193 }
153 194
154 // Cancel any and all in flight snapshot tasks from the previous page. 195 // Cancel any and all in flight snapshot tasks from the previous page.
155 weak_ptr_factory_.InvalidateWeakPtrs(); 196 CancelInFlightSnapshots();
156 downloads_latest_snapshot_info_.reset(); 197 downloads_snapshot_on_hold_ = false;
157 last_n_ongoing_snapshot_info_.reset();
158 198
159 // New navigation, new snapshot session. 199 // New navigation, new snapshot session.
160 snapshot_url_ = web_contents()->GetLastCommittedURL(); 200 snapshot_url_ = web_contents()->GetLastCommittedURL();
161 201
162 // Always reset so that posted tasks get canceled. 202 // Always reset so that posted tasks get canceled.
163 snapshot_controller_->Reset(); 203 snapshot_controller_->Reset();
164 204
165 // Check for conditions that would cause us not to snapshot. 205 // Check for conditions that would cause us not to snapshot.
166 bool can_save = !navigation_handle->IsErrorPage() && 206 bool can_save = !navigation_handle->IsErrorPage() &&
167 OfflinePageModel::CanSaveURL(snapshot_url_) && 207 OfflinePageModel::CanSaveURL(snapshot_url_) &&
(...skipping 12 matching lines...) Expand all
180 EnsureInitialized(); 220 EnsureInitialized();
181 snapshot_controller_->DocumentAvailableInMainFrame(); 221 snapshot_controller_->DocumentAvailableInMainFrame();
182 } 222 }
183 223
184 void RecentTabHelper::DocumentOnLoadCompletedInMainFrame() { 224 void RecentTabHelper::DocumentOnLoadCompletedInMainFrame() {
185 EnsureInitialized(); 225 EnsureInitialized();
186 snapshot_controller_->DocumentOnLoadCompletedInMainFrame(); 226 snapshot_controller_->DocumentOnLoadCompletedInMainFrame();
187 } 227 }
188 228
189 void RecentTabHelper::WebContentsDestroyed() { 229 void RecentTabHelper::WebContentsDestroyed() {
190 // WebContents (and maybe Tab) is destroyed, report status to Offliner. 230 // If there is an ongoing downloads request, lets allow Background Offliner to
191 if (downloads_latest_snapshot_info_) 231 // continue downloading this page.
232 if (downloads_ongoing_snapshot_info_)
192 ReportDownloadStatusToRequestCoordinator( 233 ReportDownloadStatusToRequestCoordinator(
193 downloads_latest_snapshot_info_.get()); 234 downloads_ongoing_snapshot_info_.get(), false);
194 // And cancel any ongoing snapshots. 235 // And cancel any ongoing snapshots.
195 weak_ptr_factory_.InvalidateWeakPtrs(); 236 CancelInFlightSnapshots();
196 } 237 }
197 238
198 // TODO(carlosk): this method is also called when the tab is being closed, when 239 // TODO(carlosk): this method is also called when the tab is being closed, when
199 // saving a snapshot is probably useless (low probability of the user undoing 240 // saving a snapshot is probably useless (low probability of the user undoing
200 // the close). We should detect that and avoid the saving. 241 // the close). We should detect that and avoid the saving.
201 void RecentTabHelper::WasHidden() { 242 void RecentTabHelper::WasHidden() {
202 if (!IsOffliningRecentPagesEnabled()) 243 if (!IsOffliningRecentPagesEnabled())
203 return; 244 return;
204 245
205 // Return immediately if last_n is not listening to tab hidden events or if a 246 // Return immediately if last_n is not listening to tab hidden events or if a
206 // last_n snapshot is currently being saved. 247 // last_n snapshot is currently being saved.
207 if (!last_n_listen_to_tab_hidden_ || last_n_ongoing_snapshot_info_) 248 if (!last_n_listen_to_tab_hidden_ || last_n_ongoing_snapshot_info_)
208 return; 249 return;
209 250
210 // Do not save if page quality is too low or if we already have a snapshot 251 // Do not save if page quality is too low or if we already have a snapshot
211 // with the current quality level. 252 // with the current quality level.
212 // Note: we assume page quality for a page can only increase. 253 // Note: we assume page quality for a page can only increase.
213 PageQuality current_quality = snapshot_controller_->current_page_quality(); 254 PageQuality current_quality = snapshot_controller_->current_page_quality();
214 if (current_quality == PageQuality::POOR || 255 if (current_quality == PageQuality::POOR ||
215 current_quality == last_n_latest_saved_quality_) { 256 current_quality == last_n_latest_saved_quality_) {
216 return; 257 return;
217 } 258 }
218 259
219 last_n_ongoing_snapshot_info_ = 260 last_n_ongoing_snapshot_info_ =
220 base::MakeUnique<SnapshotProgressInfo>(GetRecentPagesClientId()); 261 base::MakeUnique<SnapshotProgressInfo>(GetRecentPagesClientId());
262 DCHECK(last_n_ongoing_snapshot_info_->IsForLastN());
221 DCHECK(snapshots_enabled_); 263 DCHECK(snapshots_enabled_);
222 // Remove previously captured pages for this tab. 264 // Remove previously captured pages for this tab.
223 page_model_->GetOfflineIdsForClientId( 265 page_model_->GetOfflineIdsForClientId(
224 GetRecentPagesClientId(), 266 GetRecentPagesClientId(),
225 base::Bind(&RecentTabHelper::ContinueSnapshotWithIdsToPurge, 267 base::Bind(&RecentTabHelper::ContinueSnapshotWithIdsToPurge,
226 weak_ptr_factory_.GetWeakPtr(), 268 weak_ptr_factory_.GetWeakPtr(),
227 last_n_ongoing_snapshot_info_.get())); 269 last_n_ongoing_snapshot_info_.get()));
228 } 270 }
229 271
230 // TODO(carlosk): rename this to RequestSnapshot and make it return a bool 272 // TODO(carlosk): rename this to RequestSnapshot and make it return a bool
231 // representing the acceptance of the snapshot request. 273 // representing the acceptance of the snapshot request.
232 void RecentTabHelper::StartSnapshot() { 274 void RecentTabHelper::StartSnapshot() {
233 DCHECK_NE(PageQuality::POOR, snapshot_controller_->current_page_quality()); 275 DCHECK_NE(PageQuality::POOR, snapshot_controller_->current_page_quality());
234 276
235 // This is a navigation based snapshot request so check that snapshots are 277 // As long as snapshots are enabled for this tab, there are two situations
236 // both enabled and there is a downloads request for one. 278 // that allow for a navigation event to start a snapshot:
237 // TODO(carlosk): This is a good moment to add the check for an ongoing 279 // 1) There is a request on hold waiting for the page to be minimally loaded.
238 // snapshot that could trigger the early cancellation of this request. 280 if (snapshots_enabled_ && downloads_snapshot_on_hold_) {
239 if (snapshots_enabled_ && downloads_latest_snapshot_info_) 281 downloads_snapshot_on_hold_ = false;
240 SaveSnapshotForDownloads(); 282 SaveSnapshotForDownloads(false);
241 else 283 return;
242 snapshot_controller_->PendingSnapshotCompleted(); 284 }
285
286 // 2) There's no ongoing snapshot and a previous one was saved with lower
287 // expected quality than what would be possible now.
288 if (snapshots_enabled_ &&
289 (!downloads_ongoing_snapshot_info_ &&
290 downloads_latest_saved_snapshot_info_ &&
291 downloads_latest_saved_snapshot_info_->expected_page_quality <
292 snapshot_controller_->current_page_quality())) {
293 SaveSnapshotForDownloads(true);
294 return;
295 }
296
297 // Notify the controller that a snapshot was not started.
298 snapshot_controller_->PendingSnapshotCompleted();
243 } 299 }
244 300
245 // TODO(carlosk): There is still the possibility of overlapping snapshots with 301 void RecentTabHelper::SaveSnapshotForDownloads(bool replace_latest) {
246 // some combinations of calls to ObserveAndDownloadCurrentPage and
247 // StartSnapshot. It won't cause side effects beyond wasted resources and will
248 // be dealt with later.
249 void RecentTabHelper::SaveSnapshotForDownloads() {
250 DCHECK_NE(PageQuality::POOR, snapshot_controller_->current_page_quality()); 302 DCHECK_NE(PageQuality::POOR, snapshot_controller_->current_page_quality());
251 DCHECK(downloads_latest_snapshot_info_);
252 303
253 // Requests the deletion of a potentially existing previous snapshot of this 304 if (replace_latest) {
254 // page. 305 // Start by requesting the deletion of the existing previous snapshot of
255 std::vector<int64_t> ids{downloads_latest_snapshot_info_->request_id}; 306 // this page.
256 ContinueSnapshotWithIdsToPurge(downloads_latest_snapshot_info_.get(), ids); 307 DCHECK(downloads_latest_saved_snapshot_info_);
308 DCHECK(!downloads_ongoing_snapshot_info_);
309 downloads_ongoing_snapshot_info_ = base::MakeUnique<SnapshotProgressInfo>(
310 downloads_latest_saved_snapshot_info_->client_id,
311 downloads_latest_saved_snapshot_info_->request_id);
312 std::vector<int64_t> ids{downloads_latest_saved_snapshot_info_->request_id};
313 ContinueSnapshotWithIdsToPurge(downloads_ongoing_snapshot_info_.get(), ids);
314 } else {
315 // Otherwise go straight to saving the page.
316 DCHECK(downloads_ongoing_snapshot_info_);
317 ContinueSnapshotAfterPurge(downloads_ongoing_snapshot_info_.get(),
318 OfflinePageModel::DeletePageResult::SUCCESS);
319 }
257 } 320 }
258 321
259 // This is the 1st step of a sequence of async operations chained through 322 // This is the 1st step of a sequence of async operations chained through
260 // callbacks, mostly shared between last_n and downloads: 323 // callbacks, mostly shared between last_n and downloads:
261 // 1) Compute the set of old 'last_n' pages that have to be purged. 324 // 1) Compute the set of old 'last_n' pages that have to be purged.
262 // 2) Delete the pages found in the previous step. 325 // 2) Delete the pages found in the previous step.
263 // 3) Snapshot the current web contents. 326 // 3) Snapshot the current web contents.
264 // 4) Notify requesters about the final result of the operation. 327 // 4) Notify requesters about the final result of the operation.
265 // 328 //
266 // For last_n requests the sequence is started in 1); for downloads it starts in 329 // For last_n requests the sequence is always started in 1). For downloads it
267 // 2). Step 4) might be called anytime during the chain for early termination in 330 // starts in either 2) or 3). Step 4) might be called anytime during the chain
268 // case of errors. 331 // for early termination in case of errors.
269 void RecentTabHelper::ContinueSnapshotWithIdsToPurge( 332 void RecentTabHelper::ContinueSnapshotWithIdsToPurge(
270 SnapshotProgressInfo* snapshot_info, 333 SnapshotProgressInfo* snapshot_info,
271 const std::vector<int64_t>& page_ids) { 334 const std::vector<int64_t>& page_ids) {
272 DCHECK(snapshot_info); 335 DCHECK(snapshot_info);
273 336
274 page_model_->DeletePagesByOfflineId( 337 page_model_->DeletePagesByOfflineId(
275 page_ids, base::Bind(&RecentTabHelper::ContinueSnapshotAfterPurge, 338 page_ids, base::Bind(&RecentTabHelper::ContinueSnapshotAfterPurge,
276 weak_ptr_factory_.GetWeakPtr(), snapshot_info)); 339 weak_ptr_factory_.GetWeakPtr(), snapshot_info));
277 } 340 }
278 341
279 void RecentTabHelper::ContinueSnapshotAfterPurge( 342 void RecentTabHelper::ContinueSnapshotAfterPurge(
280 SnapshotProgressInfo* snapshot_info, 343 SnapshotProgressInfo* snapshot_info,
281 OfflinePageModel::DeletePageResult result) { 344 OfflinePageModel::DeletePageResult result) {
282 DCHECK_EQ(snapshot_url_, web_contents()->GetLastCommittedURL()); 345 DCHECK_EQ(snapshot_url_, web_contents()->GetLastCommittedURL());
283 if (result != OfflinePageModel::DeletePageResult::SUCCESS) { 346 if (result != OfflinePageModel::DeletePageResult::SUCCESS) {
284 ReportSnapshotCompleted(snapshot_info); 347 ReportSnapshotCompleted(snapshot_info, false);
285 return; 348 return;
286 } 349 }
287 350
288 snapshot_info->expected_page_quality = 351 snapshot_info->expected_page_quality =
289 snapshot_controller_->current_page_quality(); 352 snapshot_controller_->current_page_quality();
290 OfflinePageModel::SavePageParams save_page_params; 353 OfflinePageModel::SavePageParams save_page_params;
291 save_page_params.url = snapshot_url_; 354 save_page_params.url = snapshot_url_;
292 save_page_params.client_id = snapshot_info->client_id; 355 save_page_params.client_id = snapshot_info->client_id;
293 save_page_params.proposed_offline_id = snapshot_info->request_id; 356 save_page_params.proposed_offline_id = snapshot_info->request_id;
294 page_model_->SavePage( 357 page_model_->SavePage(
295 save_page_params, delegate_->CreatePageArchiver(web_contents()), 358 save_page_params, delegate_->CreatePageArchiver(web_contents()),
296 base::Bind(&RecentTabHelper::SavePageCallback, 359 base::Bind(&RecentTabHelper::SavePageCallback,
297 weak_ptr_factory_.GetWeakPtr(), snapshot_info)); 360 weak_ptr_factory_.GetWeakPtr(), snapshot_info));
298 } 361 }
299 362
300 void RecentTabHelper::SavePageCallback(SnapshotProgressInfo* snapshot_info, 363 void RecentTabHelper::SavePageCallback(SnapshotProgressInfo* snapshot_info,
301 OfflinePageModel::SavePageResult result, 364 OfflinePageModel::SavePageResult result,
302 int64_t offline_id) { 365 int64_t offline_id) {
303 DCHECK(snapshot_info->IsForLastN() || 366 DCHECK(snapshot_info->IsForLastN() ||
304 snapshot_info->request_id == offline_id); 367 snapshot_info->request_id == offline_id);
305 snapshot_info->page_snapshot_completed = (result == SavePageResult::SUCCESS); 368 ReportSnapshotCompleted(snapshot_info, result == SavePageResult::SUCCESS);
306 ReportSnapshotCompleted(snapshot_info);
307 } 369 }
308 370
309 // Note: this is the final step in the chain of callbacks and it's where the 371 // Note: this is the final step in the chain of callbacks and it's where the
310 // behavior is different depending on this being a last_n or downloads snapshot. 372 // behavior is different depending on this being a last_n or downloads snapshot.
311 void RecentTabHelper::ReportSnapshotCompleted( 373 void RecentTabHelper::ReportSnapshotCompleted(
312 SnapshotProgressInfo* snapshot_info) { 374 SnapshotProgressInfo* snapshot_info,
375 bool success) {
313 if (snapshot_info->IsForLastN()) { 376 if (snapshot_info->IsForLastN()) {
314 DCHECK_EQ(snapshot_info, last_n_ongoing_snapshot_info_.get()); 377 DCHECK_EQ(snapshot_info, last_n_ongoing_snapshot_info_.get());
315 if (snapshot_info->page_snapshot_completed) 378 if (success)
316 last_n_latest_saved_quality_ = snapshot_info->expected_page_quality; 379 last_n_latest_saved_quality_ = snapshot_info->expected_page_quality;
317 last_n_ongoing_snapshot_info_.reset(); 380 last_n_ongoing_snapshot_info_.reset();
318 return; 381 return;
319 } 382 }
320 383
384 DCHECK_EQ(snapshot_info, downloads_ongoing_snapshot_info_.get());
321 snapshot_controller_->PendingSnapshotCompleted(); 385 snapshot_controller_->PendingSnapshotCompleted();
322 // Tell RequestCoordinator how the request should be processed further. 386 // Tell RequestCoordinator how the request should be processed further.
323 ReportDownloadStatusToRequestCoordinator(snapshot_info); 387 ReportDownloadStatusToRequestCoordinator(snapshot_info, success);
388 if (success) {
389 downloads_latest_saved_snapshot_info_ =
390 std::move(downloads_ongoing_snapshot_info_);
391 } else {
392 downloads_ongoing_snapshot_info_.reset();
393 }
324 } 394 }
325 395
326 // Note: we cannot assume that snapshot_info == downloads_latest_snapshot_info_ 396 // Note: we cannot assume that snapshot_info == downloads_latest_snapshot_info_
327 // because further calls made to ObserveAndDownloadCurrentPage will replace 397 // because further calls made to ObserveAndDownloadCurrentPage will replace
328 // downloads_latest_snapshot_info_ with a new instance. 398 // downloads_latest_snapshot_info_ with a new instance.
329 void RecentTabHelper::ReportDownloadStatusToRequestCoordinator( 399 void RecentTabHelper::ReportDownloadStatusToRequestCoordinator(
330 SnapshotProgressInfo* snapshot_info) { 400 SnapshotProgressInfo* snapshot_info,
401 bool cancel_background_request) {
331 DCHECK(snapshot_info); 402 DCHECK(snapshot_info);
332 DCHECK(!snapshot_info->IsForLastN()); 403 DCHECK(!snapshot_info->IsForLastN());
333 404
334 RequestCoordinator* request_coordinator = 405 RequestCoordinator* request_coordinator =
335 RequestCoordinatorFactory::GetForBrowserContext( 406 RequestCoordinatorFactory::GetForBrowserContext(
336 web_contents()->GetBrowserContext()); 407 web_contents()->GetBrowserContext());
337 if (!request_coordinator) 408 if (!request_coordinator)
338 return; 409 return;
339 410
340 // It is OK to call these methods more then once, depending on 411 // It is OK to call these methods more then once, depending on
341 // number of snapshots attempted in this tab helper. If the request_id is not 412 // number of snapshots attempted in this tab helper. If the request_id is not
342 // in the list of RequestCoordinator, these calls have no effect. 413 // in the list of RequestCoordinator, these calls have no effect.
343 if (snapshot_info->page_snapshot_completed) 414 if (cancel_background_request)
344 request_coordinator->MarkRequestCompleted(snapshot_info->request_id); 415 request_coordinator->MarkRequestCompleted(snapshot_info->request_id);
345 else 416 else
346 request_coordinator->EnableForOffliner(snapshot_info->request_id, 417 request_coordinator->EnableForOffliner(snapshot_info->request_id,
347 snapshot_info->client_id); 418 snapshot_info->client_id);
348 } 419 }
349 420
350 ClientId RecentTabHelper::GetRecentPagesClientId() const { 421 ClientId RecentTabHelper::GetRecentPagesClientId() const {
351 return ClientId(kLastNNamespace, tab_id_); 422 return ClientId(kLastNNamespace, tab_id_);
352 } 423 }
353 424
425 void RecentTabHelper::CancelInFlightSnapshots() {
426 weak_ptr_factory_.InvalidateWeakPtrs();
427 downloads_ongoing_snapshot_info_.reset();
428 downloads_latest_saved_snapshot_info_.reset();
429 last_n_ongoing_snapshot_info_.reset();
430 }
431
354 } // namespace offline_pages 432 } // namespace offline_pages
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698