Minor refactoring plus other minor changes

Added more evocative error messages to linter.

Made the content of _My filters_ trusted by default in
dev build.
This commit is contained in:
Raymond Hill 2023-10-22 08:53:01 -04:00
parent 5dd9584da2
commit e33c0f9d9c
No known key found for this signature in database
GPG Key ID: 25E1490B761470C2
9 changed files with 81 additions and 93 deletions

View File

@ -63,20 +63,14 @@ let cachedUserFilters = '';
let hintUpdateToken = 0;
const getHints = async function() {
const response = await vAPI.messaging.send('dashboard', {
const hints = await vAPI.messaging.send('dashboard', {
what: 'getAutoCompleteDetails',
hintUpdateToken
});
if ( response instanceof Object === false ) { return; }
if ( response.hintUpdateToken !== undefined ) {
const mode = cmEditor.getMode();
if ( mode.setHints instanceof Function ) {
mode.setHints(response);
}
if ( hintUpdateToken === 0 ) {
mode.parser.expertMode = response.expertMode !== false;
}
hintUpdateToken = response.hintUpdateToken;
if ( hints instanceof Object === false ) { return; }
if ( hints.hintUpdateToken !== undefined ) {
cmEditor.setOption('uboHints', hints);
hintUpdateToken = hints.hintUpdateToken;
}
timer.on(2503);
};

View File

@ -72,9 +72,7 @@ import './codemirror/ubo-static-filtering.js';
what: 'getAutoCompleteDetails'
}).then(hints => {
if ( hints instanceof Object === false ) { return; }
const mode = cmEditor.getMode();
if ( mode.setHints instanceof Function === false ) { return; }
mode.setHints(hints);
cmEditor.setOption('uboHints', hints);
});
vAPI.messaging.send('dashboard', {

View File

@ -89,6 +89,10 @@ const hiddenSettingsDefault = {
userResourcesLocation: 'unset',
};
if ( vAPI.webextFlavor.soup.has('devbuild') ) {
hiddenSettingsDefault.trustedListPrefixes += ' user-';
}
const userSettingsDefault = {
advancedUserEnabled: false,
alwaysDetachLogger: true,

View File

@ -39,22 +39,19 @@ let hintHelperRegistered = false;
/******************************************************************************/
const trustedScriptletTokens = new Set();
let trustedSource = false;
CodeMirror.defineOption('trustedSource', false, (cm, value) => {
trustedSource = value;
self.dispatchEvent(new Event('trustedSource'));
CodeMirror.defineOption('trustedSource', false, (cm, state) => {
if ( typeof state !== 'boolean' ) { return; }
self.dispatchEvent(new CustomEvent('trustedSource', {
detail: state,
}));
});
CodeMirror.defineOption('trustedScriptletTokens', trustedScriptletTokens, (cm, tokens) => {
CodeMirror.defineOption('trustedScriptletTokens', undefined, (cm, tokens) => {
if ( tokens === undefined || tokens === null ) { return; }
if ( typeof tokens[Symbol.iterator] !== 'function' ) { return; }
trustedScriptletTokens.clear();
for ( const token of tokens ) {
trustedScriptletTokens.add(token);
}
self.dispatchEvent(new Event('trustedScriptletTokens'));
self.dispatchEvent(new CustomEvent('trustedScriptletTokens', {
detail: new Set(tokens),
}));
});
/******************************************************************************/
@ -63,8 +60,6 @@ CodeMirror.defineMode('ubo-static-filtering', function() {
const astParser = new sfp.AstFilterParser({
interactive: true,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),
trustedSource,
trustedScriptletTokens,
});
const astWalker = astParser.getWalker();
let currentWalkerNode = 0;
@ -226,12 +221,12 @@ CodeMirror.defineMode('ubo-static-filtering', function() {
return '+';
};
self.addEventListener('trustedSource', ( ) => {
astParser.options.trustedSource = trustedSource;
self.addEventListener('trustedSource', ev => {
astParser.options.trustedSource = ev.detail;
});
self.addEventListener('trustedScriptletTokens', ( ) => {
astParser.options.trustedScriptletTokens = trustedScriptletTokens;
self.addEventListener('trustedScriptletTokens', ev => {
astParser.options.trustedScriptletTokens = ev.detail;
});
return {
@ -283,9 +278,19 @@ CodeMirror.defineMode('ubo-static-filtering', function() {
style = style.trim();
return style !== '' ? style : null;
},
setHints: function(details) {
if ( Array.isArray(details.redirectResources) ) {
for ( const [ name, desc ] of details.redirectResources ) {
parser: astParser,
};
});
/******************************************************************************/
// Following code is for auto-completion. Reference:
// https://codemirror.net/demo/complete.html
CodeMirror.defineOption('uboHints', null, (cm, hints) => {
if ( hints instanceof Object === false ) { return; }
if ( Array.isArray(hints.redirectResources) ) {
for ( const [ name, desc ] of hints.redirectResources ) {
const displayText = desc.aliasOf !== ''
? `${name} (${desc.aliasOf})`
: '';
@ -297,34 +302,25 @@ CodeMirror.defineMode('ubo-static-filtering', function() {
}
}
}
if ( Array.isArray(details.preparseDirectiveEnv)) {
if ( Array.isArray(hints.preparseDirectiveEnv)) {
preparseDirectiveEnv.length = 0;
preparseDirectiveEnv.push(...details.preparseDirectiveEnv);
preparseDirectiveEnv.push(...hints.preparseDirectiveEnv);
}
if ( Array.isArray(details.preparseDirectiveHints)) {
preparseDirectiveHints.push(...details.preparseDirectiveHints);
if ( Array.isArray(hints.preparseDirectiveHints)) {
preparseDirectiveHints.push(...hints.preparseDirectiveHints);
}
if ( Array.isArray(details.originHints) ) {
if ( Array.isArray(hints.originHints) ) {
originHints.length = 0;
for ( const hint of details.originHints ) {
for ( const hint of hints.originHints ) {
originHints.push(hint);
}
}
if ( hintHelperRegistered === false ) {
if ( hintHelperRegistered ) { return; }
hintHelperRegistered = true;
initHints();
}
},
parser: astParser,
};
});
/******************************************************************************/
// Following code is for auto-completion. Reference:
// https://codemirror.net/demo/complete.html
const initHints = function() {
function initHints() {
const astParser = new sfp.AstFilterParser({
interactive: true,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),
@ -629,7 +625,7 @@ const initHints = function() {
}
return getOriginHints(cursor, line);
});
};
}
/******************************************************************************/
@ -695,8 +691,6 @@ CodeMirror.registerHelper('fold', 'ubo-static-filtering', (( ) => {
const astParser = new sfp.AstFilterParser({
interactive: true,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),
trustedSource,
trustedScriptletTokens,
});
const changeset = [];
@ -724,6 +718,9 @@ CodeMirror.registerHelper('fold', 'ubo-static-filtering', (( ) => {
case sfp.AST_ERROR_DOMAIN_NAME:
msg = `${msg}: Bad domain name`;
break;
case sfp.AST_ERROR_OPTION_BADVALUE:
msg = `${msg}: Bad value assigned to a valid option`;
break;
case sfp.AST_ERROR_OPTION_DUPLICATE:
msg = `${msg}: Duplicate filter option`;
break;
@ -1011,12 +1008,12 @@ CodeMirror.registerHelper('fold', 'ubo-static-filtering', (( ) => {
}
};
self.addEventListener('trustedSource', ( ) => {
astParser.options.trustedSource = trustedSource;
self.addEventListener('trustedSource', ev => {
astParser.options.trustedSource = ev.detail;
});
self.addEventListener('trustedScriptletTokens', ( ) => {
astParser.options.trustedScriptletTokens = trustedScriptletTokens;
self.addEventListener('trustedScriptletTokens', ev => {
astParser.options.trustedScriptletTokens = ev.detail;
});
CodeMirror.defineInitHook(cm => {

View File

@ -89,13 +89,10 @@ const cmEditor = new CodeMirror(document.querySelector('.codeMirrorContainer'),
vAPI.messaging.send('dashboard', {
what: 'getAutoCompleteDetails'
}).then(response => {
}).then(hints => {
// For unknown reasons, `instanceof Object` does not work here in Firefox.
if ( typeof response !== 'object' ) { return; }
const mode = cmEditor.getMode();
if ( mode.setHints instanceof Function ) {
mode.setHints(response);
}
if ( hints instanceof Object === false ) { return; }
cmEditor.setOption('uboHints', hints);
});
/******************************************************************************/

View File

@ -1602,9 +1602,7 @@ const onMessage = function(request, sender, callback) {
if ( (request.hintUpdateToken || 0) === 0 ) {
response.redirectResources = redirectEngine.getResourceDetails();
response.preparseDirectiveEnv = vAPI.webextFlavor.env.slice();
response.preparseDirectiveHints =
sfp.utils.preparser.getHints();
response.expertMode = µb.hiddenSettings.filterAuthorMode;
response.preparseDirectiveHints = sfp.utils.preparser.getHints();
}
if ( request.hintUpdateToken !== µb.pageStoresToken ) {
response.originHints = getOriginHints();

View File

@ -130,7 +130,6 @@ const fromNetFilter = async function(rawFilter) {
const writer = new CompiledListWriter();
const parser = new sfp.AstFilterParser({
expertMode: true,
trustedSource: true,
maxTokenLength: staticNetFilteringEngine.MAX_TOKEN_LENGTH,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),
@ -169,7 +168,6 @@ const fromExtendedFilter = async function(details) {
const hostname = hostnameFromURI(details.url);
const parser = new sfp.AstFilterParser({
expertMode: true,
trustedSource: true,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),
});

View File

@ -99,6 +99,7 @@ export const AST_ERROR_PATTERN = 1 << iota++;
export const AST_ERROR_DOMAIN_NAME = 1 << iota++;
export const AST_ERROR_OPTION_DUPLICATE = 1 << iota++;
export const AST_ERROR_OPTION_UNKNOWN = 1 << iota++;
export const AST_ERROR_OPTION_BADVALUE = 1 << iota++;
export const AST_ERROR_IF_TOKEN_UNKNOWN = 1 << iota++;
export const AST_ERROR_UNTRUSTED_SOURCE = 1 << iota++;
@ -845,7 +846,6 @@ export class AstFilterParser {
// Options
this.options = options;
this.interactive = options.interactive || false;
this.expertMode = options.expertMode || false;
this.badTypes = new Set(options.badTypes || []);
this.maxTokenLength = options.maxTokenLength || 7;
// TODO: rethink this
@ -1475,11 +1475,17 @@ export class AstFilterParser {
break;
}
case NODE_TYPE_NET_OPTION_NAME_URLTRANSFORM:
realBad = abstractTypeCount || behaviorTypeCount || unredirectableTypeCount ||
this.options.trustedSource !== true;
if ( realBad !== true ) {
realBad = abstractTypeCount || behaviorTypeCount || unredirectableTypeCount;
if ( realBad ) { break; }
if ( this.options.trustedSource !== true ) {
this.astError = AST_ERROR_UNTRUSTED_SOURCE;
realBad = true;
break;
}
const path = this.getNetOptionValue(NODE_TYPE_NET_OPTION_NAME_URLTRANSFORM);
realBad = path.charCodeAt(0) !== 0x2F /* / */;
if ( path.charCodeAt(0) !== 0x2F /* / */ ) {
this.astError = AST_ERROR_OPTION_BADVALUE;
realBad = true;
}
break;
case NODE_TYPE_NET_OPTION_NAME_REMOVEPARAM:

View File

@ -1069,11 +1069,7 @@ import {
writer.properties.set('trustedSource', trustedSource);
}
const assetName = details.assetKey ? details.assetKey : '?';
const expertMode =
details.assetKey !== this.userFiltersPath ||
this.hiddenSettings.filterAuthorMode !== false;
const parser = new sfp.AstFilterParser({
expertMode,
trustedSource,
maxTokenLength: staticNetFilteringEngine.MAX_TOKEN_LENGTH,
nativeCssHas: vAPI.webextFlavor.env.includes('native_css_has'),