1
votes

almost a week ago I started to make an add-on that I finally understood how it works (yes, because before I had never made an add-on ^^) and I managed to make it work under Manifest 2 but when I wanted to publish it on the Google Web Store I had the surprise that the add-on must be in Manifest 3 while Mozilla and Opera had accepted the 2. But no matter, I've been looking for a little bit how to migrate it to V3 and I found some interesting things but not really what I was looking for to fix my bugs that changed during the migration.

I have to explain you what is an add-on so that we can find a solution together. It's an add-on to alert people when a streamer is live. And what blocks it is the offline visual part which is still in Live while the streamer is offline. I think it's the local storage that blocks but I'm not sure because of the number of bugs I had. But what I am sure of is that the worker service is marked as Inactiv. I put a little bit of my codes in hope that someone who knows well the Manifest 3 can help me. And I'm willing to send the whole code if people need it.

manifest.json

{
"manifest_version": 3,

"author": "Sardan",
"name": "__MSG_appName__",
"short_name": "__MSG_appName__",
"description": "__MSG_appDesc__",
"version": "0.1.4",
"default_locale": "fr",
"minimum_chrome_version": "93",

"background": {
    "service_worker": "js/background.js",
    "type": "module"
},

"action": {
    "default_title": "StreamerName - __MSG_statut_off__",
    "default_icon": "images/live_off.png",
    "default_popup": "popup.html"
},

"icons": {
    "128": "images/logo.png",
    "64": "images/logo-64.png",
    "32": "images/32.png"
},

"permissions": [
    "notifications",
    "unlimitedStorage",
    "alarms",
    "unlimitedStorage",
    "background",
    "audio",
    "storage"
],

"host_permissions": [
    "<all_urls>"
],

"content_scripts": [{
    "js": ["js/libs/jquery.js"],
    "matches": ["https://*/*"]
    }],

"update_url": "https://clients2.google.com/service/update2/crx"

}

background.js

if (typeof chrome.storage.local.notifications === 'undefined' || chrome.storage.local.notifications === null || chrome.storage.local.notifications == "true" || chrome.storage.local.notifications == "false") {
    chrome.storage.local.get({notifications: "1"}, function() {
        console.log(chrome.storage.local.notifications)
      });
};

if (typeof chrome.storage.lastOnline === 'undefined' || chrome.storage.lastOnline === null) {
    chrome.storage.local.set({lastOnline: "0"}, function() {
        console.log(chrome.storage.local.lastOnline)
      });
};

if(typeof Audio != "undefined") {
    var audioAlert = new Audio("audio/alert_0.ogg");
};

function createBasicNotification(id, title, message, iconUrl, buttons) {
    if ($.browser.chrome && !$.browser.opera) {
        chrome.notifications.create(id, {
            type: "basic",
            title: title,
            message: message,
            iconUrl: iconUrl,
            buttons: buttons,
            silent: true,
            priority: 2
        });         
    } else {
        chrome.notifications.create(id, {
            type: "basic",
            title: title,
            message: message,
            iconUrl: iconUrl,
            priority: 2
        }); 
    }

    audioAlert.play();
}

function createImageNotification(id, title, message, imageUrl, iconUrl, contextMessage, buttons) {
    if ($.browser.chrome && !$.browser.opera) {
        chrome.notifications.create(id, {
            type: "image",
            title: title,
            message: message,
            imageUrl: imageUrl,
            iconUrl: iconUrl,
            contextMessage: contextMessage,
            buttons: buttons,
            silent: true,
            priority: 2
        });
    } else {
        chrome.notifications.create(id, {
            type: "basic",
            title: title,
            message: message,
            iconUrl: iconUrl,
            contextMessage: contextMessage,
            priority: 2
        });
    }

    audioAlert.play();
}

var stream = [];

$.getJSON('config.json', function(json) {
    $.each(json, function(key, value) {
        stream[key] = value;
    });
});

stream.title = chrome.i18n.getMessage("statut_off");
stream.game = "-";
stream.viewers = "-";
stream.thumbnail = null;

var isLive = false;
var prevStatus = false;

function checkLive() {
    "use strict";

    $.ajax({
        type: "GET",
        dataType: "json",
        timeout: 10000,
        cache: false,
        url: "https://api.twitch.tv/helix/streams?user_id=ID",
        headers: {
            "Authorization": "Bearer KEY",
            "Client-Id": "KEY_PRIVATE"
        },
        success: function (data) {
            if(data.data.length > '0'){
                isLive = true;
            }else{
                isLive = false;
            }
            
            if (isLive) {
                stream.title = data.data[0].title;
                stream.game = data.data[0].game_name;
                stream.viewers = '0';
                stream.thumbnail = data.data[0].thumbnail_url.replace('{width}','320').replace('{height}','180');

                if (!prevStatus) {
                    chrome.action.setTitle({title: stream.name + " - " + chrome.i18n.getMessage("statut_on")});
                    chrome.action.setIcon({path: "images/live_on.png"});
                    if (parseInt(chrome.storage.local.notifications) && parseInt(chrome.storage.local.lastOnline) < Date.now() - 900000) {
                        createImageNotification(
                            stream.name.toLowerCase() + "-live", 
                            stream.name + " " + chrome.i18n.getMessage("live"), 
                            "Je " + stream.game + ", " + chrome.i18n.getMessage("jm"), 
                            stream.thumbnail, "images/logo.png", 
                            stream.game + " • " + stream.viewers + " viewers",
                                [{ 
                                    title: chrome.i18n.getMessage("watch"), 
                                    iconUrl: (
                                        stream.liveURL.toLowerCase().indexOf("twitch.tv") >= "images/icons/twitch.png"
                                        )
                                }]
                        );
                    }
                    prevStatus = true;
                }
                
                chrome.storage.local.lastOnline = Date.now();
            } else if (prevStatus) {
                chrome.action.setTitle({title: stream.name + " - " + chrome.i18n.getMessage("statut_off")});
                chrome.action.setIcon({path: "images/live_off.png"});
                prevStatus = false;
                stream.title = chrome.i18n.getMessage("statut_off");
                stream.game = "-";
                stream.viewers = "-";
                stream.thumbnail = null;

                chrome.storage.local.lastOnline = 0;
            }
        }
    });
}

chrome.action.setIcon({
    path: "images/live_off.png"
});

setTimeout(function () {
    if (typeof chrome.storage.local.firstTime === 'undefined' || chrome.storage.local.firstTime === null) {
        chrome.storage.local.firstTime = true;
    }

    checkLive();
}, 500);

setInterval(function() { checkLive(); }, 11000);

And finnaly the actual errors in the navigator :

Screenshot of my actual errors

Thanks all

As the error says $ is not defined. You can't use jQuery in a service worker. Use fetch instead. - wOxxOm
Hello @wOxxOm, thanks for your answer. I tried it and that unlock the problem. Thanks a lot ^^ - Sardan