package-management 0.0.9 → 0.0.11
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.
- package/dist/index.cjs +388 -131
- package/dist/index.d.cts +208 -63
- package/dist/index.d.mts +208 -63
- package/dist/index.d.ts +208 -63
- package/dist/index.mjs +381 -133
- package/package.json +45 -38
package/dist/index.mjs
CHANGED
|
@@ -1,12 +1,13 @@
|
|
|
1
1
|
import ErrorStackParser from 'error-stack-parser';
|
|
2
|
-
import path$1, { normalize, basename, dirname, relative } from 'pathe';
|
|
2
|
+
import path$1, { normalize, basename, dirname, relative, join } from 'pathe';
|
|
3
3
|
import process from 'node:process';
|
|
4
4
|
import path from 'node:path';
|
|
5
|
+
import { fileURLToPath } from 'node:url';
|
|
5
6
|
import { readFileSync, existsSync, writeFileSync } from 'node:fs';
|
|
6
|
-
import { execa, execaSync } from 'execa';
|
|
7
7
|
import { asyncCacheFn } from 'async-cache-fn';
|
|
8
|
+
import { execaSync, execa } from 'execa';
|
|
8
9
|
import { findUp } from 'find-up';
|
|
9
|
-
import { readFile } from 'node:fs/promises';
|
|
10
|
+
import { readFile, rm } from 'node:fs/promises';
|
|
10
11
|
import { resolvePathSync } from 'mlly';
|
|
11
12
|
import { globbySync } from 'globby';
|
|
12
13
|
import gitignoreParser from 'parse-gitignore';
|
|
@@ -14,16 +15,19 @@ import * as WST from 'workspace-tools';
|
|
|
14
15
|
import { resolveAlias } from 'pathe/utils';
|
|
15
16
|
import os from 'node:os';
|
|
16
17
|
import { modify, applyEdits } from 'jsonc-parser';
|
|
18
|
+
import { morph } from '@arktype/util';
|
|
19
|
+
import { createStorage, restoreSnapshot, snapshot } from 'unstorage';
|
|
20
|
+
import defineMemoryDriver from 'unstorage/drivers/memory';
|
|
21
|
+
import defineFsLiteDriver from 'unstorage/drivers/fs-lite';
|
|
17
22
|
|
|
18
23
|
const toArray = (data) => Array.isArray(data) ? data : [data];
|
|
19
24
|
const entriesOf = (o) => Object.entries(o);
|
|
20
25
|
const fromEntries = (entries) => Object.fromEntries(entries);
|
|
21
26
|
const notFalsy = (value) => [false, null, void 0].every((v) => v !== value);
|
|
22
27
|
const select = (obj, selection, mode) => {
|
|
23
|
-
if (!selection)
|
|
24
|
-
return obj;
|
|
28
|
+
if (!selection) return obj;
|
|
25
29
|
const filtered = entriesOf(obj).filter(([key]) => {
|
|
26
|
-
return
|
|
30
|
+
return selection[key];
|
|
27
31
|
});
|
|
28
32
|
return fromEntries(filtered);
|
|
29
33
|
};
|
|
@@ -42,15 +46,36 @@ const invariant = (predicate, message) => {
|
|
|
42
46
|
}
|
|
43
47
|
};
|
|
44
48
|
function getArrayItemAtOffset(arr, index, offset = 0) {
|
|
45
|
-
if (
|
|
46
|
-
return void 0;
|
|
49
|
+
if (arr === void 0 || index === void 0) return void 0;
|
|
47
50
|
return arr[index + offset];
|
|
48
51
|
}
|
|
49
52
|
function isMatching(a, b) {
|
|
50
|
-
if (!a || !b)
|
|
51
|
-
return false;
|
|
53
|
+
if (!a || !b) return false;
|
|
52
54
|
return a === b;
|
|
53
55
|
}
|
|
56
|
+
function checkResult(cb, options) {
|
|
57
|
+
try {
|
|
58
|
+
return buildSingleProp({
|
|
59
|
+
key: options?.keys?.data ?? "data",
|
|
60
|
+
value: cb()
|
|
61
|
+
});
|
|
62
|
+
} catch (error) {
|
|
63
|
+
return buildSingleProp({
|
|
64
|
+
key: "error",
|
|
65
|
+
value: error
|
|
66
|
+
});
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
function isPropertyKey(input) {
|
|
70
|
+
return typeof input === "string" || typeof input === "number" || typeof input === "symbol";
|
|
71
|
+
}
|
|
72
|
+
function buildSingleProp(entry) {
|
|
73
|
+
const [key, value] = Array.isArray(entry) ? entry : [entry.key, entry.value];
|
|
74
|
+
if (!isPropertyKey(key)) {
|
|
75
|
+
return {};
|
|
76
|
+
}
|
|
77
|
+
return { [key]: value };
|
|
78
|
+
}
|
|
54
79
|
|
|
55
80
|
function findCallerStackFrame(options) {
|
|
56
81
|
return findErrorStackFrame(options, (frame) => frame.isParentOfRootFunction);
|
|
@@ -111,7 +136,7 @@ function getFilePathData({
|
|
|
111
136
|
cwd
|
|
112
137
|
}) {
|
|
113
138
|
const workingDir = cwd ?? process.cwd();
|
|
114
|
-
const filePath = normalize(filepath);
|
|
139
|
+
const filePath = normalize(toFilePath(filepath));
|
|
115
140
|
const fileBasename = basename(filePath);
|
|
116
141
|
const dirPath = dirname(filePath);
|
|
117
142
|
const dirBasename = basename(dirPath);
|
|
@@ -128,17 +153,18 @@ function getFilePathData({
|
|
|
128
153
|
isFileInCwd
|
|
129
154
|
};
|
|
130
155
|
}
|
|
156
|
+
function toFilePath(fileName) {
|
|
157
|
+
return fileName.startsWith("file:") ? fileURLToPath(fileName) : fileName;
|
|
158
|
+
}
|
|
131
159
|
function parseFunctionName(functionName) {
|
|
132
|
-
if (!functionName)
|
|
133
|
-
return void 0;
|
|
160
|
+
if (!functionName) return void 0;
|
|
134
161
|
return removeStart(functionName, "Module.");
|
|
135
162
|
}
|
|
136
163
|
function removeStart(input, value) {
|
|
137
164
|
return input.startsWith(value) ? input.slice(value.length) : input;
|
|
138
165
|
}
|
|
139
166
|
function placeFormatter(index, total) {
|
|
140
|
-
if (
|
|
141
|
-
return void 0;
|
|
167
|
+
if (index === void 0 || !total) return void 0;
|
|
142
168
|
return [index, total].join("/");
|
|
143
169
|
}
|
|
144
170
|
|
|
@@ -172,8 +198,7 @@ function resolvePackageModulePath(name, options) {
|
|
|
172
198
|
function findResolvedModulePath(paths, options) {
|
|
173
199
|
for (const path of paths) {
|
|
174
200
|
const resolvedPath = resolveModulePath(path, options);
|
|
175
|
-
if (resolvedPath === void 0)
|
|
176
|
-
continue;
|
|
201
|
+
if (resolvedPath === void 0) continue;
|
|
177
202
|
return resolvedPath;
|
|
178
203
|
}
|
|
179
204
|
}
|
|
@@ -227,8 +252,7 @@ function isDependencyInPackageJson(options, packageJson) {
|
|
|
227
252
|
}
|
|
228
253
|
function findDependencyInPackageJson(option, packageJson) {
|
|
229
254
|
const { name, type } = typeof option === "string" ? { name: option, type: void 0 } : option;
|
|
230
|
-
if (!packageJson)
|
|
231
|
-
return void 0;
|
|
255
|
+
if (!packageJson) return void 0;
|
|
232
256
|
const allowedTypes = typeof type === "string" ? {
|
|
233
257
|
[type]: true
|
|
234
258
|
} : type ?? {
|
|
@@ -239,8 +263,7 @@ function findDependencyInPackageJson(option, packageJson) {
|
|
|
239
263
|
const matches = allowedDependencyTypes.map((type2) => {
|
|
240
264
|
return getPackageJsonDependencyItem({ name, type: type2 }, packageJson);
|
|
241
265
|
}).filter(notFalsy);
|
|
242
|
-
if (matches.length === 0)
|
|
243
|
-
return void 0;
|
|
266
|
+
if (matches.length === 0) return void 0;
|
|
244
267
|
return {
|
|
245
268
|
firstMatch: matches[0],
|
|
246
269
|
matches
|
|
@@ -250,12 +273,10 @@ function getPackageJsonDependencyItem({
|
|
|
250
273
|
name,
|
|
251
274
|
type
|
|
252
275
|
}, packageJson) {
|
|
253
|
-
if (!packageJson)
|
|
254
|
-
return void 0;
|
|
276
|
+
if (!packageJson) return void 0;
|
|
255
277
|
const dependencyMap = getPackageJsonDependencyMap(type, packageJson);
|
|
256
278
|
const version = dependencyMap?.[name];
|
|
257
|
-
if (version === void 0)
|
|
258
|
-
return void 0;
|
|
279
|
+
if (version === void 0) return void 0;
|
|
259
280
|
return {
|
|
260
281
|
name,
|
|
261
282
|
version,
|
|
@@ -277,7 +298,7 @@ function getWorkspaceFolder(options) {
|
|
|
277
298
|
fallbackToGitRoot = true,
|
|
278
299
|
throwIfNotFound = true
|
|
279
300
|
} = options ?? {};
|
|
280
|
-
const getFolder = fallbackToGitRoot ? WST.findProjectRoot : WST.
|
|
301
|
+
const getFolder = fallbackToGitRoot ? WST.findProjectRoot : WST.getWorkspaceManagerRoot;
|
|
281
302
|
const folder = getFolder(cwd);
|
|
282
303
|
if (folder === void 0 && throwIfNotFound) {
|
|
283
304
|
throw new Error(`Could not find workspace folder`);
|
|
@@ -320,17 +341,15 @@ function getWorkspaceProjectInfo(options) {
|
|
|
320
341
|
|
|
321
342
|
function getWorkspacePackageInfoList(options) {
|
|
322
343
|
const { workspaceDir, resolveWstList } = common(options);
|
|
323
|
-
const wstList = WST.
|
|
344
|
+
const wstList = WST.getWorkspaceInfos(workspaceDir);
|
|
324
345
|
return resolveWstList(wstList);
|
|
325
346
|
}
|
|
326
347
|
function common(options) {
|
|
327
348
|
const { cwd, includeRoot: includeWorkspace } = options ?? {};
|
|
328
349
|
const workspaceDir = getWorkspaceFolder({ cwd });
|
|
329
350
|
function resolveWstList(list) {
|
|
330
|
-
if (!workspaceDir)
|
|
331
|
-
|
|
332
|
-
if (includeWorkspace)
|
|
333
|
-
return [getWorkspaceProjectInfo(), ...list];
|
|
351
|
+
if (!workspaceDir || !list) return [];
|
|
352
|
+
if (includeWorkspace) return [getWorkspaceProjectInfo(), ...list];
|
|
334
353
|
return list;
|
|
335
354
|
}
|
|
336
355
|
return {
|
|
@@ -351,6 +370,21 @@ function getProjectInfoByName(name, options) {
|
|
|
351
370
|
return getWorkspacePackageInfoMap({ cwd })[name];
|
|
352
371
|
}
|
|
353
372
|
|
|
373
|
+
function getGitRootFolder(options) {
|
|
374
|
+
const { cwd = process.cwd(), throwIfNotFound = true } = options ?? {};
|
|
375
|
+
const { stdout } = execaSync("git", ["rev-parse", "--show-toplevel"], {
|
|
376
|
+
cwd,
|
|
377
|
+
reject: false
|
|
378
|
+
});
|
|
379
|
+
if (!stdout) {
|
|
380
|
+
if (throwIfNotFound) {
|
|
381
|
+
throw new Error(`Directory "${cwd}" is not in a git repository`);
|
|
382
|
+
}
|
|
383
|
+
return void 0;
|
|
384
|
+
}
|
|
385
|
+
return path$1.normalize(stdout);
|
|
386
|
+
}
|
|
387
|
+
|
|
354
388
|
function getProjectInfo(folder, options) {
|
|
355
389
|
if (isWorkspaceFolderTypeOption(folder)) {
|
|
356
390
|
return getWorkspaceProjectInfo(
|
|
@@ -361,7 +395,7 @@ function getProjectInfo(folder, options) {
|
|
|
361
395
|
return getPackageInfo(options);
|
|
362
396
|
}
|
|
363
397
|
if (folder === "<gitroot_folder>") {
|
|
364
|
-
return
|
|
398
|
+
return readPackageInfo({ packageDir: getGitRootFolder(options) });
|
|
365
399
|
}
|
|
366
400
|
return getProjectInfoByName(folder.packageName, options);
|
|
367
401
|
}
|
|
@@ -376,9 +410,6 @@ function parseWorkspaceFolderTypeOptions(option, defaultOptions) {
|
|
|
376
410
|
}
|
|
377
411
|
return { ...defaultOptions, ...option["<workspace_folder>"] };
|
|
378
412
|
}
|
|
379
|
-
getProjectInfo({
|
|
380
|
-
"<workspace_folder>": {}
|
|
381
|
-
});
|
|
382
413
|
|
|
383
414
|
const project = (...args) => {
|
|
384
415
|
const [source, projectOptions] = args;
|
|
@@ -388,7 +419,9 @@ const project = (...args) => {
|
|
|
388
419
|
detectPackageManagers,
|
|
389
420
|
detectLockfilePackageManagers,
|
|
390
421
|
detectGlobalPackageManagers,
|
|
391
|
-
|
|
422
|
+
globalVersions,
|
|
423
|
+
filterPackageManagers,
|
|
424
|
+
mapPackageManagers
|
|
392
425
|
} = definePackageManagerClient({ cwd: projectDir });
|
|
393
426
|
return {
|
|
394
427
|
packageJson,
|
|
@@ -399,6 +432,8 @@ const project = (...args) => {
|
|
|
399
432
|
detectPackageManagers,
|
|
400
433
|
detectGlobalPackageManagers,
|
|
401
434
|
detectLockfilePackageManagers,
|
|
435
|
+
globalVersions,
|
|
436
|
+
mapPackageManagers,
|
|
402
437
|
tsconfig: tsconfig(projectDir ?? ""),
|
|
403
438
|
gitignore: gitignore(path$1.join(projectDir ?? "", ".gitignore")),
|
|
404
439
|
filterPackageManagers,
|
|
@@ -473,11 +508,9 @@ function resolveImportOption(option) {
|
|
|
473
508
|
return option;
|
|
474
509
|
}
|
|
475
510
|
async function installImport(packageName, options, installer) {
|
|
476
|
-
if (!packageName)
|
|
477
|
-
return;
|
|
511
|
+
if (!packageName) return;
|
|
478
512
|
const { checkExists } = options ?? {};
|
|
479
|
-
if (checkExists && isPackageDependency(packageName))
|
|
480
|
-
return;
|
|
513
|
+
if (checkExists && isPackageDependency(packageName)) return;
|
|
481
514
|
const installerFn = installer ?? (await workspace.getProject("<package_folder>").findPackageManager()).installPackage;
|
|
482
515
|
await installerFn(packageName, options);
|
|
483
516
|
}
|
|
@@ -509,9 +542,7 @@ function definePackageManager(config, options) {
|
|
|
509
542
|
preferOffline: true,
|
|
510
543
|
cwd: defaultCwd,
|
|
511
544
|
...options2
|
|
512
|
-
}
|
|
513
|
-
"pick"
|
|
514
|
-
);
|
|
545
|
+
});
|
|
515
546
|
const packageNames = toArray(packageName);
|
|
516
547
|
try {
|
|
517
548
|
await $$({
|
|
@@ -520,25 +551,32 @@ function definePackageManager(config, options) {
|
|
|
520
551
|
cwd: defaultCwd,
|
|
521
552
|
...options2
|
|
522
553
|
});
|
|
523
|
-
} catch (
|
|
524
|
-
throw new Error(`Failed to install: ${packageNames.join(", ")}
|
|
554
|
+
} catch (error) {
|
|
555
|
+
throw new Error(`Failed to install: ${packageNames.join(", ")}`, {
|
|
556
|
+
cause: error
|
|
557
|
+
});
|
|
525
558
|
}
|
|
526
559
|
};
|
|
527
560
|
const uninstallPackage = async (packageName, options2) => {
|
|
528
561
|
const uninstall = agentArgs.uninstall;
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
|
|
532
|
-
|
|
533
|
-
command,
|
|
534
|
-
args: [uninstall.command, name],
|
|
535
|
-
cwd: defaultCwd,
|
|
536
|
-
...options2
|
|
537
|
-
});
|
|
538
|
-
} catch (e) {
|
|
539
|
-
}
|
|
540
|
-
})
|
|
562
|
+
const cwd = options2?.cwd ?? defaultCwd;
|
|
563
|
+
const { packageJson } = getPackageInfo({ cwd });
|
|
564
|
+
const installed = toArray(packageName).filter(
|
|
565
|
+
(name) => isDependencyInPackageJson(name, packageJson)
|
|
541
566
|
);
|
|
567
|
+
if (installed.length === 0) return;
|
|
568
|
+
try {
|
|
569
|
+
await $$({
|
|
570
|
+
command,
|
|
571
|
+
args: [uninstall.command, ...installed],
|
|
572
|
+
cwd,
|
|
573
|
+
...options2
|
|
574
|
+
});
|
|
575
|
+
} catch (error) {
|
|
576
|
+
throw new Error(`Failed to uninstall: ${installed.join(", ")}`, {
|
|
577
|
+
cause: error
|
|
578
|
+
});
|
|
579
|
+
}
|
|
542
580
|
};
|
|
543
581
|
return {
|
|
544
582
|
id: config.id,
|
|
@@ -550,8 +588,7 @@ function definePackageManager(config, options) {
|
|
|
550
588
|
}),
|
|
551
589
|
readLockfile: asyncCacheFn(async (...args) => {
|
|
552
590
|
const lockfilePath = await findLockfilePath.noCache(...args);
|
|
553
|
-
if (!lockfilePath)
|
|
554
|
-
return void 0;
|
|
591
|
+
if (!lockfilePath) return void 0;
|
|
555
592
|
return readFile(lockfilePath, "utf8");
|
|
556
593
|
}),
|
|
557
594
|
globalVersion: asyncCacheFn(async (...args) => {
|
|
@@ -585,7 +622,10 @@ async function $$(options) {
|
|
|
585
622
|
return execa(command, args.filter(notFalsy), {
|
|
586
623
|
cwd,
|
|
587
624
|
...shellOptions,
|
|
588
|
-
|
|
625
|
+
// `pipe` keeps output off the console while still capturing it: a failed
|
|
626
|
+
// command can report why it failed, and `globalVersion` can read stdout.
|
|
627
|
+
// `ignore` discards the reason along with the output.
|
|
628
|
+
stdio: silent ? "pipe" : "inherit"
|
|
589
629
|
});
|
|
590
630
|
}
|
|
591
631
|
|
|
@@ -694,18 +734,24 @@ const yarn = definePackageManagerConfig({
|
|
|
694
734
|
});
|
|
695
735
|
|
|
696
736
|
async function findPackageManager(packageManagers, options) {
|
|
697
|
-
const
|
|
698
|
-
|
|
737
|
+
const packageManager = await findPackageManagerSafely(
|
|
738
|
+
packageManagers,
|
|
739
|
+
options
|
|
740
|
+
);
|
|
699
741
|
invariant(packageManager, "No package manager found");
|
|
700
742
|
return packageManager;
|
|
701
743
|
}
|
|
702
744
|
async function findPackageManagerSafely(packageManagers, options) {
|
|
703
|
-
const
|
|
704
|
-
|
|
705
|
-
|
|
706
|
-
|
|
707
|
-
|
|
708
|
-
|
|
745
|
+
const [fromLockfile] = await detectLockfilePackageManagers(
|
|
746
|
+
packageManagers,
|
|
747
|
+
options
|
|
748
|
+
);
|
|
749
|
+
if (fromLockfile) return fromLockfile;
|
|
750
|
+
const [fromGlobal] = await detectGlobalPackageManagers(
|
|
751
|
+
packageManagers,
|
|
752
|
+
options
|
|
753
|
+
);
|
|
754
|
+
return fromGlobal;
|
|
709
755
|
}
|
|
710
756
|
async function detectPackageManagers(packageManagers, options) {
|
|
711
757
|
return [
|
|
@@ -716,29 +762,47 @@ async function detectPackageManagers(packageManagers, options) {
|
|
|
716
762
|
async function detectLockfilePackageManagers(packageManagers, options) {
|
|
717
763
|
return filterPackageManagers(
|
|
718
764
|
packageManagers,
|
|
719
|
-
(
|
|
765
|
+
(packageManager) => packageManager.hasLockfile(options),
|
|
720
766
|
options
|
|
721
767
|
);
|
|
722
768
|
}
|
|
723
769
|
async function detectGlobalPackageManagers(packageManagers, options) {
|
|
724
770
|
return filterPackageManagers(
|
|
725
771
|
packageManagers,
|
|
726
|
-
|
|
772
|
+
// Without the `await`, `Boolean` receives a pending promise and is always
|
|
773
|
+
// `true`, so every package manager passes the filter regardless of whether
|
|
774
|
+
// it is actually installed.
|
|
775
|
+
async (packageManager) => Boolean(await packageManager.globalVersion(options)),
|
|
776
|
+
options
|
|
777
|
+
);
|
|
778
|
+
}
|
|
779
|
+
async function getGlobalVersions(packageManagers, options) {
|
|
780
|
+
const entries = await mapPackageManagers(
|
|
781
|
+
packageManagers,
|
|
782
|
+
async (packageManager) => [packageManager.id, await packageManager.globalVersion(options)],
|
|
727
783
|
options
|
|
728
784
|
);
|
|
785
|
+
return Object.fromEntries(entries);
|
|
786
|
+
}
|
|
787
|
+
async function mapPackageManagers(packageManagers, mapFn, options) {
|
|
788
|
+
return Promise.all(
|
|
789
|
+
selectAllowedPackageManagers(packageManagers, options).map(
|
|
790
|
+
(packageManager) => mapFn(packageManager)
|
|
791
|
+
)
|
|
792
|
+
);
|
|
729
793
|
}
|
|
730
794
|
async function filterPackageManagers(packageManagers, filterFn, options) {
|
|
731
|
-
const
|
|
732
|
-
|
|
733
|
-
|
|
734
|
-
|
|
735
|
-
|
|
736
|
-
return
|
|
737
|
-
|
|
738
|
-
|
|
739
|
-
|
|
740
|
-
})
|
|
741
|
-
)
|
|
795
|
+
const matches = await mapPackageManagers(
|
|
796
|
+
packageManagers,
|
|
797
|
+
async (packageManager) => await filterFn(packageManager) ? packageManager : void 0,
|
|
798
|
+
options
|
|
799
|
+
);
|
|
800
|
+
return matches.filter(notFalsy);
|
|
801
|
+
}
|
|
802
|
+
function selectAllowedPackageManagers(packageManagers, options) {
|
|
803
|
+
return packageManagers.filter(
|
|
804
|
+
({ id }) => options?.allowed ? id in options.allowed : true
|
|
805
|
+
);
|
|
742
806
|
}
|
|
743
807
|
|
|
744
808
|
const packageManagerConfigs = [pnpm, yarn, bun, npm];
|
|
@@ -763,7 +827,11 @@ function definePackageManagerClient(options) {
|
|
|
763
827
|
detectGlobalPackageManagers: asyncCacheFn(
|
|
764
828
|
async (options2) => detectGlobalPackageManagers(configs, options2)
|
|
765
829
|
),
|
|
766
|
-
|
|
830
|
+
globalVersions: asyncCacheFn(
|
|
831
|
+
async (options2) => getGlobalVersions(configs, options2)
|
|
832
|
+
),
|
|
833
|
+
filterPackageManagers: async (filterFn, options2) => filterPackageManagers(configs, filterFn, options2),
|
|
834
|
+
mapPackageManagers: async (mapFn, options2) => mapPackageManagers(configs, mapFn, options2)
|
|
767
835
|
};
|
|
768
836
|
}
|
|
769
837
|
|
|
@@ -786,17 +854,13 @@ function definePathAliases(aliasDefinitions) {
|
|
|
786
854
|
};
|
|
787
855
|
}
|
|
788
856
|
function getAliasedFilePath(aliasMap, options) {
|
|
857
|
+
const { to, startingFrom, cwd, checkExistence, glob } = typeof options === "string" || Array.isArray(options) ? { to: options } : options;
|
|
858
|
+
const resolveOptions = { cwd, checkExistence, glob, aliasMap };
|
|
789
859
|
try {
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
794
|
-
if (opts.startingFrom) {
|
|
795
|
-
return resolveRelativePathTo(opts.to, opts.startingFrom, opts);
|
|
796
|
-
}
|
|
797
|
-
return resolvePathTo(opts.to, opts);
|
|
798
|
-
} catch (e) {
|
|
799
|
-
return void 0;
|
|
860
|
+
return startingFrom ? resolveRelativePathTo(to, startingFrom, resolveOptions) : resolvePathTo(to, resolveOptions);
|
|
861
|
+
} catch (error) {
|
|
862
|
+
if (checkExistence || glob) return void 0;
|
|
863
|
+
throw error;
|
|
800
864
|
}
|
|
801
865
|
}
|
|
802
866
|
function resolveRelativePathTo(to, from, options) {
|
|
@@ -818,18 +882,20 @@ function resolvePathTo(pathTo, { cwd, checkExistence, glob, aliasMap }) {
|
|
|
818
882
|
}
|
|
819
883
|
function normalizePathTo(pathTo, options) {
|
|
820
884
|
const { cwd, aliasMap } = options ?? {};
|
|
821
|
-
|
|
822
|
-
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
});
|
|
885
|
+
const aliasedPath = Array.isArray(pathTo) ? path$1.join(...pathTo.filter(isNotNull)) : pathTo;
|
|
886
|
+
const baseDir = Array.isArray(pathTo) ? pathTo[0] : findAliasToken(aliasedPath, aliasMap);
|
|
887
|
+
if (baseDir === void 0) return aliasedPath;
|
|
888
|
+
const baseDirPath = executeMapFn(aliasMap, baseDir, [{ cwd }]);
|
|
889
|
+
if (typeof baseDirPath !== "string" || baseDirPath.length === 0) {
|
|
890
|
+
throw new Error(`Path alias resolved to no location: ${baseDir}`);
|
|
827
891
|
}
|
|
828
|
-
return
|
|
892
|
+
return resolveAlias(aliasedPath, { [baseDir]: baseDirPath });
|
|
893
|
+
}
|
|
894
|
+
function findAliasToken(pathTo, aliasMap) {
|
|
895
|
+
return Object.keys(aliasMap ?? {}).filter((alias) => pathTo === alias || pathTo.startsWith(`${alias}/`)).sort((a, b) => b.length - a.length)[0];
|
|
829
896
|
}
|
|
830
897
|
function executeMapFn(map, key, args) {
|
|
831
|
-
if (!map || !key || !(key in map))
|
|
832
|
-
return void 0;
|
|
898
|
+
if (!map || !key || !(key in map)) return void 0;
|
|
833
899
|
const fnArgs = Array.isArray(args) ? args : [args];
|
|
834
900
|
const resolver = map?.[key];
|
|
835
901
|
return typeof resolver === "function" ? resolver?.(...fnArgs) : resolver;
|
|
@@ -868,7 +934,7 @@ const predefinedPathAliases = {
|
|
|
868
934
|
]
|
|
869
935
|
},
|
|
870
936
|
"<workspace_folder?>": {
|
|
871
|
-
resolve: (opts) => getWorkspaceFolder(opts),
|
|
937
|
+
resolve: (opts) => getWorkspaceFolder({ ...opts, fallbackToGitRoot: false }),
|
|
872
938
|
subpaths: [
|
|
873
939
|
{
|
|
874
940
|
to: "node_modules"
|
|
@@ -938,44 +1004,226 @@ function getFolderByPackageName(name, options) {
|
|
|
938
1004
|
return info?.dirpath;
|
|
939
1005
|
}
|
|
940
1006
|
|
|
941
|
-
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
1007
|
+
const jsonSourceResolvers = {
|
|
1008
|
+
data: (json) => {
|
|
1009
|
+
return {
|
|
1010
|
+
text: () => JSON.stringify(json),
|
|
1011
|
+
data: () => json
|
|
1012
|
+
};
|
|
1013
|
+
},
|
|
1014
|
+
text: (text) => {
|
|
1015
|
+
return {
|
|
1016
|
+
text: () => text,
|
|
1017
|
+
data: () => JSON.parse(text)
|
|
1018
|
+
};
|
|
1019
|
+
},
|
|
1020
|
+
filepath: (filepath) => {
|
|
1021
|
+
const text = readFileSync(filepath, "utf-8");
|
|
1022
|
+
return {
|
|
1023
|
+
text: () => text,
|
|
1024
|
+
data: () => JSON.parse(text)
|
|
1025
|
+
};
|
|
1026
|
+
}
|
|
1027
|
+
};
|
|
1028
|
+
function resolveJsonSource(source, as) {
|
|
1029
|
+
const [sourceType, sourceData] = Object.entries(source).find(([_, selected]) => selected !== void 0) ?? [];
|
|
1030
|
+
if (!sourceType || !(sourceType in jsonSourceResolvers) || !sourceData) {
|
|
1031
|
+
throw new Error("Invalid source data");
|
|
1032
|
+
}
|
|
1033
|
+
const sourceTypeResolvers = jsonSourceResolvers[sourceType](
|
|
1034
|
+
sourceData
|
|
1035
|
+
);
|
|
1036
|
+
const resolved = morph(sourceTypeResolvers, (key, v) => {
|
|
1037
|
+
try {
|
|
1038
|
+
const value = v();
|
|
1039
|
+
return !as || key === as ? [key, value] : [];
|
|
1040
|
+
} catch (e) {
|
|
1041
|
+
throw new Error(`Failed to resolve ${key} from ${sourceType}`);
|
|
1042
|
+
}
|
|
945
1043
|
});
|
|
946
|
-
if (
|
|
947
|
-
|
|
948
|
-
return void 0;
|
|
1044
|
+
if (as) {
|
|
1045
|
+
return resolved[as];
|
|
949
1046
|
}
|
|
950
|
-
return
|
|
1047
|
+
return resolved;
|
|
951
1048
|
}
|
|
952
1049
|
|
|
953
|
-
function
|
|
954
|
-
|
|
955
|
-
|
|
956
|
-
|
|
957
|
-
|
|
958
|
-
|
|
959
|
-
|
|
960
|
-
|
|
961
|
-
|
|
962
|
-
|
|
1050
|
+
function resolveEditPath(path, options) {
|
|
1051
|
+
const { pathSeparator = "." } = {};
|
|
1052
|
+
const arr = toArray(path);
|
|
1053
|
+
return arr.map((path2) => {
|
|
1054
|
+
if (typeof path2 === "string") {
|
|
1055
|
+
return pathSeparator === false ? path2 : path2.split(pathSeparator);
|
|
1056
|
+
}
|
|
1057
|
+
return path2;
|
|
1058
|
+
}).flat();
|
|
1059
|
+
}
|
|
1060
|
+
function parseJSONCEdits(edits) {
|
|
1061
|
+
if (Array.isArray(edits)) {
|
|
1062
|
+
return edits.map(({ path, ...edit }) => ({
|
|
1063
|
+
path: resolveEditPath(path),
|
|
1064
|
+
...edit
|
|
1065
|
+
}));
|
|
1066
|
+
}
|
|
1067
|
+
return Object.entries(edits).map(
|
|
1068
|
+
([path, value]) => ({
|
|
1069
|
+
path: resolveEditPath(path),
|
|
1070
|
+
...value
|
|
963
1071
|
})
|
|
964
1072
|
);
|
|
965
|
-
|
|
966
|
-
|
|
967
|
-
|
|
968
|
-
|
|
969
|
-
|
|
970
|
-
|
|
971
|
-
|
|
972
|
-
|
|
1073
|
+
}
|
|
1074
|
+
function modifyJSON({
|
|
1075
|
+
json,
|
|
1076
|
+
edits,
|
|
1077
|
+
defaultEditOptions
|
|
1078
|
+
}) {
|
|
1079
|
+
return checkResult(() => {
|
|
1080
|
+
const text = resolveJsonSource(json, "text");
|
|
1081
|
+
const jsoncEdits = parseJSONCEdits(edits);
|
|
1082
|
+
const editResult = jsoncEdits.flatMap(
|
|
1083
|
+
(edit) => modify(text, edit.path, edit.value, {
|
|
1084
|
+
...defaultEditOptions,
|
|
1085
|
+
...edit.options
|
|
1086
|
+
})
|
|
1087
|
+
);
|
|
1088
|
+
const updated = applyEdits(text, editResult);
|
|
1089
|
+
return resolveJsonSource({ text: updated });
|
|
1090
|
+
});
|
|
1091
|
+
}
|
|
1092
|
+
function modifyJSONFile(filepath, edits, options) {
|
|
1093
|
+
return checkResult(() => {
|
|
1094
|
+
const { autoCommit = true, defaultEditOptions } = options || {};
|
|
1095
|
+
const { data: json, error } = modifyJSON({
|
|
1096
|
+
json: { filepath },
|
|
1097
|
+
edits,
|
|
1098
|
+
defaultEditOptions
|
|
1099
|
+
});
|
|
1100
|
+
if (error) {
|
|
1101
|
+
throw error;
|
|
1102
|
+
}
|
|
1103
|
+
const commit = () => writeFileSync(filepath, json.text);
|
|
1104
|
+
if (autoCommit) {
|
|
1105
|
+
commit();
|
|
1106
|
+
return json;
|
|
1107
|
+
}
|
|
1108
|
+
return {
|
|
1109
|
+
json,
|
|
1110
|
+
commit
|
|
1111
|
+
};
|
|
1112
|
+
});
|
|
1113
|
+
}
|
|
1114
|
+
|
|
1115
|
+
function isStorageValue(input) {
|
|
1116
|
+
return input === null || typeof input === "string" || typeof input === "number" || typeof input === "boolean" || typeof input === "object";
|
|
1117
|
+
}
|
|
1118
|
+
|
|
1119
|
+
const storage = createStorage({ driver: defineMemoryDriver() });
|
|
1120
|
+
const tempFileSystem = defineFileSystemStorage({
|
|
1121
|
+
base: join(os.tmpdir(), ".package-manager")
|
|
1122
|
+
});
|
|
1123
|
+
function defineFileSystemEntries(definition) {
|
|
1124
|
+
const fileSystemEntries = Object.entries(definition).map(([k, v]) => {
|
|
1125
|
+
if (v instanceof Function) {
|
|
1126
|
+
const {
|
|
1127
|
+
file,
|
|
1128
|
+
options,
|
|
1129
|
+
serialize = (input) => JSON.stringify(input),
|
|
1130
|
+
deserialize = (input) => {
|
|
1131
|
+
try {
|
|
1132
|
+
return JSON.parse(input);
|
|
1133
|
+
} catch {
|
|
1134
|
+
return input;
|
|
1135
|
+
}
|
|
1136
|
+
}
|
|
1137
|
+
} = v();
|
|
1138
|
+
return {
|
|
1139
|
+
key: k,
|
|
1140
|
+
value: serialize(file),
|
|
1141
|
+
options,
|
|
1142
|
+
serialize,
|
|
1143
|
+
deserialize
|
|
1144
|
+
};
|
|
1145
|
+
}
|
|
1146
|
+
if (isStorageValue(v)) {
|
|
1147
|
+
return {
|
|
1148
|
+
key: k,
|
|
1149
|
+
value: JSON.stringify(v)
|
|
1150
|
+
};
|
|
1151
|
+
}
|
|
1152
|
+
return void 0;
|
|
1153
|
+
}).filter((v) => v !== void 0);
|
|
1154
|
+
const resolved = {
|
|
1155
|
+
definition,
|
|
1156
|
+
fileSystemEntries
|
|
973
1157
|
};
|
|
1158
|
+
return resolved;
|
|
974
1159
|
}
|
|
975
|
-
|
|
976
|
-
|
|
977
|
-
|
|
1160
|
+
function defineFileSystemStorage(options) {
|
|
1161
|
+
const { base: root, initial, ...storageOptions } = options;
|
|
1162
|
+
let initialFileEntriesData = defineFileSystemEntries(initial ?? {});
|
|
1163
|
+
const storage2 = createStorage({
|
|
1164
|
+
driver: defineFsLiteDriver({ base: root, ...storageOptions })
|
|
1165
|
+
});
|
|
1166
|
+
const fileStorage = {
|
|
1167
|
+
createFile: async (key, data) => {
|
|
1168
|
+
await storage2.setItem(key, data);
|
|
1169
|
+
return {
|
|
1170
|
+
key,
|
|
1171
|
+
filepath: join(root, key),
|
|
1172
|
+
get: async () => storage2.getItem(key),
|
|
1173
|
+
update: async (data2) => storage2.setItem(key, data2)
|
|
1174
|
+
};
|
|
1175
|
+
},
|
|
1176
|
+
async getFilePath(key) {
|
|
1177
|
+
return (await this.getFile(key)).filepath;
|
|
1178
|
+
},
|
|
1179
|
+
getFile: async (key) => {
|
|
1180
|
+
const storageData = await storage2.getItem(key);
|
|
1181
|
+
return {
|
|
1182
|
+
key,
|
|
1183
|
+
filepath: join(root, key),
|
|
1184
|
+
data: storageData,
|
|
1185
|
+
read: async () => (await storage2.getItemRaw(key))?.toString()
|
|
1186
|
+
};
|
|
1187
|
+
},
|
|
1188
|
+
async readFile(key) {
|
|
1189
|
+
const { read } = await this.getFile(key);
|
|
1190
|
+
const content = await read();
|
|
1191
|
+
return content;
|
|
1192
|
+
},
|
|
1193
|
+
snapshotFs: async (base = root) => {
|
|
1194
|
+
return snapshot(storage2, base);
|
|
1195
|
+
},
|
|
1196
|
+
restoreFs: async (snapshot2) => {
|
|
1197
|
+
return restoreSnapshot(storage2, snapshot2);
|
|
1198
|
+
},
|
|
1199
|
+
initializeFs: async (override) => {
|
|
1200
|
+
if (override) {
|
|
1201
|
+
initialFileEntriesData = defineFileSystemEntries(override);
|
|
1202
|
+
}
|
|
1203
|
+
await storage2.clear();
|
|
1204
|
+
return storage2.setItems(initialFileEntriesData.fileSystemEntries);
|
|
1205
|
+
},
|
|
1206
|
+
defineFileSystemEntries,
|
|
1207
|
+
removeAllFiles: storage2.clear,
|
|
1208
|
+
async deleteFileSystem() {
|
|
1209
|
+
await this.removeAllFiles();
|
|
1210
|
+
await storage2.unmount(root, true);
|
|
1211
|
+
await rm(root, { recursive: true, force: true });
|
|
1212
|
+
},
|
|
1213
|
+
storage: storage2,
|
|
1214
|
+
meta: {
|
|
1215
|
+
fileEntriesData: initialFileEntriesData
|
|
1216
|
+
}
|
|
978
1217
|
};
|
|
979
|
-
|
|
1218
|
+
if (initial) {
|
|
1219
|
+
return {
|
|
1220
|
+
initialize: async () => {
|
|
1221
|
+
await fileStorage.initializeFs(initial);
|
|
1222
|
+
return fileStorage;
|
|
1223
|
+
}
|
|
1224
|
+
};
|
|
1225
|
+
}
|
|
1226
|
+
return fileStorage;
|
|
1227
|
+
}
|
|
980
1228
|
|
|
981
|
-
export { _dirname, _filename, definePackage, definePackageManagerClient, definePathAliases, detectGlobalPackageManagers, detectLockfilePackageManagers, detectPackageManagers, filterPackageManagers, findDependencyInPackageJson, findPackageManager, findPackageManagerSafely, findResolvedModulePath, getAliasMap, getFolderByPackageName, getGitRootFolder, getPackageFolder, getPath, getWorkspaceFolder, importMap, importer, isDependencyInPackageJson, isPackageDependency, isPackageModuleFound,
|
|
1229
|
+
export { _dirname, _filename, defineFileSystemEntries, defineFileSystemStorage, definePackage, definePackageManagerClient, definePathAliases, detectGlobalPackageManagers, detectLockfilePackageManagers, detectPackageManagers, filterPackageManagers, findDependencyInPackageJson, findPackageManager, findPackageManagerSafely, findResolvedModulePath, getAliasMap, getFolderByPackageName, getGitRootFolder, getGlobalVersions, getPackageFolder, getPath, getWorkspaceFolder, importMap, importer, isDependencyInPackageJson, isPackageDependency, isPackageModuleFound, mapPackageManagers, modifyJSON, modifyJSONFile, packageManagerConfigs, predefinedPathAliases, project, resolveModule, resolveModulePath, resolvePackageModulePath, storage, tempFileSystem, workspace };
|