Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
109 changes: 60 additions & 49 deletions src/ext/background/main.js
Original file line number Diff line number Diff line change
Expand Up @@ -124,71 +124,82 @@ async function setBadgeCount() {
}
}

// on startup get declarativeNetRequests
// and set the requests for the session
// on startup set declarativeNetRequest rulesets
// should also check and refresh when:
// 1. dnr item save event in the page occurs
// 2. dnr item toggle event in the page occurs
// 3. external editor changes script file content
async function setSessionRules() {
async function setDNRRulesets() {
// not supported below safari 15.4
if (!browser.declarativeNetRequest.updateSessionRules) return;
await clearAllSessionRules();
if (!browser.declarativeNetRequest.updateDynamicRules) return;
const message = { name: "REQ_REQUESTS" };
const response = await sendNativeMessage(message);
if (response.error) {
console.error(response.error);
return;
}
// there are no rules to apply
if (!response.length) return;
// loop through response, parse the rules, push to array and log
const rules = [];
/** @type {import("webextension-polyfill").DeclarativeNetRequest.Rule[]} */
const addRules = [];
let ruleId = 1;
for (let i = 0; i < response.length; i++) {
const rule = response[i];
const code = JSON.parse(rule.code);
// check if an array or single rule
if (Array.isArray(code)) {
code.forEach((r) => rules.push(r));
console.info(`Setting session rule: ${rule.name} (${code.length})`);
} else {
rules.push(code);
console.info(`Setting session rule: ${rule.name}`);
if (
ruleId >
browser.declarativeNetRequest.MAX_NUMBER_OF_DYNAMIC_AND_SESSION_RULES
) {
console.warn(
"Rules exceed the maximum number, some rules will be ignored",
);
break;
}
const ruleset = response[i];
/** @type {Array} */
let rules;
try {
const res = JSON.parse(ruleset.code);
// check if an array or single rule
if (Array.isArray(res)) {
rules = res;
} else if (typeof res === "object") {
rules = [res];
} else {
console.warn(`Not a valid DNR ruleset: ${ruleset.name}`);
continue;
}
console.info(`Setting DNR ruleset: ${ruleset.name} (${rules.length})`);
} catch (error) {
console.warn(
`Failed parsed into a valid DNR ruleset: ${ruleset.name}`,
error,
);
continue;
}
for (const rule of rules) {
// simple check if it is a rule object
if (!rule.action || !rule.condition || !rule.id) {
console.warn("Not a valid DNR rule:", rule);
continue;
}
// set unique ids for all rules to ensure no repeats
rule.id = ruleId++;
addRules.push(rule);
}
}
// generate unique ids for all rules to ensure no repeats
const ids = randomNumberSet(1000, rules.length);
rules.map((rule, index) => (rule.id = ids[index]));
// remove all then add declarativeNetRequest rules
try {
await browser.declarativeNetRequest.updateSessionRules({ addRules: rules });
const oldRules = await browser.declarativeNetRequest.getDynamicRules();
const removeRuleIds = oldRules.map((rule) => rule.id);
await browser.declarativeNetRequest.updateDynamicRules({
addRules,
removeRuleIds,
});
} catch (error) {
console.error(`Error setting session rules: ${error}`);
return;
}
console.info(`Finished setting ${rules.length} session rules`);
}

async function clearAllSessionRules() {
const rules = await browser.declarativeNetRequest.getSessionRules();
if (!rules.length) return;
console.info(`Clearing ${rules.length} session rules`);
const ruleIds = rules.map((a) => a.id);
await browser.declarativeNetRequest.updateSessionRules({
removeRuleIds: ruleIds,
});
}

function randomNumberSet(max, count) {
// generates a set of random unique numbers
// returns an array
const numbers = new Set();
while (numbers.size < count) {
numbers.add(Math.floor(Math.random() * (max - 1 + 1)) + 1);
return console.error(error);
}
return [...numbers];
console.info(`Finished setting ${addRules.length} DNR rules`);
}

// the current update logic is similar to setSessionRules()
// the current update logic is similar to setDNRRulesets()
// this feature needs a more detailed redesign in the future
// https://github.com/quoid/userscripts/issues/453
async function getContextMenuItems() {
Expand Down Expand Up @@ -489,8 +500,8 @@ async function handleMessage(message, sender) {
}
return { status: "fulfilled" };
}
case "REFRESH_SESSION_RULES": {
setSessionRules();
case "REFRESH_DNR_RULES": {
setDNRRulesets();
break;
}
case "REFRESH_CONTEXT_MENU_SCRIPTS": {
Expand All @@ -512,7 +523,7 @@ browser.runtime.onInstalled.addListener(async () => {
await contentScriptRegistration(enable);
});
browser.runtime.onStartup.addListener(async () => {
setSessionRules();
setDNRRulesets();
getContextMenuItems();
});
// listens for messages from content script, popup and page
Expand All @@ -526,7 +537,7 @@ browser.windows.onFocusChanged.addListener(async (windowId) => {
}
nativeChecks();
setBadgeCount();
setSessionRules();
setDNRRulesets();
getContextMenuItems();
});
browser.webNavigation.onCompleted.addListener(setBadgeCount);
Expand Down
2 changes: 1 addition & 1 deletion src/ext/extension-page/Components/Editor/Editor.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -86,7 +86,7 @@
// set the newly saved file contents in codemirror instance
cmSetSavedCode(response.content);
// refresh session rules
browser.runtime.sendMessage({ name: "REFRESH_SESSION_RULES" });
browser.runtime.sendMessage({ name: "REFRESH_DNR_RULES" });
// refresh context-menu scripts
browser.runtime.sendMessage({ name: "REFRESH_CONTEXT_MENU_SCRIPTS" });
}
Expand Down
2 changes: 1 addition & 1 deletion src/ext/extension-page/Components/Sidebar/Sidebar.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -177,7 +177,7 @@
});
if (item.request) {
// refresh session rules
browser.runtime.sendMessage({ name: "REFRESH_SESSION_RULES" });
browser.runtime.sendMessage({ name: "REFRESH_DNR_RULES" });
}
} else {
log.add("Failed to toggle item", "error", true);
Expand Down
2 changes: 1 addition & 1 deletion src/ext/shared/dev.js
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ const _browser = {
const name = message.name;
console.info(`Got message: ${name}`);
let response = {};
if (name === "REFRESH_SESSION_RULES") {
if (name === "REFRESH_DNR_RULES") {
response = { success: true };
}
if (!responseCallback) {
Expand Down