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

Side by Side Diff: chrome/browser/permissions/permission_decision_auto_blocker.cc

Issue 2622983003: Implement embargo in PermissionDecisionAutoBlocker (Closed)
Patch Set: Review, comments, formatting. Created 3 years, 11 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/permissions/permission_decision_auto_blocker.h" 5 #include "chrome/browser/permissions/permission_decision_auto_blocker.h"
6 6
7 #include <memory> 7 #include <memory>
8 8
9 #include "base/feature_list.h" 9 #include "base/feature_list.h"
10 #include "base/logging.h" 10 #include "base/logging.h"
11 #include "base/memory/ptr_util.h" 11 #include "base/memory/ptr_util.h"
12 #include "base/strings/string_number_conversions.h" 12 #include "base/strings/string_number_conversions.h"
13 #include "base/time/time.h"
13 #include "base/values.h" 14 #include "base/values.h"
14 #include "chrome/browser/content_settings/host_content_settings_map_factory.h" 15 #include "chrome/browser/content_settings/host_content_settings_map_factory.h"
16 #include "chrome/browser/permissions/permission_blacklist_client.h"
15 #include "chrome/browser/permissions/permission_util.h" 17 #include "chrome/browser/permissions/permission_util.h"
16 #include "chrome/common/chrome_features.h" 18 #include "chrome/common/chrome_features.h"
17 #include "components/content_settings/core/browser/host_content_settings_map.h" 19 #include "components/content_settings/core/browser/host_content_settings_map.h"
18 #include "components/variations/variations_associated_data.h" 20 #include "components/variations/variations_associated_data.h"
19 #include "content/public/browser/permission_type.h" 21 #include "content/public/browser/permission_type.h"
22 #include "content/public/browser/web_contents.h"
20 #include "url/gurl.h" 23 #include "url/gurl.h"
21 24
22 namespace { 25 namespace {
23 26
24 // The number of times that users may explicitly dismiss a permission prompt 27 // The number of times that users may explicitly dismiss a permission prompt
25 // from an origin before it is automatically blocked. 28 // from an origin before it is automatically blocked.
26 int g_prompt_dismissals_before_block = 3; 29 int g_prompt_dismissals_before_block = 3;
27 30
31 // The number of days that an origin will stay under embargo for a requested
32 // permission.
33 int g_embargo_days = 7;
34
28 std::unique_ptr<base::DictionaryValue> GetOriginDict( 35 std::unique_ptr<base::DictionaryValue> GetOriginDict(
29 HostContentSettingsMap* settings, 36 HostContentSettingsMap* settings,
30 const GURL& origin_url) { 37 const GURL& origin_url) {
31 std::unique_ptr<base::DictionaryValue> dict = 38 std::unique_ptr<base::DictionaryValue> dict =
32 base::DictionaryValue::From(settings->GetWebsiteSetting( 39 base::DictionaryValue::From(settings->GetWebsiteSetting(
33 origin_url, origin_url, 40 origin_url, GURL(), CONTENT_SETTINGS_TYPE_PROMPT_NO_DECISION_COUNT,
34 CONTENT_SETTINGS_TYPE_PROMPT_NO_DECISION_COUNT, std::string(), 41 std::string(), nullptr));
35 nullptr));
36 if (!dict) 42 if (!dict)
37 return base::MakeUnique<base::DictionaryValue>(); 43 return base::MakeUnique<base::DictionaryValue>();
38 44
39 return dict; 45 return dict;
40 } 46 }
41 47
42 base::DictionaryValue* GetOrCreatePermissionDict( 48 base::DictionaryValue* GetOrCreatePermissionDict(
43 base::DictionaryValue* origin_dict, 49 base::DictionaryValue* origin_dict,
44 const std::string& permission) { 50 const std::string& permission) {
45 base::DictionaryValue* permission_dict = nullptr; 51 base::DictionaryValue* permission_dict = nullptr;
(...skipping 29 matching lines...) Expand all
75 return current_count; 81 return current_count;
76 } 82 }
77 83
78 int GetActionCount(const GURL& url, 84 int GetActionCount(const GURL& url,
79 content::PermissionType permission, 85 content::PermissionType permission,
80 const char* key, 86 const char* key,
81 Profile* profile) { 87 Profile* profile) {
82 HostContentSettingsMap* map = 88 HostContentSettingsMap* map =
83 HostContentSettingsMapFactory::GetForProfile(profile); 89 HostContentSettingsMapFactory::GetForProfile(profile);
84 std::unique_ptr<base::DictionaryValue> dict = GetOriginDict(map, url); 90 std::unique_ptr<base::DictionaryValue> dict = GetOriginDict(map, url);
85
86 base::DictionaryValue* permission_dict = GetOrCreatePermissionDict( 91 base::DictionaryValue* permission_dict = GetOrCreatePermissionDict(
87 dict.get(), PermissionUtil::GetPermissionString(permission)); 92 dict.get(), PermissionUtil::GetPermissionString(permission));
88 93
89 int current_count = 0; 94 int current_count = 0;
90 permission_dict->GetInteger(key, &current_count); 95 permission_dict->GetInteger(key, &current_count);
91 return current_count; 96 return current_count;
92 } 97 }
93 98
94 } // namespace 99 } // namespace
95 100
96 // static 101 // static
97 const char PermissionDecisionAutoBlocker::kPromptDismissCountKey[] = 102 const char PermissionDecisionAutoBlocker::kPromptDismissCountKey[] =
98 "dismiss_count"; 103 "dismiss_count";
99 104
100 // static 105 // static
101 const char PermissionDecisionAutoBlocker::kPromptIgnoreCountKey[] = 106 const char PermissionDecisionAutoBlocker::kPromptIgnoreCountKey[] =
102 "ignore_count"; 107 "ignore_count";
103 108
104 // static 109 // static
110 const char PermissionDecisionAutoBlocker::kPermissionOriginEmbargoKey[] =
111 "embargo_days";
112
113 // static
105 void PermissionDecisionAutoBlocker::RemoveCountsByUrl( 114 void PermissionDecisionAutoBlocker::RemoveCountsByUrl(
106 Profile* profile, 115 Profile* profile,
107 base::Callback<bool(const GURL& url)> filter) { 116 base::Callback<bool(const GURL& url)> filter) {
108 HostContentSettingsMap* map = 117 HostContentSettingsMap* map =
109 HostContentSettingsMapFactory::GetForProfile(profile); 118 HostContentSettingsMapFactory::GetForProfile(profile);
110 119
111 std::unique_ptr<ContentSettingsForOneType> settings( 120 std::unique_ptr<ContentSettingsForOneType> settings(
112 new ContentSettingsForOneType); 121 new ContentSettingsForOneType);
113 map->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_PROMPT_NO_DECISION_COUNT, 122 map->GetSettingsForOneType(CONTENT_SETTINGS_TYPE_PROMPT_NO_DECISION_COUNT,
114 std::string(), settings.get()); 123 std::string(), settings.get());
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
167 176
168 if (!base::FeatureList::IsEnabled(features::kBlockPromptsIfDismissedOften)) 177 if (!base::FeatureList::IsEnabled(features::kBlockPromptsIfDismissedOften))
169 return false; 178 return false;
170 179
171 return current_dismissal_count >= g_prompt_dismissals_before_block; 180 return current_dismissal_count >= g_prompt_dismissals_before_block;
172 } 181 }
173 182
174 // static 183 // static
175 void PermissionDecisionAutoBlocker::UpdateFromVariations() { 184 void PermissionDecisionAutoBlocker::UpdateFromVariations() {
176 int prompt_dismissals = -1; 185 int prompt_dismissals = -1;
177 std::string value = variations::GetVariationParamValueByFeature( 186 int embargo_days = -1;
187 std::string dismissals_value = variations::GetVariationParamValueByFeature(
178 features::kBlockPromptsIfDismissedOften, kPromptDismissCountKey); 188 features::kBlockPromptsIfDismissedOften, kPromptDismissCountKey);
189 std::string embargo_value = variations::GetVariationParamValueByFeature(
190 features::kPermissionsBlacklist, kPermissionOriginEmbargoKey);
191 // If converting the value fails, stick with the current value.
192 if (base::StringToInt(dismissals_value, &prompt_dismissals) &&
193 prompt_dismissals > 0)
194 g_prompt_dismissals_before_block = prompt_dismissals;
195 if (base::StringToInt(embargo_value, &embargo_days) && embargo_days > 0)
196 g_embargo_days = embargo_days;
197 }
179 198
180 // If converting the value fails, stick with the current value. 199 // static
181 if (base::StringToInt(value, &prompt_dismissals) && prompt_dismissals > 0) 200 // TODO(meredithl): Have PermissionDecisionAutoBlocker handle the database
182 g_prompt_dismissals_before_block = prompt_dismissals; 201 // manager, rather than passing it in.
202 void PermissionDecisionAutoBlocker::ShouldAutomaticallyBlock(
203 scoped_refptr<safe_browsing::SafeBrowsingDatabaseManager> db_manager,
204 content::PermissionType permission,
205 const GURL& request_origin,
206 content::WebContents* web_contents,
207 int timeout,
208 Profile* profile,
209 base::Time current_time,
210 base::Callback<void(bool)> callback) {
211 if (!base::FeatureList::IsEnabled(features::kPermissionsBlacklist)) {
212 callback.Run(false /* permission blocked */);
213 } else if (IsUnderEmbargo(permission, profile, request_origin,
214 current_time)) {
215 callback.Run(true /* permission blocked */);
216 } else if (!db_manager) {
217 callback.Run(false /* permission blocked */);
218 } else {
219 // Request origin is not yet under embargo, so we check it with Safe
220 // Browsing.
221 PermissionBlacklistClient::CheckSafeBrowsingBlacklist(
222 db_manager, permission, request_origin, web_contents, timeout,
223 base::Bind(&PermissionDecisionAutoBlocker::CheckSafeBrowsingResult,
224 permission, profile, request_origin, current_time,
225 callback));
226 }
183 } 227 }
228
229 // static
230 void PermissionDecisionAutoBlocker::CheckSafeBrowsingResult(
231 content::PermissionType permission,
232 Profile* profile,
233 const GURL& request_origin,
234 base::Time current_time,
235 base::Callback<void(bool)> callback,
236 bool should_be_embargoed) {
237 if (should_be_embargoed) {
238 // Requesting site is blacklisted for this permission, update the content
239 // setting to place it under embargo.
240 PlaceUnderEmbargo(permission, request_origin,
241 HostContentSettingsMapFactory::GetForProfile(profile),
242 current_time);
243 }
244 callback.Run(should_be_embargoed /* permission blocked */);
245 }
246
247 // static
248 bool PermissionDecisionAutoBlocker::IsUnderEmbargo(
249 content::PermissionType permission,
250 Profile* profile,
251 const GURL& request_origin,
252 base::Time current_time) {
253 HostContentSettingsMap* map =
254 HostContentSettingsMapFactory::GetForProfile(profile);
255 std::unique_ptr<base::DictionaryValue> dict =
256 GetOriginDict(map, request_origin);
257 base::DictionaryValue* permission_dict = GetOrCreatePermissionDict(
258 dict.get(), PermissionUtil::GetPermissionString(permission));
259 double embargo_date = -1;
260 if ((permission_dict->GetDouble(kPermissionOriginEmbargoKey,
261 &embargo_date))) {
262 if (current_time < base::Time::FromInternalValue(embargo_date) +
263 base::TimeDelta::FromDays(g_embargo_days))
264 return true;
265 }
266 return false;
267 }
268
269 // static
270 void PermissionDecisionAutoBlocker::PlaceUnderEmbargo(
271 content::PermissionType permission,
272 const GURL& request_origin,
273 HostContentSettingsMap* map,
274 base::Time current_time) {
275 std::unique_ptr<base::DictionaryValue> dict =
276 GetOriginDict(map, request_origin);
277 base::DictionaryValue* permission_dict = GetOrCreatePermissionDict(
278 dict.get(), PermissionUtil::GetPermissionString(permission));
279 permission_dict->SetDouble(kPermissionOriginEmbargoKey,
280 current_time.ToInternalValue());
281 map->SetWebsiteSettingDefaultScope(
282 request_origin, GURL(), CONTENT_SETTINGS_TYPE_PROMPT_NO_DECISION_COUNT,
raymes 2017/01/16 02:23:42 We need to decide what to do about this pref. It d
meredithl 2017/01/16 04:28:20 Sgtm. The original plan was to rename it, but if t
283 std::string(), std::move(dict));
284 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698