Search code examples
javascriptjquerygoogle-chrome-extensioncontent-scriptmessage-passing

Chrome Extension Message Passing - How to pass HTML


I'm trying to send HTML from locally within a chrome extension to a div on the active tab. I'm sending the HTML via the background script and receiving with a content script injected into the active tab.

I've gotten the port to work and tested with various simple text-based messages. The div is also appearing, but it's blank, since the HTML isn't sending properly. Anyone know what is wrong with my code?

background script:

chrome.runtime.onConnect.addListener(function(port) {
    console.assert(port.name == "sidebar");
    port.onMessage.addListener(function(msg) {
        if (msg.command == "read_sidebar")
        {
            //var sidebarURL = chrome.extension.getURL("sidebar.html");
            //console.log(sidebarURL);
            var element = document.createElement('div');
            element.id = "test";
            $("test").load('sidebar.html');
            port.postMessage({command: "load_sidebar", html: element.innerHTML})
        } 
        else if (msg.command == "close_load") {
            console.log("told to close load");
        } 
    });
});

content script:

function loadSidebar() {

    var port = chrome.runtime.connect({name: "sidebar"});
    port.postMessage({command: "read_sidebar"});
    port.onMessage.addListener(function(msg) {
        if (msg.command == "load_sidebar")
        {
            console.log(msg.html);
            document.getElementById("mySidebar").innerHTML= msg.html;
            port.postMessage({command: "close_load"});
        }
    });
}

Solution

  • This API can only send JSON-serializable objects, and HTMLElement is not serializable.

    What you may try to do is to add your HTML to web_accessible_resources section of the manifest:

      "web_accessible_resources" : [
        "sidebar.html",
        (any resources used by sidebar.html)
      ],
    

    Then you can directly load the file from a content script, using

    chrome.runtime.getURL('sidebar.html')
    

    as its URL.

    You can inject it as an iframe, or if it's static HTML, you can request it with XHR and manipulate the response.