diff --git a/index.js b/index.js index 59de8c7..18b7fd2 100644 --- a/index.js +++ b/index.js @@ -32,16 +32,21 @@ let ContainerService = // only these methods are allowed. We have a 1:1 mapping between messages // and methods. These methods must return a promise. let methods = [ - 'queryTabs', 'hideTabs', 'showTabs', - 'removeTabs', 'sortTabs', 'openTab', 'queryIdentities', - 'getIdentitiesState', + 'getIdentity', ]; + // Map of identities. + ContextualIdentityService.getIdentities().forEach(identity => { + this._identitiesState[identity.userContextId] = {hiddenTabUrls: []}; + }); + + // WebExtension startup + webExtension.startup().then(api => { api.browser.runtime.onMessage.addListener((message, sender, sendReply) => { if ("method" in message && methods.indexOf(message.method) != -1) { @@ -54,27 +59,19 @@ let ContainerService = // utility methods _convert(identity) { - let hiddenTabUrls = []; - - if (identity.userContextId in this._identitiesState) { - hiddenTabUrls = this._identitiesState[identity.userContextId].hiddenTabUrls; - } - return { name: ContextualIdentityService.getUserContextLabel(identity.userContextId), icon: identity.icon, color: identity.color, userContextId: identity.userContextId, - hiddenTabUrls: hiddenTabUrls + hasHiddenTabs: !!this._identitiesState[identity.userContextId].hiddenTabUrls.length, }; }, // Tabs management - queryTabs(args) { + hideTabs(args) { return new Promise((resolve, reject) => { - let tabList = []; - for (let tab of tabs) { let xulTab = viewFor(tab); let userContextId = parseInt(xulTab.getAttribute('usercontextid') || 0, 10); @@ -83,39 +80,24 @@ let ContainerService = continue; } - tabList.push({ - id: tab.id, - url: tab.url, - userContextId: userContextId, - }); + this._identitiesState[args.userContextId].hiddenTabUrls.push(tab.url); + tab.close(); } - resolve(tabList); + resolve(null); }); }, - hideTabs(args) { - this._identitiesState[args.userContextId].hiddenTabUrls = args.tabUrlsToSave; - return Promise.resolve(null); - }, - showTabs(args) { - return new Promise((resolve, reject) => { - let hiddenTabUrls = this._identitiesState[args.userContextId].hiddenTabUrls; - this._identitiesState[args.userContextId].hiddenTabUrls = []; - resolve(hiddenTabUrls); - }); - }, + let promises = []; - removeTabs(args) { - return new Promise((resolve, reject) => { - for (let tab of tabs) { - if (args.tabIds.indexOf(tab.id) != -1) { - tab.close(); - } - } - resolve(null); - }); + for (let url of this._identitiesState[args.userContextId].hiddenTabUrls) { + promises.push(this.openTab({ userContextId: args.userContextId, url })); + } + + this._identitiesState[args.userContextId].hiddenTabUrls = []; + + return Promise.all(promises); }, sortTabs(args) { @@ -187,17 +169,15 @@ let ContainerService = ContextualIdentityService.getIdentities().forEach(identity => { let convertedIdentity = this._convert(identity); identities.push(convertedIdentity); - if (!(convertedIdentity.userContextId in this._identitiesState)) { - this._identitiesState[convertedIdentity.userContextId] = {hiddenTabUrls: []}; - } }); resolve(identities); }); }, - getIdentitiesState(args) { - return Promise.resolve(this._identitiesState); + getIdentity(args) { + let identity = ContextualIdentityService.getIdentityFromId(args.userContextId); + return Promise.resolve(identity ? this._convert(identity) : null); }, }; diff --git a/webextension/js/popup.js b/webextension/js/popup.js index 1bc8af6..6f03947 100644 --- a/webextension/js/popup.js +++ b/webextension/js/popup.js @@ -2,51 +2,15 @@ const CONTAINER_HIDE_SRC = '/img/container-hide.svg'; const CONTAINER_UNHIDE_SRC = '/img/container-unhide.svg'; -function hideContainerTabs(userContextId) { - const tabIdsToRemove = []; - const tabUrlsToSave = []; - const hideorshowIcon = document.querySelector(`#uci-${userContextId}-hideorshow-icon`); - - browser.runtime.sendMessage({ - method: 'queryTabs', - userContextId: userContextId - }).then(tabs=> { - tabs.forEach(tab=> { - tabIdsToRemove.push(tab.id); - tabUrlsToSave.push(tab.url); - }); - browser.runtime.sendMessage({ - method: 'hideTabs', - userContextId: userContextId, - tabUrlsToSave: tabUrlsToSave - }).then(()=> { - return browser.runtime.sendMessage({ - method: 'removeTabs', - tabIds: tabIdsToRemove - }); - }).then(() => { - hideorshowIcon.src = CONTAINER_UNHIDE_SRC; - }); - }); -} - -function showContainerTabs(userContextId) { +function showOrHideContainerTabs(userContextId, hasHiddenTabs) { return new Promise((resolve, reject) => { const hideorshowIcon = document.querySelector(`#uci-${userContextId}-hideorshow-icon`); browser.runtime.sendMessage({ - method: 'showTabs', + method: hasHiddenTabs ? 'showTabs' : 'hideTabs', userContextId: userContextId - }).then(hiddenTabUrls=> { - hiddenTabUrls.forEach(url=> { - browser.runtime.sendMessage({ - method: 'openTab', - userContextId: userContextId, - url: url - }); - }); }).then(() => { - hideorshowIcon.src = CONTAINER_HIDE_SRC; + hideorshowIcon.src = hasHiddenTabs ? CONTAINER_HIDE_SRC : CONTAINER_UNHIDE_SRC; }).then(resolve); }); } @@ -84,7 +48,7 @@ browser.runtime.sendMessage({method: 'queryIdentities'}).then(identities=> { identities.forEach(identity=> { let hideOrShowIconSrc = CONTAINER_HIDE_SRC; - if (identity.hiddenTabUrls.length) { + if (identity.hasHiddenTabs) { hideOrShowIconSrc = CONTAINER_UNHIDE_SRC; } const identityRow = ` @@ -124,15 +88,14 @@ browser.runtime.sendMessage({method: 'queryIdentities'}).then(identities=> { const userContextId = e.target.parentElement.parentElement.dataset.identityCookieStoreId; if (e.target.matches('.hideorshow-icon')) { - browser.runtime.sendMessage({method: 'getIdentitiesState'}).then(identitiesState=> { - if (identitiesState[userContextId].hiddenTabUrls.length) { - showContainerTabs(userContextId); - } else { - hideContainerTabs(userContextId); - } + browser.runtime.sendMessage({ + method: 'getIdentity', + userContextId + }).then(identity=> { + showOrHideContainerTabs(userContextId, identity.hasHiddenTabs); }); } else if (e.target.matches('.newtab-icon')) { - showContainerTabs(userContextId).then(() => { + showOrHideContainerTabs(userContextId, true).then(() => { browser.runtime.sendMessage({ method: 'openTab', userContextId: userContextId})