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

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

Issue 2322833002: Support serving offline page by offline ID (Closed)
Patch Set: Remove unused variable to fix trybot Created 4 years, 3 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 2016 The Chromium Authors. All rights reserved. 1 // Copyright 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/offline_page_request_job.h" 5 #include "chrome/browser/android/offline_pages/offline_page_request_job.h"
6 6
7 #include <string> 7 #include <string>
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/files/file_path.h" 10 #include "base/files/file_path.h"
11 #include "base/logging.h" 11 #include "base/logging.h"
12 #include "base/metrics/histogram_macros.h" 12 #include "base/metrics/histogram_macros.h"
13 #include "base/strings/string_number_conversions.h"
13 #include "base/strings/string_tokenizer.h" 14 #include "base/strings/string_tokenizer.h"
14 #include "base/strings/string_util.h" 15 #include "base/strings/string_util.h"
15 #include "base/threading/thread_task_runner_handle.h" 16 #include "base/threading/thread_task_runner_handle.h"
16 #include "chrome/browser/android/offline_pages/offline_page_model_factory.h" 17 #include "chrome/browser/android/offline_pages/offline_page_model_factory.h"
17 #include "chrome/browser/android/offline_pages/offline_page_tab_helper.h" 18 #include "chrome/browser/android/offline_pages/offline_page_tab_helper.h"
18 #include "chrome/browser/android/offline_pages/offline_page_utils.h" 19 #include "chrome/browser/android/offline_pages/offline_page_utils.h"
19 #include "chrome/browser/browser_process.h" 20 #include "chrome/browser/browser_process.h"
20 #include "chrome/browser/profiles/profile.h"
21 #include "chrome/browser/profiles/profile_manager.h" 21 #include "chrome/browser/profiles/profile_manager.h"
22 #include "components/offline_pages/offline_page_model.h" 22 #include "components/offline_pages/offline_page_model.h"
23 #include "components/previews/previews_experiments.h" 23 #include "components/previews/previews_experiments.h"
24 #include "content/public/browser/browser_thread.h" 24 #include "content/public/browser/browser_thread.h"
25 #include "content/public/browser/resource_request_info.h" 25 #include "content/public/browser/resource_request_info.h"
26 #include "content/public/browser/web_contents.h" 26 #include "content/public/browser/web_contents.h"
27 #include "content/public/common/resource_type.h" 27 #include "content/public/common/resource_type.h"
28 #include "net/base/network_change_notifier.h" 28 #include "net/base/network_change_notifier.h"
29 #include "net/http/http_request_headers.h" 29 #include "net/http/http_request_headers.h"
30 #include "net/nqe/network_quality_estimator.h" 30 #include "net/nqe/network_quality_estimator.h"
31 #include "net/url_request/url_request.h" 31 #include "net/url_request/url_request.h"
32 #include "net/url_request/url_request_context.h" 32 #include "net/url_request/url_request_context.h"
33 33
34 namespace offline_pages { 34 namespace offline_pages {
35 35
36 const char kLoadingOfflinePageHeader[] = "X-Chrome-offline"; 36 const char kOfflinePageHeader[] = "X-Chrome-offline";
37 const char kLoadingOfflinePageReason[] = "reason="; 37 const char kOfflinePageHeaderReasonKey[] = "reason";
38 const char kLoadingOfflinePageDueToNetError[] = "error"; 38 const char kOfflinePageHeaderReasonValueDueToNetError[] = "error";
39 const char kOfflinePageHeaderReasonValueFromDownload[] = "download";
40 const char kOfflinePageHeaderPersistKey[] = "persist";
41 const char kOfflinePageHeaderIDKey[] = "id";
39 42
40 namespace { 43 namespace {
41 44
42 enum class NetworkState { 45 enum class NetworkState {
43 // No network connection. 46 // No network connection.
44 DISCONNECTED_NETWORK, 47 DISCONNECTED_NETWORK,
45 // Prohibitively slow means that the NetworkQualityEstimator reported a 48 // Prohibitively slow means that the NetworkQualityEstimator reported a
46 // connection slow enough to warrant showing an offline page if available. 49 // connection slow enough to warrant showing an offline page if available.
47 PROHIBITIVELY_SLOW_NETWORK, 50 PROHIBITIVELY_SLOW_NETWORK,
48 // Network error received due to bad network, i.e. connected to a hotspot or 51 // Network error received due to bad network, i.e. connected to a hotspot or
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after
106 } 109 }
107 110
108 private: 111 private:
109 static bool GetTabId(content::WebContents* web_contents, int* tab_id) { 112 static bool GetTabId(content::WebContents* web_contents, int* tab_id) {
110 return OfflinePageUtils::GetTabId(web_contents, tab_id); 113 return OfflinePageUtils::GetTabId(web_contents, tab_id);
111 } 114 }
112 115
113 DISALLOW_COPY_AND_ASSIGN(DefaultDelegate); 116 DISALLOW_COPY_AND_ASSIGN(DefaultDelegate);
114 }; 117 };
115 118
116 // Returns true if custom offline header is present. 119 // Used to parse the extra request header string that defines offline page
117 // |reason| may be set with the reason to trigger the offline page loading. 120 // loading behaviors.
118 bool ParseOfflineHeader(net::URLRequest* request, std::string* reason) { 121 class OfflinePageHeader {
119 std::string value; 122 public:
120 if (!request->extra_request_headers().GetHeader(kLoadingOfflinePageHeader, 123 enum class Reason {
121 &value)) { 124 NET_ERROR,
122 return false; 125 DOWNLOAD,
126 UNKNOWN
127 };
128
129 explicit OfflinePageHeader(const std::string& header_string);
130 ~OfflinePageHeader() {}
131
132 bool successfully_parsed() const { return successfully_parsed_; }
133 bool need_to_persist() const { return need_to_persist_; }
134 Reason reason() const { return reason_; }
135 const std::string& id() const { return id_; }
136
137 private:
138 // True if the header is present and parsed successfully.
139 bool successfully_parsed_;
140 // Flag to indicate if the header should be persisted across session restore.
141 bool need_to_persist_;
142 // Describes the reason to load offline page.
143 Reason reason_;
144 // The offline ID of the page to load.
145 std::string id_;
146
147 DISALLOW_COPY_AND_ASSIGN(OfflinePageHeader);
148 };
149
150 OfflinePageHeader::OfflinePageHeader(const std::string& header_string)
151 : successfully_parsed_(false),
152 need_to_persist_(false),
153 reason_(Reason::UNKNOWN) {
154 // If the offline header is not present, treat it as not parsed successfully.
155 if (header_string.empty())
156 return;
157
158 base::StringTokenizer tokenizer(header_string, ", ");
159 while (tokenizer.GetNext()) {
160 std::string pair = tokenizer.token();
161 std::size_t pos = pair.find('=');
162 if (pos == std::string::npos)
163 return;
164 std::string key = base::ToLowerASCII(pair.substr(0, pos));
165 std::string value = base::ToLowerASCII(pair.substr(pos + 1));
166 if (key == kOfflinePageHeaderPersistKey) {
167 need_to_persist_ = (value == "1");
168 } else if (key == kOfflinePageHeaderReasonKey) {
169 if (value == kOfflinePageHeaderReasonValueDueToNetError)
170 reason_ = Reason::NET_ERROR;
171 else if (value == kOfflinePageHeaderReasonValueFromDownload)
172 reason_ = Reason::DOWNLOAD;
173 else
174 reason_ = Reason::UNKNOWN;
175 } else if (key == kOfflinePageHeaderIDKey) {
176 id_ = value;
177 }
123 } 178 }
124 179
125 // Currently we only support reason field. 180 successfully_parsed_ = true;
126 base::StringTokenizer tokenizer(value, ", ");
127 while (tokenizer.GetNext()) {
128 if (base::StartsWith(tokenizer.token(),
129 kLoadingOfflinePageReason,
130 base::CompareCase::INSENSITIVE_ASCII)) {
131 *reason = tokenizer.token().substr(
132 arraysize(kLoadingOfflinePageReason) - 1);
133 break;
134 }
135 }
136 return true;
137 } 181 }
138 182
139 bool IsNetworkProhibitivelySlow(net::URLRequest* request) { 183 bool IsNetworkProhibitivelySlow(net::URLRequest* request) {
140 // NetworkQualityEstimator only works when it is enabled. 184 // NetworkQualityEstimator only works when it is enabled.
141 if (!previews::IsOfflinePreviewsEnabled()) 185 if (!previews::IsOfflinePreviewsEnabled())
142 return false; 186 return false;
143 187
144 if (!request->context()) 188 if (!request->context())
145 return false; 189 return false;
146 190
147 net::NetworkQualityEstimator* network_quality_estimator = 191 net::NetworkQualityEstimator* network_quality_estimator =
148 request->context()->network_quality_estimator(); 192 request->context()->network_quality_estimator();
149 if (!network_quality_estimator) 193 if (!network_quality_estimator)
150 return false; 194 return false;
151 195
152 net::EffectiveConnectionType effective_connection_type = 196 net::EffectiveConnectionType effective_connection_type =
153 network_quality_estimator->GetEffectiveConnectionType(); 197 network_quality_estimator->GetEffectiveConnectionType();
154 return effective_connection_type >= net::EFFECTIVE_CONNECTION_TYPE_OFFLINE && 198 return effective_connection_type >= net::EFFECTIVE_CONNECTION_TYPE_OFFLINE &&
155 effective_connection_type <= net::EFFECTIVE_CONNECTION_TYPE_SLOW_2G; 199 effective_connection_type <= net::EFFECTIVE_CONNECTION_TYPE_SLOW_2G;
156 } 200 }
157 201
158 NetworkState GetNetworkState(net::URLRequest* request) { 202 NetworkState GetNetworkState(net::URLRequest* request) {
159 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); 203 DCHECK_CURRENTLY_ON(content::BrowserThread::IO);
160 204
161 std::string reason; 205 std::string offline_header_string;
162 bool has_offline_header = ParseOfflineHeader(request, &reason); 206 request->extra_request_headers().GetHeader(
163 if (has_offline_header && 207 kOfflinePageHeader, &offline_header_string);
164 base::EqualsCaseInsensitiveASCII(reason, 208 OfflinePageHeader offline_header(offline_header_string);
165 kLoadingOfflinePageDueToNetError)) { 209 if (offline_header.reason() == OfflinePageHeader::Reason::NET_ERROR)
166 return NetworkState::FLAKY_NETWORK; 210 return NetworkState::FLAKY_NETWORK;
167 }
168 211
169 if (net::NetworkChangeNotifier::IsOffline()) 212 if (net::NetworkChangeNotifier::IsOffline())
170 return NetworkState::DISCONNECTED_NETWORK; 213 return NetworkState::DISCONNECTED_NETWORK;
171 214
172 if (IsNetworkProhibitivelySlow(request)) 215 if (IsNetworkProhibitivelySlow(request))
173 return NetworkState::PROHIBITIVELY_SLOW_NETWORK; 216 return NetworkState::PROHIBITIVELY_SLOW_NETWORK;
174 217
175 // The presence of custom offline header will force to load an offline page 218 // If custom offline header is present, the offline page should be forced to
176 // even when network is connected. 219 // load even when the network is connected.
177 return has_offline_header ? NetworkState::FORCE_OFFLINE_ON_CONNECTED_NETWORK 220 return offline_header.successfully_parsed()
178 : NetworkState::CONNECTED_NETWORK; 221 ? NetworkState::FORCE_OFFLINE_ON_CONNECTED_NETWORK
222 : NetworkState::CONNECTED_NETWORK;
179 } 223 }
180 224
181 OfflinePageRequestJob::AggregatedRequestResult 225 OfflinePageRequestJob::AggregatedRequestResult
182 RequestResultToAggregatedRequestResult( 226 RequestResultToAggregatedRequestResult(
183 RequestResult request_result, NetworkState network_state) { 227 RequestResult request_result, NetworkState network_state) {
184 if (request_result == RequestResult::NO_TAB_ID) 228 if (request_result == RequestResult::NO_TAB_ID)
185 return OfflinePageRequestJob::AggregatedRequestResult::NO_TAB_ID; 229 return OfflinePageRequestJob::AggregatedRequestResult::NO_TAB_ID;
186 230
187 if (request_result == RequestResult::NO_WEB_CONTENTS) 231 if (request_result == RequestResult::NO_WEB_CONTENTS)
188 return OfflinePageRequestJob::AggregatedRequestResult::NO_WEB_CONTENTS; 232 return OfflinePageRequestJob::AggregatedRequestResult::NO_WEB_CONTENTS;
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
234 return OfflinePageRequestJob::AggregatedRequestResult:: 278 return OfflinePageRequestJob::AggregatedRequestResult::
235 AGGREGATED_REQUEST_RESULT_MAX; 279 AGGREGATED_REQUEST_RESULT_MAX;
236 } 280 }
237 281
238 void ReportRequestResult( 282 void ReportRequestResult(
239 RequestResult request_result, NetworkState network_state) { 283 RequestResult request_result, NetworkState network_state) {
240 OfflinePageRequestJob::ReportAggregatedRequestResult( 284 OfflinePageRequestJob::ReportAggregatedRequestResult(
241 RequestResultToAggregatedRequestResult(request_result, network_state)); 285 RequestResultToAggregatedRequestResult(request_result, network_state));
242 } 286 }
243 287
288 OfflinePageModel* GetOfflinePageModel(
289 content::ResourceRequestInfo::WebContentsGetter web_contents_getter) {
290 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
291
292 content::WebContents* web_contents = web_contents_getter.Run();
293 return web_contents ?
294 OfflinePageModelFactory::GetForBrowserContext(
295 web_contents->GetBrowserContext()) :
296 nullptr;
297 }
298
244 void NotifyOfflineFilePathOnIO(base::WeakPtr<OfflinePageRequestJob> job, 299 void NotifyOfflineFilePathOnIO(base::WeakPtr<OfflinePageRequestJob> job,
245 const base::FilePath& offline_file_path) { 300 const base::FilePath& offline_file_path) {
246 DCHECK_CURRENTLY_ON(content::BrowserThread::IO); 301 DCHECK_CURRENTLY_ON(content::BrowserThread::IO);
247 302
248 if (!job) 303 if (!job)
249 return; 304 return;
250 job->OnOfflineFilePathAvailable(offline_file_path); 305 job->OnOfflineFilePathAvailable(offline_file_path);
251 } 306 }
252 307
253 // Notifies OfflinePageRequestJob about the offline file path. Note that the 308 // Notifies OfflinePageRequestJob about the offline file path. Note that the
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
307 OfflinePageTabHelper::FromWebContents(web_contents); 362 OfflinePageTabHelper::FromWebContents(web_contents);
308 DCHECK(tab_helper); 363 DCHECK(tab_helper);
309 tab_helper->SetOfflinePage( 364 tab_helper->SetOfflinePage(
310 *offline_page, network_state == NetworkState::PROHIBITIVELY_SLOW_NETWORK); 365 *offline_page, network_state == NetworkState::PROHIBITIVELY_SLOW_NETWORK);
311 366
312 *offline_file_path = offline_page->file_path; 367 *offline_file_path = offline_page->file_path;
313 return RequestResult::OFFLINE_PAGE_SERVED; 368 return RequestResult::OFFLINE_PAGE_SERVED;
314 } 369 }
315 370
316 // Handles the result of finding an offline page. 371 // Handles the result of finding an offline page.
317 void SelectPageForOnlineURLDone( 372 void SucceededToFindOfflinePage(
318 NetworkState network_state, 373 NetworkState network_state,
319 base::WeakPtr<OfflinePageRequestJob> job, 374 base::WeakPtr<OfflinePageRequestJob> job,
320 content::ResourceRequestInfo::WebContentsGetter web_contents_getter, 375 content::ResourceRequestInfo::WebContentsGetter web_contents_getter,
321 const OfflinePageItem* offline_page) { 376 const OfflinePageItem* offline_page) {
322 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); 377 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
323 378
324 base::FilePath offline_file_path; 379 base::FilePath offline_file_path;
325 RequestResult request_result = AccessOfflineFile( 380 RequestResult request_result = AccessOfflineFile(
326 network_state, job, web_contents_getter, offline_page, 381 network_state, job, web_contents_getter, offline_page,
327 &offline_file_path); 382 &offline_file_path);
328 383
329 ReportRequestResult(request_result, network_state); 384 ReportRequestResult(request_result, network_state);
330 385
331 // NotifyOfflineFilePathOnUI should always be called regardless the failure 386 // NotifyOfflineFilePathOnUI should always be called regardless the failure
332 // result and empty file path such that OfflinePageRequestJob will be notified 387 // result and empty file path such that OfflinePageRequestJob will be notified
333 // on failure. 388 // on failure.
334 NotifyOfflineFilePathOnUI(job, offline_file_path); 389 NotifyOfflineFilePathOnUI(job, offline_file_path);
335 } 390 }
336 391
337 void FailedToSelectOfflinePage(base::WeakPtr<OfflinePageRequestJob> job) { 392 void FailedToFindOfflinePage(base::WeakPtr<OfflinePageRequestJob> job) {
338 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); 393 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
339 394
340 // Proceed with empty file path in order to notify the OfflinePageRequestJob 395 // Proceed with empty file path in order to notify the OfflinePageRequestJob
341 // about the failure. 396 // about the failure.
342 base::FilePath empty_file_path; 397 base::FilePath empty_file_path;
343 NotifyOfflineFilePathOnUI(job, empty_file_path); 398 NotifyOfflineFilePathOnUI(job, empty_file_path);
344 } 399 }
345 400
346 // Tries to find the offline page to serve for |online_url|. 401 // Tries to find the offline page to serve for |online_url|.
347 void SelectOfflinePage( 402 void SelectPageForOnlineURL(
348 const GURL& online_url, 403 const GURL& online_url,
349 NetworkState network_state, 404 NetworkState network_state,
350 void* profile_id,
351 content::ResourceRequestInfo::WebContentsGetter web_contents_getter, 405 content::ResourceRequestInfo::WebContentsGetter web_contents_getter,
352 OfflinePageRequestJob::Delegate::TabIdGetter tab_id_getter, 406 OfflinePageRequestJob::Delegate::TabIdGetter tab_id_getter,
353 base::WeakPtr<OfflinePageRequestJob> job) { 407 base::WeakPtr<OfflinePageRequestJob> job) {
354 DCHECK_CURRENTLY_ON(content::BrowserThread::UI); 408 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
355 409
356 // |profile_id| needs to be checked with ProfileManager::IsValidProfile
357 // before using it.
358 if (!g_browser_process->profile_manager()->IsValidProfile(profile_id)) {
359 FailedToSelectOfflinePage(job);
360 return;
361 }
362 Profile* profile = reinterpret_cast<Profile*>(profile_id);
363
364 content::WebContents* web_contents = web_contents_getter.Run(); 410 content::WebContents* web_contents = web_contents_getter.Run();
365 if (!web_contents){ 411 if (!web_contents){
366 ReportRequestResult(RequestResult::NO_WEB_CONTENTS, network_state); 412 ReportRequestResult(RequestResult::NO_WEB_CONTENTS, network_state);
367 FailedToSelectOfflinePage(job); 413 FailedToFindOfflinePage(job);
368 return; 414 return;
369 } 415 }
370 int tab_id; 416 int tab_id;
371 if (!tab_id_getter.Run(web_contents, &tab_id)) { 417 if (!tab_id_getter.Run(web_contents, &tab_id)) {
372 ReportRequestResult(RequestResult::NO_TAB_ID, network_state); 418 ReportRequestResult(RequestResult::NO_TAB_ID, network_state);
373 FailedToSelectOfflinePage(job); 419 FailedToFindOfflinePage(job);
374 return; 420 return;
375 } 421 }
376 422
377 OfflinePageUtils::SelectPageForOnlineURL( 423 OfflinePageUtils::SelectPageForOnlineURL(
378 profile, 424 web_contents->GetBrowserContext(),
379 online_url, 425 online_url,
380 tab_id, 426 tab_id,
381 base::Bind(&SelectPageForOnlineURLDone, 427 base::Bind(&SucceededToFindOfflinePage,
382 network_state, 428 network_state,
383 job, 429 job,
384 web_contents_getter)); 430 web_contents_getter));
385 } 431 }
386 432
433 void FindPageWithOfflineIDDone(
434 const GURL& online_url,
435 NetworkState network_state,
436 content::ResourceRequestInfo::WebContentsGetter web_contents_getter,
437 OfflinePageRequestJob::Delegate::TabIdGetter tab_id_getter,
438 base::WeakPtr<OfflinePageRequestJob> job,
439 const OfflinePageItem* offline_page) {
440 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
441
442 // If the found offline page does not has same URL as the request URL, fall
443 // back to find the offline page based on the URL.
444 if (!offline_page || offline_page->url != online_url) {
445 SelectPageForOnlineURL(
446 online_url, network_state, web_contents_getter, tab_id_getter, job);
447 return;
448 }
449
450 SucceededToFindOfflinePage(
451 network_state, job, web_contents_getter, offline_page);
452 }
453
454 // Tries to find an offline page associated with |offline_id|.
455 void FindPageWithOfflineID(
456 const GURL& online_url,
457 int64_t offline_id,
458 NetworkState network_state,
459 content::ResourceRequestInfo::WebContentsGetter web_contents_getter,
460 OfflinePageRequestJob::Delegate::TabIdGetter tab_id_getter,
461 base::WeakPtr<OfflinePageRequestJob> job) {
462 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
463
464 OfflinePageModel* offline_page_model =
465 GetOfflinePageModel(web_contents_getter);
466 if (!offline_page_model) {
467 FailedToFindOfflinePage(job);
468 return;
469 }
470
471 offline_page_model->GetPageByOfflineId(
472 offline_id,
473 base::Bind(&FindPageWithOfflineIDDone,
474 online_url,
475 network_state,
476 web_contents_getter,
477 tab_id_getter,
478 job));
479 }
480
481 // Tries to find the offline page to serve for |online_url|.
482 void SelectPage(
483 const GURL& online_url,
484 const std::string& offline_header_string,
485 NetworkState network_state,
486 content::ResourceRequestInfo::WebContentsGetter web_contents_getter,
487 OfflinePageRequestJob::Delegate::TabIdGetter tab_id_getter,
488 base::WeakPtr<OfflinePageRequestJob> job) {
489 DCHECK_CURRENTLY_ON(content::BrowserThread::UI);
490
491 OfflinePageHeader offline_header(offline_header_string);
492
493 // If an offline ID is present in the offline header, try to load that
494 // particular version.
495 if (!offline_header.id().empty()) {
496 // if the id string cannot be converted to int64 id, fall through to
497 // select page via online URL.
498 int64_t offline_id;
499 if (base::StringToInt64(offline_header.id(), &offline_id)) {
500 FindPageWithOfflineID(online_url, offline_id, network_state,
501 web_contents_getter, tab_id_getter, job);
502 return;
503 }
504 }
505
506 SelectPageForOnlineURL(online_url, network_state, web_contents_getter,
507 tab_id_getter, job);
508 }
509
387 } // namespace 510 } // namespace
388 511
389 // static 512 // static
390 void OfflinePageRequestJob::ReportAggregatedRequestResult( 513 void OfflinePageRequestJob::ReportAggregatedRequestResult(
391 AggregatedRequestResult result) { 514 AggregatedRequestResult result) {
392 UMA_HISTOGRAM_ENUMERATION("OfflinePages.AggregatedRequestResult", 515 UMA_HISTOGRAM_ENUMERATION("OfflinePages.AggregatedRequestResult",
393 static_cast<int>(result), 516 static_cast<int>(result),
394 static_cast<int>(AggregatedRequestResult::AGGREGATED_REQUEST_RESULT_MAX)); 517 static_cast<int>(AggregatedRequestResult::AGGREGATED_REQUEST_RESULT_MAX));
395 } 518 }
396 519
397 // static 520 // static
398 OfflinePageRequestJob* OfflinePageRequestJob::Create( 521 OfflinePageRequestJob* OfflinePageRequestJob::Create(
399 void* profile_id,
400 net::URLRequest* request, 522 net::URLRequest* request,
401 net::NetworkDelegate* network_delegate) { 523 net::NetworkDelegate* network_delegate) {
402 const content::ResourceRequestInfo* resource_request_info = 524 const content::ResourceRequestInfo* resource_request_info =
403 content::ResourceRequestInfo::ForRequest(request); 525 content::ResourceRequestInfo::ForRequest(request);
404 if (!resource_request_info) 526 if (!resource_request_info)
405 return nullptr; 527 return nullptr;
406 528
407 // Ignore the requests not for the main resource. 529 // Ignore the requests not for the main resource.
408 if (resource_request_info->GetResourceType() != 530 if (resource_request_info->GetResourceType() !=
409 content::RESOURCE_TYPE_MAIN_FRAME) { 531 content::RESOURCE_TYPE_MAIN_FRAME) {
(...skipping 12 matching lines...) Expand all
422 OfflinePageRequestInfo::GetFromRequest(request); 544 OfflinePageRequestInfo::GetFromRequest(request);
423 if (info) { 545 if (info) {
424 // Fall back to default which is set when an offline page cannot be served, 546 // Fall back to default which is set when an offline page cannot be served,
425 // either page not found or online version desired. 547 // either page not found or online version desired.
426 if (info->use_default()) 548 if (info->use_default())
427 return nullptr; 549 return nullptr;
428 } else { 550 } else {
429 request->SetUserData(&kUserDataKey, new OfflinePageRequestInfo()); 551 request->SetUserData(&kUserDataKey, new OfflinePageRequestInfo());
430 } 552 }
431 553
432 return new OfflinePageRequestJob(profile_id, request, network_delegate); 554 return new OfflinePageRequestJob(request, network_delegate);
433 } 555 }
434 556
435 OfflinePageRequestJob::OfflinePageRequestJob( 557 OfflinePageRequestJob::OfflinePageRequestJob(
436 void* profile_id,
437 net::URLRequest* request, 558 net::URLRequest* request,
438 net::NetworkDelegate* network_delegate) 559 net::NetworkDelegate* network_delegate)
439 : net::URLRequestFileJob( 560 : net::URLRequestFileJob(
440 request, 561 request,
441 network_delegate, 562 network_delegate,
442 base::FilePath(), 563 base::FilePath(),
443 content::BrowserThread::GetBlockingPool()-> 564 content::BrowserThread::GetBlockingPool()->
444 GetTaskRunnerWithShutdownBehavior( 565 GetTaskRunnerWithShutdownBehavior(
445 base::SequencedWorkerPool::SKIP_ON_SHUTDOWN)), 566 base::SequencedWorkerPool::SKIP_ON_SHUTDOWN)),
446 profile_id_(profile_id),
447 delegate_(new DefaultDelegate()), 567 delegate_(new DefaultDelegate()),
448 weak_ptr_factory_(this) { 568 weak_ptr_factory_(this) {
449 } 569 }
450 570
451 OfflinePageRequestJob::~OfflinePageRequestJob() { 571 OfflinePageRequestJob::~OfflinePageRequestJob() {
452 } 572 }
453 573
454 void OfflinePageRequestJob::Start() { 574 void OfflinePageRequestJob::Start() {
455 base::ThreadTaskRunnerHandle::Get()->PostTask( 575 base::ThreadTaskRunnerHandle::Get()->PostTask(
456 FROM_HERE, base::Bind(&OfflinePageRequestJob::StartAsync, 576 FROM_HERE, base::Bind(&OfflinePageRequestJob::StartAsync,
457 weak_ptr_factory_.GetWeakPtr())); 577 weak_ptr_factory_.GetWeakPtr()));
458 } 578 }
459 579
460 void OfflinePageRequestJob::StartAsync() { 580 void OfflinePageRequestJob::StartAsync() {
461 NetworkState network_state = GetNetworkState(request()); 581 NetworkState network_state = GetNetworkState(request());
462 if (network_state == NetworkState::CONNECTED_NETWORK) { 582 if (network_state == NetworkState::CONNECTED_NETWORK) {
463 FallbackToDefault(); 583 FallbackToDefault();
464 return; 584 return;
465 } 585 }
466 586
587 std::string offline_header_string;
588 request()->extra_request_headers().GetHeader(kOfflinePageHeader,
589 &offline_header_string);
467 content::BrowserThread::PostTask( 590 content::BrowserThread::PostTask(
468 content::BrowserThread::UI, 591 content::BrowserThread::UI,
469 FROM_HERE, 592 FROM_HERE,
470 base::Bind(&SelectOfflinePage, 593 base::Bind(&SelectPage,
471 request()->url(), 594 request()->url(),
595 offline_header_string,
472 network_state, 596 network_state,
473 profile_id_,
474 delegate_->GetWebContentsGetter(request()), 597 delegate_->GetWebContentsGetter(request()),
475 delegate_->GetTabIdGetter(), 598 delegate_->GetTabIdGetter(),
476 weak_ptr_factory_.GetWeakPtr())); 599 weak_ptr_factory_.GetWeakPtr()));
477 } 600 }
478 601
479 void OfflinePageRequestJob::Kill() { 602 void OfflinePageRequestJob::Kill() {
480 net::URLRequestJob::Kill(); 603 net::URLRequestJob::Kill();
481 weak_ptr_factory_.InvalidateWeakPtrs(); 604 weak_ptr_factory_.InvalidateWeakPtrs();
482 } 605 }
483 606
(...skipping 19 matching lines...) Expand all
503 file_path_ = offline_file_path; 626 file_path_ = offline_file_path;
504 URLRequestFileJob::Start(); 627 URLRequestFileJob::Start();
505 } 628 }
506 629
507 void OfflinePageRequestJob::SetDelegateForTesting( 630 void OfflinePageRequestJob::SetDelegateForTesting(
508 std::unique_ptr<Delegate> delegate) { 631 std::unique_ptr<Delegate> delegate) {
509 delegate_ = std::move(delegate); 632 delegate_ = std::move(delegate);
510 } 633 }
511 634
512 } // namespace offline_pages 635 } // namespace offline_pages
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698