| 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/browser/feedback/feedback_util.h" | 5 #include "components/feedback/feedback_util.h" |
| 6 | 6 |
| 7 #include <sstream> | |
| 8 #include <string> | 7 #include <string> |
| 9 #include <vector> | |
| 10 | 8 |
| 11 #include "base/bind.h" | 9 #include "base/bind.h" |
| 12 #include "base/command_line.h" | |
| 13 #include "base/file_util.h" | 10 #include "base/file_util.h" |
| 14 #include "base/file_version_info.h" | 11 #include "components/feedback/feedback_data.h" |
| 15 #include "base/memory/singleton.h" | 12 #include "components/feedback/feedback_uploader.h" |
| 16 #include "base/message_loop/message_loop.h" | 13 #include "components/feedback/feedback_uploader_factory.h" |
| 17 #include "base/strings/string_number_conversions.h" | 14 #include "components/feedback/proto/common.pb.h" |
| 18 #include "base/strings/stringprintf.h" | 15 #include "components/feedback/proto/dom.pb.h" |
| 19 #include "base/strings/utf_string_conversions.h" | 16 #include "components/feedback/proto/extension.pb.h" |
| 20 #include "base/win/windows_version.h" | 17 #include "components/feedback/proto/math.pb.h" |
| 21 #include "chrome/browser/browser_process.h" | |
| 22 #include "chrome/browser/extensions/api/feedback_private/feedback_private_api.h" | |
| 23 #include "chrome/browser/feedback/feedback_data.h" | |
| 24 #include "chrome/browser/feedback/feedback_uploader.h" | |
| 25 #include "chrome/browser/feedback/feedback_uploader_factory.h" | |
| 26 #include "chrome/browser/metrics/variations/variations_http_header_provider.h" | |
| 27 #include "chrome/browser/profiles/profile.h" | |
| 28 #include "chrome/browser/profiles/profile_manager.h" | |
| 29 #include "chrome/browser/safe_browsing/safe_browsing_util.h" | |
| 30 #include "chrome/browser/ui/browser_finder.h" | |
| 31 #include "chrome/browser/ui/browser_list.h" | |
| 32 #include "chrome/browser/ui/browser_window.h" | |
| 33 #include "chrome/browser/ui/tabs/tab_strip_model.h" | |
| 34 #include "chrome/common/chrome_content_client.h" | |
| 35 #include "chrome/common/chrome_switches.h" | |
| 36 #include "chrome/common/chrome_version_info.h" | |
| 37 #include "components/metrics/metrics_log_manager.h" | |
| 38 #include "content/public/browser/navigation_controller.h" | |
| 39 #include "content/public/browser/web_contents.h" | |
| 40 #include "grit/generated_resources.h" | |
| 41 #include "grit/locale_settings.h" | |
| 42 #include "grit/theme_resources.h" | |
| 43 #include "net/base/load_flags.h" | |
| 44 #include "net/http/http_request_headers.h" | |
| 45 #include "net/url_request/url_fetcher.h" | |
| 46 #include "net/url_request/url_fetcher_delegate.h" | |
| 47 #include "net/url_request/url_request_status.h" | |
| 48 #include "third_party/icu/source/common/unicode/locid.h" | |
| 49 #include "third_party/zlib/google/zip.h" | 18 #include "third_party/zlib/google/zip.h" |
| 50 #include "ui/base/l10n/l10n_util.h" | 19 |
| 51 #include "url/gurl.h" | 20 using feedback::FeedbackData; |
| 52 | 21 |
| 53 namespace { | 22 namespace { |
| 54 | 23 |
| 55 GURL GetTargetTabUrl(int session_id, int index) { | |
| 56 Browser* browser = chrome::FindBrowserWithID(session_id); | |
| 57 // Sanity checks. | |
| 58 if (!browser || index >= browser->tab_strip_model()->count()) | |
| 59 return GURL(); | |
| 60 | |
| 61 if (index >= 0) { | |
| 62 content::WebContents* target_tab = | |
| 63 browser->tab_strip_model()->GetWebContentsAt(index); | |
| 64 if (target_tab) | |
| 65 return target_tab->GetURL(); | |
| 66 } | |
| 67 | |
| 68 return GURL(); | |
| 69 } | |
| 70 | |
| 71 const char kPngMimeType[] = "image/png"; | 24 const char kPngMimeType[] = "image/png"; |
| 72 const char kArbitraryMimeType[] = "application/octet-stream"; | 25 const char kArbitraryMimeType[] = "application/octet-stream"; |
| 73 const char kHistogramsAttachmentName[] = "histograms.zip"; | 26 const char kHistogramsAttachmentName[] = "histograms.zip"; |
| 74 const char kLogsAttachmentName[] = "system_logs.zip"; | 27 const char kLogsAttachmentName[] = "system_logs.zip"; |
| 75 | 28 |
| 76 #if defined(OS_CHROMEOS) | 29 #if defined(OS_CHROMEOS) |
| 77 const int kChromeOSProductId = 208; | 30 const int kChromeOSProductId = 208; |
| 78 #else | 31 #else |
| 79 const int kChromeBrowserProductId = 237; | 32 const int kChromeBrowserProductId = 237; |
| 80 #endif | 33 #endif |
| (...skipping 19 matching lines...) Expand all Loading... |
| 100 | 53 |
| 101 userfeedback::ProductSpecificBinaryData* attachment = | 54 userfeedback::ProductSpecificBinaryData* attachment = |
| 102 feedback_data->add_product_specific_binary_data(); | 55 feedback_data->add_product_specific_binary_data(); |
| 103 attachment->set_mime_type(kArbitraryMimeType); | 56 attachment->set_mime_type(kArbitraryMimeType); |
| 104 attachment->set_name(name); | 57 attachment->set_name(name); |
| 105 attachment->set_data(*data); | 58 attachment->set_data(*data); |
| 106 } | 59 } |
| 107 | 60 |
| 108 } // namespace | 61 } // namespace |
| 109 | 62 |
| 110 namespace chrome { | |
| 111 | |
| 112 const char kAppLauncherCategoryTag[] = "AppLauncher"; | |
| 113 | |
| 114 void ShowFeedbackPage(Browser* browser, | |
| 115 const std::string& description_template, | |
| 116 const std::string& category_tag) { | |
| 117 GURL page_url; | |
| 118 if (browser) { | |
| 119 page_url = GetTargetTabUrl(browser->session_id().id(), | |
| 120 browser->tab_strip_model()->active_index()); | |
| 121 } | |
| 122 | |
| 123 Profile* profile = NULL; | |
| 124 if (browser) { | |
| 125 profile = browser->profile(); | |
| 126 } else { | |
| 127 profile = ProfileManager::GetLastUsedProfileAllowedByPolicy(); | |
| 128 } | |
| 129 if (!profile) { | |
| 130 LOG(ERROR) << "Cannot invoke feedback: No profile found!"; | |
| 131 return; | |
| 132 } | |
| 133 | |
| 134 // We do not want to launch on an OTR profile. | |
| 135 profile = profile->GetOriginalProfile(); | |
| 136 DCHECK(profile); | |
| 137 | |
| 138 extensions::FeedbackPrivateAPI* api = | |
| 139 extensions::FeedbackPrivateAPI::GetFactoryInstance()->Get(profile); | |
| 140 | |
| 141 api->RequestFeedback(description_template, | |
| 142 category_tag, | |
| 143 page_url); | |
| 144 } | |
| 145 | |
| 146 } // namespace chrome | |
| 147 | |
| 148 namespace feedback_util { | 63 namespace feedback_util { |
| 149 | 64 |
| 150 void SendReport(scoped_refptr<FeedbackData> data) { | 65 void SendReport(scoped_refptr<FeedbackData> data) { |
| 151 if (!data.get()) { | 66 if (!data.get()) { |
| 152 LOG(ERROR) << "SendReport called with NULL data!"; | 67 LOG(ERROR) << "SendReport called with NULL data!"; |
| 153 NOTREACHED(); | 68 NOTREACHED(); |
| 154 return; | 69 return; |
| 155 } | 70 } |
| 156 | 71 |
| 157 userfeedback::ExtensionSubmit feedback_data; | 72 userfeedback::ExtensionSubmit feedback_data; |
| 158 // Unused field, needs to be 0 though. | 73 // Unused field, needs to be 0 though. |
| 159 feedback_data.set_type_id(0); | 74 feedback_data.set_type_id(0); |
| 160 | 75 |
| 161 userfeedback::CommonData* common_data = feedback_data.mutable_common_data(); | 76 userfeedback::CommonData* common_data = feedback_data.mutable_common_data(); |
| 162 // We're not using gaia ids, we're using the e-mail field instead. | 77 // We're not using gaia ids, we're using the e-mail field instead. |
| 163 common_data->set_gaia_id(0); | 78 common_data->set_gaia_id(0); |
| 164 common_data->set_user_email(data->user_email()); | 79 common_data->set_user_email(data->user_email()); |
| 165 common_data->set_description(data->description()); | 80 common_data->set_description(data->description()); |
| 166 | 81 common_data->set_source_description_language(data->locale()); |
| 167 std::string chrome_locale = g_browser_process->GetApplicationLocale(); | |
| 168 common_data->set_source_description_language(chrome_locale); | |
| 169 | 82 |
| 170 userfeedback::WebData* web_data = feedback_data.mutable_web_data(); | 83 userfeedback::WebData* web_data = feedback_data.mutable_web_data(); |
| 171 web_data->set_url(data->page_url()); | 84 web_data->set_url(data->page_url()); |
| 172 web_data->mutable_navigator()->set_user_agent(GetUserAgent()); | 85 web_data->mutable_navigator()->set_user_agent(data->user_agent()); |
| 173 | 86 |
| 174 gfx::Rect screen_size; | |
| 175 if (data->sys_info()) { | 87 if (data->sys_info()) { |
| 176 for (FeedbackData::SystemLogsMap::const_iterator i = | 88 for (FeedbackData::SystemLogsMap::const_iterator i = |
| 177 data->sys_info()->begin(); i != data->sys_info()->end(); ++i) { | 89 data->sys_info()->begin(); i != data->sys_info()->end(); ++i) { |
| 178 if (FeedbackData::BelowCompressionThreshold(i->second)) | 90 if (FeedbackData::BelowCompressionThreshold(i->second)) |
| 179 AddFeedbackData(&feedback_data, i->first, i->second); | 91 AddFeedbackData(&feedback_data, i->first, i->second); |
| 180 } | 92 } |
| 181 | 93 |
| 182 AddAttachment(&feedback_data, kLogsAttachmentName, data->compressed_logs()); | 94 AddAttachment(&feedback_data, kLogsAttachmentName, data->compressed_logs()); |
| 183 } | 95 } |
| 184 | 96 |
| (...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 238 #endif | 150 #endif |
| 239 | 151 |
| 240 *(feedback_data.mutable_chrome_data()) = chrome_data; | 152 *(feedback_data.mutable_chrome_data()) = chrome_data; |
| 241 | 153 |
| 242 // This pointer will eventually get deleted by the PostCleanup class, after | 154 // This pointer will eventually get deleted by the PostCleanup class, after |
| 243 // we've either managed to successfully upload the report or died trying. | 155 // we've either managed to successfully upload the report or died trying. |
| 244 std::string post_body; | 156 std::string post_body; |
| 245 feedback_data.SerializeToString(&post_body); | 157 feedback_data.SerializeToString(&post_body); |
| 246 | 158 |
| 247 feedback::FeedbackUploader *uploader = | 159 feedback::FeedbackUploader *uploader = |
| 248 feedback::FeedbackUploaderFactory::GetForBrowserContext(data->profile()); | 160 feedback::FeedbackUploaderFactory::GetForBrowserContext(data->context()); |
| 249 uploader->QueueReport(post_body); | 161 uploader->QueueReport(post_body); |
| 250 } | 162 } |
| 251 | 163 |
| 252 bool ZipString(const base::FilePath& filename, | 164 bool ZipString(const base::FilePath& filename, |
| 253 const std::string& data, std::string* compressed_logs) { | 165 const std::string& data, std::string* compressed_logs) { |
| 254 base::FilePath temp_path; | 166 base::FilePath temp_path; |
| 255 base::FilePath zip_file; | 167 base::FilePath zip_file; |
| 256 | 168 |
| 257 // Create a temporary directory, put the logs into a file in it. Create | 169 // Create a temporary directory, put the logs into a file in it. Create |
| 258 // another temporary file to receive the zip file in. | 170 // another temporary file to receive the zip file in. |
| 259 if (!base::CreateNewTempDirectory(base::FilePath::StringType(), &temp_path)) | 171 if (!base::CreateNewTempDirectory(base::FilePath::StringType(), &temp_path)) |
| 260 return false; | 172 return false; |
| 261 if (base::WriteFile(temp_path.Append(filename), data.c_str(), data.size()) == | 173 if (base::WriteFile(temp_path.Append(filename), data.c_str(), data.size()) == |
| 262 -1) | 174 -1) |
| 263 return false; | 175 return false; |
| 264 | 176 |
| 265 bool succeed = base::CreateTemporaryFile(&zip_file) && | 177 bool succeed = base::CreateTemporaryFile(&zip_file) && |
| 266 zip::Zip(temp_path, zip_file, false) && | 178 zip::Zip(temp_path, zip_file, false) && |
| 267 base::ReadFileToString(zip_file, compressed_logs); | 179 base::ReadFileToString(zip_file, compressed_logs); |
| 268 | 180 |
| 269 base::DeleteFile(temp_path, true); | 181 base::DeleteFile(temp_path, true); |
| 270 base::DeleteFile(zip_file, false); | 182 base::DeleteFile(zip_file, false); |
| 271 | 183 |
| 272 return succeed; | 184 return succeed; |
| 273 } | 185 } |
| 274 | 186 |
| 275 } // namespace feedback_util | 187 } // namespace feedback_util |
| OLD | NEW |