aboutsummaryrefslogtreecommitdiff
path: root/src/background
diff options
context:
space:
mode:
authorShin'ya Ueoka <ueokande@i-beam.org>2021-09-25 18:17:50 +0900
committerShin'ya Ueoka <ueokande@i-beam.org>2021-09-25 18:57:07 +0900
commita0f2c3ee107508e406a4a41cbda76ecd2d3f0d8f (patch)
tree2a14c2b99fa32e3a7c7473adaa60c8f544a9a56d /src/background
parentfa3500e3bbd11caa0e7ad1633b85f95600cf962f (diff)
Discover frames on search by count of connections
When a tab switches pages quickly, a disconnect event on top frame is sometime delivered after second connect event. In addition, `tabs.onUpdated()` event is independent on port connection event. Now the background script finds alive frames by only port connection.
Diffstat (limited to 'src/background')
-rw-r--r--src/background/Application.ts1
-rw-r--r--src/background/repositories/ReadyFrameRepository.ts37
-rw-r--r--src/background/usecases/ReadyFrameUseCase.ts18
3 files changed, 21 insertions, 35 deletions
diff --git a/src/background/Application.ts b/src/background/Application.ts
index c7bcc42..b439d19 100644
--- a/src/background/Application.ts
+++ b/src/background/Application.ts
@@ -31,7 +31,6 @@ export default class Application {
browser.tabs.onUpdated.addListener((tabId: number, info) => {
if (info.status == "loading") {
- this.frameRepository.clearFrameIds(tabId);
this.findRepository.deleteLocalState(tabId);
}
});
diff --git a/src/background/repositories/ReadyFrameRepository.ts b/src/background/repositories/ReadyFrameRepository.ts
index aa5d986..c993858 100644
--- a/src/background/repositories/ReadyFrameRepository.ts
+++ b/src/background/repositories/ReadyFrameRepository.ts
@@ -2,11 +2,9 @@ import MemoryStorage from "../infrastructures/MemoryStorage";
const REPOSITORY_KEY = "readyFrameRepository";
-type State = { [tabId: number]: number[] };
+type State = { [tabId: number]: { [frameId: number]: number } };
export default interface ReadyFrameRepository {
- clearFrameIds(tabId: number): Promise<void>;
-
addFrameId(tabId: number, frameId: number): Promise<void>;
removeFrameId(tabId: number, frameId: number): Promise<void>;
@@ -21,22 +19,14 @@ export class ReadyFrameRepositoryImpl implements ReadyFrameRepository {
this.cache = new MemoryStorage();
}
- clearFrameIds(tabId: number): Promise<void> {
- let state: State | undefined = this.cache.get(REPOSITORY_KEY);
- if (typeof state === "undefined") {
- state = {};
- }
- delete state[tabId];
- this.cache.set(REPOSITORY_KEY, state);
- return Promise.resolve();
- }
-
addFrameId(tabId: number, frameId: number): Promise<void> {
let state: State | undefined = this.cache.get(REPOSITORY_KEY);
if (typeof state === "undefined") {
state = {};
}
- state[tabId] = (state[tabId] || []).concat(frameId).sort();
+ const tab = state[tabId] || {};
+ tab[frameId] = (tab[frameId] || 0) + 1;
+ state[tabId] = tab;
this.cache.set(REPOSITORY_KEY, state);
return Promise.resolve();
}
@@ -50,7 +40,15 @@ export class ReadyFrameRepositoryImpl implements ReadyFrameRepository {
if (typeof ids === "undefined") {
return Promise.resolve();
}
- state[tabId] = ids.filter((id) => id != frameId);
+ const tab = state[tabId] || {};
+ tab[frameId] = (tab[frameId] || 0) - 1;
+ if (tab[frameId] == 0) {
+ delete tab[frameId];
+ }
+ if (Object.keys(tab).length === 0) {
+ delete state[tabId];
+ }
+
this.cache.set(REPOSITORY_KEY, state);
return Promise.resolve();
}
@@ -60,6 +58,13 @@ export class ReadyFrameRepositoryImpl implements ReadyFrameRepository {
if (typeof state === "undefined") {
return Promise.resolve(undefined);
}
- return Promise.resolve(state[tabId]);
+ const tab = state[tabId];
+ if (typeof tab === "undefined") {
+ return Promise.resolve(undefined);
+ }
+ const frameIds = Object.keys(tab)
+ .map((v) => Number(v))
+ .sort();
+ return Promise.resolve(frameIds);
}
}
diff --git a/src/background/usecases/ReadyFrameUseCase.ts b/src/background/usecases/ReadyFrameUseCase.ts
deleted file mode 100644
index 81bee0c..0000000
--- a/src/background/usecases/ReadyFrameUseCase.ts
+++ /dev/null
@@ -1,18 +0,0 @@
-import { inject, injectable } from "tsyringe";
-import ReadyFrameRepository from "../repositories/ReadyFrameRepository";
-
-@injectable()
-export default class ReadyFrameUseCase {
- constructor(
- @inject("ReadyFrameRepository")
- private readonly frameRepository: ReadyFrameRepository
- ) {}
-
- async addReadyFrame(tabId: number, frameId: number): Promise<void> {
- return this.frameRepository.addFrameId(tabId, frameId);
- }
-
- async clearReadyFrame(tabId: number): Promise<void> {
- return this.frameRepository.clearFrameIds(tabId);
- }
-}