Is Auto Link Bypasser safe?

High risk

Auto Link Bypasser is high risk. When Auto Link Bypasser handles a page matched by its domain list, it sends the URL to api.yuumari.com. The background accepts any http/https result without checking the host, redirecting the tab. Testing saw the fetch, not the redirect.…

yuumari devv1.6.1Chrome Web Store
75Risk

AI-generated. Findings may contain errors. Those marked Verified have been manually reviewed.

Publishers can request a review.

Findings

SeverityHIGH
ClassUNWANTED
TypeUnexpected
CWECWE-940
SourceAI SANDBOX

Server response can redirect matching pages

When Auto Link Bypasser handles a page matched by its domain list, it sends the URL to api.yuumari.com.

The background accepts any http/https result without checking the host, redirecting the tab.

Testing saw the fetch, not the redirect.

01EvidenceCAUSE EFFECT
What actually happens
You did this

You open a page that matches the extension's downloaded domain list.

The extension did this

The extension sends that page URL to api.yuumari.com and can redirect the tab to the URL returned by the server.

02EvidenceFIELD TABLE
Fields used by the redirect decision
FieldValueWhy it matters
Visited page URL
https://adfoc.us/123456This tells the server which page you are trying to open so it can decide whether to return a redirect destination.
Access value
6d69e175-derived-access-valueThis value is sent with the page URL and comes from the extension's downloaded configuration.
Returned destination
https://yuumari.com/ex/alb/If this is a web URL, the extension uses it as the next page for your tab.
Message field
A non-empty message stops the redirect; an empty message lets the returned destination be used.
03EvidenceNETWORK CAPTURE
Captured request
POSThttps://api.yuumari.com/ex-alb-centre/
Code path expects JSON with result and message; dynamic analysis did not capture a redirect POST body or response result.
Headers
X-Meow6d69e175
content-typeapplication/x-www-form-urlencoded; charset=utf-8
04EvidenceNETWORK CAPTURE
Captured request
GEThttps://api.yuumari.com/ex-alb-centre/_/
200 OK configuration fetch observed during dynamic analysis; the response populates accepted domains and timing settings.
Headers
X-Meow6d69e175
05EvidenceCODE COMPARE
The code that does this

The POST response is accepted as a redirect target and passed to the content script

What it actually does
Readable POST helperdeobfuscated/background/service-worker.js
  U = (e, r = !1) => new Promise((async (t, i) => {
    const o = {
        [String.fromCharCode(104, 101, 97, 100, 101, 114, 115)]: {
          [String.fromCharCode(88, 45, 77, 101, 111, 119)]: Mi.hex2bin(String.fromCharCode(54, 100, 54, 57, 101, 49, 55, 53), String.fromCharCode(98, 105, 110, 97, 114, 121))
        },
        [String.fromCharCode(116, 105, 109, 101, 111, 117, 116)]: 6e4
      },
      n = r ? String.fromCharCode(104, 116, 116, 112, 115, 58, 47, 47, 97, 112, 105, 46) + b.author + String.fromCharCode(47, 97, 108, 112, 104, 97, 45, 98, 121, 112, 97, 115, 115, 47) : String.fromCharCode(104, 116, 116, 112, 115, 58, 47, 47, 97, 112, 105, 46) + b.author + String.fromCharCode(47, 101, 120, 45, 97, 108, 98, 45, 99, 101, 110, 116, 114, 101, 47);
    await D.post(n, e, o).done((e => {
      Mi.properties_exists(e, ["result", "message"]) ? t(e) : i("invalid response.");
    })).fail((A => {
      A === Z ? t({
        result: "",
        message: "timeout error."
      }) : i("request error.");
    }));
  })),
Readable content-process-three handlerdeobfuscated/background/service-worker.js
      case String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 112, 114, 111, 99, 101, 115, 115, 45, 116, 104, 114, 101, 101):
        return void i(await (async (r, t) => {
          try {
            const i = Mi.property_exists(l, String.fromCharCode(97, 108, 112, 104, 97, 95, 107, 101, 121)) && l[String.fromCharCode(97, 108, 112, 104, 97, 95, 107, 101, 121)] ? Mi[String.fromCharCode(114, 111, 116, 52, 55)](Mi[String.fromCharCode(98, 97, 115, 101, 54, 52, 95, 100, 101, 99, 111, 100, 101)](Mi[String.fromCharCode(114, 111, 116, 52, 55)](Mi[String.fromCharCode(98, 97, 115, 101, 54, 52, 95, 100, 101, 99, 111, 100, 101)](Mi[String.fromCharCode(114, 111, 116, 52, 55)](Mi[String.fromCharCode(98, 97, 115, 101, 54, 52, 95, 100, 101, 99, 111, 100, 101)](l[String.fromCharCode(97, 108, 112, 104, 97, 95, 107, 101, 121)])))))) : null;
            l.cnt_utime < 1 && (l.cnt_utime = +new Date, g$1.storage.local.set({
              cnt_utime: l.cnt_utime
            }));
            const o = await U({
              [String.fromCharCode(108)]: r,
              [String.fromCharCode(117)]: i || l.key
            }, !!i).catch((async A => {
              throw l.query_err_utime = l.query_err_utime > 0 ? l.query_err_utime : +new Date, l.query_err_cur = l.query_err_cur + 1 | 0, g$1.storage.local.set({
                query_err_utime: l.query_err_utime,
                query_err_cur: l.query_err_cur
              }), "query error."
            }));
            return !/^https?:\/\/.+$/.test(o.result) || o.message ? (await g$1.action.setBadgeBackgroundColor({
              color: S.blue,
              tabId: t.tab.id
            }), await g$1.action.setBadgeText({
              text: "1",
              tabId: t.tab.id
            }), "") : o.result
          } catch (A) {}
          return await g$1.action.setIcon({
            path: I.red,
            tabId: t.tab.id
          }).catch((A => {})), null
        })(r.data, t));
Readable content script redirectdeobfuscated/content/script.js
const t = (e = 0) => {
  if (Number.isInteger(e)) return new Promise((t => window.setTimeout(t, e)))
};
(async () => {
  try {
    const r = await g.runtime.sendMessage({
      type: String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 112, 114, 111, 99, 101, 115, 115, 45, 111, 110, 101),
      data: Object.assign({}, window.location)
    });
    if (null === r) throw "no response.";
    if (!r) return;
    for (await t(1500);;) {
      const r = await g.runtime.sendMessage({
        type: String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 112, 114, 111, 99, 101, 115, 115, 45, 116, 119, 111),
        data: null
      });
      if (!Number.isInteger(r)) throw "failure.";
      if (!(r > 0)) break;
      await t(r);
    }
    const n = await g.runtime.sendMessage({
      type: String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 112, 114, 111, 99, 101, 115, 115, 45, 116, 104, 114, 101, 101),
      data: r
    });
    if (null === n) throw "no response.";
    if (!n) return;
    let a = await g.runtime.sendMessage({
      type: String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 112, 114, 111, 99, 101, 115, 115, 45, 102, 111, 117, 114),
      data: null
    });
    if (!Number.isInteger(a)) throw "failure.";
    a && await new Promise((t => {
      const r = window.setInterval((async () => {
        if (--a < 0) return window.clearInterval(r), void t();
        await g.runtime.sendMessage({
          type: String.fromCharCode(99, 111, 110, 116, 101, 110, 116, 45, 115, 108, 101, 101, 112, 45, 98, 97, 100, 103, 101, 45, 115, 101, 116),
          data: a + ""
        });
      }), 1e3);
    })), window.location.href = n;
  } catch (e) {}
})();
06EvidenceTHIRD PARTY LIST
Network destinations involved in this behavior
  • api.yuumari.com

    Receives the selected page URL and returns the redirect decision for Auto Link Bypasser.

  • yuumari.com

    Extension author domain named in the manifest and used to construct the API hostname.

SeverityMEDIUM
ClassUNWANTED
TypeUnexpected
CWECWE-506
SourceAI SANDBOX

Encoded strings wrap Auto Link Bypasser redirects

Auto Link Bypasser runs on every matching page at document start, sends the location to its worker, and builds redirects to yuumari.com from character-code strings.

It decodes an alpha key via rot47/base64 before AES-GCM config decrypt.

01EvidenceCAUSE EFFECT
What actually happens
You did this

You open a page covered by the extension's broad HTTP and HTTPS match rules.

The manifest runs content/script.js at document start on http://*/* and https://*/*.

The extension did this

The extension sends the page location into its redirect workflow and may replace the tab URL.

The content script passes window.location to the service worker, waits for a returned URL, then assigns window.location.href.

02EvidenceFIELD TABLE
Concrete fields and strings used by the redirect workflow
FieldValueWhy it matters
Current page address
https://shorte.st/example-link (illustrative)This tells the redirect service which page you are on so it can decide whether to return a replacement URL.
Redirect message name
content-process-threeThis identifies the step where your page address is sent from the page script to the extension's background logic.
Redirect request fields
l=https://shorte.st/example-link; u=decoded alpha key (illustrative)These fields carry the page address and the decoded key used by the redirect check.
Stored alpha key
alpha_keyThis stored value controls an alternate redirect path after it is decoded through several layers.
Custom request header
X-Meow: 6d69e175 (hex input decoded before use)This header marks requests from the extension to the remote service.
03EvidenceNETWORK CAPTURE
Captured request
POSThttps://api.yuumari.com/alpha-bypass/
The source expects a JSON response with result and message; no request body or response body was recorded in the verification evidence.
Headers
X-Meow6d69e175 (hex input decoded by extension code)
content-typeapplication/x-www-form-urlencoded; charset=utf-8
04EvidenceOPAQUE REVEAL
Why you can't catch this in DevTools

The source represents readable routing strings as character-code expressions before using them.

What's actually being sent
https://api.yuumari.com/alpha-bypass/
content-process-three
alpha_key
subtle
digest
SHA-256
AES-GCM
05EvidenceCODE COMPARE
The code that does this

Shipped snippets and decoded equivalents for the redirect path

What it actually does
Decoded content-script behaviorcontent/script.js (decoded String.fromCharCode values)
const delay = (milliseconds = 0) => {
  if (Number.isInteger(milliseconds)) {
    return new Promise(resolve => window.setTimeout(resolve, milliseconds));
  }
};

(async () => {
  try {
    const shouldProcess = await browser.runtime.sendMessage({
      type: "content-process-one",
      data: Object.assign({}, window.location)
    });
    if (shouldProcess === null) throw "no response.";
    if (!shouldProcess) return;

    for (await delay(1500);;) {
      const waitMs = await browser.runtime.sendMessage({
        type: "content-process-two",
        data: null
      });
      if (!Number.isInteger(waitMs)) throw "failure.";
      if (!(waitMs > 0)) break;
      await delay(waitMs);
    }

    const redirectUrl = await browser.runtime.sendMessage({
      type: "content-process-three",
      data: shouldProcess
    });
    if (redirectUrl === null) throw "no response.";
    if (!redirectUrl) return;

    let sleepSeconds = await browser.runtime.sendMessage({
      type: "content-process-four",
      data: null
    });
    if (!Number.isInteger(sleepSeconds)) throw "failure.";
    if (sleepSeconds) {
      await new Promise(resolve => {
        const timer = window.setInterval(async () => {
          if (--sleepSeconds < 0) {
            window.clearInterval(timer);
            resolve();
            return;
          }
          await browser.runtime.sendMessage({
            type: "content-sleep-badge-set",
            data: sleepSeconds + ""
          });
        }, 1000);
      });
    }

    window.location.href = redirectUrl;
  } catch (error) {}
})();
Decoded service-worker endpoint constructionbackground/service-worker.js (decoded String.fromCharCode values)
const getInitialConfig = () => new Promise(async (resolve, reject) => {
  const options = {
    headers: {
      "X-Meow": Mi.hex2bin("6d69e175", "binary")
    },
    timeout: 10000
  };
  const url = "https://api." + manifest.author + "/ex-alb-centre/_/";
  await D.get(url, options).done(response => {
    Mi.properties_exists(response, [
      "accept_domains",
      "diff_domains",
      "access_key",
      "cnt_max",
      "cnt_interval_sec",
      "ex_version",
      "ex_message"
    ]) ? resolve(response) : reject("missing props.");
  }).fail(error => {
    reject(error === Z ? "timeout error." : "request error.");
  });
});

const postRedirectCheck = (body, useAlpha = false) => new Promise(async (resolve, reject) => {
  const options = {
    headers: {
      "X-Meow": Mi.hex2bin("6d69e175", "binary")
    },
    timeout: 60000
  };
  const url = useAlpha
    ? "https://api." + manifest.author + "/alpha-bypass/"
    : "https://api." + manifest.author + "/ex-alb-centre/";
  await D.post(url, body, options).done(response => {
    Mi.properties_exists(response, ["result", "message"]) ? resolve(response) : reject("invalid response.");
  }).fail(error => {
    error === Z ? resolve({ result: "", message: "timeout error." }) : reject("request error.");
  });
});
Decoded alpha-key and AES-GCM processingbackground/service-worker.js (decoded String.fromCharCode values)
async function decryptServerConfig(ciphertextHex, serializedAcceptDomains) {
  const cryptoRef = crypto;
  try {
    const keyMaterial = new TextEncoder("utf-8").encode(serializedAcceptDomains);
    const digest = await cryptoRef.subtle.digest("SHA-256", keyMaterial);
    const bytes = Mi.hexToBytes(ciphertextHex);
    const iv = new Uint8Array(bytes.slice(0, 12));
    const algorithm = { name: "AES-GCM", iv, tagLength: 128 };
    const key = await cryptoRef.subtle.importKey("raw", digest, algorithm, false, ["decrypt"]);
    const encryptedBody = new Uint8Array(bytes.slice(12));
    const plaintext = await cryptoRef.subtle.decrypt(algorithm, key, encryptedBody);
    return new TextDecoder("utf-8").decode(plaintext);
  } catch (error) {}
  const randomValues = crypto.getRandomValues.bind(crypto);
  if (randomValues) {
    try {
      return [...randomValues(new Uint8Array(112))].map(value => ("0" + value.toString(16)).slice(-2)).join("");
    } catch (error) {}
  }
  return null;
}

const decodedAlphaKey = storage.alpha_key
  ? Mi.rot47(Mi.base64_decode(Mi.rot47(Mi.base64_decode(Mi.rot47(Mi.base64_decode(storage.alpha_key))))))
  : null;

const redirectResponse = await postRedirectCheck({
  l: pageLocationFromContentScript,
  u: decodedAlphaKey || storage.key
}, !!decodedAlphaKey);
06EvidenceTHIRD PARTY LIST
Remote hosts reached by the redirect workflow
  • api.yuumari.com

    Receives redirect-check requests built by the service worker and returns result/message responses.

  • yuumari.com

    Named as the manifest author and homepage domain; used to compose the api.yuumari.com endpoints.

Updated 17 September 2026doiagnjlaingkmdjlbfalakpnphfmnoh