No dual_mode on Win10+ shortcuts.
[chromium-blink-merge.git] / chrome / browser / download / download_danger_prompt.cc
blobf581e42b6408ba8d18ccab4cf71b672b937b6a56
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
3 // found in the LICENSE file.
5 #include "chrome/browser/download/download_danger_prompt.h"
7 #include "base/bind.h"
8 #include "base/strings/utf_string_conversions.h"
9 #include "chrome/browser/chrome_notification_types.h"
10 #include "chrome/browser/download/chrome_download_manager_delegate.h"
11 #include "chrome/browser/download/download_stats.h"
12 #include "chrome/browser/extensions/api/experience_sampling_private/experience_sampling.h"
13 #include "chrome/browser/ui/tab_modal_confirm_dialog.h"
14 #include "chrome/browser/ui/tab_modal_confirm_dialog_delegate.h"
15 #include "chrome/grit/chromium_strings.h"
16 #include "chrome/grit/generated_resources.h"
17 #include "content/public/browser/download_danger_type.h"
18 #include "content/public/browser/download_item.h"
19 #include "ui/base/l10n/l10n_util.h"
21 using extensions::ExperienceSamplingEvent;
23 namespace {
25 // TODO(wittman): Create a native web contents modal dialog implementation of
26 // this dialog for non-Views platforms, to support bold formatting of the
27 // message lead.
29 // Implements DownloadDangerPrompt using a TabModalConfirmDialog.
30 class DownloadDangerPromptImpl : public DownloadDangerPrompt,
31 public content::DownloadItem::Observer,
32 public TabModalConfirmDialogDelegate {
33 public:
34 DownloadDangerPromptImpl(content::DownloadItem* item,
35 content::WebContents* web_contents,
36 bool show_context,
37 const OnDone& done);
38 ~DownloadDangerPromptImpl() override;
40 // DownloadDangerPrompt:
41 void InvokeActionForTesting(Action action) override;
43 private:
44 // content::DownloadItem::Observer:
45 void OnDownloadUpdated(content::DownloadItem* download) override;
47 // TabModalConfirmDialogDelegate:
48 base::string16 GetTitle() override;
49 base::string16 GetDialogMessage() override;
50 base::string16 GetAcceptButtonTitle() override;
51 base::string16 GetCancelButtonTitle() override;
52 void OnAccepted() override;
53 void OnCanceled() override;
54 void OnClosed() override;
56 void RunDone(Action action);
58 content::DownloadItem* download_;
59 bool show_context_;
60 OnDone done_;
62 scoped_ptr<ExperienceSamplingEvent> sampling_event_;
64 DISALLOW_COPY_AND_ASSIGN(DownloadDangerPromptImpl);
67 DownloadDangerPromptImpl::DownloadDangerPromptImpl(
68 content::DownloadItem* download,
69 content::WebContents* web_contents,
70 bool show_context,
71 const OnDone& done)
72 : TabModalConfirmDialogDelegate(web_contents),
73 download_(download),
74 show_context_(show_context),
75 done_(done) {
76 DCHECK(!done_.is_null());
77 download_->AddObserver(this);
78 RecordOpenedDangerousConfirmDialog(download_->GetDangerType());
80 // ExperienceSampling: A malicious download warning is being shown to the
81 // user, so we start a new SamplingEvent and track it.
82 sampling_event_.reset(new ExperienceSamplingEvent(
83 ExperienceSamplingEvent::kDownloadDangerPrompt,
84 download->GetURL(),
85 download->GetReferrerUrl(),
86 download->GetBrowserContext()));
89 DownloadDangerPromptImpl::~DownloadDangerPromptImpl() {
90 // |this| might be deleted without invoking any callbacks. E.g. pressing Esc
91 // on GTK or if the user navigates away from the page showing the prompt.
92 RunDone(DISMISS);
95 void DownloadDangerPromptImpl::InvokeActionForTesting(Action action) {
96 switch (action) {
97 case ACCEPT: Accept(); break;
98 case CANCEL: Cancel(); break;
99 case DISMISS:
100 RunDone(DISMISS);
101 Cancel();
102 break;
106 void DownloadDangerPromptImpl::OnDownloadUpdated(
107 content::DownloadItem* download) {
108 // If the download is nolonger dangerous (accepted externally) or the download
109 // is in a terminal state, then the download danger prompt is no longer
110 // necessary.
111 if (!download->IsDangerous() || download->IsDone()) {
112 RunDone(DISMISS);
113 Cancel();
117 base::string16 DownloadDangerPromptImpl::GetTitle() {
118 if (show_context_)
119 return l10n_util::GetStringUTF16(IDS_CONFIRM_KEEP_DANGEROUS_DOWNLOAD_TITLE);
120 switch (download_->GetDangerType()) {
121 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_URL:
122 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT:
123 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_HOST:
124 case content::DOWNLOAD_DANGER_TYPE_POTENTIALLY_UNWANTED: {
125 return l10n_util::GetStringUTF16(
126 IDS_RESTORE_KEEP_DANGEROUS_DOWNLOAD_TITLE);
128 default: {
129 return l10n_util::GetStringUTF16(
130 IDS_CONFIRM_KEEP_DANGEROUS_DOWNLOAD_TITLE);
135 base::string16 DownloadDangerPromptImpl::GetDialogMessage() {
136 if (show_context_) {
137 switch (download_->GetDangerType()) {
138 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_FILE: {
139 return l10n_util::GetStringFUTF16(
140 IDS_PROMPT_DANGEROUS_DOWNLOAD,
141 download_->GetFileNameToReportUser().LossyDisplayName());
143 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_URL: // Fall through
144 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT:
145 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_HOST: {
146 return l10n_util::GetStringFUTF16(
147 IDS_PROMPT_MALICIOUS_DOWNLOAD_CONTENT,
148 download_->GetFileNameToReportUser().LossyDisplayName());
150 case content::DOWNLOAD_DANGER_TYPE_UNCOMMON_CONTENT: {
151 return l10n_util::GetStringFUTF16(
152 IDS_PROMPT_UNCOMMON_DOWNLOAD_CONTENT,
153 download_->GetFileNameToReportUser().LossyDisplayName());
155 case content::DOWNLOAD_DANGER_TYPE_POTENTIALLY_UNWANTED: {
156 return l10n_util::GetStringFUTF16(
157 IDS_PROMPT_DOWNLOAD_CHANGES_SETTINGS,
158 download_->GetFileNameToReportUser().LossyDisplayName());
160 case content::DOWNLOAD_DANGER_TYPE_NOT_DANGEROUS:
161 case content::DOWNLOAD_DANGER_TYPE_MAYBE_DANGEROUS_CONTENT:
162 case content::DOWNLOAD_DANGER_TYPE_USER_VALIDATED:
163 case content::DOWNLOAD_DANGER_TYPE_MAX: {
164 break;
167 } else {
168 switch (download_->GetDangerType()) {
169 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_URL:
170 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT:
171 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_HOST: {
172 return l10n_util::GetStringUTF16(
173 IDS_PROMPT_CONFIRM_KEEP_MALICIOUS_DOWNLOAD_LEAD) +
174 base::ASCIIToUTF16("\n\n") +
175 l10n_util::GetStringUTF16(
176 IDS_PROMPT_CONFIRM_KEEP_MALICIOUS_DOWNLOAD_BODY);
178 default: {
179 return l10n_util::GetStringUTF16(
180 IDS_PROMPT_CONFIRM_KEEP_DANGEROUS_DOWNLOAD);
184 NOTREACHED();
185 return base::string16();
188 base::string16 DownloadDangerPromptImpl::GetAcceptButtonTitle() {
189 if (show_context_)
190 return l10n_util::GetStringUTF16(IDS_CONFIRM_DOWNLOAD);
191 switch (download_->GetDangerType()) {
192 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_URL:
193 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT:
194 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_HOST:
195 case content::DOWNLOAD_DANGER_TYPE_POTENTIALLY_UNWANTED: {
196 return l10n_util::GetStringUTF16(IDS_CONFIRM_DOWNLOAD_AGAIN_MALICIOUS);
198 default:
199 return l10n_util::GetStringUTF16(IDS_CONFIRM_DOWNLOAD_AGAIN);
203 base::string16 DownloadDangerPromptImpl::GetCancelButtonTitle() {
204 if (show_context_)
205 return l10n_util::GetStringUTF16(IDS_CANCEL);
206 switch (download_->GetDangerType()) {
207 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_URL:
208 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_CONTENT:
209 case content::DOWNLOAD_DANGER_TYPE_DANGEROUS_HOST:
210 case content::DOWNLOAD_DANGER_TYPE_POTENTIALLY_UNWANTED: {
211 return l10n_util::GetStringUTF16(IDS_CONFIRM_CANCEL_AGAIN_MALICIOUS);
213 default:
214 return l10n_util::GetStringUTF16(IDS_CANCEL);
218 void DownloadDangerPromptImpl::OnAccepted() {
219 // ExperienceSampling: User proceeded through the warning.
220 sampling_event_->CreateUserDecisionEvent(ExperienceSamplingEvent::kProceed);
221 RunDone(ACCEPT);
224 void DownloadDangerPromptImpl::OnCanceled() {
225 // ExperienceSampling: User canceled the warning.
226 sampling_event_->CreateUserDecisionEvent(ExperienceSamplingEvent::kDeny);
227 RunDone(CANCEL);
230 void DownloadDangerPromptImpl::OnClosed() {
231 // ExperienceSampling: User canceled the warning.
232 sampling_event_->CreateUserDecisionEvent(ExperienceSamplingEvent::kDeny);
233 RunDone(DISMISS);
236 void DownloadDangerPromptImpl::RunDone(Action action) {
237 // Invoking the callback can cause the download item state to change or cause
238 // the constrained window to close, and |callback| refers to a member
239 // variable.
240 OnDone done = done_;
241 done_.Reset();
242 if (download_ != NULL) {
243 download_->RemoveObserver(this);
244 download_ = NULL;
246 if (!done.is_null())
247 done.Run(action);
250 } // namespace
252 #if !defined(USE_AURA)
253 // static
254 DownloadDangerPrompt* DownloadDangerPrompt::Create(
255 content::DownloadItem* item,
256 content::WebContents* web_contents,
257 bool show_context,
258 const OnDone& done) {
259 DownloadDangerPromptImpl* prompt = new DownloadDangerPromptImpl(
260 item, web_contents, show_context, done);
261 // |prompt| will be deleted when the dialog is done.
262 TabModalConfirmDialog::Create(prompt, web_contents);
263 return prompt;
265 #endif