Monday 31 January 2022

response is undefined despite sendResponse from bg script

I just don't understand why it isn't working!I have a background.js script that creates a tab (history.html). This html page contains a content script (history.js) that sends a message to the background script to get some history data (historyItems) and waits for a response from the background script containing that data.

The manifest file includes the following:

"web_accessible_resources": [
        "/history.html",
        "/script/history.js",
        "/images/*.png"
],
"content_security_policy": "script-src 'self'; object-src 'self'; img-src *; ",
"background": {
    "scripts": [
        "/scripts/background.js"
    ]
},
"permissions": [
    "<all_urls>",
    "contextMenus",
    "storage",
    "tabs",
    "search",
    "webRequest",
    "webRequestBlocking"
],
"optional_permissions": [
    "notifications",
    "downloads",
    "bookmarks",
    "history"
],
"content_scripts": [
    {
        "matches": [
            "<all_urls>"
        ],
        "js": [
            "/scripts/history.js",
            "/scripts/selection.js",
            "/scripts/exif.js",
            "/scripts/color-thief.min.js",
            "/scripts/Sortable.min.js",
            "/scripts/RGraph.svg.common.core.js",
            "/scripts/RGraph.svg.line.js",
            "/scripts/exif_tags.js"
        ]
    }
]

I'm not sure whether history.js should be defined as a content script or if extension scripts can message to/from background scripts.

history.js contains the following code:

document.addEventListener('DOMContentLoaded', getHistoryItems);

function getHistoryItems() {
    // Send message to background script and get response
    browser.runtime.sendMessage({ action: 'getHistoryItems' })
        .then(handleResponse)
        .catch((err) => {
            console.error(err);
            console.log('Failed to get history items.');
        });
}

function handleResponse(response) {
    const historyItems = response.historyItems;
    const ol = document.getElementById('historyItems');
    for (let item of historyItems) {
        let li = document.createElement('li');
        li.style.listStyleType = 'none';
        li.style.margin = '0px';
        li.style.padding = '0px';
        let title = document.createElement('h3');
        title.textContent = item.title;
        let url = document.createElement('p');
        url.textContent = item.url;
        let lastVisitTime = document.createElement('p');
        lastVisitTime.textContent = item.lastVisitTime;
        li.appendChild(title);
        li.appendChild(url);
        li.appendChild(lastVisitTime);
        ol.appendChild(li);
    }
}

and background.js contains the following code:

let historyItems;

/// Handle Incoming Messages
// Listen for messages from the content or options script
browser.runtime.onMessage.addListener(async (message, sender, sendResponse) => {
    switch (message.action) {
...
        case 'getHistoryItems':
            if (logToConsole) console.log(historyItems);
            sendResponse({ historyItems: historyItems });
            return true;
        default:
            break;
    }
});
...
            switch (keyword) {
...
                case ('!h' || 'history'):
                    historyItems = await browser.history.search({ text: searchTerms });
                    await browser.tabs.create({
                        active: contextsearch_makeNewTabOrWindowActive,
                        index: tabPosition,
                        url: '/history.html'
                    })
                    break;
...

Finally, history.html just contains the history.js script:

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8">
        <meta http-equiv="X-UA-Compatible" content="IE=edge">
        <meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>History Search</title>
    </head>
    <body>
        <h2>History Search Results</h2>
        <ol id="historyItems"></ol>
        <script src="/scripts/history.js"></script>
    </body>
</html>


from response is undefined despite sendResponse from bg script

No comments:

Post a Comment