renovate 40.14.5 → 40.15.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -8,7 +8,7 @@ const tslib_1 = require("tslib");
|
|
8
8
|
const is_1 = tslib_1.__importDefault(require("@sindresorhus/is"));
|
9
9
|
const logger_1 = require("../../../logger");
|
10
10
|
const external_host_error_1 = require("../../../types/errors/external-host-error");
|
11
|
-
const
|
11
|
+
const repository_http_cache_provider_1 = require("../../../util/http/cache/repository-http-cache-provider");
|
12
12
|
const github_1 = require("../../../util/http/github");
|
13
13
|
const string_1 = require("../../../util/string");
|
14
14
|
const util_1 = require("../util");
|
@@ -24,7 +24,7 @@ async function fetchJSONFile(repo, fileName, endpoint, tag) {
|
|
24
24
|
let res;
|
25
25
|
try {
|
26
26
|
res = await http.getJsonUnchecked(url, {
|
27
|
-
cacheProvider:
|
27
|
+
cacheProvider: repository_http_cache_provider_1.repoCacheProvider,
|
28
28
|
});
|
29
29
|
}
|
30
30
|
catch (err) {
|
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../lib/config/presets/github/index.ts"],"names":[],"mappings":";;;AAaA,sCA0BC;AAED,sDAeC;AAED,8BAOC;;AAjED,kEAAkC;AAClC,4CAAyC;AACzC,mFAA8E;AAC9E,
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../lib/config/presets/github/index.ts"],"names":[],"mappings":";;;AAaA,sCA0BC;AAED,sDAeC;AAED,8BAOC;;AAjED,kEAAkC;AAClC,4CAAyC;AACzC,mFAA8E;AAC9E,4GAA4F;AAC5F,sDAAuD;AACvD,iDAAkD;AAElD,kCAAyE;AAE5D,QAAA,QAAQ,GAAG,yBAAyB,CAAC;AAElD,MAAM,IAAI,GAAG,IAAI,mBAAU,EAAE,CAAC;AAEvB,KAAK,UAAU,aAAa,CACjC,IAAY,EACZ,QAAgB,EAChB,QAAgB,EAChB,GAAY;IAEZ,IAAI,GAAG,GAAG,EAAE,CAAC;IACb,IAAI,YAAE,CAAC,cAAc,CAAC,GAAG,CAAC,EAAE,CAAC;QAC3B,GAAG,GAAG,QAAQ,GAAG,EAAE,CAAC;IACtB,CAAC;IACD,MAAM,GAAG,GAAG,GAAG,QAAQ,SAAS,IAAI,aAAa,QAAQ,GAAG,GAAG,EAAE,CAAC;IAClE,eAAM,CAAC,KAAK,CAAC,EAAE,GAAG,EAAE,EAAE,YAAY,CAAC,CAAC;IACpC,IAAI,GAAkC,CAAC;IACvC,IAAI,CAAC;QACH,GAAG,GAAG,MAAM,IAAI,CAAC,gBAAgB,CAAC,GAAG,EAAE;YACrC,aAAa,EAAE,kDAAiB;SACjC,CAAC,CAAC;IACL,CAAC;IAAC,OAAO,GAAG,EAAE,CAAC;QACb,IAAI,GAAG,YAAY,uCAAiB,EAAE,CAAC;YACrC,MAAM,GAAG,CAAC;QACZ,CAAC;QACD,eAAM,CAAC,KAAK,CAAC,eAAe,QAAQ,iBAAiB,IAAI,EAAE,CAAC,CAAC;QAC7D,MAAM,IAAI,KAAK,CAAC,2BAAoB,CAAC,CAAC;IACxC,CAAC;IAED,OAAO,IAAA,kBAAW,EAAC,IAAA,mBAAU,EAAC,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,EAAE,QAAQ,CAAC,CAAC;AAC7D,CAAC;AAED,SAAgB,qBAAqB,CACnC,IAAY,EACZ,UAAkB,EAClB,UAAmB,EACnB,QAAQ,GAAG,gBAAQ,EACnB,GAAY;IAEZ,OAAO,IAAA,kBAAW,EAAC;QACjB,IAAI;QACJ,UAAU;QACV,UAAU;QACV,QAAQ;QACR,GAAG;QACH,KAAK,EAAE,aAAa;KACrB,CAAC,CAAC;AACL,CAAC;AAED,SAAgB,SAAS,CAAC,EACxB,IAAI,EACJ,UAAU,GAAG,SAAS,EACtB,UAAU,EACV,GAAG,GACU;IACb,OAAO,qBAAqB,CAAC,IAAI,EAAE,UAAU,EAAE,UAAU,EAAE,gBAAQ,EAAE,GAAG,CAAC,CAAC;AAC5E,CAAC","sourcesContent":["import is from '@sindresorhus/is';\nimport { logger } from '../../../logger';\nimport { ExternalHostError } from '../../../types/errors/external-host-error';\nimport { repoCacheProvider } from '../../../util/http/cache/repository-http-cache-provider';\nimport { GithubHttp } from '../../../util/http/github';\nimport { fromBase64 } from '../../../util/string';\nimport type { Preset, PresetConfig } from '../types';\nimport { PRESET_DEP_NOT_FOUND, fetchPreset, parsePreset } from '../util';\n\nexport const Endpoint = 'https://api.github.com/';\n\nconst http = new GithubHttp();\n\nexport async function fetchJSONFile(\n repo: string,\n fileName: string,\n endpoint: string,\n tag?: string,\n): Promise<Preset> {\n let ref = '';\n if (is.nonEmptyString(tag)) {\n ref = `?ref=${tag}`;\n }\n const url = `${endpoint}repos/${repo}/contents/${fileName}${ref}`;\n logger.trace({ url }, `Preset URL`);\n let res: { body: { content: string } };\n try {\n res = await http.getJsonUnchecked(url, {\n cacheProvider: repoCacheProvider,\n });\n } catch (err) {\n if (err instanceof ExternalHostError) {\n throw err;\n }\n logger.debug(`Preset file ${fileName} not found in ${repo}`);\n throw new Error(PRESET_DEP_NOT_FOUND);\n }\n\n return parsePreset(fromBase64(res.body.content), fileName);\n}\n\nexport function getPresetFromEndpoint(\n repo: string,\n filePreset: string,\n presetPath?: string,\n endpoint = Endpoint,\n tag?: string,\n): Promise<Preset | undefined> {\n return fetchPreset({\n repo,\n filePreset,\n presetPath,\n endpoint,\n tag,\n fetch: fetchJSONFile,\n });\n}\n\nexport function getPreset({\n repo,\n presetName = 'default',\n presetPath,\n tag,\n}: PresetConfig): Promise<Preset | undefined> {\n return getPresetFromEndpoint(repo, presetName, presetPath, Endpoint, tag);\n}\n"]}
|
package/dist/util/stats.d.ts
CHANGED
@@ -104,12 +104,10 @@ export declare class HttpCacheStats {
|
|
104
104
|
static report(): void;
|
105
105
|
}
|
106
106
|
type ObsoleteCacheStats = Record<string, {
|
107
|
-
callsite?: string;
|
108
107
|
count: number;
|
109
108
|
}>;
|
110
109
|
export declare class ObsoleteCacheHitLogger {
|
111
110
|
static getData(): ObsoleteCacheStats;
|
112
|
-
private static getCallsite;
|
113
111
|
static write(url: string): void;
|
114
112
|
static report(): void;
|
115
113
|
}
|
package/dist/util/stats.js
CHANGED
@@ -329,34 +329,10 @@ class ObsoleteCacheHitLogger {
|
|
329
329
|
static getData() {
|
330
330
|
return memCache.get('obsolete-cache-stats') ?? {};
|
331
331
|
}
|
332
|
-
static getCallsite() {
|
333
|
-
const _prepareStackTrace = Error.prepareStackTrace;
|
334
|
-
try {
|
335
|
-
let result;
|
336
|
-
Error.prepareStackTrace = (_, stack) => {
|
337
|
-
result = stack
|
338
|
-
.find((frame) => {
|
339
|
-
const callsite = frame.toString();
|
340
|
-
return (!callsite.includes('lib/util/http') &&
|
341
|
-
!callsite.includes('lib/util/stats') &&
|
342
|
-
!callsite.includes('(node:'));
|
343
|
-
})
|
344
|
-
?.toString()
|
345
|
-
?.replace(/:\d+(?::\d+)?\)$/, ')');
|
346
|
-
};
|
347
|
-
// eslint-disable-next-line @typescript-eslint/no-unused-expressions
|
348
|
-
new Error().stack;
|
349
|
-
return result;
|
350
|
-
}
|
351
|
-
finally {
|
352
|
-
Error.prepareStackTrace = _prepareStackTrace;
|
353
|
-
}
|
354
|
-
}
|
355
332
|
static write(url) {
|
356
333
|
const data = this.getData();
|
357
334
|
if (!data[url]) {
|
358
|
-
|
359
|
-
data[url] = { callsite, count: 0 };
|
335
|
+
data[url] = { count: 0 };
|
360
336
|
}
|
361
337
|
data[url].count++;
|
362
338
|
memCache.set('obsolete-cache-stats', data);
|
package/dist/util/stats.js.map
CHANGED
@@ -1 +1 @@
|
|
1
|
-
{"version":3,"file":"stats.js","sourceRoot":"","sources":["../../lib/util/stats.ts"],"names":[],"mappings":";;;AAcA,4CAQC;;AAtBD,sCAAmC;AACnC,iEAA2C;AAC3C,+BAAiC;AAYjC,SAAgB,gBAAgB,CAAC,IAAc;IAC7C,MAAM,KAAK,GAAG,IAAI,CAAC,MAAM,CAAC;IAC1B,MAAM,OAAO,GAAG,IAAI,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAC;IAChD,MAAM,KAAK,GAAG,KAAK,CAAC,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,OAAO,GAAG,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACtD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,GAAG,IAAI,CAAC,CAAC;IACnC,MAAM,MAAM,GAAG,IAAI,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;IAC1C,MAAM,QAAQ,GAAG,KAAK,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC3D,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,QAAQ,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;AACpD,CAAC;AAED,MAAa,WAAW;IACtB,MAAM,CAAC,KAAK,CAAC,UAAkB,EAAE,QAAgB;QAC/C,MAAM,IAAI,GAAG,QAAQ,CAAC,GAAG,CAAkB,cAAc,CAAC,IAAI,EAAE,CAAC;QACjE,IAAI,CAAC,UAAU,CAAC,KAAK,EAAE,CAAC;QACxB,IAAI,CAAC,UAAU,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QAChC,QAAQ,CAAC,GAAG,CAAC,cAAc,EAAE,IAAI,CAAC,CAAC;IACrC,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,IAAI,CACf,UAAkB,EAClB,QAA0B;QAE1B,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,MAAM,QAAQ,EAAE,CAAC;QAChC,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;QACpC,WAAW,CAAC,KAAK,CAAC,UAAU,EAAE,QAAQ,CAAC,CAAC;QACxC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,CAAC,SAAS;QACd,MAAM,MAAM,GAAsC,EAAE,CAAC;QACrD,MAAM,IAAI,GAAG,QAAQ,CAAC,GAAG,CAAkB,cAAc,CAAC,IAAI,EAAE,CAAC;QACjE,KAAK,MAAM,CAAC,UAAU,EAAE,SAAS,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC;YAC3D,MAAM,CAAC,UAAU,CAAC,GAAG,gBAAgB,CAAC,SAAS,CAAC,CAAC;QACnD,CAAC;QACD,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,MAAM,GAAG,WAAW,CAAC,SAAS,EAAE,CAAC;QACvC,eAAM,CAAC,KAAK,CAAC,MAAM,EAAE,mBAAmB,CAAC,CAAC;IAC5C,CAAC;CACF;AAhCD,kCAgCC;AAID,MAAa,iBAAiB;IAC5B,MAAM,CAAC,QAAQ,CAAC,QAAgB;QAC9B,MAAM,IAAI,GAAG,QAAQ,CAAC,GAAG,CAAmB,oBAAoB,CAAC,IAAI,EAAE,CAAC;QACxE,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACpB,QAAQ,CAAC,GAAG,CAAC,oBAAoB,EAAE,IAAI,CAAC,CAAC;IAC3C,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,OAAO,CAAI,QAA0B;QAChD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,MAAM,QAAQ,EAAE,CAAC;QAChC,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;QACpC,iBAAiB,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;QACrC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,CAAC,QAAQ,CAAC,QAAgB;QAC9B,MAAM,IAAI,GAAG,QAAQ,CAAC,GAAG,CAAmB,oBAAoB,CAAC,IAAI,EAAE,CAAC;QACxE,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QACpB,QAAQ,CAAC,GAAG,CAAC,oBAAoB,EAAE,IAAI,CAAC,CAAC;IAC3C,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,OAAO,CAAI,QAA0B;QAChD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;QACzB,MAAM,MAAM,GAAG,MAAM,QAAQ,EAAE,CAAC;QAChC,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC;QACpC,iBAAiB,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC;QACrC,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,CAAC,SAAS;QACd,MAAM,gBAAgB,GACpB,QAAQ,CAAC,GAAG,CAAmB,oBAAoB,CAAC,IAAI,EAAE,CAAC;QAC7D,MAAM,GAAG,GAAG,gBAAgB,CAAC,gBAAgB,CAAC,CAAC;QAE/C,MAAM,gBAAgB,GACpB,QAAQ,CAAC,GAAG,CAAmB,oBAAoB,CAAC,IAAI,EAAE,CAAC;QAC7D,MAAM,GAAG,GAAG,gBAAgB,CAAC,gBAAgB,CAAC,CAAC;QAE/C,OAAO,EAAE,GAAG,EAAE,GAAG,EAAE,CAAC;IACtB,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,MAAM,GAAG,iBAAiB,CAAC,SAAS,EAAE,CAAC;QAC7C,eAAM,CAAC,KAAK,CAAC,MAAM,EAAE,0BAA0B,CAAC,CAAC;IACnD,CAAC;CACF;AA7CD,8CA6CC;AAgCD,sEAAsE;AAEtE,MAAa,oBAAoB;IACvB,MAAM,CAAC,OAAO;QACpB,OAAO,CACL,QAAQ,CAAC,GAAG,CAA6B,wBAAwB,CAAC,IAAI,EAAE,CACzE,CAAC;IACJ,CAAC;IAEO,MAAM,CAAC,OAAO,CAAC,IAAgC;QACrD,QAAQ,CAAC,GAAG,CAAC,wBAAwB,EAAE,IAAI,CAAC,CAAC;IAC/C,CAAC;IAED,MAAM,CAAC,GAAG,CACR,UAAkB,EAClB,WAAmB,EACnB,WAAmB;QAEnB,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;QACnE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,IAAI,CACT,UAAkB,EAClB,WAAmB,EACnB,WAAmB;QAEnB,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;QACpE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,GAAG,CACR,UAAkB,EAClB,WAAmB,EACnB,WAAmB;QAEnB,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;QACnE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,IAAI,CACT,UAAkB,EAClB,WAAmB,EACnB,WAAmB;QAEnB,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC,CAAC;QACpE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC;IACrB,CAAC;IAED,MAAM,CAAC,SAAS;QACd,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,MAAM,MAAM,GAA0B,EAAE,IAAI,EAAE,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,CAAC;QAC9D,KAAK,MAAM,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,EAAE,IAAI,IAAI,EAAE,CAAC;YACpE,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,KAAK,EAAE,CAAC;YAC/B,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,KAAK,EAAE,CAAC;YAC5C,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,KAAK,EAAE,CAAC;YAC5C,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,WAAW,CAAC,KAAK,EAAE,CAAC;YAEzD,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,KAAK,EAAE,CAAC;YAChC,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,KAAK;gBACxC,GAAG,EAAE,CAAC;gBACN,IAAI,EAAE,CAAC;gBACP,GAAG,EAAE,CAAC;gBACN,IAAI,EAAE,CAAC;aACR,CAAC;YAEF,IAAI,MAAM,KAAK,KAAK,EAAE,CAAC;gBACrB,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,WAAW,CAAC,CAAC,IAAI,GAAG,KAAK,CAAC;gBAC/D,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;gBAC/C,SAAS;YACX,CAAC;YAED,IAAI,MAAM,KAAK,MAAM,EAAE,CAAC;gBACtB,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,WAAW,CAAC,CAAC,IAAI,GAAG,MAAM,CAAC;gBAChE,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC;gBAChD,SAAS;YACX,CAAC;YAED,IAAI,MAAM,KAAK,KAAK,EAAE,CAAC;gBACrB,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,WAAW,CAAC,CAAC,KAAK,GAAG,KAAK,CAAC;gBAChE,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;gBAC/C,SAAS;YACX,CAAC;YAED,IAAI,MAAM,KAAK,MAAM,EAAE,CAAC;gBACtB,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,WAAW,CAAC,CAAC,KAAK,GAAG,MAAM,CAAC;gBACjE,MAAM,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,WAAW,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC;gBAChD,SAAS;YACX,CAAC;QACH,CAAC;QAED,OAAO,MAAM,CAAC;IAChB,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,EAAE,IAAI,EAAE,KAAK,EAAE,GAAG,IAAI,CAAC,SAAS,EAAE,CAAC;QAEzC,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YAClC,eAAM,CAAC,KAAK,CAAC,KAAK,EAAE,6BAA6B,CAAC,CAAC;QACrD,CAAC;QAED,IAAI,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;YACjC,eAAM,CAAC,KAAK,CAAC,IAAI,EAAE,sCAAsC,CAAC,CAAC;QAC7D,CAAC;IACH,CAAC;CACF;AA3GD,oDA2GC;AAkCD,MAAa,SAAS;IACpB,MAAM,CAAC,KAAK,CAAC,IAA+B;QAC1C,MAAM,YAAY,GAChB,QAAQ,CAAC,GAAG,CAA8B,eAAe,CAAC,IAAI,EAAE,CAAC;QACnE,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACxB,QAAQ,CAAC,GAAG,CAAC,eAAe,EAAE,YAAY,CAAC,CAAC;IAC9C,CAAC;IAED,MAAM,CAAC,aAAa;QAClB,MAAM,YAAY,GAChB,QAAQ,CAAC,GAAG,CAA8B,eAAe,CAAC,IAAI,EAAE,CAAC;QAEnE,8DAA8D;QAC9D,YAAY,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;YACzB,IAAI,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,GAAG,EAAE,CAAC;gBAClB,OAAO,CAAC,CAAC,CAAC;YACZ,CAAC;YAED,IAAI,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,GAAG,EAAE,CAAC;gBAClB,OAAO,CAAC,CAAC;YACX,CAAC;YAED,OAAO,CAAC,CAAC;QACX,CAAC,CAAC,CAAC;QAEH,OAAO,YAAY,CAAC;IACtB,CAAC;IAED,MAAM,CAAC,SAAS;QACd,MAAM,UAAU,GAAG,SAAS,CAAC,aAAa,EAAE,CAAC;QAE7C,MAAM,QAAQ,GAAG,UAAU,CAAC,MAAM,CAAC;QAEnC,MAAM,IAAI,GAAgB,EAAE,CAAC;QAC7B,MAAM,WAAW,GAAa,EAAE,CAAC;QACjC,MAAM,YAAY,GAAgD,EAAE,CAAC;QAErE,KAAK,MAAM,SAAS,IAAI,UAAU,EAAE,CAAC;YACnC,MAAM,EAAE,GAAG,EAAE,KAAK,EAAE,OAAO,EAAE,MAAM,EAAE,GAAG,SAAS,CAAC;YAClD,MAAM,MAAM,GAAG,SAAS,CAAC,MAAM,CAAC,WAAW,EAAE,CAAC;YAE9C,MAAM,SAAS,GAAG,IAAA,cAAQ,EAAC,GAAG,CAAC,CAAC;YAChC,IAAI,CAAC,SAAS,EAAE,CAAC;gBACf,eAAM,CAAC,KAAK,CAAC,EAAE,GAAG,EAAE,EAAE,4CAA4C,CAAC,CAAC;gBACpE,SAAS;YACX,CAAC;YACD,MAAM,EAAE,QAAQ,EAAE,MAAM,EAAE,QAAQ,EAAE,GAAG,SAAS,CAAC;YACjD,MAAM,OAAO,GAAG,GAAG,MAAM,GAAG,QAAQ,EAAE,CAAC;YAEvC,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAC;YACrB,IAAI,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC;YAC7B,IAAI,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;YACpC,IAAI,CAAC,OAAO,CAAC,CAAC,MAAM,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;YAEnC,WAAW,CAAC,IAAI,CAAC,GAAG,MAAM,IAAI,GAAG,IAAI,MAAM,IAAI,KAAK,IAAI,OAAO,EAAE,CAAC,CAAC;YAEnE,YAAY,CAAC,QAAQ,CAAC,KAAK,EAAE,CAAC;YAC9B,YAAY,CAAC,QAAQ,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;QACzC,CAAC;QAED,MAAM,KAAK,GAAkC,EAAE,CAAC;QAEhD,KAAK,MAAM,CAAC,QAAQ,EAAE,UAAU,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,YAAY,CAAC,EAAE,CAAC;YAClE,MAAM,KAAK,GAAG,UAAU,CAAC,MAAM,CAAC;YAEhC,MAAM,QAAQ,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC;YAChD,MAAM,UAAU,GAAG,UAAU,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,OAAO,CAAC,CAAC;YAEpD,MAAM,SAAS,GAAG,gBAAgB,CAAC,QAAQ,CAAC,CAAC;YAC7C,MAAM,WAAW,GAAG,gBAAgB,CAAC,UAAU,CAAC,CAAC;YAEjD,KAAK,CAAC,QAAQ,CAAC,GAAG;gBAChB,KAAK;gBACL,QAAQ,EAAE,SAAS,CAAC,KAAK;gBACzB,WAAW,EAAE,SAAS,CAAC,QAAQ;gBAC/B,QAAQ,EAAE,SAAS,CAAC,KAAK;gBACzB,UAAU,EAAE,WAAW,CAAC,KAAK;gBAC7B,aAAa,EAAE,WAAW,CAAC,QAAQ;gBACnC,UAAU,EAAE,WAAW,CAAC,KAAK;aAC9B,CAAC;QACJ,CAAC;QAED,OAAO;YACL,IAAI;YACJ,WAAW;YACX,YAAY;YACZ,KAAK;YACL,QAAQ;SACT,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,EAAE,IAAI,EAAE,WAAW,EAAE,YAAY,EAAE,KAAK,EAAE,QAAQ,EAAE,GACxD,SAAS,CAAC,SAAS,EAAE,CAAC;QACxB,eAAM,CAAC,KAAK,CAAC,EAAE,WAAW,EAAE,YAAY,EAAE,EAAE,sBAAsB,CAAC,CAAC;QACpE,eAAM,CAAC,KAAK,CAAC,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE,iBAAiB,CAAC,CAAC;QACrD,eAAM,CAAC,KAAK,CAAC,EAAE,IAAI,EAAE,EAAE,qBAAqB,CAAC,CAAC;IAChD,CAAC;CACF;AAlGD,8BAkGC;AAWD,SAAS,UAAU,CAAI,GAAsB;IAC3C,MAAM,MAAM,GAAsB,EAAE,CAAC;IACrC,KAAK,MAAM,GAAG,IAAI,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC;QAC1C,MAAM,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC,GAAG,CAAC,CAAC;IACzB,CAAC;IACD,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,MAAa,cAAc;IACzB,MAAM,CAAC,OAAO;QACZ,OAAO,QAAQ,CAAC,GAAG,CAAqB,kBAAkB,CAAC,IAAI,EAAE,CAAC;IACpE,CAAC;IAED,MAAM,CAAC,IAAI,CAAC,GAAW;QACrB,OAAO,CACL,IAAI,CAAC,OAAO,EAAE,EAAE,CAAC,GAAG,CAAC,IAAI;YACvB,GAAG,EAAE,CAAC;YACN,IAAI,EAAE,CAAC;SACR,CACF,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,GAAW,EAAE,IAA4B;QACpD,MAAM,KAAK,GAAG,QAAQ,CAAC,GAAG,CAAqB,kBAAkB,CAAC,IAAI,EAAE,CAAC;QACzE,KAAK,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC;QAClB,QAAQ,CAAC,GAAG,CAAC,kBAAkB,EAAE,KAAK,CAAC,CAAC;IAC1C,CAAC;IAED,MAAM,CAAC,UAAU,CAAC,GAAW;QAC3B,MAAM,SAAS,GAAG,IAAA,cAAQ,EAAC,GAAG,CAAC,CAAC;QAChC,IAAI,CAAC,SAAS,EAAE,CAAC;YACf,eAAM,CAAC,KAAK,CAAC,EAAE,GAAG,EAAE,EAAE,wCAAwC,CAAC,CAAC;YAChE,OAAO,IAAI,CAAC;QACd,CAAC;QACD,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,GAAG,SAAS,CAAC;QACvC,MAAM,OAAO,GAAG,GAAG,MAAM,GAAG,QAAQ,EAAE,CAAC;QACvC,OAAO,OAAO,CAAC;IACjB,CAAC;IAED,MAAM,CAAC,YAAY,CAAC,GAAW;QAC7B,MAAM,OAAO,GAAG,cAAc,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;QAC/C,IAAI,OAAO,EAAE,CAAC;YACZ,MAAM,IAAI,GAAG,OAAO,CAAC;YACrB,MAAM,KAAK,GAAG,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACxC,KAAK,CAAC,QAAQ,KAAK,CAAC,CAAC;YACrB,KAAK,CAAC,QAAQ,IAAI,CAAC,CAAC;YACpB,cAAc,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IAED,MAAM,CAAC,cAAc,CAAC,GAAW;QAC/B,MAAM,OAAO,GAAG,cAAc,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;QAC/C,IAAI,OAAO,EAAE,CAAC;YACZ,MAAM,IAAI,GAAG,OAAO,CAAC;YACrB,MAAM,KAAK,GAAG,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACxC,KAAK,CAAC,SAAS,KAAK,CAAC,CAAC;YACtB,KAAK,CAAC,SAAS,IAAI,CAAC,CAAC;YACrB,cAAc,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IAED,MAAM,CAAC,aAAa,CAAC,GAAW;QAC9B,MAAM,OAAO,GAAG,cAAc,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;QAC/C,IAAI,OAAO,EAAE,CAAC;YACZ,MAAM,IAAI,GAAG,OAAO,CAAC;YACrB,MAAM,KAAK,GAAG,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACxC,KAAK,CAAC,GAAG,IAAI,CAAC,CAAC;YACf,cAAc,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IAED,MAAM,CAAC,eAAe,CAAC,GAAW;QAChC,MAAM,OAAO,GAAG,cAAc,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;QAC/C,IAAI,OAAO,EAAE,CAAC;YACZ,MAAM,IAAI,GAAG,OAAO,CAAC;YACrB,MAAM,KAAK,GAAG,cAAc,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;YACxC,KAAK,CAAC,IAAI,IAAI,CAAC,CAAC;YAChB,cAAc,CAAC,KAAK,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACpC,CAAC;IACH,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,IAAI,GAAG,cAAc,CAAC,OAAO,EAAE,CAAC;QACtC,IAAI,MAAM,GAA2D,EAAE,CAAC;QACxE,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,IAAI,CAAC,EAAE,CAAC;YAChD,MAAM,SAAS,GAAG,IAAA,cAAQ,EAAC,GAAG,CAAC,CAAC;YAChC,IAAI,SAAS,EAAE,CAAC;gBACd,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,GAAG,SAAS,CAAC;gBACvC,MAAM,CAAC,MAAM,CAAC,KAAK,EAAE,CAAC;gBACtB,MAAM,CAAC,MAAM,CAAC,CAAC,QAAQ,CAAC,GAAG,KAAK,CAAC;YACnC,CAAC;QACH,CAAC;QAED,KAAK,MAAM,CAAC,IAAI,EAAE,SAAS,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,MAAM,CAAC,EAAE,CAAC;YACvD,MAAM,CAAC,IAAI,CAAC,GAAG,UAAU,CAAC,SAAS,CAAC,CAAC;QACvC,CAAC;QACD,MAAM,GAAG,UAAU,CAAC,MAAM,CAAC,CAAC;QAE5B,eAAM,CAAC,KAAK,CAAC,MAAM,EAAE,uBAAuB,CAAC,CAAC;IAChD,CAAC;CACF;AA5FD,wCA4FC;AAUD,qCAAqC;AACrC,MAAa,sBAAsB;IACjC,MAAM,CAAC,OAAO;QACZ,OAAO,QAAQ,CAAC,GAAG,CAAqB,sBAAsB,CAAC,IAAI,EAAE,CAAC;IACxE,CAAC;IAEO,MAAM,CAAC,WAAW;QACxB,MAAM,kBAAkB,GAAG,KAAK,CAAC,iBAAiB,CAAC;QACnD,IAAI,CAAC;YACH,IAAI,MAA0B,CAAC;YAC/B,KAAK,CAAC,iBAAiB,GAAG,CAAC,CAAC,EAAE,KAAK,EAAE,EAAE;gBACrC,MAAM,GAAG,KAAK;qBACX,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE;oBACd,MAAM,QAAQ,GAAG,KAAK,CAAC,QAAQ,EAAE,CAAC;oBAClC,OAAO,CACL,CAAC,QAAQ,CAAC,QAAQ,CAAC,eAAe,CAAC;wBACnC,CAAC,QAAQ,CAAC,QAAQ,CAAC,gBAAgB,CAAC;wBACpC,CAAC,QAAQ,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAC7B,CAAC;gBACJ,CAAC,CAAC;oBACF,EAAE,QAAQ,EAAE;oBACZ,EAAE,OAAO,CAAC,kBAAkB,EAAE,GAAG,CAAC,CAAC;YACvC,CAAC,CAAC;YAEF,oEAAoE;YACpE,IAAI,KAAK,EAAE,CAAC,KAAK,CAAC;YAElB,OAAO,MAAM,CAAC;QAChB,CAAC;gBAAS,CAAC;YACT,KAAK,CAAC,iBAAiB,GAAG,kBAAkB,CAAC;QAC/C,CAAC;IACH,CAAC;IAED,MAAM,CAAC,KAAK,CAAC,GAAW;QACtB,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,IAAI,CAAC,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC;YACf,MAAM,QAAQ,GAAG,IAAI,CAAC,WAAW,EAAE,CAAC;YACpC,IAAI,CAAC,GAAG,CAAC,GAAG,EAAE,QAAQ,EAAE,KAAK,EAAE,CAAC,EAAE,CAAC;QACrC,CAAC;QACD,IAAI,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,CAAC;QAClB,QAAQ,CAAC,GAAG,CAAC,sBAAsB,EAAE,IAAI,CAAC,CAAC;IAC7C,CAAC;IAED,MAAM,CAAC,MAAM;QACX,MAAM,IAAI,GAAG,IAAI,CAAC,OAAO,EAAE,CAAC;QAC5B,eAAM,CAAC,KAAK,CACV,EAAE,KAAK,EAAE,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC,MAAM,EAAE,IAAI,EAAE,EACzC,qBAAqB,CACtB,CAAC;IACJ,CAAC;CACF;AAjDD,wDAiDC;AACD,oCAAoC","sourcesContent":["import { logger } from '../logger';\nimport * as memCache from './cache/memory';\nimport { parseUrl } from './url';\n\ntype LookupStatsData = Record<string, number[]>;\n\ninterface TimingStatsReport {\n count: number;\n avgMs: number;\n medianMs: number;\n maxMs: number;\n totalMs: number;\n}\n\nexport function makeTimingReport(data: number[]): TimingStatsReport {\n const count = data.length;\n const totalMs = data.reduce((a, c) => a + c, 0);\n const avgMs = count ? Math.round(totalMs / count) : 0;\n const maxMs = Math.max(0, ...data);\n const sorted = data.sort((a, b) => a - b);\n const medianMs = count ? sorted[Math.floor(count / 2)] : 0;\n return { count, avgMs, medianMs, maxMs, totalMs };\n}\n\nexport class LookupStats {\n static write(datasource: string, duration: number): void {\n const data = memCache.get<LookupStatsData>('lookup-stats') ?? {};\n data[datasource] ??= [];\n data[datasource].push(duration);\n memCache.set('lookup-stats', data);\n }\n\n static async wrap<T>(\n datasource: string,\n callback: () => Promise<T>,\n ): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n LookupStats.write(datasource, duration);\n return result;\n }\n\n static getReport(): Record<string, TimingStatsReport> {\n const report: Record<string, TimingStatsReport> = {};\n const data = memCache.get<LookupStatsData>('lookup-stats') ?? {};\n for (const [datasource, durations] of Object.entries(data)) {\n report[datasource] = makeTimingReport(durations);\n }\n return report;\n }\n\n static report(): void {\n const report = LookupStats.getReport();\n logger.debug(report, 'Lookup statistics');\n }\n}\n\ntype PackageCacheData = number[];\n\nexport class PackageCacheStats {\n static writeSet(duration: number): void {\n const data = memCache.get<PackageCacheData>('package-cache-sets') ?? [];\n data.push(duration);\n memCache.set('package-cache-sets', data);\n }\n\n static async wrapSet<T>(callback: () => Promise<T>): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n PackageCacheStats.writeSet(duration);\n return result;\n }\n\n static writeGet(duration: number): void {\n const data = memCache.get<PackageCacheData>('package-cache-gets') ?? [];\n data.push(duration);\n memCache.set('package-cache-gets', data);\n }\n\n static async wrapGet<T>(callback: () => Promise<T>): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n PackageCacheStats.writeGet(duration);\n return result;\n }\n\n static getReport(): { get: TimingStatsReport; set: TimingStatsReport } {\n const packageCacheGets =\n memCache.get<PackageCacheData>('package-cache-gets') ?? [];\n const get = makeTimingReport(packageCacheGets);\n\n const packageCacheSets =\n memCache.get<PackageCacheData>('package-cache-sets') ?? [];\n const set = makeTimingReport(packageCacheSets);\n\n return { get, set };\n }\n\n static report(): void {\n const report = PackageCacheStats.getReport();\n logger.debug(report, 'Package cache statistics');\n }\n}\n\ninterface DatasourceCacheDataPoint {\n datasource: string;\n registryUrl: string;\n packageName: string;\n action: 'hit' | 'miss' | 'set' | 'skip';\n}\n\n/* eslint-disable @typescript-eslint/consistent-indexed-object-style */\nexport interface DatasourceCacheReport {\n long: {\n [datasource in string]: {\n [registryUrl in string]: {\n [packageName in string]: {\n read?: 'hit' | 'miss';\n write?: 'set' | 'skip';\n };\n };\n };\n };\n short: {\n [datasource in string]: {\n [registryUrl in string]: {\n hit: number;\n miss: number;\n set: number;\n skip: number;\n };\n };\n };\n}\n/* eslint-enable @typescript-eslint/consistent-indexed-object-style */\n\nexport class DatasourceCacheStats {\n private static getData(): DatasourceCacheDataPoint[] {\n return (\n memCache.get<DatasourceCacheDataPoint[]>('datasource-cache-stats') ?? []\n );\n }\n\n private static setData(data: DatasourceCacheDataPoint[]): void {\n memCache.set('datasource-cache-stats', data);\n }\n\n static hit(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'hit' });\n this.setData(data);\n }\n\n static miss(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'miss' });\n this.setData(data);\n }\n\n static set(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'set' });\n this.setData(data);\n }\n\n static skip(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'skip' });\n this.setData(data);\n }\n\n static getReport(): DatasourceCacheReport {\n const data = this.getData();\n const result: DatasourceCacheReport = { long: {}, short: {} };\n for (const { datasource, registryUrl, packageName, action } of data) {\n result.long[datasource] ??= {};\n result.long[datasource][registryUrl] ??= {};\n result.long[datasource][registryUrl] ??= {};\n result.long[datasource][registryUrl][packageName] ??= {};\n\n result.short[datasource] ??= {};\n result.short[datasource][registryUrl] ??= {\n hit: 0,\n miss: 0,\n set: 0,\n skip: 0,\n };\n\n if (action === 'hit') {\n result.long[datasource][registryUrl][packageName].read = 'hit';\n result.short[datasource][registryUrl].hit += 1;\n continue;\n }\n\n if (action === 'miss') {\n result.long[datasource][registryUrl][packageName].read = 'miss';\n result.short[datasource][registryUrl].miss += 1;\n continue;\n }\n\n if (action === 'set') {\n result.long[datasource][registryUrl][packageName].write = 'set';\n result.short[datasource][registryUrl].set += 1;\n continue;\n }\n\n if (action === 'skip') {\n result.long[datasource][registryUrl][packageName].write = 'skip';\n result.short[datasource][registryUrl].skip += 1;\n continue;\n }\n }\n\n return result;\n }\n\n static report(): void {\n const { long, short } = this.getReport();\n\n if (Object.keys(short).length > 0) {\n logger.debug(short, 'Datasource cache statistics');\n }\n\n if (Object.keys(long).length > 0) {\n logger.trace(long, 'Datasource cache detailed statistics');\n }\n }\n}\n\nexport interface HttpRequestStatsDataPoint {\n method: string;\n url: string;\n reqMs: number;\n queueMs: number;\n status: number;\n}\n\ninterface HostStatsData {\n count: number;\n reqAvgMs: number;\n reqMedianMs: number;\n reqMaxMs: number;\n queueAvgMs: number;\n queueMedianMs: number;\n queueMaxMs: number;\n}\n\n// url -> method -> status -> count\ntype UrlHttpStat = Record<string, Record<string, Record<string, number>>>;\n\ninterface HttpStatsCollection {\n // debug data\n urls: UrlHttpStat;\n hosts: Record<string, HostStatsData>;\n requests: number;\n\n // trace data\n rawRequests: string[];\n hostRequests: Record<string, HttpRequestStatsDataPoint[]>;\n}\n\nexport class HttpStats {\n static write(data: HttpRequestStatsDataPoint): void {\n const httpRequests =\n memCache.get<HttpRequestStatsDataPoint[]>('http-requests') ?? [];\n httpRequests.push(data);\n memCache.set('http-requests', httpRequests);\n }\n\n static getDataPoints(): HttpRequestStatsDataPoint[] {\n const httpRequests =\n memCache.get<HttpRequestStatsDataPoint[]>('http-requests') ?? [];\n\n // istanbul ignore next: sorting is hard and not worth testing\n httpRequests.sort((a, b) => {\n if (a.url < b.url) {\n return -1;\n }\n\n if (a.url > b.url) {\n return 1;\n }\n\n return 0;\n });\n\n return httpRequests;\n }\n\n static getReport(): HttpStatsCollection {\n const dataPoints = HttpStats.getDataPoints();\n\n const requests = dataPoints.length;\n\n const urls: UrlHttpStat = {};\n const rawRequests: string[] = [];\n const hostRequests: Record<string, HttpRequestStatsDataPoint[]> = {};\n\n for (const dataPoint of dataPoints) {\n const { url, reqMs, queueMs, status } = dataPoint;\n const method = dataPoint.method.toUpperCase();\n\n const parsedUrl = parseUrl(url);\n if (!parsedUrl) {\n logger.debug({ url }, 'Failed to parse URL during stats reporting');\n continue;\n }\n const { hostname, origin, pathname } = parsedUrl;\n const baseUrl = `${origin}${pathname}`;\n\n urls[baseUrl] ??= {};\n urls[baseUrl][method] ??= {};\n urls[baseUrl][method][status] ??= 0;\n urls[baseUrl][method][status] += 1;\n\n rawRequests.push(`${method} ${url} ${status} ${reqMs} ${queueMs}`);\n\n hostRequests[hostname] ??= [];\n hostRequests[hostname].push(dataPoint);\n }\n\n const hosts: Record<string, HostStatsData> = {};\n\n for (const [hostname, dataPoints] of Object.entries(hostRequests)) {\n const count = dataPoints.length;\n\n const reqTimes = dataPoints.map((r) => r.reqMs);\n const queueTimes = dataPoints.map((r) => r.queueMs);\n\n const reqReport = makeTimingReport(reqTimes);\n const queueReport = makeTimingReport(queueTimes);\n\n hosts[hostname] = {\n count,\n reqAvgMs: reqReport.avgMs,\n reqMedianMs: reqReport.medianMs,\n reqMaxMs: reqReport.maxMs,\n queueAvgMs: queueReport.avgMs,\n queueMedianMs: queueReport.medianMs,\n queueMaxMs: queueReport.maxMs,\n };\n }\n\n return {\n urls,\n rawRequests,\n hostRequests,\n hosts,\n requests,\n };\n }\n\n static report(): void {\n const { urls, rawRequests, hostRequests, hosts, requests } =\n HttpStats.getReport();\n logger.trace({ rawRequests, hostRequests }, 'HTTP full statistics');\n logger.debug({ hosts, requests }, 'HTTP statistics');\n logger.trace({ urls }, 'HTTP URL statistics');\n }\n}\n\ninterface HttpCacheHostStatsData {\n hit: number;\n miss: number;\n localHit?: number;\n localMiss?: number;\n}\n\ntype HttpCacheStatsData = Record<string, HttpCacheHostStatsData>;\n\nfunction sortObject<T>(obj: Record<string, T>): Record<string, T> {\n const result: Record<string, T> = {};\n for (const key of Object.keys(obj).sort()) {\n result[key] = obj[key];\n }\n return result;\n}\n\nexport class HttpCacheStats {\n static getData(): HttpCacheStatsData {\n return memCache.get<HttpCacheStatsData>('http-cache-stats') ?? {};\n }\n\n static read(key: string): HttpCacheHostStatsData {\n return (\n this.getData()?.[key] ?? {\n hit: 0,\n miss: 0,\n }\n );\n }\n\n static write(key: string, data: HttpCacheHostStatsData): void {\n const stats = memCache.get<HttpCacheStatsData>('http-cache-stats') ?? {};\n stats[key] = data;\n memCache.set('http-cache-stats', stats);\n }\n\n static getBaseUrl(url: string): string | null {\n const parsedUrl = parseUrl(url);\n if (!parsedUrl) {\n logger.debug({ url }, 'Failed to parse URL during cache stats');\n return null;\n }\n const { origin, pathname } = parsedUrl;\n const baseUrl = `${origin}${pathname}`;\n return baseUrl;\n }\n\n static incLocalHits(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.localHit ??= 0;\n stats.localHit += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incLocalMisses(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.localMiss ??= 0;\n stats.localMiss += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incRemoteHits(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.hit += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incRemoteMisses(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.miss += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static report(): void {\n const data = HttpCacheStats.getData();\n let report: Record<string, Record<string, HttpCacheHostStatsData>> = {};\n for (const [url, stats] of Object.entries(data)) {\n const parsedUrl = parseUrl(url);\n if (parsedUrl) {\n const { origin, pathname } = parsedUrl;\n report[origin] ??= {};\n report[origin][pathname] = stats;\n }\n }\n\n for (const [host, hostStats] of Object.entries(report)) {\n report[host] = sortObject(hostStats);\n }\n report = sortObject(report);\n\n logger.debug(report, 'HTTP cache statistics');\n }\n}\n\ntype ObsoleteCacheStats = Record<\n string,\n {\n callsite?: string;\n count: number;\n }\n>;\n\n/* v8 ignore start: temporary code */\nexport class ObsoleteCacheHitLogger {\n static getData(): ObsoleteCacheStats {\n return memCache.get<ObsoleteCacheStats>('obsolete-cache-stats') ?? {};\n }\n\n private static getCallsite(): string | undefined {\n const _prepareStackTrace = Error.prepareStackTrace;\n try {\n let result: string | undefined;\n Error.prepareStackTrace = (_, stack) => {\n result = stack\n .find((frame) => {\n const callsite = frame.toString();\n return (\n !callsite.includes('lib/util/http') &&\n !callsite.includes('lib/util/stats') &&\n !callsite.includes('(node:')\n );\n })\n ?.toString()\n ?.replace(/:\\d+(?::\\d+)?\\)$/, ')');\n };\n\n // eslint-disable-next-line @typescript-eslint/no-unused-expressions\n new Error().stack;\n\n return result;\n } finally {\n Error.prepareStackTrace = _prepareStackTrace;\n }\n }\n\n static write(url: string): void {\n const data = this.getData();\n if (!data[url]) {\n const callsite = this.getCallsite();\n data[url] = { callsite, count: 0 };\n }\n data[url].count++;\n memCache.set('obsolete-cache-stats', data);\n }\n\n static report(): void {\n const hits = this.getData();\n logger.debug(\n { count: Object.keys(hits).length, hits },\n 'Cache fallback URLs',\n );\n }\n}\n/* v8 ignore stop: temporary code */\n"]}
|
1
|
+
{"version":3,"file":"stats.js","sourceRoot":"","sources":["../../lib/util/stats.ts"],"names":[],"mappings":"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","sourcesContent":["import { logger } from '../logger';\nimport * as memCache from './cache/memory';\nimport { parseUrl } from './url';\n\ntype LookupStatsData = Record<string, number[]>;\n\ninterface TimingStatsReport {\n count: number;\n avgMs: number;\n medianMs: number;\n maxMs: number;\n totalMs: number;\n}\n\nexport function makeTimingReport(data: number[]): TimingStatsReport {\n const count = data.length;\n const totalMs = data.reduce((a, c) => a + c, 0);\n const avgMs = count ? Math.round(totalMs / count) : 0;\n const maxMs = Math.max(0, ...data);\n const sorted = data.sort((a, b) => a - b);\n const medianMs = count ? sorted[Math.floor(count / 2)] : 0;\n return { count, avgMs, medianMs, maxMs, totalMs };\n}\n\nexport class LookupStats {\n static write(datasource: string, duration: number): void {\n const data = memCache.get<LookupStatsData>('lookup-stats') ?? {};\n data[datasource] ??= [];\n data[datasource].push(duration);\n memCache.set('lookup-stats', data);\n }\n\n static async wrap<T>(\n datasource: string,\n callback: () => Promise<T>,\n ): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n LookupStats.write(datasource, duration);\n return result;\n }\n\n static getReport(): Record<string, TimingStatsReport> {\n const report: Record<string, TimingStatsReport> = {};\n const data = memCache.get<LookupStatsData>('lookup-stats') ?? {};\n for (const [datasource, durations] of Object.entries(data)) {\n report[datasource] = makeTimingReport(durations);\n }\n return report;\n }\n\n static report(): void {\n const report = LookupStats.getReport();\n logger.debug(report, 'Lookup statistics');\n }\n}\n\ntype PackageCacheData = number[];\n\nexport class PackageCacheStats {\n static writeSet(duration: number): void {\n const data = memCache.get<PackageCacheData>('package-cache-sets') ?? [];\n data.push(duration);\n memCache.set('package-cache-sets', data);\n }\n\n static async wrapSet<T>(callback: () => Promise<T>): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n PackageCacheStats.writeSet(duration);\n return result;\n }\n\n static writeGet(duration: number): void {\n const data = memCache.get<PackageCacheData>('package-cache-gets') ?? [];\n data.push(duration);\n memCache.set('package-cache-gets', data);\n }\n\n static async wrapGet<T>(callback: () => Promise<T>): Promise<T> {\n const start = Date.now();\n const result = await callback();\n const duration = Date.now() - start;\n PackageCacheStats.writeGet(duration);\n return result;\n }\n\n static getReport(): { get: TimingStatsReport; set: TimingStatsReport } {\n const packageCacheGets =\n memCache.get<PackageCacheData>('package-cache-gets') ?? [];\n const get = makeTimingReport(packageCacheGets);\n\n const packageCacheSets =\n memCache.get<PackageCacheData>('package-cache-sets') ?? [];\n const set = makeTimingReport(packageCacheSets);\n\n return { get, set };\n }\n\n static report(): void {\n const report = PackageCacheStats.getReport();\n logger.debug(report, 'Package cache statistics');\n }\n}\n\ninterface DatasourceCacheDataPoint {\n datasource: string;\n registryUrl: string;\n packageName: string;\n action: 'hit' | 'miss' | 'set' | 'skip';\n}\n\n/* eslint-disable @typescript-eslint/consistent-indexed-object-style */\nexport interface DatasourceCacheReport {\n long: {\n [datasource in string]: {\n [registryUrl in string]: {\n [packageName in string]: {\n read?: 'hit' | 'miss';\n write?: 'set' | 'skip';\n };\n };\n };\n };\n short: {\n [datasource in string]: {\n [registryUrl in string]: {\n hit: number;\n miss: number;\n set: number;\n skip: number;\n };\n };\n };\n}\n/* eslint-enable @typescript-eslint/consistent-indexed-object-style */\n\nexport class DatasourceCacheStats {\n private static getData(): DatasourceCacheDataPoint[] {\n return (\n memCache.get<DatasourceCacheDataPoint[]>('datasource-cache-stats') ?? []\n );\n }\n\n private static setData(data: DatasourceCacheDataPoint[]): void {\n memCache.set('datasource-cache-stats', data);\n }\n\n static hit(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'hit' });\n this.setData(data);\n }\n\n static miss(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'miss' });\n this.setData(data);\n }\n\n static set(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'set' });\n this.setData(data);\n }\n\n static skip(\n datasource: string,\n registryUrl: string,\n packageName: string,\n ): void {\n const data = this.getData();\n data.push({ datasource, registryUrl, packageName, action: 'skip' });\n this.setData(data);\n }\n\n static getReport(): DatasourceCacheReport {\n const data = this.getData();\n const result: DatasourceCacheReport = { long: {}, short: {} };\n for (const { datasource, registryUrl, packageName, action } of data) {\n result.long[datasource] ??= {};\n result.long[datasource][registryUrl] ??= {};\n result.long[datasource][registryUrl] ??= {};\n result.long[datasource][registryUrl][packageName] ??= {};\n\n result.short[datasource] ??= {};\n result.short[datasource][registryUrl] ??= {\n hit: 0,\n miss: 0,\n set: 0,\n skip: 0,\n };\n\n if (action === 'hit') {\n result.long[datasource][registryUrl][packageName].read = 'hit';\n result.short[datasource][registryUrl].hit += 1;\n continue;\n }\n\n if (action === 'miss') {\n result.long[datasource][registryUrl][packageName].read = 'miss';\n result.short[datasource][registryUrl].miss += 1;\n continue;\n }\n\n if (action === 'set') {\n result.long[datasource][registryUrl][packageName].write = 'set';\n result.short[datasource][registryUrl].set += 1;\n continue;\n }\n\n if (action === 'skip') {\n result.long[datasource][registryUrl][packageName].write = 'skip';\n result.short[datasource][registryUrl].skip += 1;\n continue;\n }\n }\n\n return result;\n }\n\n static report(): void {\n const { long, short } = this.getReport();\n\n if (Object.keys(short).length > 0) {\n logger.debug(short, 'Datasource cache statistics');\n }\n\n if (Object.keys(long).length > 0) {\n logger.trace(long, 'Datasource cache detailed statistics');\n }\n }\n}\n\nexport interface HttpRequestStatsDataPoint {\n method: string;\n url: string;\n reqMs: number;\n queueMs: number;\n status: number;\n}\n\ninterface HostStatsData {\n count: number;\n reqAvgMs: number;\n reqMedianMs: number;\n reqMaxMs: number;\n queueAvgMs: number;\n queueMedianMs: number;\n queueMaxMs: number;\n}\n\n// url -> method -> status -> count\ntype UrlHttpStat = Record<string, Record<string, Record<string, number>>>;\n\ninterface HttpStatsCollection {\n // debug data\n urls: UrlHttpStat;\n hosts: Record<string, HostStatsData>;\n requests: number;\n\n // trace data\n rawRequests: string[];\n hostRequests: Record<string, HttpRequestStatsDataPoint[]>;\n}\n\nexport class HttpStats {\n static write(data: HttpRequestStatsDataPoint): void {\n const httpRequests =\n memCache.get<HttpRequestStatsDataPoint[]>('http-requests') ?? [];\n httpRequests.push(data);\n memCache.set('http-requests', httpRequests);\n }\n\n static getDataPoints(): HttpRequestStatsDataPoint[] {\n const httpRequests =\n memCache.get<HttpRequestStatsDataPoint[]>('http-requests') ?? [];\n\n // istanbul ignore next: sorting is hard and not worth testing\n httpRequests.sort((a, b) => {\n if (a.url < b.url) {\n return -1;\n }\n\n if (a.url > b.url) {\n return 1;\n }\n\n return 0;\n });\n\n return httpRequests;\n }\n\n static getReport(): HttpStatsCollection {\n const dataPoints = HttpStats.getDataPoints();\n\n const requests = dataPoints.length;\n\n const urls: UrlHttpStat = {};\n const rawRequests: string[] = [];\n const hostRequests: Record<string, HttpRequestStatsDataPoint[]> = {};\n\n for (const dataPoint of dataPoints) {\n const { url, reqMs, queueMs, status } = dataPoint;\n const method = dataPoint.method.toUpperCase();\n\n const parsedUrl = parseUrl(url);\n if (!parsedUrl) {\n logger.debug({ url }, 'Failed to parse URL during stats reporting');\n continue;\n }\n const { hostname, origin, pathname } = parsedUrl;\n const baseUrl = `${origin}${pathname}`;\n\n urls[baseUrl] ??= {};\n urls[baseUrl][method] ??= {};\n urls[baseUrl][method][status] ??= 0;\n urls[baseUrl][method][status] += 1;\n\n rawRequests.push(`${method} ${url} ${status} ${reqMs} ${queueMs}`);\n\n hostRequests[hostname] ??= [];\n hostRequests[hostname].push(dataPoint);\n }\n\n const hosts: Record<string, HostStatsData> = {};\n\n for (const [hostname, dataPoints] of Object.entries(hostRequests)) {\n const count = dataPoints.length;\n\n const reqTimes = dataPoints.map((r) => r.reqMs);\n const queueTimes = dataPoints.map((r) => r.queueMs);\n\n const reqReport = makeTimingReport(reqTimes);\n const queueReport = makeTimingReport(queueTimes);\n\n hosts[hostname] = {\n count,\n reqAvgMs: reqReport.avgMs,\n reqMedianMs: reqReport.medianMs,\n reqMaxMs: reqReport.maxMs,\n queueAvgMs: queueReport.avgMs,\n queueMedianMs: queueReport.medianMs,\n queueMaxMs: queueReport.maxMs,\n };\n }\n\n return {\n urls,\n rawRequests,\n hostRequests,\n hosts,\n requests,\n };\n }\n\n static report(): void {\n const { urls, rawRequests, hostRequests, hosts, requests } =\n HttpStats.getReport();\n logger.trace({ rawRequests, hostRequests }, 'HTTP full statistics');\n logger.debug({ hosts, requests }, 'HTTP statistics');\n logger.trace({ urls }, 'HTTP URL statistics');\n }\n}\n\ninterface HttpCacheHostStatsData {\n hit: number;\n miss: number;\n localHit?: number;\n localMiss?: number;\n}\n\ntype HttpCacheStatsData = Record<string, HttpCacheHostStatsData>;\n\nfunction sortObject<T>(obj: Record<string, T>): Record<string, T> {\n const result: Record<string, T> = {};\n for (const key of Object.keys(obj).sort()) {\n result[key] = obj[key];\n }\n return result;\n}\n\nexport class HttpCacheStats {\n static getData(): HttpCacheStatsData {\n return memCache.get<HttpCacheStatsData>('http-cache-stats') ?? {};\n }\n\n static read(key: string): HttpCacheHostStatsData {\n return (\n this.getData()?.[key] ?? {\n hit: 0,\n miss: 0,\n }\n );\n }\n\n static write(key: string, data: HttpCacheHostStatsData): void {\n const stats = memCache.get<HttpCacheStatsData>('http-cache-stats') ?? {};\n stats[key] = data;\n memCache.set('http-cache-stats', stats);\n }\n\n static getBaseUrl(url: string): string | null {\n const parsedUrl = parseUrl(url);\n if (!parsedUrl) {\n logger.debug({ url }, 'Failed to parse URL during cache stats');\n return null;\n }\n const { origin, pathname } = parsedUrl;\n const baseUrl = `${origin}${pathname}`;\n return baseUrl;\n }\n\n static incLocalHits(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.localHit ??= 0;\n stats.localHit += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incLocalMisses(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.localMiss ??= 0;\n stats.localMiss += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incRemoteHits(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.hit += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static incRemoteMisses(url: string): void {\n const baseUrl = HttpCacheStats.getBaseUrl(url);\n if (baseUrl) {\n const host = baseUrl;\n const stats = HttpCacheStats.read(host);\n stats.miss += 1;\n HttpCacheStats.write(host, stats);\n }\n }\n\n static report(): void {\n const data = HttpCacheStats.getData();\n let report: Record<string, Record<string, HttpCacheHostStatsData>> = {};\n for (const [url, stats] of Object.entries(data)) {\n const parsedUrl = parseUrl(url);\n if (parsedUrl) {\n const { origin, pathname } = parsedUrl;\n report[origin] ??= {};\n report[origin][pathname] = stats;\n }\n }\n\n for (const [host, hostStats] of Object.entries(report)) {\n report[host] = sortObject(hostStats);\n }\n report = sortObject(report);\n\n logger.debug(report, 'HTTP cache statistics');\n }\n}\n\ntype ObsoleteCacheStats = Record<\n string,\n {\n count: number;\n }\n>;\n\n/* v8 ignore start: temporary code */\nexport class ObsoleteCacheHitLogger {\n static getData(): ObsoleteCacheStats {\n return memCache.get<ObsoleteCacheStats>('obsolete-cache-stats') ?? {};\n }\n\n static write(url: string): void {\n const data = this.getData();\n if (!data[url]) {\n data[url] = { count: 0 };\n }\n data[url].count++;\n memCache.set('obsolete-cache-stats', data);\n }\n\n static report(): void {\n const hits = this.getData();\n logger.debug(\n { count: Object.keys(hits).length, hits },\n 'Cache fallback URLs',\n );\n }\n}\n/* v8 ignore stop: temporary code */\n"]}
|