Chrome extension: load and execute external script

jenush picture jenush · Jan 19, 2015 · Viewed 16.6k times · Source

I have trouble loading and executing external js-script into my chrome extension. Looks the same as this question, but I still cant't figure out why it doesn't work in my case.

The idea is that I want to have in my content script some default function which should parse a web-page content. And for some specific web-pages I want to load and use specific parsers, so I try to load proper js-script for a wep-page, and this script shoud extend functionality of default parser.

By now I try only execute code from external script, but have such error: Unchecked runtime.lastError while running tabs.executeScript: No source code or file specified at Object.callback

This is my manifest.json:

{
"name": "Extension name",
"version": "1.2",
"description": "My chrome extension",
"browser_action": {
    "default_popup": "popup.html",
},
"content_scripts": [{
    "css": [
        "style.css"
    ],
    "js": [
        "bower_components/jquery/dist/jquery.js",
        "bower_components/bootstrap/dist/js/bootstrap.js",
        "content.js"
    ],
    "matches": ["*://*/*"]
}],
"web_accessible_resources": [
    "frame.html",
    "logo-48.png"
],
"icons": {
    "16": "logo-16.png",
    "48": "logo-48.png",
    "128": "logo-128.png"
},
"permissions": [
    "tabs",
    "storage",
    "http://*/",
    "https://*/"
],
"manifest_version": 2

}

This is popup.html

<!doctype html>
 <html>
 <head>
  <title>Title</title>
  <script src="popup.js"></script>
 </head>
 <body>
  <ul>
    <li>Some link</li>
  </ul>
 </body>
</html>

And in popup.js i execute scrip like this:

chrome.tabs.query({active: true, currentWindow: true}, function(tabs) {
    chrome.tabs.executeScript(tabs[0].id, {file: "http://127.0.0.1:8000/static/plugin/somesite.js"});
});

What am I dong wrong, did I miss something? Or should I use another approach to solve the issue?

Answer

Thomas Karachristos picture Thomas Karachristos · Apr 15, 2016

Running scripts from external sources like you try is forbidden by google chrome and will block or even not publish your extension. All scripts must be in the extension. But there is a solution, from google chrome doc:

The restriction against resources loaded over HTTP applies only to those resources which are directly executed. You're still free, for example, to make XMLHTTPRequest connections to any origin you like; the default policy doesn't restrict connect-src or any of the other CSP directives in any way.

If you need badly an external source, you can do a XML HTTP request and use the eval to the content. Here is a part of code from google doc:

var xhr = new XMLHttpRequest();
xhr.open("GET", "http://127.0.0.1:8000/static/plugin/somesite.js", true);
xhr.onreadystatechange = function() {
  if (xhr.readyState == 4) {
      // WARNING! Might be evaluating an evil script!
      var resp = eval("(" + xhr.responseText + ")");
      // Or this if it's work
      chrome.tabs.executeScript(tabs[0].id, {code: xhr.responseText});
  }
}
xhr.send();

or you can use some library, $.get() with jquery or $http with angularjs. if you add eval in your code you must add in manifest.json this:

"content_security_policy":  "script-src 'self' 'unsafe-eval'; object-src 'self'"`,