mirror of
https://github.com/trezor/trezor-suite.git
synced 2026-03-02 13:35:10 +01:00
feat(utils): add urlToOnion util
This commit is contained in:
@@ -29,6 +29,7 @@ export * from './scheduleAction';
|
||||
export * from './throwError';
|
||||
export * from './truncateMiddle';
|
||||
export * from './topologicalSort';
|
||||
export * from './urlToOnion';
|
||||
export * as versionUtils from './versionUtils';
|
||||
export * as xssFilters from './xssFilters';
|
||||
export * from './getLocaleSeparators';
|
||||
|
||||
16
packages/utils/src/urlToOnion.ts
Normal file
16
packages/utils/src/urlToOnion.ts
Normal file
@@ -0,0 +1,16 @@
|
||||
/**
|
||||
* Tries to replace clearnet domain name in given `url` by any of the onion domain names in
|
||||
* `onionDomains` map and return it. When no onion replacement is found, returns `undefined`.
|
||||
*/
|
||||
export const urlToOnion = (url: string, onionDomains: { [domain: string]: string }) => {
|
||||
const [, protocol, subdomain, domain, rest] =
|
||||
url.match(/^(http|ws)s?:\/\/([^:/]+\.)?([^/.]+\.[^/.]+)(\/.*)?$/i) ?? [];
|
||||
// ^(http|ws)s?:\/\/ - required http(s)/ws(s) protocol
|
||||
// ([^:/]+\.)? - optional subdomains, e.g. 'blog.'
|
||||
// ([^/.]+\.[^/.]+) - required two-part domain name, e.g. 'trezor.io'
|
||||
// (\/.*)?$ - optional path and/or query, e.g. '/api/data?id=1234'
|
||||
|
||||
if (!domain || !onionDomains[domain]) return;
|
||||
|
||||
return `${protocol}://${subdomain ?? ''}${onionDomains[domain]}${rest ?? ''}`;
|
||||
};
|
||||
28
packages/utils/tests/urlToOnion.test.ts
Normal file
28
packages/utils/tests/urlToOnion.test.ts
Normal file
@@ -0,0 +1,28 @@
|
||||
import { urlToOnion } from '../src/urlToOnion';
|
||||
|
||||
const DICT = {
|
||||
'trezor.io': 'trezorioabcd.onion',
|
||||
'coingecko.com': 'coingeckoabcd.onion',
|
||||
};
|
||||
|
||||
const FIXTURE = [
|
||||
['invalid domain', 'aaaa', undefined],
|
||||
['unknown domain', 'http://www.something.test', undefined],
|
||||
['missing protocol', 'trezor.io', undefined],
|
||||
['simple domain http', 'https://trezor.io/', `http://trezorioabcd.onion/`],
|
||||
['simple domain https', 'https://trezor.io/', `http://trezorioabcd.onion/`],
|
||||
['subdomain', 'https://cdn.trezor.io/x/1*ab.png', `http://cdn.trezorioabcd.onion/x/1*ab.png`],
|
||||
['subsubdomain', 'http://alpha.beta.trezor.io', `http://alpha.beta.trezorioabcd.onion`],
|
||||
['blockbook', 'https://btc1.trezor.io/api?t=13#a', `http://btc1.trezorioabcd.onion/api?t=13#a`],
|
||||
['coingecko', 'https://coingecko.com/?dt=5-1-2021', `http://coingeckoabcd.onion/?dt=5-1-2021`],
|
||||
['websocket wss', 'wss://trezor.io', 'ws://trezorioabcd.onion'],
|
||||
['websocket ws', 'ws://foo.bar.trezor.io/?foo=bar', 'ws://foo.bar.trezorioabcd.onion/?foo=bar'],
|
||||
['duplicate match', 'http://trezor.io/trezor.io', 'http://trezorioabcd.onion/trezor.io'],
|
||||
['false match', 'http://a.test/b?url=trezor.io', undefined],
|
||||
] as [string, string, string | undefined][];
|
||||
|
||||
describe('urlToOnion', () => {
|
||||
FIXTURE.forEach(([desc, clear, onion]) =>
|
||||
it(desc, () => expect(urlToOnion(clear, DICT)).toBe(onion)),
|
||||
);
|
||||
});
|
||||
Reference in New Issue
Block a user