Is North Ad-Block safe?
North Ad-Block transmits open-tab domains to its server on install and allows that server to push arbitrary JavaScript into every browsed page.
On installation, the extension collects the hostnames of all open browser tabs and sends them to api.n-adb.com, then continues forwarding per-site ad-block counts and tab domains every 60 seconds. The server can respond with inline JavaScript code that the extension injects and executes in the main world of each page the user visits, giving the server full access to page content, credentials, and session data. A separate message handler in the content script accepts storage writes from any web page without validating the origin, which can allow a malicious site to overwrite authentication tokens used by the extension.
AI-generated. Findings may contain errors. Those marked Verified have been manually reviewed.
Publishers can request a review.
Findings
The vendor server can run arbitrary JavaScript on every site you visit
This ad blocker periodically checks in with api.n-adb.com.
A reply header x-fetch-scriptlets triggers a rules download whose lines run as raw JavaScript in the page (MAIN world), with the site's own script access.
DA confirmed it.
The vendor server replies to a routine check-in with a header that points to a rules file.
The x-fetch-scriptlets header on the /heartbeat response tells the extension to download /rules/scriptlets.txt.
On your next page load, JavaScript from that file runs inside the page with the same access the website's own scripts have.
Lines marked with #%# are stored as inline code and executed in the page's MAIN world.
Server-supplied lines are parsed as JavaScript, then executed in the page
// 1. Routine /heartbeat reply includes x-fetch-scriptlets. // 2. Extension downloads /rules/scriptlets.txt from the same server. // 3. Any line like example.com#%#<JS> is stored as runnable code for example.com. // 4. When you open example.com, the extension runs <JS> in the page's // MAIN world via new Function(<JS>) - same access as the page's own scripts. // 5. The content script is granted <all_urls>, so this works on any site.
Shows the exact storage shape the extension produces from a server-supplied scriptlets.txt line, and the line of server text that produces it. Confirms a single server-controlled line becomes JavaScript that runs in the page.
// A single line in /rules/scriptlets.txt served by api.n-adb.com:
const serverLine = "example.com#%#window.__marker='ran'; document.title='changed';";
// transformScriptletTextToObject() turns that line into this storage entry:
const storedRule = {
"scriplet_example.com": [
{
code: "window.__marker='ran'; document.title='changed';",
isOnlyForMainFrame: false,
type: "inline"
}
]
};
// On navigation to example.com, adBlocking.js executes, in the page's MAIN world:
// new Function(storedRule['scriplet_example.com'][0].code)()
// i.e. the server-supplied string runs as page JavaScript.
console.log(JSON.stringify(storedRule, null, 2));- 1Run: node scriptlets-rule-shape.js.
- 2Compare output to the shape from transformScriptletTextToObject() in rulesManager.js.
- 3The 'code' value runs via new Function() in the page's MAIN world by executeScriptletInjections().
Code run in the MAIN world shares the page's JavaScript context. It can read and modify anything the website's own scripts can: page content, form inputs, and the logged-in session for whatever site you are on. Because the content script is granted access to all URLs, the same mechanism applies to every site you visit, and the code that runs is chosen by the server at request time rather than fixed in the published extension.
Domains of every open tab sent to api.n-adb.com the moment you install
On install, this ad blocker reads every open tab's domain (e.g. chatgpt.com, x.com) and sends that list in its first request to api.n-adb.com.
DA confirmed both domains were stored, then transmitted, a snapshot an ad blocker doesn't need.
You install the ad blocker while other tabs are already open.
The extension reads the domain of every open tab and sends that list to its vendor server.
It runs chrome.tabs.query({}) on the install event, skips chrome:// and extension pages, and keeps the unique domain of every other tab.
The install handler collects open-tab domains and includes them in the first server request
// 1. On install, list every open tab. // 2. Throw away chrome:// and extension URLs. // 3. Reduce each remaining URL to its domain (chatgpt.com, x.com). // 4. Save that list, then POST it to https://api.n-adb.com/initialize // inside the initialTabDomains field of the first request body.
| Content-Type | application/json |
{
"blockedCounts": {},
"initialTabDomains": [
"chatgpt.com",
"x.com"
]
}| Field | Value | Why it matters | |
|---|---|---|---|
Domains of your open tabs | ["chatgpt.com", "x.com"] | The website of every tab you had open when you installed the ad blocker, captured as a one-time snapshot of what you were doing. |
Open-tab domains and per-site block counts sent to api.n-adb.com on a timer
Beyond the install report, this ad blocker posts to api.n-adb.com/heartbeat roughly every 60 seconds, an interval the server can change.
The payload has install-time tab domains plus a per-site count of blocked ads.
A repeating alarm fires roughly once a minute.
configureSynchronizationAlarm sets the period; the server can change it via x-heartbeat-interval.
The extension sends your install-time tab domains and per-site block counts to its vendor server.
buildTelemetryPayload assembles the report and POSTs it to api.n-adb.com/heartbeat.
A synchronization alarm POSTs a telemetry payload to api.n-adb.com/heartbeat about every 60 seconds. The interval defaults to 60s and is overridden by the x-heartbeat-interval header the server returns, so the vendor controls how often reporting happens.
| Content-Type | application/json |
| Authorization | Bearer <redacted> |
{
"blockedCounts": {},
"initialTabDomains": [
"chatgpt.com",
"x.com"
]
}| Field | Value | Why it matters | |
|---|---|---|---|
Install-time tab domains | ["chatgpt.com", "x.com"] | The domains of the tabs you had open when the extension was installed, re-sent on every heartbeat. | |
Per-site block counts | {"nytimes.com": 14, "youtube.com": 7} | How many ad requests were blocked on each site. Because counts only accrue on sites you open, this map reveals which sites you visit. |