0

I'm trying to have webRequest as an optional permission in my Google Chrome extension. So I want the backgorund script to only listen for webRequest events if that permission is given.

Trying to achieve that through this code:

chrome.permissions.contains({
    origins: ["https://www.freelancer.com/projects/fileshare/*",
        "https://freelancer-filestorage-pmb.s3.amazonaws.com/*"],
    permissions: ["webRequest",
        "webRequestBlocking"]
}, response => { 
        // only register the webRequest listener if there is this permission...
        // I don't know if this is a valid way of doing this, but I don't have other ideas
        if (response) {
            chrome.webRequest.onHeadersReceived.addListener(details => {
                    console.log("went through the request");
                 return {responseHeaders: details.responseHeaders};
                },

                { urls: ['https://freelancer-filestorage-pmb.s3.amazonaws.com/*'] },

                ['blocking', 'responseHeaders']
            );
        }
});

This does not seem to work, i.e. even when I give the permission, web requests are not intercepted.

I remember reading something in the documentation that adding an event listener inside of an asynchronous function (like I'm doing here) will not work properly. But how can I achieve what I need, then? Do not register listeners asynchronously, as they will not be properly triggered.

If I just put

chrome.webRequest.onHeadersReceived.addListener

in the background script, without checking for the permission, then I will get an error that webRequest is not defined.

EDIT: pasted more of the code

EDIT2: The chrome developer docs at https://developer.chrome.com/extensions/background_pages say this:

Do not register listeners asynchronously, as they will not be properly triggered.

I fixed my problem by setting up a message listener in the background script, which adds and removes a listener for webRequest, depending on whether the user set the permission or revoked it.

Something strange is still happening in about 5% of the cases, where after the permission is granted, for a while it still appears as non-granted and registering the listener fails.

Scruffy
  • 444
  • 1
  • 6
  • 13
  • You can add listeners in any code, asynchronous or not, but your code is not a valid JavaScript, it misses `)` and additional parameters for addListener. You can debug your code in [devtools for the background page](https://stackoverflow.com/questions/10257301/where-to-read-console-messages-from-background-js-in-a-chrome-extension). – wOxxOm Mar 13 '19 at 04:43
  • thanks @wOxxOm but this is just a typo as I was pasting it here, and I cut the code that I thought didn't matter. The actual extension doesn't throw any errors and works when loaded from my disc. Do you think I should do something like calling the the background page `runtime.getBackgroundPage()` after the permission was granted? I thought this is not necessary since I have it set to `persistent: true`. – Scruffy Mar 13 '19 at 07:51
  • Without a reproducible test case one can only guess. It could be a bug in Chrome. It could be something else in your code. – wOxxOm Mar 13 '19 at 07:56
  • @wOxxOm I see. Well, I included more of the relevant code. Don't want to paste the entire thing here as it would just be a big mess. I'm just wondering, if I call the background page many times, will the event listener there be registered many times, or is Chrome smart enough to noly do it once? What if the background page is persistent? How often does the code in it run then? Do you have any info on this? Thanks :) – Scruffy Mar 13 '19 at 08:06
  • 1
    If you repeated chrome.permissions.contains callback more than once it would add a new listener in addition to the old one because you're creating a new function object inside the callback so Chrome sees it as a different listener each time. Only if the function object reference is the same, it'll be skipped automatically. You can declare the function globally and use its name in addListener. – wOxxOm Mar 13 '19 at 08:13
  • It could be a bug in Chrome so try in Chrome Canary or in an old portable Chrome like v.60. – wOxxOm Mar 13 '19 at 08:15
  • @wOxxOm thanks, it makes sense with the listener. I will try using `runtime.getBackgroundPage()` after the permission is granted - I thought I could avoid it in persistent background script. Will write here if it succeeds. – Scruffy Mar 13 '19 at 08:28

0 Answers0