mirror of
https://github.com/gorhill/uBlock.git
synced 2024-11-22 18:32:45 +01:00
[mv3] Add badge reflecting number of injectable content on current site
Additonally, general code review.
This commit is contained in:
parent
c0bce368a7
commit
e1b54514cc
@ -185,11 +185,12 @@ body.mobile.no-tooltips .toolRibbon .tool {
|
||||
position: relative;
|
||||
}
|
||||
#toggleGreatPowers .badge {
|
||||
bottom: 4px;
|
||||
font-size: var(--font-size-xsmall);
|
||||
line-height: 1;
|
||||
right: 4px;
|
||||
pointer-events: none;
|
||||
position: absolute;
|
||||
bottom: 2px;
|
||||
right: 4px;
|
||||
}
|
||||
body:not(.hasGreatPowers) [data-i18n-title="popupGrantGreatPowers"],
|
||||
body.hasGreatPowers [data-i18n-title="popupRevokeGreatPowers"] {
|
||||
|
@ -27,7 +27,8 @@
|
||||
|
||||
import { browser, dnr, i18n, runtime } from './ext.js';
|
||||
import { fetchJSON } from './fetch.js';
|
||||
import { registerInjectable } from './scripting-manager.js';
|
||||
import { getInjectableCount, registerInjectable } from './scripting-manager.js';
|
||||
import { parsedURLromOrigin } from './utils.js';
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
@ -229,7 +230,9 @@ async function updateRegexRules() {
|
||||
/******************************************************************************/
|
||||
|
||||
async function matchesTrustedSiteDirective(details) {
|
||||
const url = new URL(details.origin);
|
||||
const url = parsedURLromOrigin(details.origin);
|
||||
if ( url === undefined ) { return false; }
|
||||
|
||||
const dynamicRuleMap = await getDynamicRules();
|
||||
let rule = dynamicRuleMap.get(TRUSTED_DIRECTIVE_BASE_RULE_ID);
|
||||
if ( rule === undefined ) { return false; }
|
||||
@ -241,11 +244,14 @@ async function matchesTrustedSiteDirective(details) {
|
||||
if ( pos === -1 ) { break; }
|
||||
hostname = hostname.slice(pos+1);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
async function addTrustedSiteDirective(details) {
|
||||
const url = new URL(details.origin);
|
||||
const url = parsedURLromOrigin(details.origin);
|
||||
if ( url === undefined ) { return false; }
|
||||
|
||||
const dynamicRuleMap = await getDynamicRules();
|
||||
let rule = dynamicRuleMap.get(TRUSTED_DIRECTIVE_BASE_RULE_ID);
|
||||
if ( rule !== undefined ) {
|
||||
@ -254,6 +260,7 @@ async function addTrustedSiteDirective(details) {
|
||||
rule.condition.requestDomains = [];
|
||||
}
|
||||
}
|
||||
|
||||
if ( rule === undefined ) {
|
||||
rule = {
|
||||
id: TRUSTED_DIRECTIVE_BASE_RULE_ID,
|
||||
@ -270,15 +277,19 @@ async function addTrustedSiteDirective(details) {
|
||||
} else if ( rule.condition.requestDomains.includes(url.hostname) === false ) {
|
||||
rule.condition.requestDomains.push(url.hostname);
|
||||
}
|
||||
|
||||
await dnr.updateDynamicRules({
|
||||
addRules: [ rule ],
|
||||
removeRuleIds: [ TRUSTED_DIRECTIVE_BASE_RULE_ID ],
|
||||
});
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
async function removeTrustedSiteDirective(details) {
|
||||
const url = new URL(details.origin);
|
||||
const url = parsedURLromOrigin(details.origin);
|
||||
if ( url === undefined ) { return false; }
|
||||
|
||||
const dynamicRuleMap = await getDynamicRules();
|
||||
let rule = dynamicRuleMap.get(TRUSTED_DIRECTIVE_BASE_RULE_ID);
|
||||
if ( rule === undefined ) { return false; }
|
||||
@ -286,6 +297,7 @@ async function removeTrustedSiteDirective(details) {
|
||||
if ( Array.isArray(rule.condition.requestDomains) === false ) {
|
||||
rule.condition.requestDomains = [];
|
||||
}
|
||||
|
||||
const domainSet = new Set(rule.condition.requestDomains);
|
||||
const beforeCount = domainSet.size;
|
||||
let hostname = url.hostname;
|
||||
@ -295,7 +307,9 @@ async function removeTrustedSiteDirective(details) {
|
||||
if ( pos === -1 ) { break; }
|
||||
hostname = hostname.slice(pos+1);
|
||||
}
|
||||
|
||||
if ( domainSet.size === beforeCount ) { return false; }
|
||||
|
||||
if ( domainSet.size === 0 ) {
|
||||
dynamicRuleMap.delete(TRUSTED_DIRECTIVE_BASE_RULE_ID);
|
||||
await dnr.updateDynamicRules({
|
||||
@ -303,11 +317,14 @@ async function removeTrustedSiteDirective(details) {
|
||||
});
|
||||
return false;
|
||||
}
|
||||
|
||||
rule.condition.requestDomains = Array.from(domainSet);
|
||||
|
||||
await dnr.updateDynamicRules({
|
||||
addRules: [ rule ],
|
||||
removeRuleIds: [ TRUSTED_DIRECTIVE_BASE_RULE_ID ],
|
||||
});
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
@ -450,11 +467,13 @@ function onMessage(request, sender, callback) {
|
||||
matchesTrustedSiteDirective(request),
|
||||
hasGreatPowers(request.origin),
|
||||
getEnabledRulesetsStats(),
|
||||
getInjectableCount(request.origin),
|
||||
]).then(results => {
|
||||
callback({
|
||||
isTrusted: results[0],
|
||||
hasGreatPowers: results[1],
|
||||
rulesetDetails: results[2],
|
||||
injectableCount: results[3],
|
||||
});
|
||||
});
|
||||
return true;
|
||||
@ -493,13 +512,15 @@ async function start() {
|
||||
// We need to update the regex rules only when ruleset version changes.
|
||||
const currentVersion = getCurrentVersion();
|
||||
if ( currentVersion !== rulesetConfig.version ) {
|
||||
await updateRegexRules();
|
||||
console.log(`Version change: ${rulesetConfig.version} => ${currentVersion}`);
|
||||
await Promise.all([
|
||||
updateRegexRules(),
|
||||
registerInjectable(),
|
||||
]);
|
||||
rulesetConfig.version = currentVersion;
|
||||
saveRulesetConfig();
|
||||
}
|
||||
|
||||
saveRulesetConfig();
|
||||
|
||||
const enabledRulesets = await dnr.getEnabledRulesets();
|
||||
console.log(`Enabled rulesets: ${enabledRulesets}`);
|
||||
|
||||
|
@ -219,6 +219,10 @@ async function init() {
|
||||
);
|
||||
|
||||
dom.text(qs$('#hostname'), tabHostname);
|
||||
dom.text(
|
||||
qs$('#toggleGreatPowers .badge'),
|
||||
popupPanelData.injectableCount || ''
|
||||
);
|
||||
|
||||
const parent = qs$('#rulesetStats');
|
||||
for ( const details of popupPanelData.rulesetDetails || [] ) {
|
||||
|
@ -27,6 +27,7 @@
|
||||
|
||||
import { browser, dnr } from './ext.js';
|
||||
import { fetchJSON } from './fetch.js';
|
||||
import { parsedURLromOrigin } from './utils.js';
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
@ -89,21 +90,21 @@ const toRegisterable = (fname, entry) => {
|
||||
id: fname,
|
||||
allFrames: true,
|
||||
};
|
||||
if ( entry.matches ) {
|
||||
if ( entry.y ) {
|
||||
directive.matches = matchesFromHostnames(entry.y);
|
||||
} else {
|
||||
directive.matches = [ '*://*/*' ];
|
||||
}
|
||||
if ( entry.excludeMatches ) {
|
||||
if ( entry.n ) {
|
||||
directive.excludeMatches = matchesFromHostnames(entry.n);
|
||||
}
|
||||
if ( entry.type === CSS_TYPE ) {
|
||||
directive.css = [
|
||||
`/content-css/${entry.id}/${fname.slice(0,1)}/${fname.slice(1,8)}.css`
|
||||
`/content-css/${fname.slice(0,1)}/${fname.slice(1,2)}/${fname.slice(2,8)}.css`
|
||||
];
|
||||
} else if ( entry.type === JS_TYPE ) {
|
||||
directive.js = [
|
||||
`/content-js/${entry.id}/${fname.slice(0,1)}/${fname.slice(1,8)}.js`
|
||||
`/content-js/${fname.slice(0,1)}/${fname.slice(1,8)}.js`
|
||||
];
|
||||
directive.runAt = 'document_start';
|
||||
directive.world = 'MAIN';
|
||||
@ -115,15 +116,12 @@ const toRegisterable = (fname, entry) => {
|
||||
/******************************************************************************/
|
||||
|
||||
const shouldRegister = (origins, matches) => {
|
||||
if ( Array.isArray(matches) === false ) { return true; }
|
||||
for ( const origin of origins ) {
|
||||
if ( origin === '*' || Array.isArray(matches) === false ) {
|
||||
return true;
|
||||
}
|
||||
if ( origin === '*' ) { return true; }
|
||||
let hn = origin;
|
||||
for (;;) {
|
||||
if ( matches.includes(hn) ) {
|
||||
return true;
|
||||
}
|
||||
if ( matches.includes(hn) ) { return true; }
|
||||
if ( hn === '*' ) { break; }
|
||||
const pos = hn.indexOf('.');
|
||||
hn = pos !== -1
|
||||
@ -136,7 +134,9 @@ const shouldRegister = (origins, matches) => {
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
async function getInjectableCount(hostname) {
|
||||
async function getInjectableCount(origin) {
|
||||
const url = parsedURLromOrigin(origin);
|
||||
if ( url === undefined ) { return 0; }
|
||||
|
||||
const [
|
||||
rulesetIds,
|
||||
@ -151,23 +151,22 @@ async function getInjectableCount(hostname) {
|
||||
let total = 0;
|
||||
|
||||
for ( const rulesetId of rulesetIds ) {
|
||||
|
||||
if ( cssDetails.has(rulesetId) ) {
|
||||
for ( const entry of cssDetails ) {
|
||||
if ( shouldRegister([ hostname ], entry[1].y) === true ) {
|
||||
const entries = cssDetails.get(rulesetId);
|
||||
for ( const entry of entries ) {
|
||||
if ( shouldRegister([ url.hostname ], entry[1].y) ) {
|
||||
total += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ( scriptletDetails.has(rulesetId) ) {
|
||||
for ( const entry of cssDetails ) {
|
||||
if ( shouldRegister([ hostname ], entry[1].y) === true ) {
|
||||
const entries = cssDetails.get(rulesetId);
|
||||
for ( const entry of entries ) {
|
||||
if ( shouldRegister([ url.hostname ], entry[1].y) ) {
|
||||
total += 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return total;
|
||||
@ -199,23 +198,47 @@ async function registerInjectable() {
|
||||
origins.add('*');
|
||||
}
|
||||
|
||||
const mergeEntries = (a, b) => {
|
||||
if ( b.y !== undefined ) {
|
||||
if ( a.y === undefined ) {
|
||||
a.y = new Set(b.y);
|
||||
} else {
|
||||
b.y.forEach(v => a.y.add(v));
|
||||
}
|
||||
}
|
||||
if ( b.n !== undefined ) {
|
||||
if ( a.n === undefined ) {
|
||||
a.n = new Set(b.n);
|
||||
} else {
|
||||
b.n.forEach(v => a.n.add(v));
|
||||
}
|
||||
}
|
||||
return a;
|
||||
};
|
||||
|
||||
const toRegister = new Map();
|
||||
|
||||
for ( const rulesetId of rulesetIds ) {
|
||||
if ( cssDetails.has(rulesetId) ) {
|
||||
for ( const [ fname, entry ] of cssDetails.get(rulesetId) ) {
|
||||
entry.id = rulesetId;
|
||||
entry.type = CSS_TYPE;
|
||||
if ( shouldRegister(origins, entry.y) !== true ) { continue; }
|
||||
toRegister.set(fname, entry);
|
||||
if ( shouldRegister(origins, entry.y) === false ) { continue; }
|
||||
let existing = toRegister.get(fname);
|
||||
if ( existing === undefined ) {
|
||||
existing = { type: CSS_TYPE };
|
||||
toRegister.set(fname, existing);
|
||||
}
|
||||
mergeEntries(existing, entry);
|
||||
}
|
||||
}
|
||||
if ( scriptletDetails.has(rulesetId) ) {
|
||||
for ( const [ fname, entry ] of scriptletDetails.get(rulesetId) ) {
|
||||
entry.id = rulesetId;
|
||||
entry.type = JS_TYPE;
|
||||
if ( shouldRegister(origins, entry.y) !== true ) { continue; }
|
||||
toRegister.set(fname, entry);
|
||||
if ( shouldRegister(origins, entry.y) === false ) { continue; }
|
||||
let existing = toRegister.get(fname);
|
||||
if ( existing === undefined ) {
|
||||
existing = { type: JS_TYPE };
|
||||
toRegister.set(fname, existing);
|
||||
}
|
||||
mergeEntries(existing, entry);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
37
platform/mv3/extension/js/utils.js
Normal file
37
platform/mv3/extension/js/utils.js
Normal file
@ -0,0 +1,37 @@
|
||||
/*******************************************************************************
|
||||
|
||||
uBlock Origin - a browser extension to block requests.
|
||||
Copyright (C) 2022-present Raymond Hill
|
||||
|
||||
This program is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
This program is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with this program. If not, see {http://www.gnu.org/licenses/}.
|
||||
|
||||
Home: https://github.com/gorhill/uBlock
|
||||
*/
|
||||
|
||||
/* jshint esversion:11 */
|
||||
|
||||
'use strict';
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
function parsedURLromOrigin(origin) {
|
||||
try {
|
||||
return new URL(origin);
|
||||
} catch(ex) {
|
||||
}
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
export { parsedURLromOrigin };
|
@ -305,6 +305,8 @@ function optimizeExtendedFilters(filters) {
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
const globalCSSFileSet = new Set();
|
||||
|
||||
const style = [
|
||||
' display:none!important;',
|
||||
' position:absolute!important;',
|
||||
@ -320,15 +322,34 @@ function processCosmeticFilters(assetDetails, mapin) {
|
||||
for ( const entry of optimized ) {
|
||||
const selectors = entry.payload.join(',\n');
|
||||
const fname = createHash('sha256').update(selectors).digest('hex').slice(0,8);
|
||||
const fpath = `${assetDetails.id}/${fname.slice(0,1)}/${fname.slice(1,8)}`;
|
||||
writeFile(
|
||||
`${cssDir}/${fpath}.css`,
|
||||
`${selectors} {\n${style}\n}\n`
|
||||
);
|
||||
cssEntries.set(fname, {
|
||||
y: entry.matches,
|
||||
n: entry.excludeMatches,
|
||||
});
|
||||
if ( globalCSSFileSet.has(fname) === false ) {
|
||||
globalCSSFileSet.add(fname);
|
||||
const fpath = `${fname.slice(0,1)}/${fname.slice(1,2)}/${fname.slice(2,8)}`;
|
||||
writeFile(
|
||||
`${cssDir}/${fpath}.css`,
|
||||
`${selectors} {\n${style}\n}\n`
|
||||
);
|
||||
}
|
||||
const existing = cssEntries.get(fname);
|
||||
if ( existing === undefined ) {
|
||||
cssEntries.set(fname, {
|
||||
y: entry.matches,
|
||||
n: entry.excludeMatches,
|
||||
});
|
||||
continue;
|
||||
}
|
||||
if ( entry.matches ) {
|
||||
for ( const hn of entry.matches ) {
|
||||
if ( existing.y.includes(hn) ) { continue; }
|
||||
existing.y.push(hn);
|
||||
}
|
||||
}
|
||||
if ( entry.excludeMatches ) {
|
||||
for ( const hn of entry.excludeMatches ) {
|
||||
if ( existing.n.includes(hn) ) { continue; }
|
||||
existing.n.push(hn);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
log(`CSS entries: ${cssEntries.size}`);
|
||||
@ -342,11 +363,58 @@ function processCosmeticFilters(assetDetails, mapin) {
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
// Load all available scriptlets into a key-val map, where the key is the
|
||||
// scriptlet token, and val is the whole content of the file.
|
||||
|
||||
const scriptletDealiasingMap = new Map();
|
||||
let scriptletsMapPromise;
|
||||
|
||||
function loadAllScriptlets() {
|
||||
if ( scriptletsMapPromise !== undefined ) {
|
||||
return scriptletsMapPromise;
|
||||
}
|
||||
|
||||
scriptletsMapPromise = fs.readdir('./scriptlets').then(files => {
|
||||
const reScriptletNameOrAlias = /^\/\/\/\s+(?:name|alias)\s+(\S+)/gm;
|
||||
const readPromises = [];
|
||||
for ( const file of files ) {
|
||||
readPromises.push(
|
||||
fs.readFile(`./scriptlets/${file}`, { encoding: 'utf8' })
|
||||
);
|
||||
}
|
||||
return Promise.all(readPromises).then(results => {
|
||||
const originalScriptletMap = new Map();
|
||||
for ( const text of results ) {
|
||||
const aliasSet = new Set();
|
||||
for (;;) {
|
||||
const match = reScriptletNameOrAlias.exec(text);
|
||||
if ( match === null ) { break; }
|
||||
aliasSet.add(match[1]);
|
||||
}
|
||||
if ( aliasSet.size === 0 ) { continue; }
|
||||
const aliases = Array.from(aliasSet);
|
||||
originalScriptletMap.set(aliases[0], text);
|
||||
for ( let i = 0; i < aliases.length; i++ ) {
|
||||
scriptletDealiasingMap.set(aliases[i], aliases[0]);
|
||||
}
|
||||
}
|
||||
return originalScriptletMap;
|
||||
});
|
||||
});
|
||||
|
||||
return scriptletsMapPromise;
|
||||
}
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
const globalPatchedScriptletsSet = new Set();
|
||||
|
||||
async function processScriptletFilters(assetDetails, mapin) {
|
||||
if ( mapin === undefined ) { return 0; }
|
||||
|
||||
const originalScriptletMap = new Map();
|
||||
const dealiasingMap = new Map();
|
||||
// Load all available scriptlets into a key-val map, where the key is the
|
||||
// scriptlet token, and val is the whole content of the file.
|
||||
const originalScriptletMap = await loadAllScriptlets();
|
||||
|
||||
const parseArguments = (raw) => {
|
||||
const out = [];
|
||||
@ -376,7 +444,7 @@ async function processScriptletFilters(assetDetails, mapin) {
|
||||
let pos = filter.indexOf(',');
|
||||
if ( pos === -1 ) { pos = end; }
|
||||
const parts = filter.trim().split(',').map(s => s.trim());
|
||||
const token = dealiasingMap.get(parts[0]) || '';
|
||||
const token = scriptletDealiasingMap.get(parts[0]) || '';
|
||||
if ( token !== '' && originalScriptletMap.has(token) ) {
|
||||
return {
|
||||
token,
|
||||
@ -387,83 +455,45 @@ async function processScriptletFilters(assetDetails, mapin) {
|
||||
|
||||
const patchScriptlet = (filter) => {
|
||||
return originalScriptletMap.get(filter.token).replace(
|
||||
/^self\.\$args\$$/m,
|
||||
`...${JSON.stringify(filter.args, null, 4)}`
|
||||
/^(\}\)\(\.\.\.)self\.\$args\$(\);)$/m,
|
||||
`$1${JSON.stringify(filter.args, null, 4)}$2`
|
||||
);
|
||||
};
|
||||
|
||||
// Load all available scriptlets into a key-val map, where the key is the
|
||||
// scriptlet token, and val is the whole content of the file.
|
||||
const files = await fs.readdir('./scriptlets');
|
||||
const reScriptletNameOrAlias = /^\/\/\/\s+(?:name|alias)\s+(\S+)/gm;
|
||||
for ( const file of files ) {
|
||||
const text = await fs.readFile(
|
||||
`./scriptlets/${file}`,
|
||||
{ encoding: 'utf8' }
|
||||
);
|
||||
const aliasSet = new Set();
|
||||
for (;;) {
|
||||
const match = reScriptletNameOrAlias.exec(text);
|
||||
if ( match === null ) { break; }
|
||||
aliasSet.add(match[1]);
|
||||
}
|
||||
if ( aliasSet.size === 0 ) { continue; }
|
||||
const aliases = Array.from(aliasSet);
|
||||
originalScriptletMap.set(aliases[0], text);
|
||||
for ( let i = 0; i < aliases.length; i++ ) {
|
||||
dealiasingMap.set(aliases[i], aliases[0]);
|
||||
}
|
||||
}
|
||||
// Generate distinct scriptlet files according to patched scriptlets
|
||||
const scriptletEntries = new Map();
|
||||
|
||||
// Merge entries after dealiasing and expanding arguments
|
||||
const normalizedMap = new Map();
|
||||
for ( const [ rawFilter, toAdd ] of mapin ) {
|
||||
for ( const [ rawFilter, entry ] of mapin ) {
|
||||
const normalized = parseFilter(rawFilter);
|
||||
if ( normalized === undefined ) { continue; }
|
||||
const key = JSON.stringify(normalized);
|
||||
const toMerge = normalizedMap.get(key);
|
||||
if ( toMerge === undefined ) {
|
||||
normalizedMap.set(key, toAdd);
|
||||
const json = JSON.stringify(normalized);
|
||||
const fname = createHash('sha256').update(json).digest('hex').slice(0,8);
|
||||
if ( globalPatchedScriptletsSet.has(fname) === false ) {
|
||||
globalPatchedScriptletsSet.add(fname);
|
||||
const scriptlet = patchScriptlet(normalized);
|
||||
const fpath = `${fname.slice(0,1)}/${fname.slice(1,8)}`;
|
||||
writeFile(`${scriptletDir}/${fpath}.js`, scriptlet);
|
||||
}
|
||||
const existing = scriptletEntries.get(fname);
|
||||
if ( existing === undefined ) {
|
||||
scriptletEntries.set(fname, {
|
||||
y: entry.matches,
|
||||
n: entry.excludeMatches,
|
||||
});
|
||||
continue;
|
||||
}
|
||||
const matches = new Set(toMerge.matches || []);
|
||||
const excludeMatches = new Set(toMerge.excludeMatches || []);
|
||||
if ( toAdd.matches && toAdd.matches.size !== 0 ) {
|
||||
toAdd.matches.forEach(hn => {
|
||||
matches.add(hn);
|
||||
});
|
||||
if ( entry.matches ) {
|
||||
for ( const hn of entry.matches ) {
|
||||
if ( existing.y.includes(hn) ) { continue; }
|
||||
existing.y.push(hn);
|
||||
}
|
||||
}
|
||||
if ( toAdd.excludeMatches && toAdd.excludeMatches.size !== 0 ) {
|
||||
toAdd.excludeMatches.forEach(hn => {
|
||||
excludeMatches.add(hn);
|
||||
});
|
||||
if ( entry.excludeMatches ) {
|
||||
for ( const hn of entry.excludeMatches ) {
|
||||
if ( existing.n.includes(hn) ) { continue; }
|
||||
existing.n.push(hn);
|
||||
}
|
||||
}
|
||||
if ( matches.size !== 0 ) {
|
||||
toMerge.matches = matches.has('*')
|
||||
? [ '*' ]
|
||||
: Array.from(matches);
|
||||
}
|
||||
if ( excludeMatches.size !== 0 ) {
|
||||
toMerge.excludeMatches = excludeMatches.has('*')
|
||||
? [ '*' ]
|
||||
: Array.from(excludeMatches);
|
||||
}
|
||||
}
|
||||
|
||||
// Combine injected resources for same matches/excludeMatches instances
|
||||
//const optimized = optimizeExtendedFilters(normalizedMap);
|
||||
|
||||
// Generate distinct scriptlets according to patched scriptlets
|
||||
const scriptletEntries = new Map();
|
||||
for ( const [ json, entry ] of normalizedMap ) {
|
||||
const fname = createHash('sha256').update(json).digest('hex').slice(0,8);
|
||||
const scriptlet = patchScriptlet(JSON.parse(json));
|
||||
const fpath = `${assetDetails.id}/${fname.slice(0,1)}/${fname.slice(1,8)}`;
|
||||
writeFile(`${scriptletDir}/${fpath}.js`, scriptlet);
|
||||
scriptletEntries.set(fname, {
|
||||
y: entry.matches,
|
||||
n: entry.excludeMatches,
|
||||
});
|
||||
}
|
||||
|
||||
log(`Scriptlet entries: ${scriptletEntries.size}`);
|
||||
|
@ -137,9 +137,7 @@ try {
|
||||
return oe.apply(this, arguments);
|
||||
}
|
||||
}.bind();
|
||||
})(
|
||||
self.$args$
|
||||
);
|
||||
})(...self.$args$);
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
|
@ -113,9 +113,7 @@ try {
|
||||
return Reflect.apply(...arguments).then(o => pruner(o));
|
||||
},
|
||||
});
|
||||
})(
|
||||
self.$args$
|
||||
);
|
||||
})(...self.$args$);
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
|
@ -155,9 +155,7 @@ try {
|
||||
});
|
||||
};
|
||||
trapChain(window, chain);
|
||||
})(
|
||||
self.$args$
|
||||
);
|
||||
})(...self.$args$);
|
||||
|
||||
/******************************************************************************/
|
||||
|
||||
|
@ -4176,6 +4176,7 @@ FilterContainer.prototype.dnrFromCompiled = function(op, context, ...args) {
|
||||
};
|
||||
mergeRules(rulesetMap, 'resourceTypes');
|
||||
mergeRules(rulesetMap, 'initiatorDomains');
|
||||
mergeRules(rulesetMap, 'requestDomains');
|
||||
mergeRules(rulesetMap, 'removeParams');
|
||||
|
||||
// Patch case-sensitiveness
|
||||
|
Loading…
Reference in New Issue
Block a user