From d4ff4c5b2da36117bdb999d79dddd84ee371dc81 Mon Sep 17 00:00:00 2001 From: SukkaW Date: Sun, 3 Dec 2023 02:04:09 +0800 Subject: [PATCH] Make ESLint Happy --- Build/build-cdn-conf.ts | 2 +- Build/build-common.ts | 9 ++- Build/build-domestic-ruleset.ts | 13 ++-- Build/build-internal-cdn-rules.ts | 5 +- Build/build-internal-chn-domains.ts | 2 +- Build/build-internal-reverse-chn-cidr.ts | 2 +- Build/build-mitm-hostname.js | 2 +- Build/build-phishing-domainset.ts | 14 ++--- Build/build-public.ts | 2 +- Build/build-reject-domainset.ts | 13 ++-- Build/build-speedtest-domainset.ts | 8 +-- Build/build-stream-service.ts | 12 ++-- Build/download-previous-build.ts | 4 +- Build/index.ts | 2 +- Build/lib/aho-corasick.ts | 22 +++---- Build/lib/cached-tld-parse.ts | 6 +- Build/lib/constants.ts | 2 +- Build/lib/create-file.ts | 2 +- Build/lib/domain-deduper.ts | 2 +- Build/lib/fetch-retry.ts | 58 +++++++++--------- Build/lib/get-gorhill-publicsuffix.ts | 2 +- Build/lib/parse-dnsmasq.ts | 4 +- Build/lib/parse-filter.ts | 16 ++--- Build/lib/reject-data-source.ts | 2 +- Build/lib/stable-sort-domain.test.ts | 1 + Build/lib/stable-sort-domain.ts | 1 + Build/lib/text-decoder-stream.ts | 2 +- Build/lib/text-line-transform-stream.ts | 11 ++-- Build/lib/trace-runner.ts | 6 +- Build/lib/trie.test.ts | 3 +- Build/lib/trie.ts | 4 +- Build/mod.d.ts | 32 +++++----- .../build-internal-reverse-chn-cidr-worker.ts | 2 +- bun.lockb | Bin 110306 -> 106738 bytes eslint.config.js | 2 +- package.json | 6 +- 36 files changed, 136 insertions(+), 140 deletions(-) diff --git a/Build/build-cdn-conf.ts b/Build/build-cdn-conf.ts index d042cd26..a30864e1 100644 --- a/Build/build-cdn-conf.ts +++ b/Build/build-cdn-conf.ts @@ -56,7 +56,7 @@ const getS3OSSDomains = async (): Promise> => { return S3OSSDomains; }; -const buildCdnConf = task(import.meta.path, async () => { +const buildCdnConf = task(import.meta.path, async () => { /** @type {string[]} */ const cdnDomainsList: string[] = []; diff --git a/Build/build-common.ts b/Build/build-common.ts index 2188bead..b16571d4 100644 --- a/Build/build-common.ts +++ b/Build/build-common.ts @@ -18,7 +18,7 @@ const outputSurgeDir = path.resolve(import.meta.dir, '../List'); const outputClashDir = path.resolve(import.meta.dir, '../Clash'); export const buildCommon = task(import.meta.path, async () => { - const promises: Promise[] = []; + const promises: Array> = []; const pw = new PathScurry(sourceDir); for await (const entry of pw) { @@ -57,23 +57,22 @@ const processFile = async (sourcePath: string) => { let title = ''; const descriptions: string[] = []; - try { for await (const line of readFileByLine(sourcePath)) { if (line === MAGIC_COMMAND_SKIP) { return; } - + if (line.startsWith(MAGIC_COMMAND_TITLE)) { title = line.slice(MAGIC_COMMAND_TITLE.length).trim(); continue; } - + if (line.startsWith(MAGIC_COMMAND_DESCRIPTION)) { descriptions.push(line.slice(MAGIC_COMMAND_DESCRIPTION.length).trim()); continue; } - + const l = processLine(line); if (l) { lines.push(l); diff --git a/Build/build-domestic-ruleset.ts b/Build/build-domestic-ruleset.ts index 422e74d0..9dd25f0f 100644 --- a/Build/build-domestic-ruleset.ts +++ b/Build/build-domestic-ruleset.ts @@ -11,15 +11,10 @@ export const buildDomesticRuleset = task(import.meta.path, async () => { const results = await processLineFromReadline(readFileByLine(path.resolve(import.meta.dir, '../Source/non_ip/domestic.conf'))); results.push( - ...Object.entries(DOMESTICS) - .reduce( - (acc, [key, { domains }]) => { - if (key === 'SYSTEM') return acc; - return [...acc, ...domains]; - }, - [] - ) - .map((domain) => `DOMAIN-SUFFIX,${domain}`) + ...Object.entries(DOMESTICS).reduce((acc, [key, { domains }]) => { + if (key === 'SYSTEM') return acc; + return [...acc, ...domains]; + }, []).map((domain) => `DOMAIN-SUFFIX,${domain}`) ); const rulesetDescription = [ diff --git a/Build/build-internal-cdn-rules.ts b/Build/build-internal-cdn-rules.ts index 7db68873..720f3350 100644 --- a/Build/build-internal-cdn-rules.ts +++ b/Build/build-internal-cdn-rules.ts @@ -1,5 +1,4 @@ -// @ts-check -import fsp from 'fs/promises' +import fsp from 'fs/promises'; import path from 'path'; import * as tldts from 'tldts'; import { processLine } from './lib/process-line'; @@ -14,7 +13,7 @@ const escapeRegExp = (string = '') => string.replaceAll(/[$()*+.?[\\\]^{|}]/g, ' export const buildInternalCDNDomains = task(import.meta.path, async () => { const set = new Set(); - const keywords = new Set(); + const keywords = new Set(); const gorhill = await getGorhillPublicSuffixPromise(); const domainSorter = createDomainSorter(gorhill); diff --git a/Build/build-internal-chn-domains.ts b/Build/build-internal-chn-domains.ts index 3328b523..821c1bd6 100644 --- a/Build/build-internal-chn-domains.ts +++ b/Build/build-internal-chn-domains.ts @@ -1,5 +1,5 @@ import path from 'path'; -import fsp from 'fs/promises' +import fsp from 'fs/promises'; import { parseFelixDnsmasq } from './lib/parse-dnsmasq'; import { task } from './lib/trace-runner'; import { compareAndWriteFile } from './lib/create-file'; diff --git a/Build/build-internal-reverse-chn-cidr.ts b/Build/build-internal-reverse-chn-cidr.ts index 19177c78..8bf6b801 100644 --- a/Build/build-internal-reverse-chn-cidr.ts +++ b/Build/build-internal-reverse-chn-cidr.ts @@ -1,7 +1,7 @@ import { fetchRemoteTextAndCreateReadlineInterface } from './lib/fetch-remote-text-by-line'; import { processLineFromReadline } from './lib/process-line'; import path from 'path'; -import fsp from 'fs/promises' +import fsp from 'fs/promises'; import { task } from './lib/trace-runner'; const RESERVED_IPV4_CIDR = [ diff --git a/Build/build-mitm-hostname.js b/Build/build-mitm-hostname.js index eac384b7..e1563736 100644 --- a/Build/build-mitm-hostname.js +++ b/Build/build-mitm-hostname.js @@ -1,7 +1,7 @@ const fsPromises = require('fs').promises; const pathFn = require('path'); const table = require('table'); -import listDir from '@sukka/listdir'; +const listDir = require('@sukka/listdir'); const { green, yellow } = require('picocolors'); const PRESET_MITM_HOSTNAMES = [ diff --git a/Build/build-phishing-domainset.ts b/Build/build-phishing-domainset.ts index d8e08f6e..d34ba684 100644 --- a/Build/build-phishing-domainset.ts +++ b/Build/build-phishing-domainset.ts @@ -1,10 +1,10 @@ -import { processFilterRules, processHosts } from './lib/parse-filter'; +import { processHosts } from './lib/parse-filter'; import path from 'path'; import { createRuleset } from './lib/create-file'; import { processLine } from './lib/process-line'; import { createDomainSorter } from './lib/stable-sort-domain'; import { traceSync, task } from './lib/trace-runner'; -import createTrie from './lib/trie'; +import { createTrie } from './lib/trie'; import { getGorhillPublicSuffixPromise } from './lib/get-gorhill-publicsuffix'; import { createCachedGorhillGetDomain } from './lib/cached-tld-parse'; import * as tldts from 'tldts'; @@ -156,11 +156,11 @@ export const buildPhishingDomainSet = task(import.meta.path, async () => { const results = traceSync('* get final results', () => Object.entries(domainCountMap) .reduce((acc, [apexDomain, count]) => { - if (count >= 5) { - acc.push(`.${apexDomain}`); - } - return acc; - }, []) + if (count >= 5) { + acc.push(`.${apexDomain}`); + } + return acc; + }, []) .sort(domainSorter)); const description = [ diff --git a/Build/build-public.ts b/Build/build-public.ts index 91f27a7b..143fd877 100644 --- a/Build/build-public.ts +++ b/Build/build-public.ts @@ -1,6 +1,6 @@ import listDir from '@sukka/listdir'; import path from 'path'; -import fsp from 'fs/promises' +import fsp from 'fs/promises'; import { task } from './lib/trace-runner'; const rootPath = path.resolve(import.meta.dir, '../'); diff --git a/Build/build-reject-domainset.ts b/Build/build-reject-domainset.ts index 5477999a..983aec99 100644 --- a/Build/build-reject-domainset.ts +++ b/Build/build-reject-domainset.ts @@ -1,9 +1,9 @@ // @ts-check -import fsp from 'fs/promises' +import fsp from 'fs/promises'; import path from 'path'; import { processHosts, processFilterRules } from './lib/parse-filter'; -import createTrie from './lib/trie'; +import { createTrie } from './lib/trie'; import { HOSTS, ADGUARD_FILTERS, PREDEFINED_WHITELIST, PREDEFINED_ENFORCED_BACKLIST } from './lib/reject-data-source'; import { createRuleset, compareAndWriteFile } from './lib/create-file'; @@ -20,13 +20,13 @@ import { SHARED_DESCRIPTION } from './lib/constants'; /** Whitelists */ const filterRuleWhitelistDomainSets = new Set(PREDEFINED_WHITELIST); /** @type {Set} Dedupe domains inclued by DOMAIN-KEYWORD */ -const domainKeywordsSet: Set = new Set(); +const domainKeywordsSet = new Set(); /** @type {Set} Dedupe domains included by DOMAIN-SUFFIX */ -const domainSuffixSet: Set = new Set(); +const domainSuffixSet = new Set(); export const buildRejectDomainSet = task(import.meta.path, async () => { /** @type Set */ - const domainSets: Set = new Set(); + const domainSets = new Set(); // Parse from AdGuard Filters console.time('* Download and process Hosts / AdBlock Filter Rules'); @@ -91,7 +91,6 @@ export const buildRejectDomainSet = task(import.meta.path, async () => { console.timeEnd('* Download and process Hosts / AdBlock Filter Rules'); if (shouldStop) { - // eslint-disable-next-line n/no-process-exit -- force stop process.exit(1); } @@ -173,7 +172,7 @@ export const buildRejectDomainSet = task(import.meta.path, async () => { console.log(`Deduped ${previousSize - dudupedDominArray.length} rules!`); // Create reject stats - const rejectDomainsStats: [string, number][] = traceSync( + const rejectDomainsStats: Array<[string, number]> = traceSync( '* Collect reject domain stats', () => Object.entries( dudupedDominArray.reduce>((acc, cur) => { diff --git a/Build/build-speedtest-domainset.ts b/Build/build-speedtest-domainset.ts index fa0c604a..96bd2b8f 100644 --- a/Build/build-speedtest-domainset.ts +++ b/Build/build-speedtest-domainset.ts @@ -14,7 +14,7 @@ const s = new Sema(3); const latestTopUserAgentsPromise = fetchWithRetry('https://unpkg.com/top-user-agents@latest/index.json') .then(res => res.json() as Promise); -const querySpeedtestApi = async (keyword: string): Promise<(string | null)[]> => { +const querySpeedtestApi = async (keyword: string): Promise> => { const [topUserAgents] = await Promise.all([ latestTopUserAgentsPromise, s.acquire() @@ -42,10 +42,10 @@ const querySpeedtestApi = async (keyword: string): Promise<(string | null)[]> => } }); if (!res.ok) { - throw new Error(res.statusText + '\n' + await res.text()); + throw new Error(`${res.statusText}\n${await res.text()}`); } - const json = await res.json() as { url: string; }[]; + const json = await res.json() as Array<{ url: string }>; s.release(); console.timeEnd(key); @@ -60,7 +60,7 @@ const querySpeedtestApi = async (keyword: string): Promise<(string | null)[]> => export const buildSpeedtestDomainSet = task(import.meta.path, async () => { /** @type {Set} */ - const domains: Set = new Set([ + const domains = new Set([ '.speedtest.net', '.speedtestcustom.com', '.ooklaserver.net', diff --git a/Build/build-stream-service.ts b/Build/build-stream-service.ts index 2d67d447..4810acbd 100644 --- a/Build/build-stream-service.ts +++ b/Build/build-stream-service.ts @@ -7,7 +7,7 @@ import { createRuleset } from './lib/create-file'; import { ALL, NORTH_AMERICA, EU, HK, TW, JP, KR } from '../Source/stream'; import { SHARED_DESCRIPTION } from './lib/constants'; -const createRulesetForStreamService = (fileId: string, title: string, streamServices: import('../Source/stream').StreamService[]) => { +const createRulesetForStreamService = (fileId: string, title: string, streamServices: Array) => { return [ // Domains ...createRuleset( @@ -15,10 +15,10 @@ const createRulesetForStreamService = (fileId: string, title: string, streamServ [ ...SHARED_DESCRIPTION, '', - ...streamServices.map((i: { name: any; }) => `- ${i.name}`) + ...streamServices.map((i) => `- ${i.name}`) ], new Date(), - streamServices.flatMap((i: { rules: any; }) => i.rules), + streamServices.flatMap((i) => i.rules), 'ruleset', path.resolve(import.meta.dir, `../List/non_ip/${fileId}.conf`), path.resolve(import.meta.dir, `../Clash/non_ip/${fileId}.txt`) @@ -29,14 +29,14 @@ const createRulesetForStreamService = (fileId: string, title: string, streamServ [ ...SHARED_DESCRIPTION, '', - ...streamServices.map((i: { name: any; }) => `- ${i.name}`) + ...streamServices.map((i) => `- ${i.name}`) ], new Date(), streamServices.flatMap((i) => ( i.ip ? [ - ...i.ip.v4.map((ip: any) => `IP-CIDR,${ip},no-resolve`), - ...i.ip.v6.map((ip: any) => `IP-CIDR6,${ip},no-resolve`) + ...i.ip.v4.map((ip) => `IP-CIDR,${ip},no-resolve`), + ...i.ip.v6.map((ip) => `IP-CIDR6,${ip},no-resolve`) ] : [] )), diff --git a/Build/download-previous-build.ts b/Build/download-previous-build.ts index d8371c01..ef1b3ec0 100644 --- a/Build/download-previous-build.ts +++ b/Build/download-previous-build.ts @@ -71,7 +71,7 @@ export const downloadPreviousBuild = task(import.meta.path, async () => { return; } - const relativeEntryPath = entry.path.replace('ruleset.skk.moe-master' + path.sep, ''); + const relativeEntryPath = entry.path.replace(`ruleset.skk.moe-master${path.sep}`, ''); const targetPath = path.join(import.meta.dir, '..', relativeEntryPath); await fsp.mkdir(path.dirname(targetPath), { recursive: true }); @@ -105,7 +105,7 @@ export const downloadPublicSuffixList = task(import.meta.path, async () => { fsp.mkdir(publicSuffixDir, { recursive: true }) ]); - return Bun.write(publicSuffixPath, resp); + return Bun.write(publicSuffixPath, resp as Response); }, 'download-publicsuffixlist'); if (import.meta.main) { diff --git a/Build/index.ts b/Build/index.ts index 2ad96bbd..aaa46283 100644 --- a/Build/index.ts +++ b/Build/index.ts @@ -98,7 +98,7 @@ import { buildPublicHtml } from './build-public'; printStats(stats); } catch (e) { console.error(e); - console.error('Something went wrong!') + console.error('Something went wrong!'); } })(); diff --git a/Build/lib/aho-corasick.ts b/Build/lib/aho-corasick.ts index 585cb3fb..da07ff42 100644 --- a/Build/lib/aho-corasick.ts +++ b/Build/lib/aho-corasick.ts @@ -1,12 +1,12 @@ interface Node { /** @default 0 */ - depth?: number; - key: string; + depth?: number, + key: string, /** @default false */ - word?: boolean; - children: Record; - fail?: Node; - count: number; + word?: boolean, + children: Record, + fail?: Node, + count: number } const createNode = (key: string, depth = 0): Node => ({ @@ -31,15 +31,15 @@ const createKeywordFilter = (keys: string[] | Set) => { const map = beginNode.children; // eslint-disable-next-line guard-for-in -- plain object for (const key in beginNode.children) { - const node = map?.[key]; + const node = map[key]; let failNode = beginNode.fail; - while (failNode && !failNode.children?.[key]) { + while (failNode && !failNode.children[key]) { failNode = failNode.fail; } if (node) { - node.fail = failNode?.children?.[key] || root; + node.fail = failNode?.children[key] || root; queue.push(node); } @@ -86,8 +86,8 @@ const createKeywordFilter = (keys: string[] | Set) => { // const key = text.charAt(i); const key = text[i]; - while (node && !node?.children[key]) { - node = node?.fail; + while (node && !node.children[key]) { + node = node.fail; } node = node?.children[key] || root; diff --git a/Build/lib/cached-tld-parse.ts b/Build/lib/cached-tld-parse.ts index 01d75ffd..356b2888 100644 --- a/Build/lib/cached-tld-parse.ts +++ b/Build/lib/cached-tld-parse.ts @@ -1,6 +1,6 @@ -import tldts from 'tldts'; +import * as tldts from 'tldts'; import { createCache } from './cache-apply'; -import { PublicSuffixList } from 'gorhill-publicsuffixlist'; +import type { PublicSuffixList } from 'gorhill-publicsuffixlist'; const cache = createCache('cached-tld-parse', true); @@ -12,6 +12,6 @@ let gothillGetDomainCache: ReturnType | null = null; export const createCachedGorhillGetDomain = (gorhill: PublicSuffixList) => { return (domain: string) => { gothillGetDomainCache ??= createCache('cached-gorhill-get-domain', true); - return gothillGetDomainCache.sync(domain, () => gorhill.getDomain(domain[0] === '.' ? domain.slice(1) : domain)) + return gothillGetDomainCache.sync(domain, () => gorhill.getDomain(domain[0] === '.' ? domain.slice(1) : domain)); }; }; diff --git a/Build/lib/constants.ts b/Build/lib/constants.ts index a6566f2b..503c74e1 100644 --- a/Build/lib/constants.ts +++ b/Build/lib/constants.ts @@ -1,5 +1,5 @@ export const SHARED_DESCRIPTION = [ 'License: AGPL 3.0', 'Homepage: https://ruleset.skk.moe', - 'GitHub: https://github.com/SukkaW/Surge', + 'GitHub: https://github.com/SukkaW/Surge' ] as const; diff --git a/Build/lib/create-file.ts b/Build/lib/create-file.ts index d0c09cd6..c6360216 100644 --- a/Build/lib/create-file.ts +++ b/Build/lib/create-file.ts @@ -85,7 +85,7 @@ export const createRuleset = ( _clashContent = surgeRulesetToClashClassicalTextRuleset(content); break; default: - throw new TypeError(`Unknown type: ${type}`); + throw new TypeError(`Unknown type: ${type as any}`); } const clashContent = withBannerArray(title, description, date, _clashContent); diff --git a/Build/lib/domain-deduper.ts b/Build/lib/domain-deduper.ts index 875853f5..e832273e 100644 --- a/Build/lib/domain-deduper.ts +++ b/Build/lib/domain-deduper.ts @@ -1,4 +1,4 @@ -import createTrie from './trie'; +import { createTrie } from './trie'; export const domainDeduper = (inputDomains: string[]): string[] => { const trie = createTrie(inputDomains); diff --git a/Build/lib/fetch-retry.ts b/Build/lib/fetch-retry.ts index 7a6dc0d4..8cb66166 100644 --- a/Build/lib/fetch-retry.ts +++ b/Build/lib/fetch-retry.ts @@ -9,11 +9,32 @@ const FACTOR = 6; function isClientError(err: any): err is NodeJS.ErrnoException { if (!err) return false; return ( - err.code === 'ERR_UNESCAPED_CHARACTERS' || - err.message === 'Request path contains unescaped characters' + err.code === 'ERR_UNESCAPED_CHARACTERS' + || err.message === 'Request path contains unescaped characters' ); } +export class ResponseError extends Error { + readonly res: Response; + readonly code: number; + readonly statusCode: number; + readonly url: string; + + constructor(res: Response) { + super(res.statusText); + + if ('captureStackTrace' in Error) { + Error.captureStackTrace(this, ResponseError); + } + + this.name = this.constructor.name; + this.res = res; + this.code = res.status; + this.statusCode = res.status; + this.url = res.url; + } +} + interface FetchRetryOpt { minTimeout?: number, retries?: number, @@ -32,7 +53,7 @@ function createFetchRetry($fetch: typeof fetch): typeof fetch { minTimeout: MIN_TIMEOUT, retries: MAX_RETRIES, factor: FACTOR, - maxRetryAfter: MAX_RETRY_AFTER, + maxRetryAfter: MAX_RETRY_AFTER }, opts.retry ); @@ -41,19 +62,18 @@ function createFetchRetry($fetch: typeof fetch): typeof fetch { return await retry(async (bail) => { try { // this will be retried - const res = await $fetch(url, opts); + const res = (await $fetch(url, opts)) as Response; if ((res.status >= 500 && res.status < 600) || res.status === 429) { // NOTE: doesn't support http-date format const retryAfterHeader = res.headers.get('retry-after'); if (retryAfterHeader) { - const retryAfter = parseInt(retryAfterHeader, 10); + const retryAfter = Number.parseInt(retryAfterHeader, 10); if (retryAfter) { if (retryAfter > retryOpts.maxRetryAfter) { return res; - } else { - await new Promise((r) => setTimeout(r, retryAfter * 1e3)); } + await Bun.sleep(retryAfter * 1e3); } } throw new ResponseError(res); @@ -78,7 +98,7 @@ function createFetchRetry($fetch: typeof fetch): typeof fetch { } throw err; } - } + }; for (const k of Object.keys($fetch)) { const key = k as keyof typeof $fetch; @@ -88,30 +108,10 @@ function createFetchRetry($fetch: typeof fetch): typeof fetch { return fetchRetry as typeof fetch; } -export class ResponseError extends Error { - readonly res: Response; - readonly code: number; - readonly statusCode: number; - readonly url: string; - - constructor(res: Response) { - super(res.statusText); - - if (Error.captureStackTrace) { - Error.captureStackTrace(this, ResponseError); - } - - this.name = this.constructor.name; - this.res = res; - this.code = this.statusCode = res.status; - this.url = res.url; - } -} - export const defaultRequestInit: RequestInit = { headers: { 'User-Agent': 'curl/8.1.2 (https://github.com/SukkaW/Surge)' } -} +}; export const fetchWithRetry = createFetchRetry(fetch); diff --git a/Build/lib/get-gorhill-publicsuffix.ts b/Build/lib/get-gorhill-publicsuffix.ts index b7a47ab8..0d74af1f 100644 --- a/Build/lib/get-gorhill-publicsuffix.ts +++ b/Build/lib/get-gorhill-publicsuffix.ts @@ -7,7 +7,7 @@ import type { PublicSuffixList } from 'gorhill-publicsuffixlist'; const publicSuffixPath = path.resolve(import.meta.dir, '../../node_modules/.cache/public_suffix_list_dat.txt'); const getGorhillPublicSuffix = () => traceAsync('create gorhill public suffix instance', async () => { - const customFetch = async (url: string | URL) => Bun.file(url); + const customFetch = (url: string | URL) => Promise.resolve(Bun.file(url)); const publicSuffixFile = Bun.file(publicSuffixPath); diff --git a/Build/lib/parse-dnsmasq.ts b/Build/lib/parse-dnsmasq.ts index eb4b764c..18d772c6 100644 --- a/Build/lib/parse-dnsmasq.ts +++ b/Build/lib/parse-dnsmasq.ts @@ -1,8 +1,8 @@ import { fetchRemoteTextAndCreateReadlineInterface } from './fetch-remote-text-by-line'; -import tldts from 'tldts'; +import { parse } from 'tldts'; const isDomainLoose = (domain: string): boolean => { - const { isIcann, isPrivate, isIp } = tldts.parse(domain); + const { isIcann, isPrivate, isIp } = parse(domain); return !!(!isIp && (isIcann || isPrivate)); }; diff --git a/Build/lib/parse-filter.ts b/Build/lib/parse-filter.ts index 2c1cdb85..6817f827 100644 --- a/Build/lib/parse-filter.ts +++ b/Build/lib/parse-filter.ts @@ -8,7 +8,7 @@ import { performance } from 'perf_hooks'; import { getGorhillPublicSuffixPromise } from './get-gorhill-publicsuffix'; import type { PublicSuffixList } from 'gorhill-publicsuffixlist'; -const DEBUG_DOMAIN_TO_FIND = null; // example.com | null +const DEBUG_DOMAIN_TO_FIND: string | null = null; // example.com | null let foundDebugDomain = false; const warnOnceUrl = new Set(); @@ -63,7 +63,7 @@ export async function processDomainLists(domainListsUrl: string | URL) { } export async function processHosts(hostsUrl: string | URL, includeAllSubDomain = false, skipDomainCheck = false) { - console.time(`- processHosts: ${hostsUrl}`); + console.time(`- processHosts: ${hostsUrl.toString()}`); if (typeof hostsUrl === 'string') { hostsUrl = new URL(hostsUrl); @@ -95,14 +95,14 @@ export async function processHosts(hostsUrl: string | URL, includeAllSubDomain = } } - console.timeEnd(` - processHosts: ${hostsUrl}`); + console.timeEnd(` - processHosts: ${hostsUrl.toString()}`); return domainSets; } export async function processFilterRules( filterRulesUrl: string | URL, - fallbackUrls?: readonly (string | URL)[] | undefined + fallbackUrls?: ReadonlyArray | undefined ): Promise<{ white: Set, black: Set, foundDebugDomain: boolean }> { const runStart = performance.now(); @@ -167,7 +167,7 @@ export async function processFilterRules( addToBlackList(hostname, true); break; default: - throw new Error(`Unknown flag: ${flag}`); + throw new Error(`Unknown flag: ${flag as any}`); } } }; @@ -192,7 +192,7 @@ export async function processFilterRules( /** @type string[] */ filterRules = ( await Promise.any( - [filterRulesUrl, ...(fallbackUrls || [])].map(async url => { + [filterRulesUrl, ...fallbackUrls].map(async url => { const r = await fetchWithRetry(url, { signal: controller.signal, ...defaultRequestInit }); const text = await r.text(); @@ -202,7 +202,7 @@ export async function processFilterRules( ) ).split('\n'); } catch (e) { - console.log(`Download Rule for [${filterRulesUrl}] failed`); + console.log(`Download Rule for [${filterRulesUrl.toString()}] failed`); throw e; } downloadTime = performance.now() - downloadStart; @@ -212,7 +212,7 @@ export async function processFilterRules( } } - console.log(` ┬ processFilterRules (${filterRulesUrl}): ${(performance.now() - runStart).toFixed(3)}ms`); + console.log(` ┬ processFilterRules (${filterRulesUrl.toString()}): ${(performance.now() - runStart).toFixed(3)}ms`); console.log(` └── download time: ${downloadTime.toFixed(3)}ms`); return { diff --git a/Build/lib/reject-data-source.ts b/Build/lib/reject-data-source.ts index 23a3f2a7..5a2c7b11 100644 --- a/Build/lib/reject-data-source.ts +++ b/Build/lib/reject-data-source.ts @@ -177,7 +177,7 @@ export const PREDEFINED_WHITELIST = [ // https://raw.githubusercontent.com/AdguardTeam/cname-trackers/master/data/combined_disguised_trackers.txt 'vlscppe.microsoft.com', // OpenAI use this for A/B testing - 'statsig.com', + 'statsig.com' ]; export const PREDEFINED_ENFORCED_BACKLIST = [ diff --git a/Build/lib/stable-sort-domain.test.ts b/Build/lib/stable-sort-domain.test.ts index 3647a941..de3a79c7 100644 --- a/Build/lib/stable-sort-domain.test.ts +++ b/Build/lib/stable-sort-domain.test.ts @@ -1,4 +1,5 @@ import domainSorter from './stable-sort-domain'; +// eslint-disable-next-line import/no-unresolved -- fuck eslint-import import { describe, it, expect } from 'bun:test'; describe('stable-sort-domain', () => { diff --git a/Build/lib/stable-sort-domain.ts b/Build/lib/stable-sort-domain.ts index 354895d2..7aafac29 100644 --- a/Build/lib/stable-sort-domain.ts +++ b/Build/lib/stable-sort-domain.ts @@ -50,6 +50,7 @@ const createDomainSorter = (gorhill: PublicSuffixList | null = null) => { }; } + // eslint-disable-next-line @typescript-eslint/no-var-requires -- fuck const tldts = require('./cached-tld-parse'); return (a: string, b: string) => { diff --git a/Build/lib/text-decoder-stream.ts b/Build/lib/text-decoder-stream.ts index e9cd5de2..4dc51407 100644 --- a/Build/lib/text-decoder-stream.ts +++ b/Build/lib/text-decoder-stream.ts @@ -22,7 +22,7 @@ export class PolyfillTextDecoderStream extends TransformStream[1] = {}, + { fatal = false, ignoreBOM = false }: ConstructorParameters[1] = {} ) { const decoder = new TextDecoder(encoding, { fatal, ignoreBOM }); super({ diff --git a/Build/lib/text-line-transform-stream.ts b/Build/lib/text-line-transform-stream.ts index 26c4a159..9bc2f175 100644 --- a/Build/lib/text-line-transform-stream.ts +++ b/Build/lib/text-line-transform-stream.ts @@ -4,7 +4,7 @@ interface TextLineStreamOptions { /** Allow splitting by solo \r */ - allowCR: boolean; + allowCR: boolean } /** Transform a stream into a stream where each chunk is divided by a newline, @@ -36,8 +36,8 @@ export class TextLineStream extends TransformStream { const crIndex = chunk.indexOf('\r'); if ( - crIndex !== -1 && crIndex !== (chunk.length - 1) && - (lfIndex === -1 || (lfIndex - 1) > crIndex) + crIndex !== -1 && crIndex !== (chunk.length - 1) + && (lfIndex === -1 || (lfIndex - 1) > crIndex) ) { controller.enqueue(chunk.slice(0, crIndex)); chunk = chunk.slice(crIndex + 1); @@ -62,13 +62,14 @@ export class TextLineStream extends TransformStream { }, flush(controller) { if (__buf.length > 0) { + // eslint-disable-next-line sukka-ts/string/prefer-string-starts-ends-with -- performance if (allowCR && __buf[__buf.length - 1] === '\r') { controller.enqueue(__buf.slice(0, -1)); } else { controller.enqueue(__buf); - }; + } } - }, + } }); } } diff --git a/Build/lib/trace-runner.ts b/Build/lib/trace-runner.ts index bb74c478..b2bf732f 100644 --- a/Build/lib/trace-runner.ts +++ b/Build/lib/trace-runner.ts @@ -19,9 +19,9 @@ const traceAsync = async (prefix: string, fn: () => Promise): Promise = export { traceAsync }; export interface TaskResult { - readonly start: number; - readonly end: number; - readonly taskName: string; + readonly start: number, + readonly end: number, + readonly taskName: string } const task = (importMetaPath: string, fn: () => Promise, customname: string | null = null) => { diff --git a/Build/lib/trie.test.ts b/Build/lib/trie.test.ts index afaa3a34..c942453f 100644 --- a/Build/lib/trie.test.ts +++ b/Build/lib/trie.test.ts @@ -1,4 +1,5 @@ -import createTrie from './trie'; +import { createTrie } from './trie'; +// eslint-disable-next-line import/no-unresolved -- fuck eslint-import import { describe, expect, it } from 'bun:test'; describe('Trie', () => { diff --git a/Build/lib/trie.ts b/Build/lib/trie.ts index 0abcbee5..e553840c 100644 --- a/Build/lib/trie.ts +++ b/Build/lib/trie.ts @@ -8,7 +8,7 @@ export const SENTINEL: string = String.fromCodePoint(0); * @param {string[] | Set} [from] */ export const createTrie = (from?: string[] | Set) => { - let size: number = 0; + let size = 0; const root: any = {}; /** @@ -56,7 +56,7 @@ export const createTrie = (from?: string[] | Set) => { * @param {boolean} [includeEqualWithSuffix] * @return {string[]} */ - const find = (suffix: string, includeEqualWithSuffix: boolean = true): string[] => { + const find = (suffix: string, includeEqualWithSuffix = true): string[] => { let node: any = root; const matches: string[] = []; let token: string; diff --git a/Build/mod.d.ts b/Build/mod.d.ts index 1f3c0032..5e6e1299 100644 --- a/Build/mod.d.ts +++ b/Build/mod.d.ts @@ -2,33 +2,33 @@ declare module 'gorhill-publicsuffixlist' { type Selfie = | string | { - magic: number; - buf32: number[]; - }; + magic: number, + buf32: number[] + }; interface Decoder { - decode: (bufferStr: string, buffer: ArrayBuffer) => void; - decodeSize: (bufferStr: string) => number; + decode: (bufferStr: string, buffer: ArrayBuffer) => void, + decodeSize: (bufferStr: string) => number } interface Encoder { - encode: (buffer: ArrayBuffer, length: number) => string; + encode: (buffer: ArrayBuffer, length: number) => string } export interface PublicSuffixList { - version: string; + version: string, - parse(text: string, toAscii: (input: string) => string): void; + parse(text: string, toAscii: (input: string) => string): void, - getPublicSuffix(hostname: string): string; - getDomain(hostname: string): string; + getPublicSuffix(hostname: string): string, + getDomain(hostname: string): string, - suffixInPSL(hostname: string): boolean; + suffixInPSL(hostname: string): boolean, - toSelfie(encoder?: null | Encoder): Selfie; - fromSelfie(selfie: Selfie, decoder?: null | Decoder): boolean; + toSelfie(encoder?: null | Encoder): Selfie, + fromSelfie(selfie: Selfie, decoder?: null | Decoder): boolean, enableWASM(options?: { - customFetch?: null | ((url: URL) => Promise); - }): Promise; - disableWASM(): Promise; + customFetch?: null | ((url: URL) => Promise) + }): Promise, + disableWASM(): Promise } const psl: PublicSuffixList; diff --git a/Build/workers/build-internal-reverse-chn-cidr-worker.ts b/Build/workers/build-internal-reverse-chn-cidr-worker.ts index eef5944f..c692fe00 100644 --- a/Build/workers/build-internal-reverse-chn-cidr-worker.ts +++ b/Build/workers/build-internal-reverse-chn-cidr-worker.ts @@ -9,7 +9,7 @@ const handleMessage = async (e: MessageEvent<'build' | 'exit'>) => { if (e.data === 'build') { const stat = await promise; postMessage(stat); - } else if (e.data === 'exit') { + } else /* if (e.data === 'exit') */ { self.removeEventListener('message', handleMessage); self.unref(); self.terminate(); diff --git a/bun.lockb b/bun.lockb index dc6d9eba0da4602148d7c93437130a4527f2d2ce..d7b3132c1a10d80c88738ec19ca1ace3ac7d32aa 100755 GIT binary patch delta 21963 zcmeHvcUY9k^6vBq$bh4uAVU;PfC`c`14h6hhzYZzqM`&PDHvujVO+&lKg?oUa{>i1 zqHA1r#jxs{*EMI|HHZ7wH#5p}&hELtd!PH?J>TOy)m5FUtE;Pf=EMH|y3wmjqdD%b zADaY?`LMU}#Im^N{RU)Sla4z-*d%!JWan1*YplHJ@~+!}6-+`;y~2bBwh?ApMj}x_ zR7WDwWTgzs%0#-bu+Tr*NGg$-LO5_}`lz%Fi6kp=KuQua-_(#uOdt<2(9%cXYk@xv z-U{>(DAl{AD|f(9n_mh_@+c#TL=IX6O6^o}Pu4)4QxjT&8vtqn+8LBo>Hr<7R2V4L zPEAfr9+8-tnIw})@K56hxkyon^3|Z$ph=l2$!S><$!w@b^(X775?z~tPf5y2!(b#n z;E}J^m}?UnTTp6XP*Tzex8zJo4l0r&si4%65)APx@j(sG1Fa33h!)T52m%f(Y~sN546^4f$f2jEp^a943Or5cp!9)R8Odo$gOUbh50OZ?x`r&U z5_$Ni88tL{;84^}&P*DOrX|yCwHEGer*)JOiCIJ4pygDe zLn|B56uI9bP#W&w#LTRbD4mg%otZp1SJJS7R^!*8q+yt&wwF8Lsr*>fa{x^Qg#wyf zCy4|KXcEBF$Rl*^4rwU1qt^67f*P`Hq@~87@Ey%6P%?=-Dv%?Yfl|Xyp$s|Bz+|`N zw880;JK(9|%b+Nt$wRHCST!Y}a*0}^x$i8Iz=<@! z>Zry=%dZs+NHmRI#g(n84O*Ydfs%qn$fpkSLCIo$L7}szJt(GAvke`SVyWq{IMQJ) zwB=WW(tycF(7!~o2m&ft2udUN))mNw&u1b(*E4{8LSpT%Rm=pGERd8rFfk=@P}0DZ zNKy*no`0fk|k*m9KV$1)x;^3Mh>Bz^ zPtCRRm!Q<)A}B+qE�uy3t>&fGj{Xy;{=`37X7KT7hOE3J|Xf)K+A@HD`DjL#JHa{GNno^i0urNoOV3QP={Hd;_A?CL^74uQj4JnM5;W33Q2?<<(>YdKAS-c%xYKR|Pg8IO`7~m*JYP}A#qs#5GmmUK z_H`e8C2U7mw}89SYg5J+P4iAGyc)%JRP`_5#^xOz(;QwOxOlm7V9nSuqei$sYrQOI zuUqmt!;HeR!-ta_dQL4lUMGNYjkyaiH`lPfJg{z<;bJC{g!0h3!R#{MT{n!G^Y{3S z=YjRY*kqoI&wYG%y)fBdI9^~8Xbd^4=g-`DphcK$cnxgGkV!?^a=zOlOe!(pA1suz z_Bd6**QmIqKbydFEyHAgKn62wYEW@mkfB7P1ZT|i8wMDF3E`jX2Frd%DqP>D)YOPq z)K|*78A&AYSn3F^t>l4LVeAIa#b;x_8=uqodwlNWfr>Ep7td9M$=Vo8BrvpwiK=n_ z9(6DOqR?z7nI5@1vgtxNrmwuG-3L7PB#oyaRSQf#FX!o1!H&PS|6y;g!Flh+jUYSq`y29#|XU<`(`wC0@z zj;b+H*>Z3?!$7GQI*##Hmf;W%bRIawb6Q&%=5bvf{Heabp;IH26s?_zRBL@#vQ6N~@kQU1-fP4wJe9JR zjU|#!5E{^ul`d(_E4-A_JB|5=x=NXK6TO?F6KU5bJkMJxid zJk%vvwjU{P)He}VQcMf&J|Sm|iRBM~-PkC8Zf2JO~@u9tdfvAUdH!P0w#J#M@sM z3=YF0ce3`E4FN|TiCdkl7#ziD(bZ)4!BH#P=o*N%LLG_mN;VA~wIcexY$rH$Nv%MM zyIwpmOeqV56=-}?p6~519qG+KgeeVoKp4bBv233pMZ*x6rlAL-Ra?>KlacBmR-^d$ z3pnjaXpzd{`4raR*@%WJaAX!3$tu7Y3^k`6$nW63+0W3C((!yU`n9H^lLR&R^m)ASo-+9pjv~)am7ezoNpqV_k*I0Td=>|0jjz z^YKB$e@(LVH#Q(P4{ub88SO>J+u_>Y!VQ&lV(IN=RUmO0Ry;63% zjYKjS^~Jqc>fM&-MJQ$IZ6%U+5Mnw}y%ZdcLySzazrfL4VOz&K^KZxVB9*cNlqOqh zTlu9O{}8E^+PCLHQA%lCd!84iG~5iG1H{#J7pczL!dL(S_`*VV!J2l4C3GAbLSU%` zNA^Tt;9i5H6%GzNOe6G%=mn1K84nI-g9T|1ER5t8Dy8gC2r+fEy9W8oyrQ&+2C*^e z&?uf4tu$N&VQX;wG<%cH^3PGNyE6z!Yy7tLijw^YO`W#^Db<2RvrBCQq8gW{CZKG8fc zPU#{<{}0y%#Q|ju4g_e(fE1yQ0DAr|XqYcTVOot;kRCarrn7kFeu$i5$bls>9|N&S zVHkw8N;iL588{j%Ji*?dJ>`L2!(=Vc%(vNeQG+8({ZEvTT|i;XDYhw!gi1IpY)Oj% z8-@Um8WN8Tvg_br3xruX33DyUO$cUuP@-8f>5jP&AEHfxL@g^)nw23so~RU{N;Gba zQhfdsrEYNq+!{ z&IafqO10+#BtFs2tP_lonI~D0LVFN)J(*pH`qGYK;#n7fH;&Q0gy6jSOla z4wTAt)D^5wDZdlsq)<;?K2d6*pN=PL0zMg(6iv~|t5XuC;)7_KE?-RvN~h}tL@7B! zM@NEEgIPL08N1E@a+Z$%pp#dp z)bSjhoG2v=b$oS7qPaRbQL^A7P^!NKl+pgO6bT9uYjqjxKPcY6oKqMQu%-#vu(4tj|GcMtjheGjot zwlj_Xn$Tq6$CWQy+;Qo>D(6$3?(-GRoVxZ-oqFY{&yLDH1+$9}#R&nEKPEZtYg78` zOW(3)ODp4>t+4E`((JF}d@E@fyopJ^)cFFBa^jxZ3H)-FoX^izu}1thxT)Fl=ow8c zB&X{buY2EmiP8A}8rzGPQs*q#vFdAX|N5KKe?9kb>kq$I8H8_(Oi2B(?Z;igr9ZX$ zxbt_3!6&OV>-v>W;aSzXXu=C~5_mw4od1=hV$QtPs0981+?r7;=E`4!D;g!|T}P`} zb6z|;fk%#(bHiK}-dM%wCh&LQc7kikSzZEPmn-K&cws)wln*n3i{Py$z)avQe^jw3{t{f#1ej@}3SZ-kC&EkpmH+Oi{7UJaG!lGzDe?*Oi+Wz)aw>3sfwDSArW_ z05eThu^xQnRG4Y1oL>aji#tuj_`pq`reb|~6}ZvUFuv(3){o~;$M~jWeBctf=M0Pw z-253THjv*2H+2TaH&exuc;QTpZzjeEZU}ER3*!T~W|oR2^OxX?W?_6ksMv5``~$}K z1I9O7#Zr0vY>W@wPH_1Bd=ADp8{?a!Vk7x>aNXx%e1$5O$rB4PzCw%-TsAkKi}4l8 z)$40M_$?*kev_e#d)SQlxyPWwuG#66o=0u4JCxq7_JZgNWf$8y&XXR@TG+3<;^euv zyA7)xd<;hholq}(9le?_YFurqMS4Xw$Z=rmB`$?m9m!OZ{eaqKX_1s#C+wgW7GC;IXvX9 zcSxAsy*t@kXd0@C{Qh8F3^cyw*e8O_Sf`R~zwsZoLd{v_#Iw zEmJXpp8z*>shqnlSFwdWcR8kQnVeq-x0t)Gz_fvzwL-;~@+;s*FPHPsVijA?rxjz` zR>=8NaK$`uC8iDB(v>QU!eEk}jX*JBWR>d~+9&2GHaQnb*<%vJSOlz}19unPKJK{* z#+LV$-*fG{d?d3d{}mD^Xy}%&YZnxFt}3I=lGaQ zJKLsrnQqa*zS-w~&mX>fy7Y6-Znu^_GIsnCdEaY1-oAWuw#w?xc4Nb{2ah8{#%#J< zqrAr2rPBDE%r;@qgKLh;+wb&Ku<4~9H>d8}XFJOJpsVG(kH617`qzwC7Avn#icz;U zw*F&RN&HKGdZQxx)>flof5slNxhxE_lINDT|JrwLc!{Br7SKK*jTS4(`A^%i=s-u|TR(WmxV*FPmbY;W=9 zNUCdjSnogbqN03DxZ7q0@48jRj`92~O#fz>JWIt+@ZznQ{w;`$+f*?>SMM=PF=+et z^z=isH^+rL`0Z$GKCJ!YFIQh|Zn(>^G^mqjkWpH|TEE1!;jh~iR?R&&zNk{(b-KvOQled1=-0Z6}PaW)e^}Iu@(c{9h7ChT#ew^#T(@#E?{M^>o zZv683Q=e8{+w1n(c6;eEvz|{=9L`j}5_pPF!@ zq@Y97y$g@ro4;d0ag8s_Qd>Dr^c=n{rJ!NI!L1&e)yuoQD$c#aF7ov3thYAql9ScF zwW_*y6Z|LbXuEc5>**F#?oaZ)aI)F_g`4}gZ7fgimTh`+&tQMgg6xH!dw;d=`f}2n z?KgW|AH3Z(P8Hs@&biDt{(VRN;Lwc6Y*$2Yt9y3G>j_o0f3`kSGkDQ@+xVC5YtBwp zZacJUrJ^GK)tza3U-cS)x@oV`ztkABYFqHlX}vAyC)F@-lyKk&lhTQU;;Y&2JRf-g zi+%@|`2iKX$ej*i(Sw_OP{l6sDsV$fu*@q}(kl`^p|TrSl)~x2UX^gKL*4lCQn}hN zwXt)V!_;-V9}GT!d1c8E@9|4QGQ&4dRBg&qHlC^UZ>X%PZen5N)%4ZS>r0f^mq#ID>(!05^3MIQzC(wpbDByV@*mgh?V&F2kZ15Y{pGNJi6@I6 z&+a?(QfTY1`PR4Mb1c8?demm;QMpI2T1IzHggZ}2%R6o#%u{zN)H&mlUhJBgyY=|Y zpqjonqwWvSPnlNv{Kf?N+j9>SB9DG3GX8T)Ri7HC^2R(E*0X1B;>2Iv2R6Fe+wu4+ zqrH!tUjL(-v2Iq^uEwz03rt2H8~*ic?lP~{UNw7eh?OT^JePj@=$_aIwXPTV#XDYp z|Iysqs97UPhtSKJd(=hU?hQTIvG0cBlG$fEwl?JUyA(WWyNccB+p#Dv@4{(ihl<_d zi8~NK$`GQ#-R0&b2>ay-(IqN&pI3r=0Io@?iaq2bOR?^EWA4B`=1w~i_A4-VJ5_ik zQU&f^g*>{)$Y0ER2ZlJD@z{T@B|A|oLVCP>_OnkXN7p}hXjnvx%`OG4yU(4_FIHY` zUX|8LIlPT|#9 zv+7RaTDC2DlGTLbiIq2t3*GDNUV3)fu$kT#X~Vn@3|E^z{PW?6*!Cd>kJZ0_b$vMb z^k1&IZS8(7?ewc-<*MNO7X0&G1#efb!k>T@mct?U;phVHEpN3O4!Iwpb+?MW=P$u2 z4&ZQDp<*9-aRqjv1GTx)o(?he%dq}2n6$H>_mDqcTTIKFaESWufh$VqIt#A(?PB6Dyz(10B}{Sr)o}~g$W8@=ESsG&) zyK>ZonwgC^jJaQT{=DBDT_-lP`S2#C^6Q6~^JnX?7&qyDT2dQ}L#-~DrUm9{YIpT)H1<6j$y(=rO^8n%x^GJZscWCy#*L~q${63Vw;R7)2`}2G zlGb2+z`kyL>LIw%K2?k%zS8L*g8_~i%Qp8cIW_!Evui))x@YYudpm2&Skupc#vDHL z&Rk((-#lKn(a+&+?zms%oqvlskl(h;+f&nv+-e;zoY^dL@m}tBSfO4wQg~4wS@kSt z+tzvssh%sFB+3;|MXuB18?@}Y&TsTH&;5DZ%jPN5V$%aG!|%-Nv!*I|%;N*H$c8_* ziNBfYpIA+G`Z-?z7&!Y*I(2d3h;!v_CcVDhZI)Si+V$?z19`SlGrOd0?lO5><)VFC ztF|1oexn{~^QC=^yXl+`q34&svDvbt>XM7mmUe^q^}`Cj<|h@C@s~egdHe+bIHF>v zy!Z%~#}T>u%%dNVTCQ97u199Q#ZQcjhJ?mjy}e*^^u%+Uin9grJx3}Y9DbFy*0QnD zm#C?0oHH*UU0?Frzen!0y1Bh8)Cs4TRMVVZ5a=HRLkDTIVJ5w-Qjel$~txQ>UArVnwDPc7Tn~wg1+%4J&*jjVSL>VPx#X# z2nfeitPbCP4D0MDrt-KdhTcBtAA^8kk9j^noXu!+I@_o3JL?egi)qsyUVQd(I-`z|~D$fp)O3#>-)INp3U%X*f5_|fLRJzuhJDgo$Qe-Q>HPEcI zE!lszue2om{AyP6>B16b_}&A5WsKH_P-`W|mtHWj*%dz<8*akON;#S}m5QPzSBwq2 zw82l}5cQ%aidc#Dy%HmQ9CS08W2PPK)OtcY3l=75EZA5z{gO@(y|JVu{n|BOC!<$4 zl%(GT1zp+{l-@zmuk;3#iKn(Mk6wD{&t!G<b^twAq73hx z>Va_(Mc>~!(JTBi6ri^&^!^F|#J7OEDS^jEC##S2a-GapC$oZVg-&LtlPMrugEU#! z9+WI-4fLaTPGnw3T|pb96OpDz|H2E7AxYAeqnBTlO{1U=X&M@VQiJxuc!12?R9B7$ zM&XgH>#UPCKzbEG)>XUcgpOe7eG`qyRVQ;onqFp+_RVy%hDeh#Bx|mdH9~qM(xiL~ zos7P~Q(aQjO(&!2pt>Y;*UC&K<@CM}PnJTs;m8^a<1LtxU}MV$dy;Ez2DSiO0eWl1 zfq4MA=mKCNKyR7ojnr&mmMybVPeXD#Py-+jH3SZ$gP#EMPV&ZMz;WONK%PkF`cuGZ z;0!>g-m?ImFV6wzfeXMz;8)-hPy&Jy9umcDNLV!>q-i|erM<5vm zbO2OBz8$OQODD9>Ko_7Z&<#icdH_9vUO*q9FVGL@4+IGp?O1d5c8qKXPy*}(b^+x8 zd1*R|QS7HTXBz-=2yy_L+m?Vg-~%iJ$b-pa$?@nF9=%T-3y}9x44^gt0`0v7UITvt zZ)oklMPek70gM600^fJeYX;2LlpxB=V*ZUdKrE5L8SRp0<{5ZDXs z1J(n@z+zwtPy{Tb$gl{BdBAL74p0b82W9|MfC3-~NCSodLxBOnKwz*C>Hv4ykHMt@ z^a?Qr7zPXni~$OY6w5;adL{WI5DBP&XdoY$2+)gHTA5$b>_^}|kO@o#o&t}7yFewd zAJ`0R0hW`gmLlN^a9}Pl3K$LK0x3W$8m4#GZGZ^i6J%MyR$v9-1xy0skoOrh8=z?2 z8#EB0Rc8-SJX-_Ms_YNYO0=by?yr#f127(-Sg{J24-5l*09wjUI-a66g^3P8^@c`( zrw~AOs>_MjgUS$y|CW}6SwXM*@vLqjhJYB_`DxYC3YG$2kVhjUzdHyV07yZa`N;r{ zegcpWXaI~!RJswUlMv&?7ON?2(fGyzWMFa%G9t|q8F@HB&XEN41Ns1Dz+ONPfL3K! zpfk`3umjowVSo|{0fK=bfQ;@B_yJ@;Z_>yG37RQ)zzt{$)BXjTKpUVf&>n~f;(!RUNF)-mKnxHKkRly`C_tr46YU6e z0lEVT0F9i|6pKhsAPe*b1_1+r{y-uy5U2+X257mFm4*SyG$RTi9Y_VzfDB*+FcQcH z$mFCHO#`LL++#sGQ1Sb!943`_(#Fc&BUC?3oNrUGgT1XBPhFddi% z%m97>W&yJSs<w$H^8h{jA4Xgr|0E>YIz#^Le zg-8?u0#FRB0G0#GfZD)PfGSYB7O)Z^Q|fs#=UU)LU?V`jkOXW7_5$TV8L$%|pC|=( z0Na5Qn*Uu$P{wYc0@wpkp%Op?*z4$X(4T=LKqYVp_z5@+oB)mjB<~K8>1mpd0mlIY zU_5XVpmJ_NV*<^84)6@P4V(sOZuOm(m3E6a1*!=oCW#-!2tOLHBKF$ z2Yvyl4wbJ0&H?)JBv+G=v?Z#~xPUZSMBm6fq^|;3fJ*>%@+)u=$N*A+GJs^40WvvR z?>9i-E{&cnbpxoTj9To3G$GAsG&B;@oMexIr@#~75%2&Y#oU440aB34-39&t?g00I z`@lnh>i5-ADnoTT0W?LufNnJZG*4tYYUma40{ByxehEs2iIV&^@Co<`d;s19?|`?! z8y&BwbR7K(83U!`RxN<0kfwz8(3-$)n*U0`2#kI{NfELFZL&0KGC7T$MnI#d{M!JX zKIjxeR-*xs4^dui$U;CX0rDR*J$-SYEsENq>8pb@wdeJ(rZhtaRTu}5w^D;-=F1I` zfhQwIsBmFTJ5$;RsEb81s?zSvlhb?O8Z&1|}C( z=DM97lW0}$SXmafd&HVXwzQ1y=|bCkuhMfND*=kDnq2(^TPuFTuE00ruy zK%Mrx3xmzNjs4#CB4Ilf*rsb?c@s^G=97~KpaoxdFZz!I6~b3^;Y;JHjTUZI7WAI{ za-pY`_4Pmj53To_BIm35(CA4`zJwvi)7{(M8?Gh9G-KZEsgMt1>i}aYQ10r`*v?7= zJ8!8mc|}7={DfbcVH9B~Kn+bc>z$G^i7gQu^7L@`lynd(Bbc>d*PIPyg~H_K%v)+C zEvsnGq>NPw`&yv#tr}VrwCWcYVX$%Wb5!g(Lr=EkYWug# zN1&W9%6TF-31KL}P79Spw8dGeFpFyGFKD>q6>b{zYXnCvjGbE76^|0GQn_yzHgw-` zHtNsiccpB+Cnf@u-dXSrW%V7Vmcq>t7SF`tSxdi~3elm=i`5a-p_q9aVW}rbBcY0jyI`vX2@&Fm zBnqis=rdKQQi0?M#l%e(s+1r)mi$(h{p7y>GTl}pn%^$7tr5Q(c{1~!zDMKx`X#%{N%%;ZS@yRwER(d@ZRJB<4^)VMy8Gs zn)|YR=}Svti!Y1T4&OpJ-HtWDy%U0m9~*3|zi1-W)nUMfc?064%v`; z-zZTuFZ`zq<=qu%-4`nki&dPGW{qZAYrR5$#YEyEry~(X)_752bNFY<#>Ti@NsOh>aX4Q@#(GaZ*1gJ0}JrJ{+D@+SSHPIU^gsMPR zzUv@-m<6+D#`y@(wpc2HLm0EM)8FV|Ha%i@%Oh4ZMa{erJ-zxi6%K}D*7KVRX<eW6}vQx|nq@0qb!d}$1(_c*Sd&6%2lip3%H6Mc#_%oahrohm<71KyfS_n5x2;%= zt^RI`-q({;rg(e9EV@-986xy+jk(faV$tsKz=5ZoUuQ^JfUafN7Q(#N%*#)IT}J4T zvxCMK3~MZ9UbO2VeCco87+fN`oAb~CYfu-EC50`7PpvU;i&_Zv+hFysZXtAN!=iol zS8Hrd-gxm;z5VquQmW$n{ql`JuE!rsern%W%n^qu?j7}o+ijS=)VsxkwiujNWPmmF zMp)by;j&9hA(k?v7rnhv6hj12|e)@YkoUXR)>)hArKDzM5SkcPggdtK3 z_C*+SXve(jH^IWTfNP9gdtH*_Y&{fpkuONwvj7Cz;P%kL-dpI_9%F6pElh9EqV4pT zcy#Um!4w;mMsCg~Wm@Hzq96=T z1@)J7{IDi-l}+2YHPUa#ApLb8{k!+JIhd3=_(rV!^!D~*^jcMG!jz9F-l)df7lkYhJfx;%#_0eB1GVaBNLz|)uN}wwojdcCz zeuWV+%(A99AVe37Cb<^&02qY(f8ws8;gW9`N#9FJl?9rgF<)Hm#5 zA8SAH1XKuc_oe3bS9*j`x;c8zKEEs}qXQtV!C0JP$vKSfzN*)?hD8omCnR(v7!WK( zcVJ%X{~Lqq?@qa0_m181l#5t*`cvvZ8zTbeXVRo(CjQjs=msBgvc27DrSuXQ{>D$O zzwYPu)T>$BV^12Rgb&;S!_eQMqQ6apLWL*dJHADrReQ9mzfa?Pj{d$C{mmQSbM!a6 z=r8QhKpAv|XrR)|Dx&hJ+P=}zqq3vmZW}&|Ddj@t$SmApa0ylxaljr{<*+^ z>cCDI)``XHhi|tHE=Ajr{(FEKQ-=D8=luLI;aMkyn3-Wh!_I85-JJ$nTg(_VZ~NZg zPGGHx;S{k-dw#Suz&C(8!oJRkg1+IxtIh~Ie;by>X)XyD!n-hq@BjHAbSGR3wYXOQ zeVuE=nwR8kEA1w&zn}&B`fFp+|C`yYshdv0sV7qiU*nl&kbdg^dFubkheb!#O-eIk zeLI4Wiuw5Iulq@wSuc3*&m{wN>kMZp{l!40rE&JQ3sbViDG8tu7Scw*-@bWi&sY6S zBHM_+3*pKk;Z|2>;Ydfq)sWH5Pu!ODOS8bZ-Kb0l6h!bXZG^OF%%1)}qQwhO+Kfys zHx)~G(y?D$+Z?_U$_wM);MqMe0NfV&U&3?V!gArvl#ugMWY z?O1HwJ0k>_SR5yGyl^NM>+?{gaDy_dB87LcaKmenLW?*S?Weu0NTP{+Qo5@5qaVYe z6n*c*cVqo+MIClr2{!z5*CNpx;>P+gQrHrQwzO?1q%xK8dmIL+zn@5!9&+?i{GvVh z_J%LPehAa?(Sk=urcmoI8Y)g5c&1%dl<)UAtiN4Ke`yeU(>cVyMwIV4`fH6|oY>-K z(a`7|a=hJ93$F)bwBOfNIU!G%EJ=x=exSMrrtXTOK@ ze-E#Ewg25U`}!HWwBsRw zY(k{9(_d?4Sv#udz@e9dP?vTCc&pZpqFJoq)(uCgO+rLB{C@Cv3c1rES|WbUw6^}o zO;WfW#Vn1r{&plzIMP1EluA!3zs(Y7ZfJ zM=kNYjHlq(llj@|FQ7VnCC<~lcE&H_Op9N{%!H9WF-CV`28jN=ApDL6B9!-JjwT0V z@WlX6c&zYyPu5m&>BT&x{hJFtdoc&;y5>S2s7+~e?b^Nl_()=Ef#TSRSZ$@M<-(3$ zEJiLK*gf2||E;_1YcF^1W(>o|mssVPj@%o>(GO=In9Fpo0t4CY*m z`3mOw%vG2)9_L%1vZdo$e`(o}e5S@}Tc}KDjteHUnu2N)^Ajw_F(={Hd}dU(ZW6m! zgL#+Dp32;7mOY)#RvE}V^_>fa^O&X@TX#N-WC232`RsZ%Y2X4jS~!}-76>C2vf9Fn z1)xw%^;9u44^^^a=Q>L$jLI6}qj%uNL3g_%)~iwqe<^H7r<4-8y~CZd8}P$YMO< zS-B&UGF#I9c0%F;W-l7|-a2Lh^N!RoM{Uz?>*0IU77ejxnPMUP(Lk8D7X0m{?7bk( zK*8|~n9;7~thZFipTwLUvJx{|y0yfo8-fch;qRTLr4JI~Gnk!_mIRMGTg-wCkndF{ zUx^djznj}uC|t!B{*9$auV;=@Pj7)GqI-`bxWR$-ER+e`HZl*bc5^h$STNbd>VKc- qGN(-_4<{>D!ycGP8prU{X7(kT4gjujxk2&X@6;?1} zSo4~5T60dTvWEAqIplT#In^qAPhcvLX*LSX?e8q^ZB87P?)0xL+%Te2o8 zAvqx>CM~UtTA{!{eOi3duy|M}^L3#|@)c-AqrCvN0gX>fOh`^wD89l}>hGOIH^3A# zg(6#@7(Xl-vr{aCfE2PNIti3Ih>MR;aZ5;3{DFpK*mY1EXagAH&CmX?OggMiOh`&dS2$M{>yyw9 zHtKhRCxcTHl2T)Mk+OnvpcVg3Stq-PjfcVAFaRxO0^CN1#`GPWO0I1UIsWPMY(;rPFtpThgZrkZ zCM3tl#m5fquTb#8M(Q9B)X|v32PE_zfVK%~@gvZ+;-j7D?ceOhAWDfzAK(T<`woan z9EAF@e5+BlY&nP;)leufnBE$_QD~Zi($xFKq@@pmc53|4w1j>ciaZC=;uuHK!i}J` zrtLsU|0zsCSNb!cFhKvvNuhuN`V#Oo^PQlicd@3SpKSec6fl;4Y%P%v14SI^&7H-m zFF*qds?ng-u^gRphj$dB0eutP5|aB3R$Ky41Dyax6MbrYIvlT16af@O8$ro{oh}MR z6-Bl}KTg^z|n3KK+D3)Kp90rhqNrSNx*`77A6jG8$4MoZD7S=@U%_jjeQ6P5nlv@ zXw6+4OP<8$B`+r>CQ>jfh9c7G8iac4AE87`tytUyOM~(CwA+WpBq|aI4^5$lGf|;| z+>o2&ha~2bBKQ%Y6g0HQX~6!VhUk=T9>o!&UQjb}pzf%r0b7ESM^(*59*#D6@CA4) zTATD1Vz^g>CbqKvSW9kOu10ppR^m8cL1~=0gj7oEu_JY&yd~sh*IG0q4}X`sxee+F z{&!HCM`zILpw}=SIkW&2sYdV7TC^iQCdF_Qo(P`$TY`EUg~D6^4NFQLjfa3d?IKMi zs;%gVouIVs&Dx3l^6hGMHD+41<%3R|na=mOTbKW&G%M(+AGz6V%_l2W*XpgSk3G)K zG-0OhMzwp?UQ>VM_O_ZZX4tQexz;0xr__Dfn6Iha z)>V09Le`u~KFRslTe5BE`s60pc(?E373ZKu!}hu*{H{vP-+ky%LQSuUysf#bS--2H z+oIh99~?V*`l)T(UhaH^xt_J-pUp#6(~-eK_*e5_c7kVA2~`^_6$JeXhm7(5|f3^r!^)gZ@e0hjfFq_FUEJKy=jCi4?Rvm;V z6gUj32P^~FP##n@RDBt;PLLT2aHKB|UCe{5LY3cCJkv_6Zi$B& zM5|uOSy&+dY!%AR@t|sMM1rE6fbvd;I)E)>pY<#^5^{7lJ&r5Bz zY%>qCZC=#`F+yR4U@%-Z;A`=_m+km#b5l)Aa7bNxjIQwKTg~h9Ex~G2gdy3Y;5k(S zlub0ep`DiP;F=orF-JC!2h|8wUxO@F?86~gC9Xb$ zZXRNpyrVQM;4vQL5UQ?-jVo&8Gz(-^c%g$piIO^CCSn7tzoK$Cs1@#DtGdN$p3*0|KQ2i1dwKL*m zvIm~FBvUK{R7v1k@FL4#^*)ry;YQ?e^d%mot#BYh&CiCH*3q(59^?|r_VWyvP-S&nUg)A#wzcJ@E?U)G zTX>j{vIlGQo#}5s#V~6@UO5(iHzL_E#W_GiFOXWuz{8>=bsydsxG0*pMR|qtgPtB zGu^c6Bu9lJOx9KJ1t)F+te;Zp#2dP6)!|6!(FPTGo6Y70?xAX7`Zwib@I=80ywFFh)YRprAnoe%hQ3wB%?}*47Ckit9AzLA!**Kl&NBnG>gNzrmu7}&3-#co zfm+pI4~3!?FG3D1KnbDm9<2V3(vM&d@DzhxykDe(qn@#a5D*){(WppL$i$Dq(MB*e zgiZr5G3dp+N3Itywa}{1LP$FhMx%i}Hj$K*yaUv2!C}@?9A<%|fed$2^)7G}?}oIj z{sNAAL0BPQwZ^2{fw+I~dV%Ssa-@w5tx}hNlmP(u<-zw|*^1=|UdNeGc*&-cz z2Pk*>@`hTi>LY{=`PXW}YA@ zM@}kd$gbDGQGepRT=3-n4|l3!zytOXFX7(LtsC(ajpQfU{+GsCfRFuFA# z6&|emf>L8Dnd=aCG!$)cI6+a)5b?C3Rt53Q#)ttZ1RMGdcMnjxU}!BhR8K*vHRMPW zSeL8dC@+EY3Qz~50o5t!2CJF`4yhNzHo`~-1JsjI>H`fiSJuEj6xV}t`KSMNhqIac_DVRS%JE^mVWd`hK8$CAsKR++q*m28oZLtWc0NiS48u`qyaY$iMvkZxp!P!7#K9CK zy5ZmuRp2P?tp!J6gE~BKTm^@{1CAD>T$6vKL?rFzO?YW*t$H1VQbYz}BY?v)i=8QJ zH06bDw5qmP&&G7SQO`t)BF@;5aDM|wO+`CQ;Rp(JjAa>M-Wr@?xv-XWRgl+HJqb0G z%CW=41JuXCNj)|Q&@gmBoF!VQ4SAL#Afg#BZKqXFKqXDv@W7|s-;8Ir*DB4M^TPI8 zl@8DNhP721wV)W&Ol=`rV+!)J|NGWUC{`kU%=NXf_LFdIC6)Dh?Cf*S_~@jrE|9u6sO1{kU*>{J6q z{28vYv<@V3lAI`c0<$$-M3q1y!1#;K9yY|K0CfEmZAJh@GXT1X5}yee0iz^-G^h!`*~O(L*_8{>MU=EB5`*jCQL3M0 zs1+&oI+b`H(zRMR^)>?_tvrA(qQvJ*bS5ZWM5*;Gfa+%h3cj#wH7_a%0QEK(pxSu= zT||w6Ma1ATP=2$ki<-2T1B`Est;YApn%YqBs{y*oQZ;`O>%i^%T6YJMUM<@cT7Lj!*8_mAvXpv#WRQxK^d3t*QL29`@kFWqnZ*AmN_x-XqxId@*;T0> z1mp`9Rs0{)a?qHjB6zN-v9qE#e)qExhC_@0vr^cI6?Rr>Q2N>x^pUNumfyp5z^ zmeTfdkmN+k$u1I4l!~qr@5-{lNdl75s|UJ>Qn8*y>r1qOMBS(o7f~|AL*mO)lGA2V zf%=1zN&xVAtT+|4ZmLd$48b*NPpQ0K5&`erOd>c^GZ%>sHEf3m5lJ}P6 zWhsgJ;1AIlsXm(uRF0JdM5)+UqH&-!P=ARZ07`}>fznI{OZBOsbP=Tq43qe>lwxL- zB$sHmK|r$6QUy^el4pqO>CeAV8hDH(CrZV!5?_{*h`vUrizs<;Dk!z5FQ-fqe~Q^C zkYx)&@lUY`e<+An5c4mTX1*43>R>%6scew+%2KMA-qRT<@mnN4qSVh$P!@;6E)>+D z`#?$Y04QB$DH(JWat-JOP;&7ViQWLM0R9mu{wW^QABob^J=@NDSNQKeNp#LcgKPeK zPZHfw_8#@$dlK!N|K5}Sdr$iBJ?a0$J!x)#`wEetkq>6jZIGORNnFF(&XlF08McN`1d>xj_#1Tk zDNDnnvve$!FU{)A*NoC|)hHbc=j}$p;iENtC%7h@jfTUs;qcKq7QwfI+XJp@wvILD zG1+jF9&Q5HlAG({rW{S=f{y7Y3p-xb&ueb)YC8YK6Wu|F*ob4%E%q6o*pmC_g$lX9 zoNzYk5)*Y*>)uJd<4Kp@*Gq@}!aeh%CfaDLNuERE+($NXkse&B|3uNjzM9_BYg z$A`uhcJ}xy--wce-!N+fe?-03wC)@dYm(2QOdPy>Q%x?Uqf_ zU%X<6d%iUCcMC7xRH@mVxWa}@Cp0O)DahvT>9}$y-z*L|*tgav&neqXMx}d%Jw5pN z{2V?l-9a4Q=iTtZQHLG|KFf&fx@>ZfRTYclVw-xpjh;Wla{FkD-lhHQ^ItDq zHull1rY*1J=xPq+QNLJ6)*JoXn;Y2=S{DxqNv&er`EsSoYFA&M2XC8>IWy*qy_xl` z4bfu`n10?``0;Dkt!sO#ty6L;G+Ow0Z|Vx&qTG62F2fkvJ7ak}j^&?)VBk77p0i)D z{NUn$(Xm{<72JT?2!>fYHi^f~!tx86?9w4VhaEpY-t~TPJ?}eN$#=J1Y|@%PeB@#7 zGWSXNlUHv2R=)8ZeZ${o`^yXad>7_Fim+2z`zW?QZ{Ia+Y5a84(lWzOksSkSod5fS z**9l3_Z;%XAZSurseucEOMnY8BxC@_` zzIoxf+c)l5%a7fvCG_G&f_3E8A!7~}Zyl77)S-Sux45Y3Q3(E5rQ z{B7=yiF>pmSst}p8l9Z~!n5PH&Vwry$6Flw(s<`fp8?IvST~I)%tlnt(eP8Vb!-N= z5fIgLHGGtyWBL3zxGUh?=I9vb8FLWT^ECV>xLLgJTtxMJ4WBkw#{_;A++%Pd^K?=4 zwU2xm&zWwuDgSw5P5T3(J*wq&E#BuF-h6U#NrU!p$1ZgczVAF5mYr3i|I%kzpXWwN zXJR(?yM54PW1fpHCNDO!dg+48eA)tQ{$iev&F4Y$5seEqeBpc@Tgab)`vfj(fsQTa za~B{Q7isuca7%g1h1mUzHGJbj9lde{XSzhgdoI$km3-|YEI&BSVjWw}yDrA^FV*lO zaBI1G36_7Eh9@o2vGu$F+%a&~m+II?p0E^tS`I&f+stj2!A~pTr)4^}l^+Lp1)SS* z9ox<`mcvggkwf%4wv(R&7q|+UVTF$E<~b|iCvXqI6>zVW$Zo5V8CL4>a{n&47Hg3C zR_Ry~&tHZ4f%^b%9}i!R`K`rHT&-gV_#1Ft)?p{E(Xm5(=^D&$J$B++9V_AO)?$9^ zHQ7hgQpXF?uMRf&Gw{OK>pPV9++ZD< z&GUa9&_lIt(Ue;kUS%vU?VWVr_lQtzx^|&Sf&^>>eW6)!DG++|GKN}{qi{9x(>^>5qo&OF6u;CTR*(zm!2fob)9)Lx}af?Ob?^Q zcRs2|dj_mqe*Q|LbK6E{Ye(AbJJn>olhvPgr@!5K)&178Y}@+3^j-BUhC!%o+(%nuSyU4eK3)~79tfJ8O7I*+g`gpF^izc4DIx>ezjrQ;4A6g^g0Ei+WJj-vu+i{%KUf@kz^2g+)q9 zm(fdpFKIgJ`)kWolgKmWevjmb>U;X>jth6&KOOYwp7Q#wjVmmT8+@|t>=~WcY_Otp zExvJ=HJ|mXjy>Xcf5qnCjSaU~$DZ)~y@;Yc*l^&U@$e#SesC*`bnFFx18zhCHe9hT z>Qz~5dM!s#96iXkJKEOoT$`1;@4Q$|EgwX+A)W@>^ z$T@O;@rt{T`kgJQ-qz%gLucL}NzLjQ&;Gh}t=NCJ-;hH-(aWt`-!h75weXy~d9T=Y zn=4h^vAXkc^~(X<4?oUdp2u(Qwa(r!VPn@0c8>?}jo&j~w0bkcyZCuTPupQ{GiUqG zeR*Ad+vXeM}#@jmaF8dLY+jL4J#@~W9J)p_{TwC)s`O;L|_YeOV zqBT{AG1T(6m>)?IIvyzXP8Gm4&nCcO#2>7UpB()ad88`mv#o?30xmvaq_ z)~y>vk8X16kl#g+&y3@@`s~pf?Qc9}f9cYF>6Y#t`@UXfp-fBcZL_!_qNIXVzu+a~ zuNj5foOrfGed>*@ql&q*~;aYc0bn6d{3c$*f8ID zM?K7knumVLdXXSBd%Y&N!FQ{m^cBBf?s0tJ{`(mb$-fM4a`BFT!EN`M&cP#gX7)MY2y0~D zsmofI+5Nj)x8i#a1E%av8+5Mx$6+f9gSaB$#Lbu2yrMgq?Rn)mKR0E~dm9^V?zAhF zD_ze?KmPXE@{yz3Ph456{o1+L9J%I@H6MCV$13mx2a$*lArBwYF%2Jb2#M&hCi^eb zro)1?!-WA4vw9z`@p0+e6CPKbTwfgCenr!_Z(HHn>QvI8GZ#MhF>Cev@so=W z*+$jsd96w984D}eEZ7oe-1vT-T2mh6{P801%lI8@Yh9mzdX?#UUcJORyLfHv;)>_} zYOblevPZ|I{*&5G?!9rE>zLj%%}xKBzp3C)du6rzS@(9=HSs-Ntz+h~rtQO`o9ps7 zEI4}k_44oWF7$>|_N#eW>)c+PW!+w$dVBc#!lrH>du=w(w|G`}ZDL6q-pHY+dr12C z9DXu%^<|qvN5>Ouw$=)%u3wRu)M-h0tAI(@5j_clLOV$H`N)-ely?r>*j$?KMM z?kc|l!>9`5?l+EYf8u*~#<9!UIm23JpG=B0dl77R>+-awd3#0;eN}1Kxtf`YBX#Wu zRxA$JUz^}k>yu{Kz6sAQrg_wHsk-chc^T8K_|=lZs^*wLdHi}b6hAL8=6Od+LYHz{~zkHtVv36e}B$><$ht|Y4jO8wEhmx+?hOwy|e z*(9-?t)RG}7dG_r#z#`5g{H=pfR_MW^jeduD+BVK-CB~FLG})yi(Yq<9xd>F65z6x zWK~es8YK7`xj}|kTow?7NkV%`k$$w&SdvwjWb`Q8T$0t0WLDsN17xg&B&&vUZGa}_ zD9Nl*#xff&CrM@lu7>oARZ&wCB0?0mP^PPvB(p>LKFTJb&XSBedm!o6mSoi-dnoDE zkz_R>qgP^dxkxexlrN)9OPx(`d&zo7;5f>3$uD-DP(BYCtv|iwCB2%!5tM2DT^^uRbOs6}nWrQpuN0w7aY8SD(OF(z{8NMhGzhItS4kF*GS!o;n zDazp})72Z4iV*-U87*rcT7PQX3?Qp%4apm%NP9gCpsTMWYk@N9(Q?s@NUx>k*zaGFp`n9kjfXMm;2*|+J01Zsm50doSpiI9t zB101;SzDAzkNTirA>beV@>-Dtkbbfxv$mre^nJlm7;VjJ3Og)VqUH*OSAlE5b)lUl ztCl?l#j$`M$N`1{!+{Y%29ODi1hN2cfVQwN@Eo1L0A2!=u3rOhfVaRq;63mG_!FQH zCZ7QM3{VRE1$+VU`M_QA4TbLjP2~p2P2d)A8@L191?~a&f$PFoOI9m}R+F4Ut3@jj z36Mj`iR1)w5;>(k&=KeabOyQrU4d>u51=Q|3+MyH0I@({AVe5imDSI_35zIK-v;gi z_kceD%FC%xqs(;yxC9&nD7~Hl&H)F3L%?oe4^RNmwi*M_y3smO9tZ*`i_y)+5vU0` z1IYPEohYPZprL>b%C-QlE8Veb04b1LgVOEP0;mG00281bU<#B67@!1<0At`W+C2dt z01tr;zzSdyuo$3^oC_48_*DoB0x%Qcz%RfwU^*}fm<(h9Lx6$6ARr#-2P6nLtq@-^ z81E54+mp6!FCYL21oD8nz&>CTCY0(O)s8)O*YknmQOsVHlR+^{d|;{fWIWcz^w zKv`WfnlfD z0IUZ#09ybbpg*vU)}k%&?*i^1OFuQ2^2hcfb+mPfPzr&{4C1U z*YCi0T-4?!a2vP<+yJftFg)83trx)1V5E2%xCC4Tt^iko>i~7oN1~)dZ8`#Ea8E!s zIt1lEfP270seB)l^oWxD0q_!dLF@k z1bhR&0_i|9Py~=n0i9xy0)QTusAKYmVE~kAP%?Tt~}5MpMi<0W>gqjM|VfRDXxMApt!AYC*|`6g+x> z9+2n(k&L2_=s}T;^90Jq3q3^XAtOU_04LxMJ!#>((oNXp!0IHppj-uN!w=Y>etv52 zM^onO?&VI?B$%P5ZfVB6;wOhX{HSRuwJEx3v9U^r*U_d*2n<(u{H=&K&-R8kn~=N3 z-IRHGx_i2NV@nI+j?9J)5xP4vAG=KGSwOFHvx59!vrbt*`kp4Ng#ueH+=RLvB_Oh4 zdwkkF-H~yZm8_SSySKl)mv@n1?u7nM2=$3v5+aW+{B;z!Q{)@XHoK~%ZqM=jCL*WH)qbzV4A3x>)k4t-5zTT*H^y=GAGcK5-)5m*4TGWNoH z3)P*WDj!DlJg!^x%|`p1LNyRR!s6{0+ChQ+Xt7$j>&`4q43*o2#Z)Qk*vTgr#SU=} z39C>!5S@6V6O1xNctLv21P>38Xu+vANP-Ytn?+g3Clb9rJSt_u<&)=?thq2B^|fN) z6kGU3{=QT`g#q0Lxck68iY@{VhKE-OMbzJD;Y}nA!;nb)!W)SE!+V$>g zgGFBC0r>oQwA`Ru1XVT(`e6nj5F3p;{(S|+f1FiAQ+NxaJJhoPKT--SF+Kbh-G+6RA3u~g&0n$G!vc&Fl(imnecl( z=4~$@233CH-D~5@-S;tc>_s7$XdyV(hlYI2Q>S((TF02}I0_AaaSc2yh2;8JE$6Dj z-uld%?G!H7XF1B=RzjBsERq?VWyQRNy$zT>&U_NCHDLYheh%|_e*RWCG!!Z zLh(v4$G#8-yDp1~bLQtSantV^!6qHex*I2{+xa3I=_N^k*N140je~C!g0; z{z>QRp-ZNg!dmJdelTo18#Y$>%NTQu!4x0M}m(h zIx={}QW)vUa@ldg$V(R4u!}-FFHC2cFbKq6KFR6%r`VglElhpUkreXg&cYHe(Ix}|9soRL;u~j|H$gq|Kqk5o_jG{d-*sjv&qd1JW8rf6_=ZCVg4?{bRVoz zR~Mm?H?y{v545^)|I4PEIhoSUjyBk67a;{2{_>Go^W*OQKBMyLL+A?u>+bCvC?BeI zFLBw^<_~K;q*1&miF)sJ5sInpINbWmBkbhUbD%++(PVn*Bsbo^RQCt+<{Ah<%H+;^}M;z+g_ms=KRJ!vRGL}N? zCdB$7WyxoKh4eogmz6uv8M_rebN9sqw41QS4|89ILFkboS2ff1dhqq@lHafmHoFOb zpbuq%n_%tFBJJgK!8RwXzj)H3*b17`)_3<1^!~8>rZCqZj}WzLCvlNKC1vzovwTIa_Qyt2nP6JzUXg* za1M>6l>A%^wx6nq0&Anu4sf#@dI zSC|-xiKqAqdjm0X`53b3KF`0G=EeMJn7B7Bae<%U9K^i+<%7pU-tFJ|o0;DLXarF3 z;lmSdO!z3MH}2xy@s!EB5`)c#ni>JZ)F9dxSPat0GU+)#Wa`RfXh?bbrLV9by^9ZR zHbTXQ%yyuBpqIv+jZ3SRvjf`5zT^Y>?6K)9)0W#dZL?AgGkVIEPc7@yrHAeQ__Y2% zYUBgYTn?CKy*bbtPZjdhu{KD^Yly&?Pd?N3QtrL*$`t8d-aPWzXvd!TZWy}d*7F}V z@ePGrXzMGVk~Zq~g@YSf8gGZK2tBg(=i>_Xg0bSb*)r?gdgcyWJE*ZOEAJnd>9ej8!_Lue}5>$Q>Y)Mcll_vuyMCXG9G^J}vWbSI>{-r|y~oqrBXGg(c0HO*zA72-n6!rRL~*P-9_gGo(3@_qLbMj5F$O z^X@|B4IzexhNZ}DBJ^kuqh>Y{@|xqhYH<_c7WE+VRUNRg3@6lKJ}sW_Sl;95>M%5x zo(@DMYh`hS(5waX&X$jyQx9%*fqxIzD=je7t_h@{>&_evcDj!hyqeec}Z*BFP z$1ZM*Kx#FnMuJ|;Y6!o3u__IN@oC%)ll*xf@)3XXF?e$CLfZ&dRq)WVazgnq)>?V2 zrLaVcgu5K>rYD8Pwe=0^kB^TvW7-hJDGY7dN|+vou$XN@(tg@O-0XJaDrL6%i3wd~e+z~zRh@fE`d38!@{l0#V)wH$PY&;FLe<`Aa(50?CWx5?xE%+dI| z8H?k9dHp1 z%(A?k6{Fe;?RCuC@8>D$=Qlesy9lRr%mLqiz0lz~3->D1NZhM-3c->15d0ua3~bLl!+}{kWO6wv*4(Jan~6_swU1+M;oO-P9`8v8ts{gZj zHLqXGSqJo%6uvg-Ir~J7H`9-!o-)bZXC*O7xzGb=DRzyD;rr(2+LwMcUOyH5k|~sch5NHQjz%zUj3PqFe(=rYhw!bfY0uu zDXfoDn9-k^2#H;pM)2&C+cOlFpUK( ziLWRWQ-^FW=3?mDWEwLU*?lvxdUAz{kemmvD(8#St0L^mgE5BM-iufz!Dj*1qE=zD9L1?q#%wE{D5K(M!E8?Y+V7-W$v7p^v ni&zX3qh!Zo=2l)l)xva>@QnDtP2yf?zsd0RxX@w=Tlc>JT=3Zq diff --git a/eslint.config.js b/eslint.config.js index fe1c67b3..69409992 100644 --- a/eslint.config.js +++ b/eslint.config.js @@ -5,7 +5,7 @@ module.exports = require('eslint-config-sukka').sukka({ disableNoConsoleInCLI: ['Build/**'], env: { customGlobals: { - 'Bun': 'readonly' + Bun: 'readonly' } } }, diff --git a/package.json b/package.json index a2e9e1e4..9998233f 100644 --- a/package.json +++ b/package.json @@ -31,14 +31,14 @@ "tldts": "^6.0.22" }, "devDependencies": { - "@eslint-sukka/node": "4.1.9", - "@eslint-sukka/ts": "4.1.9", + "@eslint-sukka/node": "4.1.10-beta.2", + "@eslint-sukka/ts": "4.1.10-beta.2", "@types/async-retry": "^1.4.8", "@types/mocha": "10.0.2", "@types/tar": "^6.1.9", "bun-types": "^1.0.11", "chai": "4.3.10", - "eslint-config-sukka": "4.1.9", + "eslint-config-sukka": "4.1.10-beta.2", "eslint-formatter-sukka": "4.1.9", "mocha": "^10.2.0", "typescript": "^5.2.2"