refactor(scripts): completely redesign scripts moving logic to background and improving content
This commit is contained in:
parent
115312c732
commit
cbe54df40c
@ -1,3 +1,14 @@
|
||||
/**
|
||||
* @var cacheInitialState
|
||||
* @description Cache initial state
|
||||
* @type {{ enabled: boolean, matches: string[] }}
|
||||
*/
|
||||
|
||||
const cacheInitialState = {
|
||||
enabled: true,
|
||||
matches: [],
|
||||
};
|
||||
|
||||
/**
|
||||
* @function disableIcon
|
||||
* @description Disables icon
|
||||
@ -8,7 +19,7 @@
|
||||
const disableIcon = (tabId) => {
|
||||
chrome.browserAction.setIcon({
|
||||
path: "assets/icons/disabled.png",
|
||||
tabId: tabId,
|
||||
tabId,
|
||||
});
|
||||
};
|
||||
|
||||
@ -22,7 +33,7 @@ const disableIcon = (tabId) => {
|
||||
const disablePopup = (tabId) => {
|
||||
chrome.browserAction.setPopup({
|
||||
popup: "",
|
||||
tabId: tabId,
|
||||
tabId,
|
||||
});
|
||||
};
|
||||
|
||||
@ -36,7 +47,7 @@ const disablePopup = (tabId) => {
|
||||
const enableIcon = (tabId) => {
|
||||
chrome.browserAction.setIcon({
|
||||
path: "assets/icons/enabled.png",
|
||||
tabId: tabId,
|
||||
tabId,
|
||||
});
|
||||
};
|
||||
|
||||
@ -50,15 +61,78 @@ const enableIcon = (tabId) => {
|
||||
const enablePopup = (tabId) => {
|
||||
chrome.browserAction.setPopup({
|
||||
popup: "popup.html",
|
||||
tabId: tabId,
|
||||
tabId,
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function getCache
|
||||
* @description Retrieves cache state
|
||||
*
|
||||
* @returns {Promise<{ enabled: boolean, matches: string[] }>} Cache state
|
||||
*/
|
||||
|
||||
const getCache = async (hostname, responseCallback) => {
|
||||
chrome.storage.local.get(null, (store) => {
|
||||
const cache = store[hostname];
|
||||
|
||||
if (cache) {
|
||||
responseCallback(cache);
|
||||
} else {
|
||||
chrome.storage.local.set({ [hostname]: cacheInitialState });
|
||||
responseCallback(cacheInitialState);
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function updateCache
|
||||
* @description Update cache state
|
||||
*/
|
||||
|
||||
const updateCache = async (hostname, selector) => {
|
||||
chrome.storage.local.get(null, (cache) => {
|
||||
const current = cache[hostname];
|
||||
|
||||
chrome.storage.local.set({
|
||||
[hostname]: {
|
||||
...current,
|
||||
matches: [...new Set([...current.matches, selector])],
|
||||
},
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function getList
|
||||
* @description Retrieves selectors list
|
||||
*
|
||||
* @returns {Promise<{ matches: string[] }>} A selectors list
|
||||
*/
|
||||
|
||||
const getList = async (responseCallback) => {
|
||||
try {
|
||||
const url =
|
||||
"https://raw.githubusercontent.com/wanhose/do-not-consent/master/data/elements.txt";
|
||||
const response = await fetch(url);
|
||||
const data = await response.text();
|
||||
|
||||
if (response.status !== 200) throw new Error();
|
||||
|
||||
responseCallback({ matches: data.split("\n") });
|
||||
} catch {
|
||||
responseCallback({ matches: [] });
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @description Listens to content messages
|
||||
*/
|
||||
|
||||
chrome.runtime.onMessage.addListener((request) => {
|
||||
chrome.runtime.onMessage.addListener((request, sender, responseCallback) => {
|
||||
chrome.tabs.query({ active: true, currentWindow: true }, (tabs) => {
|
||||
const tab = tabs[0];
|
||||
const tabId = tab.id;
|
||||
@ -76,8 +150,19 @@ chrome.runtime.onMessage.addListener((request) => {
|
||||
case "ENABLE_POPUP":
|
||||
enablePopup(tabId);
|
||||
break;
|
||||
case "GET_CACHE":
|
||||
getCache(request.hostname, responseCallback);
|
||||
break;
|
||||
case "GET_LIST":
|
||||
getList(responseCallback);
|
||||
break;
|
||||
case "UPDATE_CACHE":
|
||||
updateCache(request.hostname, request.selector);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
});
|
||||
|
||||
return true;
|
||||
});
|
||||
|
@ -7,48 +7,36 @@
|
||||
let attempts = 1;
|
||||
|
||||
/**
|
||||
* @var enabled
|
||||
* @description Is extension enabled?
|
||||
* @var intervalId
|
||||
* @description Task interval identifier
|
||||
* @type {number}
|
||||
*/
|
||||
|
||||
let intervalId = 0;
|
||||
|
||||
/**
|
||||
* @var ready
|
||||
* @description Is extension ready?
|
||||
* @type {boolean}
|
||||
*/
|
||||
|
||||
let enabled = true;
|
||||
let ready = false;
|
||||
|
||||
/**
|
||||
* @var selectors
|
||||
* @var selectorsFromCache
|
||||
* @description Array of selectors
|
||||
* @type {string[]}
|
||||
*/
|
||||
|
||||
let selectors = [];
|
||||
let selectorsFromCache = [];
|
||||
|
||||
/**
|
||||
* @constant url
|
||||
* @description Database link
|
||||
* @type {string}
|
||||
* @var selectorsFromNetwork
|
||||
* @description Array of selectors
|
||||
* @type {string[]}
|
||||
*/
|
||||
|
||||
const url =
|
||||
"https://raw.githubusercontent.com/wanhose/do-not-consent/master/data/elements.txt";
|
||||
|
||||
/**
|
||||
* @function commit
|
||||
* @description Commits selector to cache
|
||||
* @param {string} selector
|
||||
*/
|
||||
|
||||
const commit = (selector) => {
|
||||
chrome.storage.local.get(null, (cache) => {
|
||||
const current = cache[document.location.hostname];
|
||||
|
||||
chrome.storage.local.set({
|
||||
[document.location.hostname]: {
|
||||
...current,
|
||||
matches: [...new Set([...cache.matches, selector])],
|
||||
},
|
||||
});
|
||||
});
|
||||
};
|
||||
let selectorsFromNetwork = [];
|
||||
|
||||
/**
|
||||
* @function fix
|
||||
@ -58,11 +46,12 @@ const commit = (selector) => {
|
||||
const fix = () => {
|
||||
const html = document.documentElement;
|
||||
const body = document.body;
|
||||
const facebook = document.querySelector("._31e");
|
||||
const facebook = document.getElementsByClassName("._31e")[0];
|
||||
|
||||
html.style.setProperty("overflow-y", "unset", "important");
|
||||
body.style.setProperty("overflow-y", "unset", "important");
|
||||
if (facebook) root.style.setProperty("position", "unset", "important");
|
||||
if (body) body.style.setProperty("overflow-y", "unset", "important");
|
||||
if (facebook) facebook.style.setProperty("position", "unset", "important");
|
||||
if (html) html.style.setProperty("overflow-y", "unset", "important");
|
||||
if (ready) html.style.setProperty("opacity", "1", "important");
|
||||
};
|
||||
|
||||
/**
|
||||
@ -89,59 +78,25 @@ const search = (selector) => {
|
||||
return null;
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function check
|
||||
* @description Checks if extension is enabled
|
||||
* @returns {Promise<boolean>}
|
||||
*/
|
||||
|
||||
const check = () =>
|
||||
new Promise((resolve) => {
|
||||
chrome.storage.local.get(null, (store) => {
|
||||
try {
|
||||
const cache = store[document.location.hostname];
|
||||
|
||||
resolve(cache.enabled);
|
||||
} catch {
|
||||
chrome.storage.local.set(
|
||||
{
|
||||
[document.location.hostname]: {
|
||||
enabled: true,
|
||||
matches: [],
|
||||
},
|
||||
},
|
||||
() => resolve(true)
|
||||
);
|
||||
}
|
||||
});
|
||||
});
|
||||
|
||||
/**
|
||||
* @function removeFromCache
|
||||
* @description Removes matched elements from cache results
|
||||
*/
|
||||
|
||||
const removeFromCache = () => {
|
||||
chrome.storage.local.get(null, (store) => {
|
||||
const cache = store[document.location.hostname];
|
||||
const matches = cache.matches;
|
||||
for (let i = selectorsFromCache.length; i--; ) {
|
||||
const selector = selectorsFromCache[i];
|
||||
const element = search(selector);
|
||||
|
||||
if (!!matches.length) {
|
||||
for (let i = matches.length; i--; ) {
|
||||
const selector = selectors[i];
|
||||
const element = search(selector);
|
||||
if (element) {
|
||||
const tagName = element.tagName.toUpperCase();
|
||||
|
||||
if (element) {
|
||||
const tagName = element.tagName.toUpperCase();
|
||||
|
||||
if (!["BODY", "HTML"].includes(tagName)) {
|
||||
element.remove();
|
||||
}
|
||||
}
|
||||
if (!["BODY", "HTML"].includes(tagName)) {
|
||||
element.remove();
|
||||
ready = true;
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
@ -150,8 +105,8 @@ const removeFromCache = () => {
|
||||
*/
|
||||
|
||||
const removeFromNetwork = () => {
|
||||
for (let i = selectors.length; i--; ) {
|
||||
const selector = selectors[i];
|
||||
for (let i = selectorsFromNetwork.length; i--; ) {
|
||||
const selector = selectorsFromNetwork[i];
|
||||
const element = search(selector);
|
||||
|
||||
if (element) {
|
||||
@ -159,88 +114,61 @@ const removeFromNetwork = () => {
|
||||
|
||||
if (!["BODY", "HTML"].includes(tagName)) {
|
||||
element.remove();
|
||||
commit(selector);
|
||||
ready = true;
|
||||
chrome.runtime.sendMessage({
|
||||
hostname: document.location.hostname,
|
||||
selector,
|
||||
type: "UPDATE_CACHE",
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function query
|
||||
* @description Retrieves selectors list
|
||||
*
|
||||
* @returns {Promise<string[]>} A selectors list
|
||||
* @function runTasks
|
||||
* @description Starts running tasks
|
||||
*/
|
||||
|
||||
const query = async () => {
|
||||
try {
|
||||
const response = await fetch(url, { cache: "no-cache" });
|
||||
const data = await response.text();
|
||||
const runTasks = () => {
|
||||
if (attempts >= 5 || selectorsFromCache.length === 0) ready = true;
|
||||
|
||||
if (response.status !== 200) throw new Error();
|
||||
if (attempts <= 20) {
|
||||
fix();
|
||||
removeFromCache();
|
||||
if (attempts <= 5) removeFromNetwork();
|
||||
attempts += 1;
|
||||
}
|
||||
|
||||
return data.split("\n");
|
||||
} catch {
|
||||
return [];
|
||||
if (attempts > 20) {
|
||||
clearInterval(intervalId);
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @constant observer
|
||||
* @description Observer instance
|
||||
* @type {MutationObserver}
|
||||
* @description Setup extension context
|
||||
*/
|
||||
|
||||
const observer = new MutationObserver((_, instance) => {
|
||||
instance.disconnect();
|
||||
fix();
|
||||
removeFromCache();
|
||||
if (attempts <= 5) removeFromNetwork();
|
||||
attempts += 1;
|
||||
observe();
|
||||
});
|
||||
chrome.runtime.sendMessage(
|
||||
{ hostname: document.location.hostname, type: "GET_CACHE" },
|
||||
null,
|
||||
async (cacheResponse) => {
|
||||
console.log(cacheResponse);
|
||||
chrome.runtime.sendMessage({ type: "ENABLE_POPUP" });
|
||||
|
||||
/**
|
||||
* @function observe
|
||||
* @description Starts observing document.body element
|
||||
*/
|
||||
|
||||
const observe = () => {
|
||||
observer.observe(document.body, {
|
||||
attributes: true,
|
||||
childList: true,
|
||||
});
|
||||
};
|
||||
|
||||
/**
|
||||
* @async
|
||||
* @function handleContentLoaded
|
||||
* @description Cleans, fixes scroll issues and observes document.body element
|
||||
*/
|
||||
|
||||
const handleContentLoaded = async () => {
|
||||
chrome.runtime.sendMessage({ type: "ENABLE_POPUP" });
|
||||
enabled = await check();
|
||||
|
||||
if (enabled) {
|
||||
chrome.runtime.sendMessage({ type: "ENABLE_ICON" });
|
||||
selectors = await query();
|
||||
|
||||
if (selectors.length > 0) {
|
||||
fix();
|
||||
removeFromCache();
|
||||
removeFromNetwork();
|
||||
observe();
|
||||
if (cacheResponse.enabled) {
|
||||
selectorsFromCache = cacheResponse.matches;
|
||||
chrome.runtime.sendMessage({ type: "ENABLE_ICON" });
|
||||
chrome.runtime.sendMessage(
|
||||
{ type: "GET_LIST" },
|
||||
null,
|
||||
async (networkResponse) => {
|
||||
selectorsFromNetwork = networkResponse.matches;
|
||||
intervalId = setInterval(runTasks, 500);
|
||||
}
|
||||
);
|
||||
} else {
|
||||
document.documentElement.style.setProperty("opacity", "1", "important");
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* @description Listen to document ready
|
||||
*
|
||||
* @type {Document}
|
||||
* @listens document#ready
|
||||
*/
|
||||
|
||||
document.addEventListener("DOMContentLoaded", handleContentLoaded);
|
||||
);
|
||||
|
Loading…
Reference in New Issue
Block a user