chrome.tabs.onUpdated was called twice

2024-04-10
#english #browser-extension

Intro

Lately, I've been working on a browser extension. While developing, I ran into an issue where chrome.tabs.onUpdated.addListener was triggered twice upon tab refresh. It seems odd.

Iframes caused?

Initially, my colleagues and I conducted some research on this matter and came across an article titled Chrome extension - page update twice then removed on YouTube.

To validate our hypothesis, i changed original chrome.tabs.onUpdated method to chrome.webNavigation.onHistoryStateUpdated and implemented the same logic as described in the aforementioned article. Without a double, after i refreshed tab again, chrome.webNavigation.onHistoryStateUpdated was trigged twice. Therefore there must be some other errors contributing this problem.

Furthermore, i noticed that this problem arose after certain versions were released. It's clear that it must be introduced in a specific commit. Therefore, my next step is to identify the first bad commit.

First bad commit

After using git bisect,I finally identified the problematic commit. I won't provide instructions about git bisect here, you can learn it from the link above. When I found the problematic commit, I carefully examined the code. Every line appeared normal, with no apparent issues. However, it seemed unreasonable. After double-checking the code several times, one line caught my attention.

import { generateXXX } from '@root/src/pages/background';

Yeah, i import a method from background.ts file and what does background.ts file looks like ?

export function generateXXX() {
  ...
}

chrome.tabs.onUpdated.addListener(function (
  _tabId: number,
  changeInfo: chrome.tabs.TabChangeInfo,
  tab: chrome.tabs.Tab,
) {
 ...
}

At this point, it became clear what caused the problem. It was simply because chrome.tabs.onUpdated.addListener was imported into another file, and when the tab was refreshed, this method was triggered twice.

Solution

There are many solutions to resolve this problem. The easiest way is to move that function to another file. Additionally, you can use any other approaches you prefer

References

  1. Chrome extension - page update twice then removed on YouTube.
  2. git bisect