OLD | NEW |
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/common/localized_error.h" | 5 #include "chrome/common/localized_error.h" |
6 | 6 |
7 #include "base/i18n/rtl.h" | 7 #include "base/i18n/rtl.h" |
8 #include "base/logging.h" | 8 #include "base/logging.h" |
9 #include "base/string16.h" | 9 #include "base/string16.h" |
| 10 #include "base/string_util.h" |
10 #include "base/strings/string_number_conversions.h" | 11 #include "base/strings/string_number_conversions.h" |
11 #include "base/utf_string_conversions.h" | 12 #include "base/utf_string_conversions.h" |
12 #include "base/values.h" | 13 #include "base/values.h" |
13 #include "chrome/common/extensions/api/icons/icons_handler.h" | 14 #include "chrome/common/extensions/api/icons/icons_handler.h" |
14 #include "chrome/common/extensions/extension_constants.h" | 15 #include "chrome/common/extensions/extension_constants.h" |
15 #include "chrome/common/extensions/extension_icon_set.h" | 16 #include "chrome/common/extensions/extension_icon_set.h" |
16 #include "chrome/common/extensions/extension_set.h" | 17 #include "chrome/common/extensions/extension_set.h" |
17 #include "googleurl/src/gurl.h" | 18 #include "googleurl/src/gurl.h" |
18 #include "grit/chromium_strings.h" | 19 #include "grit/chromium_strings.h" |
19 #include "grit/generated_resources.h" | 20 #include "grit/generated_resources.h" |
20 #include "net/base/escape.h" | 21 #include "net/base/escape.h" |
21 #include "net/base/net_errors.h" | 22 #include "net/base/net_errors.h" |
22 #include "third_party/WebKit/Source/Platform/chromium/public/WebURLError.h" | 23 #include "third_party/WebKit/Source/Platform/chromium/public/WebURLError.h" |
23 #include "ui/base/l10n/l10n_util.h" | 24 #include "ui/base/l10n/l10n_util.h" |
| 25 #include "ui/webui/web_ui_util.h" |
24 #include "webkit/glue/webkit_glue.h" | 26 #include "webkit/glue/webkit_glue.h" |
25 | 27 |
26 #if defined(OS_WIN) | 28 #if defined(OS_WIN) |
27 #include "base/win/windows_version.h" | 29 #include "base/win/windows_version.h" |
28 #endif | 30 #endif |
29 | 31 |
30 using WebKit::WebURLError; | 32 using WebKit::WebURLError; |
31 | 33 |
| 34 // Some error pages have no details. |
| 35 const unsigned int kErrorPagesNoDetails = 0; |
| 36 |
32 namespace { | 37 namespace { |
33 | 38 |
34 static const char kRedirectLoopLearnMoreUrl[] = | 39 static const char kRedirectLoopLearnMoreUrl[] = |
35 "https://www.google.com/support/chrome/bin/answer.py?answer=95626"; | 40 "https://www.google.com/support/chrome/bin/answer.py?answer=95626"; |
36 static const char kWeakDHKeyLearnMoreUrl[] = | 41 static const char kWeakDHKeyLearnMoreUrl[] = |
37 "http://sites.google.com/a/chromium.org/dev/" | 42 "http://sites.google.com/a/chromium.org/dev/" |
38 "err_ssl_weak_server_ephemeral_dh_key"; | 43 "err_ssl_weak_server_ephemeral_dh_key"; |
39 #if defined(OS_CHROMEOS) | 44 #if defined(OS_CHROMEOS) |
40 static const char kAppWarningLearnMoreUrl[] = | 45 static const char kAppWarningLearnMoreUrl[] = |
41 "chrome-extension://honijodknafkokifofgiaalefdiedpko/main.html" | 46 "chrome-extension://honijodknafkokifofgiaalefdiedpko/main.html" |
(...skipping 301 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
343 }, | 348 }, |
344 {505, | 349 {505, |
345 IDS_ERRORPAGES_TITLE_LOAD_FAILED, | 350 IDS_ERRORPAGES_TITLE_LOAD_FAILED, |
346 IDS_ERRORPAGES_HEADING_HTTP_SERVER_ERROR, | 351 IDS_ERRORPAGES_HEADING_HTTP_SERVER_ERROR, |
347 IDS_ERRORPAGES_SUMMARY_WEBSITE_CANNOT_HANDLE, | 352 IDS_ERRORPAGES_SUMMARY_WEBSITE_CANNOT_HANDLE, |
348 IDS_ERRORPAGES_DETAILS_HTTP_VERSION_NOT_SUPPORTED, | 353 IDS_ERRORPAGES_DETAILS_HTTP_VERSION_NOT_SUPPORTED, |
349 SUGGEST_NONE, | 354 SUGGEST_NONE, |
350 }, | 355 }, |
351 }; | 356 }; |
352 | 357 |
353 const char* HttpErrorToString(int status_code) { | |
354 switch (status_code) { | |
355 case 403: | |
356 return "Forbidden"; | |
357 case 410: | |
358 return "Gone"; | |
359 case 500: | |
360 return "Internal Server Error"; | |
361 case 501: | |
362 return "Not Implemented"; | |
363 case 502: | |
364 return "Bad Gateway"; | |
365 case 503: | |
366 return "Service Unavailable"; | |
367 case 504: | |
368 return "Gateway Timeout"; | |
369 case 505: | |
370 return "HTTP Version Not Supported"; | |
371 default: | |
372 return ""; | |
373 } | |
374 } | |
375 | |
376 string16 GetErrorDetailsString(const std::string& error_domain, | |
377 int error_code, | |
378 const string16& details) { | |
379 int error_page_template; | |
380 const char* error_string; | |
381 if (error_domain == net::kErrorDomain) { | |
382 error_page_template = IDS_ERRORPAGES_DETAILS_TEMPLATE; | |
383 error_string = net::ErrorToString(error_code); | |
384 DCHECK(error_code < 0); // Net error codes are negative. | |
385 error_code = -error_code; | |
386 } else if (error_domain == LocalizedError::kHttpErrorDomain) { | |
387 error_page_template = IDS_ERRORPAGES_HTTP_DETAILS_TEMPLATE; | |
388 error_string = HttpErrorToString(error_code); | |
389 } else { | |
390 NOTREACHED(); | |
391 return string16(); | |
392 } | |
393 return l10n_util::GetStringFUTF16( | |
394 error_page_template, | |
395 base::IntToString16(error_code), | |
396 ASCIIToUTF16(error_string), | |
397 details); | |
398 } | |
399 | |
400 const LocalizedErrorMap* FindErrorMapInArray(const LocalizedErrorMap* maps, | 358 const LocalizedErrorMap* FindErrorMapInArray(const LocalizedErrorMap* maps, |
401 size_t num_maps, | 359 size_t num_maps, |
402 int error_code) { | 360 int error_code) { |
403 for (size_t i = 0; i < num_maps; ++i) { | 361 for (size_t i = 0; i < num_maps; ++i) { |
404 if (maps[i].error_code == error_code) | 362 if (maps[i].error_code == error_code) |
405 return &maps[i]; | 363 return &maps[i]; |
406 } | 364 } |
407 return NULL; | 365 return NULL; |
408 } | 366 } |
409 | 367 |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
454 bool rtl = LocaleIsRTL(); | 412 bool rtl = LocaleIsRTL(); |
455 error_strings->SetString("textdirection", rtl ? "rtl" : "ltr"); | 413 error_strings->SetString("textdirection", rtl ? "rtl" : "ltr"); |
456 | 414 |
457 // Grab the strings and settings that depend on the error type. Init | 415 // Grab the strings and settings that depend on the error type. Init |
458 // options with default values. | 416 // options with default values. |
459 LocalizedErrorMap options = { | 417 LocalizedErrorMap options = { |
460 0, | 418 0, |
461 IDS_ERRORPAGES_TITLE_NOT_AVAILABLE, | 419 IDS_ERRORPAGES_TITLE_NOT_AVAILABLE, |
462 IDS_ERRORPAGES_HEADING_NOT_AVAILABLE, | 420 IDS_ERRORPAGES_HEADING_NOT_AVAILABLE, |
463 IDS_ERRORPAGES_SUMMARY_NOT_AVAILABLE, | 421 IDS_ERRORPAGES_SUMMARY_NOT_AVAILABLE, |
464 IDS_ERRORPAGES_DETAILS_UNKNOWN, | 422 kErrorPagesNoDetails, |
465 SUGGEST_NONE, | 423 SUGGEST_NONE, |
466 }; | 424 }; |
467 | 425 |
468 const std::string error_domain = error.domain.utf8(); | 426 const std::string error_domain = error.domain.utf8(); |
469 int error_code = error.reason; | 427 int error_code = error.reason; |
470 const LocalizedErrorMap* error_map = | 428 const LocalizedErrorMap* error_map = |
471 LookupErrorMap(error_domain, error_code); | 429 LookupErrorMap(error_domain, error_code); |
472 if (error_map) | 430 if (error_map) |
473 options = *error_map; | 431 options = *error_map; |
474 | 432 |
475 if (options.suggestions != SUGGEST_NONE) { | |
476 error_strings->SetString( | |
477 "suggestionsHeading", | |
478 l10n_util::GetStringUTF16(IDS_ERRORPAGES_SUGGESTION_HEADING)); | |
479 } | |
480 | |
481 const GURL failed_url = error.unreachableURL; | 433 const GURL failed_url = error.unreachableURL; |
482 | 434 |
483 // If we got "access denied" but the url was a file URL, then we say it was a | 435 // If we got "access denied" but the url was a file URL, then we say it was a |
484 // file instead of just using the "not available" default message. Just adding | 436 // file instead of just using the "not available" default message. Just adding |
485 // ERR_ACCESS_DENIED to the map isn't sufficient, since that message may be | 437 // ERR_ACCESS_DENIED to the map isn't sufficient, since that message may be |
486 // generated by some OSs when the operation doesn't involve a file URL. | 438 // generated by some OSs when the operation doesn't involve a file URL. |
487 if (error_domain == net::kErrorDomain && | 439 if (error_domain == net::kErrorDomain && |
488 error_code == net::ERR_ACCESS_DENIED && | 440 error_code == net::ERR_ACCESS_DENIED && |
489 failed_url.scheme() == "file") { | 441 failed_url.scheme() == "file") { |
490 options.title_resource_id = IDS_ERRORPAGES_TITLE_ACCESS_DENIED; | 442 options.title_resource_id = IDS_ERRORPAGES_TITLE_ACCESS_DENIED; |
491 options.heading_resource_id = IDS_ERRORPAGES_HEADING_FILE_ACCESS_DENIED; | 443 options.heading_resource_id = IDS_ERRORPAGES_HEADING_FILE_ACCESS_DENIED; |
492 options.summary_resource_id = IDS_ERRORPAGES_SUMMARY_FILE_ACCESS_DENIED; | 444 options.summary_resource_id = IDS_ERRORPAGES_SUMMARY_FILE_ACCESS_DENIED; |
493 options.details_resource_id = IDS_ERRORPAGES_DETAILS_FILE_ACCESS_DENIED; | 445 options.details_resource_id = IDS_ERRORPAGES_DETAILS_FILE_ACCESS_DENIED; |
494 options.suggestions = SUGGEST_NONE; | 446 options.suggestions = SUGGEST_NONE; |
495 } | 447 } |
496 | 448 |
| 449 // If there are any suggestions other than reload, populate the suggestion |
| 450 // heading (reload has a button, rather than a suggestion in the list). |
| 451 if ((options.suggestions & ~SUGGEST_RELOAD) != SUGGEST_NONE) { |
| 452 error_strings->SetString( |
| 453 "suggestionsHeading", |
| 454 l10n_util::GetStringUTF16(IDS_ERRORPAGES_SUGGESTION_HEADING)); |
| 455 } |
| 456 |
497 string16 failed_url_string(UTF8ToUTF16(failed_url.spec())); | 457 string16 failed_url_string(UTF8ToUTF16(failed_url.spec())); |
498 // URLs are always LTR. | 458 // URLs are always LTR. |
499 if (rtl) | 459 if (rtl) |
500 base::i18n::WrapStringWithLTRFormatting(&failed_url_string); | 460 base::i18n::WrapStringWithLTRFormatting(&failed_url_string); |
501 error_strings->SetString("title", | 461 error_strings->SetString("title", |
502 l10n_util::GetStringFUTF16(options.title_resource_id, failed_url_string)); | 462 l10n_util::GetStringFUTF16(options.title_resource_id, failed_url_string)); |
503 error_strings->SetString("heading", | 463 error_strings->SetString("heading", |
504 l10n_util::GetStringUTF16(options.heading_resource_id)); | 464 l10n_util::GetStringUTF16(options.heading_resource_id)); |
505 | 465 |
506 DictionaryValue* summary = new DictionaryValue; | 466 DictionaryValue* summary = new DictionaryValue; |
507 summary->SetString("msg", | 467 summary->SetString("msg", |
508 l10n_util::GetStringUTF16(options.summary_resource_id)); | 468 l10n_util::GetStringUTF16(options.summary_resource_id)); |
509 // TODO(tc): We want the unicode url and host here since they're being | 469 // TODO(tc): We want the unicode url and host here since they're being |
510 // displayed. | 470 // displayed. |
511 summary->SetString("failedUrl", failed_url_string); | 471 summary->SetString("failedUrl", failed_url_string); |
512 summary->SetString("hostName", failed_url.host()); | 472 summary->SetString("hostName", failed_url.host()); |
513 summary->SetString("productName", | 473 summary->SetString("productName", |
514 l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)); | 474 l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)); |
| 475 |
| 476 error_strings->SetString( |
| 477 "more", l10n_util::GetStringUTF16(IDS_ERRORPAGES_BUTTON_MORE)); |
| 478 error_strings->SetString( |
| 479 "less", l10n_util::GetStringUTF16(IDS_ERRORPAGES_BUTTON_LESS)); |
515 error_strings->Set("summary", summary); | 480 error_strings->Set("summary", summary); |
516 | 481 |
517 string16 details = l10n_util::GetStringUTF16(options.details_resource_id); | 482 if (options.details_resource_id != kErrorPagesNoDetails) { |
518 error_strings->SetString("details", | 483 error_strings->SetString( |
519 GetErrorDetailsString(error_domain, error_code, details)); | 484 "errorDetails", l10n_util::GetStringUTF16(options.details_resource_id)); |
| 485 } |
| 486 |
| 487 string16 error_string; |
| 488 if (error_domain == net::kErrorDomain) { |
| 489 // Non-internationalized error string, for debugging Chrome itself. |
| 490 std::string ascii_error_string = net::ErrorToString(error_code); |
| 491 // Remove the leading "net::" from the returned string. |
| 492 RemoveChars(ascii_error_string, "net:", &ascii_error_string); |
| 493 error_string = ASCIIToUTF16(ascii_error_string); |
| 494 } else { |
| 495 DCHECK_EQ(LocalizedError::kHttpErrorDomain, error_domain); |
| 496 error_string = base::IntToString16(error_code); |
| 497 } |
| 498 error_strings->SetString("errorCode", |
| 499 l10n_util::GetStringFUTF16(IDS_ERRORPAGES_ERROR_CODE, error_string)); |
520 | 500 |
521 // Platform specific instructions for diagnosing network issues on OSX and | 501 // Platform specific instructions for diagnosing network issues on OSX and |
522 // Windows. | 502 // Windows. |
523 #if defined(OS_MACOSX) || defined(OS_WIN) | 503 #if defined(OS_MACOSX) || defined(OS_WIN) |
524 if (error_domain == net::kErrorDomain && | 504 if (error_domain == net::kErrorDomain && |
525 error_code == net::ERR_INTERNET_DISCONNECTED) { | 505 error_code == net::ERR_INTERNET_DISCONNECTED) { |
526 int platform_string_id = | 506 int platform_string_id = |
527 IDS_ERRORPAGES_SUMMARY_INTERNET_DISCONNECTED_PLATFORM; | 507 IDS_ERRORPAGES_SUMMARY_INTERNET_DISCONNECTED_PLATFORM; |
528 #if defined(OS_WIN) | 508 #if defined(OS_WIN) |
529 // Different versions of Windows have different instructions. | 509 // Different versions of Windows have different instructions. |
(...skipping 12 matching lines...) Expand all Loading... |
542 // dependent portion of the summary section. | 522 // dependent portion of the summary section. |
543 summary->SetString("msg", | 523 summary->SetString("msg", |
544 l10n_util::GetStringFUTF16( | 524 l10n_util::GetStringFUTF16( |
545 IDS_ERRORPAGES_SUMMARY_INTERNET_DISCONNECTED_INSTRUCTIONS_TEMPLATE, | 525 IDS_ERRORPAGES_SUMMARY_INTERNET_DISCONNECTED_INSTRUCTIONS_TEMPLATE, |
546 l10n_util::GetStringUTF16(options.summary_resource_id), | 526 l10n_util::GetStringUTF16(options.summary_resource_id), |
547 l10n_util::GetStringUTF16(platform_string_id))); | 527 l10n_util::GetStringUTF16(platform_string_id))); |
548 } | 528 } |
549 #endif // defined(OS_MACOSX) || defined(OS_WIN) | 529 #endif // defined(OS_MACOSX) || defined(OS_WIN) |
550 | 530 |
551 if (options.suggestions & SUGGEST_RELOAD) { | 531 if (options.suggestions & SUGGEST_RELOAD) { |
552 DictionaryValue* suggest_reload = new DictionaryValue; | 532 DictionaryValue* reload_button = new DictionaryValue; |
553 suggest_reload->SetString("msg", | 533 reload_button->SetString("msg", |
554 l10n_util::GetStringUTF16(IDS_ERRORPAGES_SUGGESTION_RELOAD)); | 534 l10n_util::GetStringUTF16(IDS_ERRORPAGES_BUTTON_RELOAD)); |
555 suggest_reload->SetString("reloadUrl", failed_url_string); | 535 reload_button->SetString("reloadUrl", failed_url_string); |
556 error_strings->Set("suggestionsReload", suggest_reload); | 536 error_strings->Set("reload", reload_button); |
557 } | 537 } |
558 | 538 |
559 if (options.suggestions & SUGGEST_HOSTNAME) { | 539 if (options.suggestions & SUGGEST_HOSTNAME) { |
560 // Only show the "Go to hostname" suggestion if the failed_url has a path. | 540 // Only show the "Go to hostname" suggestion if the failed_url has a path. |
561 if (std::string() == failed_url.path()) { | 541 if (std::string() == failed_url.path()) { |
562 DictionaryValue* suggest_home_page = new DictionaryValue; | 542 DictionaryValue* suggest_home_page = new DictionaryValue; |
563 suggest_home_page->SetString("suggestionsHomepageMsg", | 543 suggest_home_page->SetString("suggestionsHomepageMsg", |
564 l10n_util::GetStringUTF16(IDS_ERRORPAGES_SUGGESTION_HOMEPAGE)); | 544 l10n_util::GetStringUTF16(IDS_ERRORPAGES_SUGGESTION_HOMEPAGE)); |
565 string16 homepage(ASCIIToUTF16(failed_url.GetWithEmptyPath().spec())); | 545 string16 homepage(ASCIIToUTF16(failed_url.GetWithEmptyPath().spec())); |
566 // URLs are always LTR. | 546 // URLs are always LTR. |
(...skipping 189 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
756 #if defined(OS_CHROMEOS) | 736 #if defined(OS_CHROMEOS) |
757 GURL learn_more_url(kAppWarningLearnMoreUrl); | 737 GURL learn_more_url(kAppWarningLearnMoreUrl); |
758 DictionaryValue* suggest_learn_more = new DictionaryValue(); | 738 DictionaryValue* suggest_learn_more = new DictionaryValue(); |
759 suggest_learn_more->SetString("msg", | 739 suggest_learn_more->SetString("msg", |
760 l10n_util::GetStringUTF16( | 740 l10n_util::GetStringUTF16( |
761 IDS_ERRORPAGES_SUGGESTION_LEARNMORE)); | 741 IDS_ERRORPAGES_SUGGESTION_LEARNMORE)); |
762 suggest_learn_more->SetString("learnMoreUrl", learn_more_url.spec()); | 742 suggest_learn_more->SetString("learnMoreUrl", learn_more_url.spec()); |
763 error_strings->Set("suggestionsLearnMore", suggest_learn_more); | 743 error_strings->Set("suggestionsLearnMore", suggest_learn_more); |
764 #endif // defined(OS_CHROMEOS) | 744 #endif // defined(OS_CHROMEOS) |
765 } | 745 } |
OLD | NEW |