Mercurial > addons > firefox-addons > set-aside
annotate background.js @ 0:d13d59494613
Initial revision
author | Guido Berhoerster <guido+set-aside@berhoerster.name> |
---|---|
date | Sat, 17 Nov 2018 10:44:16 +0100 |
parents | |
children | b0827360b8e4 |
rev | line source |
---|---|
0
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
1 /* |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
2 * Copyright (C) 2018 Guido Berhoerster <guido+set-aside@berhoerster.name> |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
3 * |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
4 * This Source Code Form is subject to the terms of the Mozilla Public |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
5 * License, v. 2.0. If a copy of the MPL was not distributed with this |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
7 */ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
8 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
9 'use strict'; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
10 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
11 const SUPPORTED_PROTOCOLS = ['https:', 'http:', 'ftp:']; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
12 const GROUP_KEY_RE = /^collection:[0-9a-f]{8}-([0-9a-f]{4}-){3}[0-9a-f]{12}$/; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
13 const FIREFOX_VERSION_RE = /^(\d+(?:\.\d+)*)(?:([ab]|pre)(\d+))?$/; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
14 const FIREFOX_RELEASE_TYPES = { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
15 'a': 'alpha', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
16 'b': 'beta', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
17 'pre': 'prerelease', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
18 '': '' |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
19 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
20 const THUMBNAIL_WIDTH = 224; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
21 const THUMBNAIL_HEIGHT = 128; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
22 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
23 var tabCollectionsProxy; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
24 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
25 function generateUuidV4String() { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
26 let uuid = new Uint8Array(16); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
27 window.crypto.getRandomValues(uuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
28 uuid[6] = (uuid[6] & 0x0f) | 0x40; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
29 uuid[8] = (uuid[8] & 0x3f) | 0x80; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
30 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
31 let result = []; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
32 for (let i = 0; i < uuid.length; i++) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
33 if (i == 4 || i == 6 || i == 8 || i == 10) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
34 result.push('-'); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
35 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
36 result.push(uuid[i].toString(16).padStart(2, '0')); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
37 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
38 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
39 return result.join(''); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
40 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
41 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
42 function parseFirefoxVersion(firefoxVersionString) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
43 let [, versionString, releaseTypeAbbrev = '', releaseNumberString = '0'] = |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
44 FIREFOX_VERSION_RE.exec(firefoxVersionString); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
45 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
46 let releaseType = FIREFOX_RELEASE_TYPES[releaseTypeAbbrev]; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
47 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
48 let releaseNumber = parseInt(releaseNumberString); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
49 let [major = 0, minor = 0, patch = 0] = versionString.split('.') |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
50 .map(x => parseInt(x)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
51 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
52 return { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
53 major, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
54 minor, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
55 patch, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
56 releaseType, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
57 releaseNumber, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
58 }; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
59 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
60 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
61 class Tab { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
62 static deserialize(object) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
63 return new Tab(object); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
64 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
65 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
66 constructor({url, title, uuid = generateUuidV4String(), favIconUrl = null, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
67 thumbnailUrl = null}) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
68 this.uuid = uuid; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
69 this.url = url; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
70 this.title = title; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
71 this.favIconUrl = favIconUrl; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
72 this.thumbnailUrl = thumbnailUrl; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
73 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
74 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
75 serialize() { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
76 return Object.assign({}, this); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
77 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
78 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
79 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
80 class TabCollection { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
81 static deserialize(object) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
82 object.tabs = Array.from(object.tabs, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
83 ([, tab]) => [tab.uuid, Tab.deserialize(tab)]); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
84 return new TabCollection(object); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
85 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
86 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
87 constructor({tabs, uuid = generateUuidV4String(), date = new Date()}) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
88 this.uuid = uuid; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
89 this.date = new Date(date); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
90 this.tabs = new Map(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
91 // allow any type which allows iteration |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
92 for (let [, tab] of tabs) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
93 this.tabs.set(tab.uuid, tab); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
94 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
95 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
96 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
97 serialize() { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
98 let serializedTabs = []; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
99 for (let [tabUuid, tab] of this.tabs) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
100 serializedTabs.push([tab.uuid, tab.serialize()]); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
101 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
102 return { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
103 uuid: this.uuid, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
104 date: this.date.toJSON(), |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
105 tabs: serializedTabs |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
106 }; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
107 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
108 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
109 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
110 class TabCollectionsStorageProxy { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
111 constructor() { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
112 this.tabCollections = new Map(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
113 this.ports = new Set(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
114 this.browserVersion = undefined; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
115 this.messageQueue = []; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
116 this.isInitialized = false; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
117 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
118 browser.runtime.onConnect.addListener(this.onConnect.bind(this)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
119 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
120 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
121 async init() { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
122 let browserInfo = await browser.runtime.getBrowserInfo(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
123 this.browserVersion = parseFirefoxVersion(browserInfo.version); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
124 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
125 // get all tab collections and deserialize them in a Map |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
126 let storageEntries = Object.entries(await browser.storage.sync.get()) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
127 .filter(([key, value]) => GROUP_KEY_RE.test(key)) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
128 .map(([key, tabCollection]) => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
129 [tabCollection.uuid, TabCollection.deserialize(tabCollection)]); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
130 this.tabCollections = new Map(storageEntries); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
131 console.log('tab collections from storage'); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
132 console.table(this.tabCollections); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
133 console.groupEnd(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
134 browser.storage.onChanged.addListener(this.onStorageChanged.bind(this)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
135 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
136 this.isInitialized = true; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
137 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
138 while (this.messageQueue.length > 0) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
139 let [message, port] = this.messageQueue.pop(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
140 if (this.ports.has(port)) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
141 this.onMessage(message, port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
142 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
143 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
144 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
145 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
146 async createTabThumbnail(tabId) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
147 let captureUrl = await browser.tabs.captureTab(tabId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
148 let thumbnailUrl = await new Promise((resolve, reject) => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
149 let image = new Image(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
150 image.addEventListener('load', ev => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
151 let canvas = document.createElement('canvas'); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
152 canvas.width = THUMBNAIL_WIDTH; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
153 canvas.height = THUMBNAIL_HEIGHT; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
154 let dWidth = canvas.width; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
155 let dHeight = dWidth * (image.height / image.width); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
156 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
157 let ctx = canvas.getContext('2d'); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
158 ctx.fillStyle = '#fff'; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
159 ctx.fillRect(0, 0, canvas.width, canvas.height); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
160 ctx.drawImage(image, 0, 0, dWidth, dHeight); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
161 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
162 resolve(canvas.toDataURL('image/jpeg', 0.75)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
163 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
164 image.addEventListener('error', e => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
165 reject(e); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
166 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
167 image.src = captureUrl; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
168 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
169 return thumbnailUrl; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
170 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
171 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
172 async createTabCollection(windowId) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
173 let browserTabs = await browser.tabs.query({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
174 windowId, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
175 hidden: false, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
176 pinned:false |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
177 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
178 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
179 // sanity check to prevent saving tabs from incognito windows |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
180 if (browserTabs.length === 0 || browserTabs[0].incognito) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
181 return; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
182 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
183 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
184 // filter out tabs which cannot be restored |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
185 browserTabs = browserTabs.filter(browserTab => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
186 SUPPORTED_PROTOCOLS.includes(new URL(browserTab.url).protocol)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
187 if (browserTabs.length === 0) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
188 return; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
189 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
190 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
191 let tabs = browserTabs.map(browserTab => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
192 let tab = new Tab({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
193 url: browserTab.url, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
194 title: browserTab.title, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
195 favIconUrl: browserTab.favIconUrl |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
196 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
197 return [tab.uuid, tab]; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
198 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
199 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
200 // create empty tab which becomes the new active tab |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
201 await browser.tabs.create({active: true}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
202 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
203 // capture tabs, return null for discarded tabs since they can only be |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
204 // captured after they have been restored, e.g. through user |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
205 // interaction, and thus might hang the capture process indefinetly |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
206 let thumbnails = await Promise.all(browserTabs.map(browserTab => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
207 !browserTab.discarded ? |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
208 this.createTabThumbnail(browserTab.id) : null)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
209 for (let [, tab] of tabs) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
210 tab.thumbnailUrl = thumbnails.shift(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
211 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
212 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
213 let tabCollection = new TabCollection({tabs}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
214 console.log('created tab collection:', tabCollection); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
215 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
216 // store tab collection |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
217 console.log('storing tab collection:', tabCollection); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
218 await browser.storage.sync.set({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
219 [`collection:${tabCollection.uuid}`]: tabCollection.serialize() |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
220 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
221 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
222 // remove tabs |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
223 await browser.tabs.remove(browserTabs.map(browserTab => browserTab.id)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
224 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
225 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
226 async removeTab(tabCollectionUuid, tabUuid) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
227 console.log('removing tab %s from collection %s', tabUuid, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
228 tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
229 let tabCollection = this.tabCollections.get(tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
230 // create shallow clone |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
231 let newTabCollection = new TabCollection(tabCollection); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
232 newTabCollection.tabs.delete(tabUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
233 // remove tab collection if there are no more tabs |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
234 if (newTabCollection.tabs.size === 0) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
235 return this.removeTabCollection(tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
236 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
237 await browser.storage.sync.set({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
238 [`collection:${tabCollectionUuid}`]: newTabCollection.serialize() |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
239 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
240 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
241 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
242 async restoreTab(tabCollectionUuid, tabUuid, windowId) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
243 console.log('restoring tab %s from collection %s in window %d', tabUuid, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
244 tabCollectionUuid, windowId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
245 let tab = this.tabCollections.get(tabCollectionUuid).tabs.get(tabUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
246 let tabProperties = { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
247 active: false, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
248 url: tab.url, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
249 windowId |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
250 }; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
251 if (this.browserVersion.major >= 63) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
252 tabProperties.discarded = true; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
253 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
254 await browser.tabs.create(tabProperties); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
255 await this.removeTab(tabCollectionUuid, tabUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
256 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
257 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
258 async removeTabCollection(tabCollectionUuid) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
259 console.log('removing tab collection %s', tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
260 await browser.storage.sync.remove(`collection:${tabCollectionUuid}`); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
261 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
262 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
263 async restoreTabCollection(tabCollectionUuid, windowId) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
264 console.log('restoring tab collection %s in window %s', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
265 tabCollectionUuid, windowId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
266 let tabProperties = { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
267 active: false, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
268 windowId |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
269 }; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
270 if (this.browserVersion.major >= 63) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
271 tabProperties.discarded = true; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
272 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
273 let creatingTabs = |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
274 Array.from(this.tabCollections.get(tabCollectionUuid).tabs, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
275 ([, tab]) => browser.tabs.create(Object.assign({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
276 url: tab.url |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
277 }, tabProperties))); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
278 await Promise.all(creatingTabs); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
279 await this.removeTabCollection(tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
280 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
281 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
282 onStorageChanged(changes, areaName) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
283 if (areaName !== 'sync') { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
284 return; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
285 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
286 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
287 console.group('sync storage area changed:', changes); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
288 console.table(Object.entries(changes)[0][1]) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
289 console.groupEnd(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
290 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
291 let [key, {oldValue, newValue}] = Object.entries(changes)[0]; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
292 if (!GROUP_KEY_RE.test(key)) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
293 return; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
294 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
295 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
296 let tabCollectionUuid = key.replace('collection:', ''); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
297 if (typeof oldValue === 'undefined') { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
298 // a new collection was created |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
299 let newTabCollection = TabCollection.deserialize(newValue); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
300 this.tabCollections.set(tabCollectionUuid, newTabCollection); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
301 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
302 this.broadcastMessage({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
303 type: 'tabCollectionCreated', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
304 tabCollection: newTabCollection |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
305 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
306 } else if (typeof newValue === 'undefined') { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
307 // a collection has been removed |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
308 this.tabCollections.delete(tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
309 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
310 this.broadcastMessage({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
311 type: 'tabCollectionRemoved', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
312 tabCollectionUuid |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
313 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
314 } else { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
315 // a collection has changed |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
316 let newTabCollection = TabCollection.deserialize(newValue); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
317 this.tabCollections.set(tabCollectionUuid, newTabCollection); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
318 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
319 this.broadcastMessage({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
320 type: 'tabCollectionChanged', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
321 tabCollection: newTabCollection |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
322 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
323 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
324 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
325 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
326 broadcastMessage(message) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
327 for (let port of this.ports) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
328 port.postMessage(message); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
329 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
330 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
331 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
332 onConnect(port) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
333 console.log('port connected:', port) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
334 this.ports.add(port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
335 port.onMessage.addListener(this.onMessage.bind(this)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
336 port.onDisconnect.addListener(this.onDisconnect.bind(this)); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
337 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
338 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
339 onDisconnect(port) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
340 if (port.error) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
341 console.log(`port connection error: ${port.error}\n`); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
342 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
343 console.log('port disconnected:', port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
344 this.ports.delete(port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
345 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
346 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
347 onMessage(message, port) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
348 if (!this.isInitialized) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
349 console.log('queued message', message, 'from port', port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
350 this.messageQueue.push([message, port]); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
351 return; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
352 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
353 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
354 console.log('received message', message, 'on port', port); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
355 switch (message.type) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
356 case 'getTabCollections': |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
357 port.postMessage({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
358 type: 'tabCollections', |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
359 tabCollections: this.tabCollections |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
360 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
361 break; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
362 case 'removeTab': |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
363 this.removeTab(message.tabCollectionUuid, message.tabUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
364 break; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
365 case 'restoreTab': |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
366 this.restoreTab(message.tabCollectionUuid, message.tabUuid, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
367 message.windowId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
368 break; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
369 case 'removeTabCollection': |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
370 this.removeTabCollection(message.tabCollectionUuid); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
371 break; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
372 case 'restoreTabCollection': |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
373 this.restoreTabCollection(message.tabCollectionUuid, |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
374 message.windowId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
375 break; |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
376 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
377 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
378 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
379 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
380 // browser action context menu entry for opening the sidebar |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
381 browser.menus.create({ |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
382 contexts: ['browser_action'], |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
383 onclick: (info, tab) => browser.sidebarAction.open(), |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
384 title: browser.i18n.getMessage('showTabsMenuItem') |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
385 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
386 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
387 // disable the browser action for new incognito tabs |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
388 browser.tabs.onCreated.addListener(tab => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
389 if (tab.incognito) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
390 // this does not work, it seems that the browser action is re-enabled |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
391 // on every update |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
392 browser.browserAction.disable(tab.id); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
393 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
394 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
395 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
396 (async () => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
397 // disable the browser action for existing incognito tabs |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
398 let tabs = await browser.tabs.query({}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
399 await Promise.all(tabs.filter(tab => tab.incognito) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
400 .map(tab => browser.browserAction.disable(tab.id))) |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
401 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
402 tabCollectionsProxy = new TabCollectionsStorageProxy(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
403 await tabCollectionsProxy.init(); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
404 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
405 browser.browserAction.onClicked.addListener(async targetTab => { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
406 // prevent browser action from being activated while a collection is |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
407 // being created |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
408 let tabs = await browser.tabs.query({windowId: targetTab.windowId}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
409 await Promise.all(tabs.map(tab => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
410 browser.browserAction.disable(tab.id))); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
411 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
412 try { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
413 await tabCollectionsProxy.createTabCollection(targetTab.windowId); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
414 } catch (e) { |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
415 tabs = await browser.tabs.query({windowId: targetTab.windowId}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
416 await Promise.all(tabs.map(tab => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
417 browser.browserAction.enable(tab.id))); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
418 throw e |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
419 } |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
420 |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
421 tabs = await browser.tabs.query({windowId: targetTab.windowId}); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
422 await Promise.all(tabs.map(tab => |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
423 browser.browserAction.enable(tab.id))); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
424 }); |
d13d59494613
Initial revision
Guido Berhoerster <guido+set-aside@berhoerster.name>
parents:
diff
changeset
|
425 })(); |