Commit 72e12fdc authored by Karan Bhatia's avatar Karan Bhatia Committed by Commit Bot

DNR: Impose limit on the max. no. of whitelisted page patterns per extension.

This CL imposes a limit on the maximum number of page patterns an extension can
whitelist using the chrome.declarativeNetRequest.addWhitelistedPages API. This
limit is currently set to 100. A new property MAX_NUMBER_OF_WHITELISTED_PAGES is
introduced in the declarativeNetRequest API for the same.

It is important to limit this since the whitelisted patterns are stored in the
browser memory (and also persisted across sessions using Extension preferences).

BUG=811460, 696822
Doc=https://docs.google.com/document/d/1Fhm-t0JCc3dcmwyBX_i7TGyuJ2QjqDechv1-VCRBo5o/edit?usp=sharing

Change-Id: I674da154107ac06269827272576f1af911f13338
Reviewed-on: https://chromium-review.googlesource.com/987392
Commit-Queue: Karan Bhatia <karandeepb@chromium.org>
Reviewed-by: default avatarIstiaque Ahmed <lazyboy@chromium.org>
Cr-Commit-Position: refs/heads/master@{#547983}
parent f0425606
...@@ -17,7 +17,11 @@ var checkUnordererArrayEquality = function(expected, actual) { ...@@ -17,7 +17,11 @@ var checkUnordererArrayEquality = function(expected, actual) {
chrome.test.runTests([ chrome.test.runTests([
function addWhitelistedPages() { function addWhitelistedPages() {
var toAdd = ['https://www.google.com/', 'https://www.yahoo.com/']; // Any duplicates in arguments will be filtered out.
var toAdd = [
'https://www.google.com/', 'https://www.google.com/',
'https://www.yahoo.com/'
];
chrome.declarativeNetRequest.addWhitelistedPages( chrome.declarativeNetRequest.addWhitelistedPages(
toAdd, callbackPass(function() {})); toAdd, callbackPass(function() {}));
}, },
...@@ -70,5 +74,65 @@ chrome.test.runTests([ ...@@ -70,5 +74,65 @@ chrome.test.runTests([
callbackPass(function(patterns) { callbackPass(function(patterns) {
checkUnordererArrayEquality(['https://www.yahoo.com/'], patterns); checkUnordererArrayEquality(['https://www.yahoo.com/'], patterns);
})); }));
},
function reachMaximumPatternLimit() {
var toAdd = [];
var numPatterns = 1; // The extension already has one whitelisted pattern.
while (numPatterns <
chrome.declarativeNetRequest.MAX_NUMBER_OF_WHITELISTED_PAGES) {
toAdd.push('https://' + numPatterns + '.com/');
numPatterns++;
}
chrome.declarativeNetRequest.addWhitelistedPages(
toAdd, callbackPass(function() {}));
},
function errorOnExceedingMaximumPatternLimit() {
chrome.declarativeNetRequest.addWhitelistedPages(
['https://example.com/'],
callbackFail(
'The number of whitelisted page patterns can\'t exceed ' +
chrome.declarativeNetRequest.MAX_NUMBER_OF_WHITELISTED_PAGES));
},
function addingDuplicatePatternSucceeds() {
// Adding a duplicate pattern should still succeed since the final set of
// whitelisted patterns is still at the limit.
chrome.declarativeNetRequest.addWhitelistedPages(
['https://www.yahoo.com/'], callbackPass(function() {}));
},
function verifyPatterns() {
chrome.declarativeNetRequest.getWhitelistedPages(
callbackPass(function(patterns) {
chrome.test.assertTrue(patterns.includes('https://www.yahoo.com/'));
chrome.test.assertEq(
chrome.declarativeNetRequest.MAX_NUMBER_OF_WHITELISTED_PAGES,
patterns.length, 'Incorrect number of patterns observed.');
}));
},
function removePattern() {
chrome.declarativeNetRequest.removeWhitelistedPages(
['https://www.yahoo.com/'], callbackPass(function() {}));
},
function addPattern() {
// Adding a pattern should now succeed since removing the pattern caused us
// to go under the limit.
chrome.declarativeNetRequest.addWhitelistedPages(
['https://www.example.com/'], callbackPass(function() {}));
},
function verifyPatterns() {
chrome.declarativeNetRequest.getWhitelistedPages(
callbackPass(function(patterns) {
chrome.test.assertTrue(patterns.includes('https://www.example.com/'));
chrome.test.assertEq(
chrome.declarativeNetRequest.MAX_NUMBER_OF_WHITELISTED_PAGES,
patterns.length, 'Incorrect number of patterns observed.');
}));
} }
]); ]);
...@@ -7,6 +7,7 @@ ...@@ -7,6 +7,7 @@
#include <utility> #include <utility>
#include "base/bind.h" #include "base/bind.h"
#include "base/strings/stringprintf.h"
#include "content/public/browser/browser_thread.h" #include "content/public/browser/browser_thread.h"
#include "extensions/browser/api/declarative_net_request/rules_monitor_service.h" #include "extensions/browser/api/declarative_net_request/rules_monitor_service.h"
#include "extensions/browser/api/declarative_net_request/ruleset_manager.h" #include "extensions/browser/api/declarative_net_request/ruleset_manager.h"
...@@ -74,8 +75,12 @@ DeclarativeNetRequestUpdateWhitelistedPagesFunction::UpdateWhitelistedPages( ...@@ -74,8 +75,12 @@ DeclarativeNetRequestUpdateWhitelistedPagesFunction::UpdateWhitelistedPages(
break; break;
} }
// TODO(crbug.com/811460): Impost a limit on the number of patterns that can if (static_cast<int>(new_set.size()) >
// be whitelisted by an extension. api::declarative_net_request::MAX_NUMBER_OF_WHITELISTED_PAGES) {
return RespondNow(Error(base::StringPrintf(
"The number of whitelisted page patterns can't exceed %d",
api::declarative_net_request::MAX_NUMBER_OF_WHITELISTED_PAGES)));
}
// Persist |new_set| as part of preferences. // Persist |new_set| as part of preferences.
prefs->SetDNRWhitelistedPages(extension_id(), new_set); prefs->SetDNRWhitelistedPages(extension_id(), new_set);
......
...@@ -117,15 +117,24 @@ namespace declarativeNetRequest { ...@@ -117,15 +117,24 @@ namespace declarativeNetRequest {
// Adds |page_patterns| to the set of whitelisted pages. Requests from these // Adds |page_patterns| to the set of whitelisted pages. Requests from these
// pages are not intercepted by the extension. These are persisted across // pages are not intercepted by the extension. These are persisted across
// browser sessions. // browser sessions.
// Note: MAX_NUMBER_OF_WHITELISTED_PAGES is the maximum number of
// whitelisted page an extension can add. Also, adding page patterns is
// atomic. In case of an error, no page pattern is added.
// |page_patterns| : Array of match patterns which are to be added to the // |page_patterns| : Array of match patterns which are to be added to the
// whitelist. // whitelist.
// |callback|: Called after the |page_patterns| have been added. // |callback|: Called after the |page_patterns| have been added.
// chrome.runtime.lastError will be set in case of an error, for example if
// an invalid page pattern is specified or the extension exceeded the
// maximum page patterns limit.
static void addWhitelistedPages(DOMString[] page_patterns, optional EmptyCallback callback); static void addWhitelistedPages(DOMString[] page_patterns, optional EmptyCallback callback);
// Removes |page_patterns| from the set of whitelisted pages. // Removes |page_patterns| from the set of whitelisted pages.
// Note: Removing page patterns is atomic. In case of an error, no page
// pattern is removed.
// |page_patterns| : Array of match patterns which are to be removed from // |page_patterns| : Array of match patterns which are to be removed from
// the whitelist. // the whitelist.
// |callback|: Called after the |page_patterns| have been removed. // |callback|: Called after the |page_patterns| have been removed.
// chrome.runtime.lastError will be set in case of an error.
static void removeWhitelistedPages(DOMString[] page_patterns, optional EmptyCallback callback); static void removeWhitelistedPages(DOMString[] page_patterns, optional EmptyCallback callback);
// Returns the current set of whitelisted pages. // Returns the current set of whitelisted pages.
...@@ -133,4 +142,8 @@ namespace declarativeNetRequest { ...@@ -133,4 +142,8 @@ namespace declarativeNetRequest {
static void getWhitelistedPages(GetWhitelistedPagesCallback callback); static void getWhitelistedPages(GetWhitelistedPagesCallback callback);
}; };
interface Properties {
// The maximum number of whitelisted pages that an extension can add.
[value=100] static long MAX_NUMBER_OF_WHITELISTED_PAGES();
};
}; };
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment