@flrande/bak-extension 0.6.9 → 0.6.10
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/.bak-e2e-build-stamp +1 -1
- package/dist/background.global.js +127 -205
- package/dist/manifest.json +1 -1
- package/package.json +2 -2
- package/src/background.ts +1949 -1991
- package/src/session-binding.ts +387 -437
|
@@ -1 +1 @@
|
|
|
1
|
-
2026-03-
|
|
1
|
+
2026-03-13T17:21:34.586Z
|
|
@@ -62,7 +62,7 @@
|
|
|
62
62
|
// package.json
|
|
63
63
|
var package_default = {
|
|
64
64
|
name: "@flrande/bak-extension",
|
|
65
|
-
version: "0.6.
|
|
65
|
+
version: "0.6.10",
|
|
66
66
|
type: "module",
|
|
67
67
|
scripts: {
|
|
68
68
|
build: "tsup src/background.ts src/content.ts src/popup.ts --format iife --out-dir dist --clean && node scripts/copy-assets.mjs",
|
|
@@ -562,6 +562,13 @@
|
|
|
562
562
|
}
|
|
563
563
|
}
|
|
564
564
|
}
|
|
565
|
+
if (!window2) {
|
|
566
|
+
const activeWindow = await this.attachBindingToActiveWindow(state);
|
|
567
|
+
if (activeWindow) {
|
|
568
|
+
window2 = activeWindow;
|
|
569
|
+
repairActions.push("attached-active-window");
|
|
570
|
+
}
|
|
571
|
+
}
|
|
565
572
|
if (!window2) {
|
|
566
573
|
const sharedWindow = await this.findSharedBindingWindow(bindingId);
|
|
567
574
|
if (sharedWindow) {
|
|
@@ -605,21 +612,11 @@
|
|
|
605
612
|
repairActions.push("pruned-missing-tabs");
|
|
606
613
|
}
|
|
607
614
|
state.tabIds = tabs.map((tab) => tab.id);
|
|
608
|
-
if (state.windowId !== null) {
|
|
609
|
-
const ownership = await this.inspectBindingWindowOwnership(state, state.windowId);
|
|
610
|
-
if (ownership.foreignTabs.length > 0 && ownership.bindingTabs.length > 0) {
|
|
611
|
-
const migrated = await this.moveBindingIntoBakWindow(state, ownership, initialUrl);
|
|
612
|
-
window2 = migrated.window;
|
|
613
|
-
tabs = migrated.tabs;
|
|
614
|
-
state.tabIds = tabs.map((tab) => tab.id);
|
|
615
|
-
repairActions.push("evacuated-foreign-window");
|
|
616
|
-
}
|
|
617
|
-
}
|
|
618
615
|
if (tabs.length === 0) {
|
|
619
616
|
const primary = await this.createBindingTab({
|
|
620
617
|
windowId: state.windowId,
|
|
621
618
|
url: initialUrl,
|
|
622
|
-
active: true
|
|
619
|
+
active: options.focus === true
|
|
623
620
|
});
|
|
624
621
|
tabs = [primary];
|
|
625
622
|
state.tabIds = [primary.id];
|
|
@@ -670,9 +667,9 @@
|
|
|
670
667
|
}
|
|
671
668
|
}
|
|
672
669
|
state.tabIds = [...new Set(tabs.map((tab) => tab.id))];
|
|
673
|
-
if (options.focus === true && state.activeTabId !== null) {
|
|
674
|
-
await this.
|
|
675
|
-
window2 = await this.
|
|
670
|
+
if (options.focus === true && state.windowId !== null && state.activeTabId !== null) {
|
|
671
|
+
await this.focusBindingWindow(state.windowId, state.activeTabId);
|
|
672
|
+
window2 = await this.waitForWindow(state.windowId, 300);
|
|
676
673
|
void window2;
|
|
677
674
|
repairActions.push("focused-window");
|
|
678
675
|
}
|
|
@@ -759,9 +756,8 @@
|
|
|
759
756
|
activeTabId: active || options.focus === true ? createdTab.id : state.activeTabId ?? state.primaryTabId ?? createdTab.id,
|
|
760
757
|
primaryTabId: state.primaryTabId ?? createdTab.id
|
|
761
758
|
};
|
|
762
|
-
if (options.focus === true) {
|
|
763
|
-
await this.
|
|
764
|
-
await this.browser.updateWindow(state.windowId, { focused: true });
|
|
759
|
+
if (options.focus === true && state.windowId !== null) {
|
|
760
|
+
await this.focusBindingWindow(state.windowId, createdTab.id);
|
|
765
761
|
}
|
|
766
762
|
await this.storage.save(nextState);
|
|
767
763
|
const tabs = await this.readTrackedTabs(nextState.tabIds, nextState.windowId);
|
|
@@ -831,15 +827,41 @@
|
|
|
831
827
|
};
|
|
832
828
|
}
|
|
833
829
|
async focus(bindingId) {
|
|
834
|
-
const
|
|
835
|
-
|
|
836
|
-
|
|
830
|
+
const normalizedBindingId = this.normalizeBindingId(bindingId);
|
|
831
|
+
let binding = await this.inspectBinding(normalizedBindingId) ?? (await this.ensureBinding({
|
|
832
|
+
bindingId: normalizedBindingId,
|
|
833
|
+
focus: false
|
|
834
|
+
})).binding;
|
|
835
|
+
let targetTabId = this.resolveFocusTabId(binding);
|
|
836
|
+
if (binding.windowId === null || targetTabId === null) {
|
|
837
|
+
binding = (await this.ensureBinding({
|
|
838
|
+
bindingId: normalizedBindingId,
|
|
839
|
+
focus: false
|
|
840
|
+
})).binding;
|
|
841
|
+
targetTabId = this.resolveFocusTabId(binding);
|
|
837
842
|
}
|
|
838
|
-
if (
|
|
839
|
-
|
|
843
|
+
if (binding.windowId !== null && targetTabId !== null) {
|
|
844
|
+
try {
|
|
845
|
+
await this.focusBindingWindow(binding.windowId, targetTabId);
|
|
846
|
+
} catch (error) {
|
|
847
|
+
if (!this.isMissingWindowError(error)) {
|
|
848
|
+
throw error;
|
|
849
|
+
}
|
|
850
|
+
binding = (await this.ensureBinding({
|
|
851
|
+
bindingId: normalizedBindingId,
|
|
852
|
+
focus: false
|
|
853
|
+
})).binding;
|
|
854
|
+
targetTabId = this.resolveFocusTabId(binding);
|
|
855
|
+
if (binding.windowId !== null && targetTabId !== null) {
|
|
856
|
+
await this.focusBindingWindow(binding.windowId, targetTabId);
|
|
857
|
+
}
|
|
858
|
+
}
|
|
840
859
|
}
|
|
841
|
-
const refreshed = await this.
|
|
842
|
-
return {
|
|
860
|
+
const refreshed = await this.inspectBinding(normalizedBindingId) ?? binding;
|
|
861
|
+
return {
|
|
862
|
+
ok: true,
|
|
863
|
+
binding: refreshed.windowId !== null && targetTabId !== null ? this.withFocusedTab(refreshed, targetTabId) : refreshed
|
|
864
|
+
};
|
|
843
865
|
}
|
|
844
866
|
async closeTab(bindingId, tabId) {
|
|
845
867
|
const binding = await this.inspectBinding(bindingId);
|
|
@@ -1081,128 +1103,27 @@
|
|
|
1081
1103
|
}
|
|
1082
1104
|
return null;
|
|
1083
1105
|
}
|
|
1084
|
-
async
|
|
1085
|
-
const
|
|
1086
|
-
|
|
1087
|
-
|
|
1088
|
-
const peerTabIds = /* @__PURE__ */ new Set();
|
|
1089
|
-
const peerGroupIds = /* @__PURE__ */ new Set();
|
|
1090
|
-
for (const peer of peerBindings) {
|
|
1091
|
-
for (const tabId of this.collectCandidateTabIds(peer)) {
|
|
1092
|
-
peerTabIds.add(tabId);
|
|
1093
|
-
}
|
|
1094
|
-
if (peer.groupId !== null) {
|
|
1095
|
-
peerGroupIds.add(peer.groupId);
|
|
1096
|
-
}
|
|
1097
|
-
}
|
|
1098
|
-
const bindingTabs = [];
|
|
1099
|
-
const sharedBindingTabs = [];
|
|
1100
|
-
const foreignTabs = [];
|
|
1101
|
-
for (const tab of windowTabs) {
|
|
1102
|
-
if (bindingTabIds.has(tab.id) || state.groupId !== null && tab.groupId === state.groupId) {
|
|
1103
|
-
bindingTabs.push(tab);
|
|
1104
|
-
continue;
|
|
1105
|
-
}
|
|
1106
|
-
if (peerTabIds.has(tab.id) || tab.groupId !== null && peerGroupIds.has(tab.groupId)) {
|
|
1107
|
-
sharedBindingTabs.push(tab);
|
|
1108
|
-
continue;
|
|
1109
|
-
}
|
|
1110
|
-
foreignTabs.push(tab);
|
|
1111
|
-
}
|
|
1112
|
-
return {
|
|
1113
|
-
bindingTabs,
|
|
1114
|
-
sharedBindingTabs,
|
|
1115
|
-
foreignTabs
|
|
1116
|
-
};
|
|
1117
|
-
}
|
|
1118
|
-
async moveBindingIntoBakWindow(state, ownership, initialUrl) {
|
|
1119
|
-
const sourceTabs = this.orderSessionBindingTabsForMigration(state, ownership.bindingTabs);
|
|
1120
|
-
const seedUrl = sourceTabs[0]?.url ?? initialUrl;
|
|
1121
|
-
const sharedWindow = await this.findSharedBindingWindow(state.id, state.windowId === null ? [] : [state.windowId]);
|
|
1122
|
-
const window2 = sharedWindow ?? await this.browser.createWindow({
|
|
1123
|
-
url: seedUrl || DEFAULT_SESSION_BINDING_URL,
|
|
1124
|
-
focused: false
|
|
1125
|
-
});
|
|
1126
|
-
const initialTab = sharedWindow || typeof window2.initialTabId !== "number" ? null : await this.waitForTrackedTab(window2.initialTabId, window2.id);
|
|
1127
|
-
const recreatedTabs = [];
|
|
1128
|
-
const tabIdMap = /* @__PURE__ */ new Map();
|
|
1129
|
-
if (sourceTabs[0]) {
|
|
1130
|
-
const firstTab = initialTab ? await this.browser.updateTab(initialTab.id, {
|
|
1131
|
-
url: sourceTabs[0].url,
|
|
1132
|
-
active: false
|
|
1133
|
-
}) : await this.createBindingTab({
|
|
1134
|
-
windowId: window2.id,
|
|
1135
|
-
url: sourceTabs[0].url,
|
|
1136
|
-
active: false
|
|
1137
|
-
});
|
|
1138
|
-
recreatedTabs.push(firstTab);
|
|
1139
|
-
tabIdMap.set(sourceTabs[0].id, firstTab.id);
|
|
1140
|
-
}
|
|
1141
|
-
for (const sourceTab of sourceTabs.slice(1)) {
|
|
1142
|
-
const recreated = await this.createBindingTab({
|
|
1143
|
-
windowId: window2.id,
|
|
1144
|
-
url: sourceTab.url,
|
|
1145
|
-
active: false
|
|
1146
|
-
});
|
|
1147
|
-
recreatedTabs.push(recreated);
|
|
1148
|
-
tabIdMap.set(sourceTab.id, recreated.id);
|
|
1106
|
+
async attachBindingToActiveWindow(state) {
|
|
1107
|
+
const activeTab = await this.browser.getActiveTab();
|
|
1108
|
+
if (!activeTab) {
|
|
1109
|
+
return null;
|
|
1149
1110
|
}
|
|
1150
|
-
const
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
await this.browser.updateTab(nextActiveTabId, { active: true });
|
|
1111
|
+
const window2 = await this.waitForWindow(activeTab.windowId, 300);
|
|
1112
|
+
if (!window2) {
|
|
1113
|
+
return null;
|
|
1154
1114
|
}
|
|
1155
1115
|
state.windowId = window2.id;
|
|
1156
1116
|
state.groupId = null;
|
|
1157
|
-
state.tabIds =
|
|
1158
|
-
state.
|
|
1159
|
-
state.
|
|
1160
|
-
|
|
1161
|
-
...state,
|
|
1162
|
-
tabIds: [...state.tabIds]
|
|
1163
|
-
});
|
|
1164
|
-
for (const bindingTab of ownership.bindingTabs) {
|
|
1165
|
-
try {
|
|
1166
|
-
await this.browser.closeTab(bindingTab.id);
|
|
1167
|
-
} catch {
|
|
1168
|
-
}
|
|
1169
|
-
}
|
|
1170
|
-
return {
|
|
1171
|
-
window: window2,
|
|
1172
|
-
tabs: await this.readTrackedTabs(state.tabIds, state.windowId)
|
|
1173
|
-
};
|
|
1174
|
-
}
|
|
1175
|
-
orderSessionBindingTabsForMigration(state, tabs) {
|
|
1176
|
-
const ordered = [];
|
|
1177
|
-
const seen = /* @__PURE__ */ new Set();
|
|
1178
|
-
const pushById = (tabId) => {
|
|
1179
|
-
if (typeof tabId !== "number") {
|
|
1180
|
-
return;
|
|
1181
|
-
}
|
|
1182
|
-
const tab = tabs.find((candidate) => candidate.id === tabId);
|
|
1183
|
-
if (!tab || seen.has(tab.id)) {
|
|
1184
|
-
return;
|
|
1185
|
-
}
|
|
1186
|
-
ordered.push(tab);
|
|
1187
|
-
seen.add(tab.id);
|
|
1188
|
-
};
|
|
1189
|
-
pushById(state.primaryTabId);
|
|
1190
|
-
pushById(state.activeTabId);
|
|
1191
|
-
for (const tab of tabs) {
|
|
1192
|
-
if (seen.has(tab.id)) {
|
|
1193
|
-
continue;
|
|
1194
|
-
}
|
|
1195
|
-
ordered.push(tab);
|
|
1196
|
-
seen.add(tab.id);
|
|
1197
|
-
}
|
|
1198
|
-
return ordered;
|
|
1117
|
+
state.tabIds = [];
|
|
1118
|
+
state.activeTabId = null;
|
|
1119
|
+
state.primaryTabId = null;
|
|
1120
|
+
return window2;
|
|
1199
1121
|
}
|
|
1200
1122
|
async findSharedBindingWindow(bindingId, excludedWindowIds = []) {
|
|
1201
1123
|
const peers = (await this.storage.list()).filter((candidate) => candidate.id !== bindingId);
|
|
1202
1124
|
const candidateWindowIds = [];
|
|
1203
1125
|
const peerTabIds = /* @__PURE__ */ new Set();
|
|
1204
1126
|
const peerGroupIds = /* @__PURE__ */ new Set();
|
|
1205
|
-
const reusablePeerIds = /* @__PURE__ */ new Set();
|
|
1206
1127
|
const pushWindowId = (windowId) => {
|
|
1207
1128
|
if (typeof windowId !== "number") {
|
|
1208
1129
|
return;
|
|
@@ -1213,48 +1134,33 @@
|
|
|
1213
1134
|
candidateWindowIds.push(windowId);
|
|
1214
1135
|
};
|
|
1215
1136
|
for (const peer of peers) {
|
|
1216
|
-
if (peer.groupId === null) {
|
|
1217
|
-
continue;
|
|
1218
|
-
}
|
|
1219
|
-
const group = await this.waitForGroup(peer.groupId, 300);
|
|
1220
|
-
if (!group) {
|
|
1221
|
-
continue;
|
|
1222
|
-
}
|
|
1223
|
-
reusablePeerIds.add(peer.id);
|
|
1224
|
-
peerGroupIds.add(group.id);
|
|
1225
|
-
pushWindowId(group.windowId);
|
|
1226
|
-
}
|
|
1227
|
-
for (const peer of peers) {
|
|
1228
|
-
if (!reusablePeerIds.has(peer.id)) {
|
|
1229
|
-
continue;
|
|
1230
|
-
}
|
|
1231
1137
|
const trackedTabIds = this.collectCandidateTabIds(peer);
|
|
1138
|
+
pushWindowId(peer.windowId);
|
|
1232
1139
|
for (const trackedTabId of trackedTabIds) {
|
|
1233
1140
|
peerTabIds.add(trackedTabId);
|
|
1234
1141
|
}
|
|
1142
|
+
if (peer.groupId !== null) {
|
|
1143
|
+
const group = await this.waitForGroup(peer.groupId, 300);
|
|
1144
|
+
if (group) {
|
|
1145
|
+
peerGroupIds.add(group.id);
|
|
1146
|
+
pushWindowId(group.windowId);
|
|
1147
|
+
}
|
|
1148
|
+
}
|
|
1235
1149
|
const trackedTabs = await this.readLooseTrackedTabs(trackedTabIds);
|
|
1236
1150
|
for (const tab of trackedTabs) {
|
|
1237
|
-
|
|
1238
|
-
pushWindowId(tab.windowId);
|
|
1239
|
-
}
|
|
1151
|
+
pushWindowId(tab.windowId);
|
|
1240
1152
|
}
|
|
1241
1153
|
}
|
|
1242
1154
|
for (const windowId of candidateWindowIds) {
|
|
1243
1155
|
const window2 = await this.waitForWindow(windowId, 300);
|
|
1244
1156
|
if (window2) {
|
|
1245
|
-
const windowTabs = await this.
|
|
1157
|
+
const windowTabs = await this.readStableWindowTabs(window2.id, WINDOW_TABS_LOOKUP_TIMEOUT_MS, 150);
|
|
1246
1158
|
const ownedTabs = windowTabs.filter(
|
|
1247
1159
|
(tab) => peerTabIds.has(tab.id) || tab.groupId !== null && peerGroupIds.has(tab.groupId)
|
|
1248
1160
|
);
|
|
1249
1161
|
if (ownedTabs.length === 0) {
|
|
1250
1162
|
continue;
|
|
1251
1163
|
}
|
|
1252
|
-
const foreignTabs = windowTabs.filter(
|
|
1253
|
-
(tab) => !peerTabIds.has(tab.id) && (tab.groupId === null || !peerGroupIds.has(tab.groupId))
|
|
1254
|
-
);
|
|
1255
|
-
if (foreignTabs.length > 0) {
|
|
1256
|
-
continue;
|
|
1257
|
-
}
|
|
1258
1164
|
return window2;
|
|
1259
1165
|
}
|
|
1260
1166
|
}
|
|
@@ -1286,6 +1192,27 @@
|
|
|
1286
1192
|
}
|
|
1287
1193
|
return existingTabs;
|
|
1288
1194
|
}
|
|
1195
|
+
resolveFocusTabId(binding) {
|
|
1196
|
+
return binding.activeTabId ?? binding.primaryTabId ?? binding.tabs[0]?.id ?? null;
|
|
1197
|
+
}
|
|
1198
|
+
withFocusedTab(binding, targetTabId) {
|
|
1199
|
+
return {
|
|
1200
|
+
...binding,
|
|
1201
|
+
activeTabId: targetTabId,
|
|
1202
|
+
tabs: binding.tabs.map((tab) => ({
|
|
1203
|
+
...tab,
|
|
1204
|
+
active: tab.id === targetTabId
|
|
1205
|
+
}))
|
|
1206
|
+
};
|
|
1207
|
+
}
|
|
1208
|
+
async focusBindingWindow(windowId, tabId) {
|
|
1209
|
+
await this.browser.updateWindow(windowId, { focused: true });
|
|
1210
|
+
await this.browser.updateTab(tabId, { active: true });
|
|
1211
|
+
const focusedTab = await this.waitForTrackedTab(tabId, windowId, 500);
|
|
1212
|
+
if (!focusedTab?.active) {
|
|
1213
|
+
await this.browser.updateTab(tabId, { active: true });
|
|
1214
|
+
}
|
|
1215
|
+
}
|
|
1289
1216
|
async collectBindingTabsForClose(state) {
|
|
1290
1217
|
const trackedTabs = await this.readLooseTrackedTabs(this.collectCandidateTabIds(state));
|
|
1291
1218
|
if (state.windowId === null || state.groupId === null) {
|
|
@@ -1416,6 +1343,34 @@
|
|
|
1416
1343
|
}
|
|
1417
1344
|
return [];
|
|
1418
1345
|
}
|
|
1346
|
+
async readStableWindowTabs(windowId, timeoutMs = WINDOW_TABS_LOOKUP_TIMEOUT_MS, settleMs = 150) {
|
|
1347
|
+
const deadline = Date.now() + timeoutMs;
|
|
1348
|
+
let bestTabs = [];
|
|
1349
|
+
let bestSignature = "";
|
|
1350
|
+
let lastSignature = "";
|
|
1351
|
+
let stableSince = 0;
|
|
1352
|
+
while (Date.now() < deadline) {
|
|
1353
|
+
const tabs = await this.browser.listTabs({ windowId });
|
|
1354
|
+
if (tabs.length > 0) {
|
|
1355
|
+
const signature = this.windowTabSnapshotSignature(tabs);
|
|
1356
|
+
if (tabs.length > bestTabs.length || tabs.length === bestTabs.length && signature !== bestSignature) {
|
|
1357
|
+
bestTabs = tabs;
|
|
1358
|
+
bestSignature = signature;
|
|
1359
|
+
}
|
|
1360
|
+
if (signature !== lastSignature) {
|
|
1361
|
+
lastSignature = signature;
|
|
1362
|
+
stableSince = Date.now();
|
|
1363
|
+
} else if (Date.now() - stableSince >= settleMs) {
|
|
1364
|
+
return bestTabs;
|
|
1365
|
+
}
|
|
1366
|
+
}
|
|
1367
|
+
await this.delay(50);
|
|
1368
|
+
}
|
|
1369
|
+
return bestTabs;
|
|
1370
|
+
}
|
|
1371
|
+
windowTabSnapshotSignature(tabs) {
|
|
1372
|
+
return [...tabs].map((tab) => `${tab.id}:${tab.groupId ?? "ungrouped"}`).sort().join("|");
|
|
1373
|
+
}
|
|
1419
1374
|
async delay(ms) {
|
|
1420
1375
|
await new Promise((resolve) => setTimeout(resolve, ms));
|
|
1421
1376
|
}
|
|
@@ -1738,54 +1693,20 @@
|
|
|
1738
1693
|
}
|
|
1739
1694
|
},
|
|
1740
1695
|
async createWindow(options) {
|
|
1741
|
-
const
|
|
1742
|
-
|
|
1743
|
-
|
|
1744
|
-
previouslyFocusedTabs.flatMap((tab) => typeof tab.id === "number" ? [tab.id] : [])
|
|
1745
|
-
);
|
|
1746
|
-
const previouslyFocusedTab = previouslyFocusedTabs.find((tab) => tab.active === true && typeof tab.id === "number") ?? null;
|
|
1747
|
-
const desiredUrl = options.url ?? "about:blank";
|
|
1748
|
-
let created = await chrome.windows.create({
|
|
1749
|
-
url: desiredUrl,
|
|
1750
|
-
focused: true
|
|
1696
|
+
const created = await chrome.windows.create({
|
|
1697
|
+
focused: options.focused,
|
|
1698
|
+
url: options.url ?? "about:blank"
|
|
1751
1699
|
});
|
|
1752
1700
|
if (!created || typeof created.id !== "number") {
|
|
1753
1701
|
throw new Error("Window missing id");
|
|
1754
1702
|
}
|
|
1755
|
-
const
|
|
1756
|
-
|
|
1757
|
-
|
|
1758
|
-
const normalizedDesiredUrl = normalizeComparableTabUrl(desiredUrl);
|
|
1759
|
-
return newlyCreatedTab ?? tabs.find((tab) => {
|
|
1760
|
-
const pendingUrl = "pendingUrl" in tab && typeof tab.pendingUrl === "string" ? tab.pendingUrl : "";
|
|
1761
|
-
return normalizeComparableTabUrl(tab.url ?? pendingUrl) === normalizedDesiredUrl;
|
|
1762
|
-
}) ?? tabs.find((tab) => tab.active === true && typeof tab.id === "number") ?? tabs.find((tab) => typeof tab.id === "number") ?? null;
|
|
1763
|
-
};
|
|
1764
|
-
let seedTab = await pickSeedTab(created.id);
|
|
1765
|
-
const createdWindowTabs = await chrome.tabs.query({ windowId: created.id });
|
|
1766
|
-
const createdWindowReusedFocusedWindow = previouslyFocusedWindow?.id === created.id;
|
|
1767
|
-
const createdWindowLooksDirty = createdWindowTabs.length > 1;
|
|
1768
|
-
if ((createdWindowReusedFocusedWindow || createdWindowLooksDirty) && typeof seedTab?.id === "number") {
|
|
1769
|
-
created = await chrome.windows.create({
|
|
1770
|
-
tabId: seedTab.id,
|
|
1771
|
-
focused: true
|
|
1772
|
-
});
|
|
1773
|
-
if (!created || typeof created.id !== "number") {
|
|
1774
|
-
throw new Error("Lifted window missing id");
|
|
1775
|
-
}
|
|
1776
|
-
seedTab = await pickSeedTab(created.id);
|
|
1777
|
-
}
|
|
1778
|
-
if (options.focused !== true && previouslyFocusedWindow?.id && previouslyFocusedWindow.id !== created.id) {
|
|
1779
|
-
await chrome.windows.update(previouslyFocusedWindow.id, { focused: true });
|
|
1780
|
-
if (typeof previouslyFocusedTab?.id === "number") {
|
|
1781
|
-
await chrome.tabs.update(previouslyFocusedTab.id, { active: true });
|
|
1782
|
-
}
|
|
1783
|
-
}
|
|
1784
|
-
const finalWindow = await chrome.windows.get(created.id);
|
|
1703
|
+
const initialTabId = created.tabs?.find((tab) => typeof tab.id === "number")?.id ?? (await chrome.tabs.query({
|
|
1704
|
+
windowId: created.id
|
|
1705
|
+
})).find((tab) => typeof tab.id === "number")?.id ?? null;
|
|
1785
1706
|
return {
|
|
1786
|
-
id:
|
|
1787
|
-
focused: Boolean(
|
|
1788
|
-
initialTabId
|
|
1707
|
+
id: created.id,
|
|
1708
|
+
focused: Boolean(created.focused),
|
|
1709
|
+
initialTabId
|
|
1789
1710
|
};
|
|
1790
1711
|
},
|
|
1791
1712
|
async updateWindow(windowId, options) {
|
|
@@ -2993,6 +2914,7 @@
|
|
|
2993
2914
|
}
|
|
2994
2915
|
case "sessionBinding.focus": {
|
|
2995
2916
|
const result = await bindingManager.focus(String(params.bindingId ?? ""));
|
|
2917
|
+
emitSessionBindingUpdated(result.binding.id, "focus", result.binding);
|
|
2996
2918
|
return {
|
|
2997
2919
|
ok: true,
|
|
2998
2920
|
browser: result.binding
|
package/dist/manifest.json
CHANGED
package/package.json
CHANGED