Extension background script is loaded after content script
Reported by
dmnkho...@gmail.com,
Sep 22 2017
|
|||
Issue description
UserAgent: Mozilla/5.0 (Windows NT 6.1; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/61.0.3163.100 Safari/537.36
Steps to reproduce the problem:
* Extension manifest:
"content_scripts": [
{
"matches" : ["<all_urls>"],
"js" : ["content.js"],
"all_frames" : true,
"run_at": "document_start"
}
],
"background": {
"scripts":["background.js"],
"persistent": true
},
* Extension background script: Directly execute chrome.runtime.onConnect.addListener...
* Extension content script: Directly execute chrome.runtime.connect and port.onDisconnect.addListener
* Install a lot of extensions with background scripts in Google Chrome
* Start chrome.exe with initial web site, e.g. "chrome.exe <url>"
This normally should establish a connection between the content script and the extension's background script.
If a lot of (other) extensions are installed in Goolge Chrome it sometimes happens that the onDisconnect listener is executed, when the page is loaded, and no connection is established.
If the error occurs and when logging the current time stamp to console in the first line of the content script and the background script, the time when the background script is loaded is AFTER the time the content script is executed.
Is this behavior intended? If yes, how can I detect in the content script when the background script is ready? Retrying to connect with a timeout is not a good solution.
What is the expected behavior?
An extension's background script is ALWAYS loaded before any of the extension's content scripts is executed, to ensure that content scripts can always connect to the background script without race conditions.
What went wrong?
In the extension's content script onDisconnect listener is called after executing chrome.runtime.connect, although the extension wasn't deleted, disabled or updated in the mean time, probably because of that the background script isn't loaded yet, as reported by the time stamps.
Did this work before? No
Does this work in other browsers? Yes
Chrome version: 61.0.3163.100 Channel: stable
OS Version: 6.1 (Windows 7, Windows Server 2008 R2)
Flash Version:
,
Sep 22 2017
Thank you for your reply! We run into this problem in automated tests where the browser is started via command line with a initial web page to load. Is this behavior documented anywhere? Why doesn't Google Chrome wait for all background scripts to be executed before it loads any web site content? What is the recommended way to work around this? Retrying to re-connect to the background page when it fails? How long to wait before considering the background page to be not present (e.g. extension has been updated while the browser started, and so the content script trying to connect cannot connect anymore as it is orphaned)?
,
Sep 22 2017
Chrome doesn't wait for the background pages in order to display the page faster. Because speed is what Chrome is about. I guess extensions aren't considered vital to that end.
I think you can retry via setTimeout for as long as you want when the response/result is undefined. On a fast machine it'll take a second. Just don't forget to stop when orphaned by checking a global variable isOrphaned, for example. As for the orphaned state detection, I suggest using a DOM event: dispatch it on start of the content script, then register a listener for that event. The old orphaned scripts will receive the event, detach all their listeners and die:
var isOrphaned = false;
window.dispatchEvent(new CustomEvent('orphaned' + chrome.runtime.id));
window.addEventListener('orphaned' + chrome.runtime.id, function onOrphaned() {
window.removeEventListener('orphaned' + chrome.runtime.id, onOrphaned);
isOrphaned = true;
// unregister listeners, do cleanup
// ........
});
,
Sep 25 2017
Ok, I understand. And how to detect orphaned state in case the extension gets disabled? So there is no "new" content script which can send an orphaned notification to the "old" content script. My idea for that case is to try to load a web visible script file from the extension via XmlHttpRequest, and if this fails, the extension is detected as disabled. Usually this works, but I'm not sure if this is really reliable and that the script is always immediately "loadable" after startup even if Chrome has not executed the background script?
,
Sep 25 2017
The orphaned script loses access to all chrome.* API except for chrome.runtime so you can simply check if chrome.storage is undefined.
,
Sep 26 2017
@ dmnkholzl-- Could you please try the steps in comment #5 and update the results. Thanks!
,
Sep 26 2017
hdodda@chromium.org, this issue can be properly answered only by an extensions API developer. Can you untriage it or cc someone, maybe rdevlin?
,
May 22 2018
Closing issue as Wontfix due to lack of feedback requested but not provided. If the issue still exists please open a new issue with the details requested. Thanks..! |
|||
►
Sign in to add a comment |
|||
Comment 1 by woxxom@gmail.com
, Sep 22 2017