flatlock 1.2.0 → 1.3.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.
Files changed (43) hide show
  1. package/README.md +42 -1
  2. package/bin/flatcover.js +398 -0
  3. package/bin/flatlock.js +158 -0
  4. package/package.json +16 -5
  5. package/src/parsers/index.js +14 -2
  6. package/src/parsers/npm.js +82 -0
  7. package/src/parsers/pnpm/index.js +70 -0
  8. package/src/parsers/yarn-berry.js +88 -0
  9. package/src/set.js +730 -41
  10. package/dist/compare.d.ts +0 -85
  11. package/dist/compare.d.ts.map +0 -1
  12. package/dist/detect.d.ts +0 -33
  13. package/dist/detect.d.ts.map +0 -1
  14. package/dist/index.d.ts +0 -72
  15. package/dist/index.d.ts.map +0 -1
  16. package/dist/parsers/index.d.ts +0 -5
  17. package/dist/parsers/index.d.ts.map +0 -1
  18. package/dist/parsers/npm.d.ts +0 -109
  19. package/dist/parsers/npm.d.ts.map +0 -1
  20. package/dist/parsers/pnpm/detect.d.ts +0 -136
  21. package/dist/parsers/pnpm/detect.d.ts.map +0 -1
  22. package/dist/parsers/pnpm/index.d.ts +0 -120
  23. package/dist/parsers/pnpm/index.d.ts.map +0 -1
  24. package/dist/parsers/pnpm/internal.d.ts +0 -5
  25. package/dist/parsers/pnpm/internal.d.ts.map +0 -1
  26. package/dist/parsers/pnpm/shrinkwrap.d.ts +0 -129
  27. package/dist/parsers/pnpm/shrinkwrap.d.ts.map +0 -1
  28. package/dist/parsers/pnpm/v5.d.ts +0 -139
  29. package/dist/parsers/pnpm/v5.d.ts.map +0 -1
  30. package/dist/parsers/pnpm/v6plus.d.ts +0 -212
  31. package/dist/parsers/pnpm/v6plus.d.ts.map +0 -1
  32. package/dist/parsers/pnpm.d.ts +0 -2
  33. package/dist/parsers/pnpm.d.ts.map +0 -1
  34. package/dist/parsers/types.d.ts +0 -23
  35. package/dist/parsers/types.d.ts.map +0 -1
  36. package/dist/parsers/yarn-berry.d.ts +0 -154
  37. package/dist/parsers/yarn-berry.d.ts.map +0 -1
  38. package/dist/parsers/yarn-classic.d.ts +0 -110
  39. package/dist/parsers/yarn-classic.d.ts.map +0 -1
  40. package/dist/result.d.ts +0 -12
  41. package/dist/result.d.ts.map +0 -1
  42. package/dist/set.d.ts +0 -189
  43. package/dist/set.d.ts.map +0 -1
package/dist/compare.d.ts DELETED
@@ -1,85 +0,0 @@
1
- /**
2
- * Compare flatlock output against established parser for a lockfile
3
- * @param {string} filepath - Path to lockfile
4
- * @param {CompareOptions} [options] - Options
5
- * @returns {Promise<ComparisonResult>}
6
- */
7
- export function compare(filepath: string, options?: CompareOptions): Promise<ComparisonResult>;
8
- /**
9
- * Compare multiple lockfiles
10
- * @param {string[]} filepaths - Paths to lockfiles
11
- * @param {CompareOptions} [options] - Options
12
- * @returns {AsyncGenerator<ComparisonResult & { filepath: string }>}
13
- */
14
- export function compareAll(filepaths: string[], options?: CompareOptions): AsyncGenerator<ComparisonResult & {
15
- filepath: string;
16
- }>;
17
- /**
18
- * Check which optional comparison parsers are available
19
- * @returns {Promise<{ arborist: boolean, cyclonedx: boolean, pnpmLockfileFs: boolean, yarnCore: boolean }>}
20
- */
21
- export function getAvailableParsers(): Promise<{
22
- arborist: boolean;
23
- cyclonedx: boolean;
24
- pnpmLockfileFs: boolean;
25
- yarnCore: boolean;
26
- }>;
27
- export type CompareOptions = {
28
- /**
29
- * - Temp directory for Arborist/CycloneDX (npm only)
30
- */
31
- tmpDir?: string;
32
- /**
33
- * - Workspace paths for CycloneDX (-w flag)
34
- */
35
- workspace?: string[];
36
- };
37
- export type ComparisonResult = {
38
- /**
39
- * - Lockfile type
40
- */
41
- type: string;
42
- /**
43
- * - Comparison source used (e.g., '@npmcli/arborist', '@cyclonedx/cyclonedx-npm')
44
- */
45
- source?: string;
46
- /**
47
- * - Whether flatlock and comparison have same cardinality
48
- */
49
- equinumerous: boolean | null;
50
- /**
51
- * - Number of packages found by flatlock
52
- */
53
- flatlockCount: number;
54
- /**
55
- * - Number of packages found by comparison parser
56
- */
57
- comparisonCount?: number;
58
- /**
59
- * - Number of workspace packages skipped
60
- */
61
- workspaceCount?: number;
62
- /**
63
- * - Packages only found by flatlock
64
- */
65
- onlyInFlatlock?: string[];
66
- /**
67
- * - Packages only found by comparison parser
68
- */
69
- onlyInComparison?: string[];
70
- };
71
- export type PackagesResult = {
72
- /**
73
- * - Set of package@version strings
74
- */
75
- packages: Set<string>;
76
- /**
77
- * - Number of workspace packages skipped
78
- */
79
- workspaceCount: number;
80
- /**
81
- * - Comparison source used
82
- */
83
- source: string;
84
- };
85
- //# sourceMappingURL=compare.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"compare.d.ts","sourceRoot":"","sources":["../src/compare.js"],"names":[],"mappings":"AAyhBA;;;;;GAKG;AACH,kCAJW,MAAM,YACN,cAAc,GACZ,OAAO,CAAC,gBAAgB,CAAC,CA8CrC;AAED;;;;;GAKG;AACH,sCAJW,MAAM,EAAE,YACR,cAAc,GACZ,cAAc,CAAC,gBAAgB,GAAG;IAAE,QAAQ,EAAE,MAAM,CAAA;CAAE,CAAC,CAMnE;AAED;;;GAGG;AACH,uCAFa,OAAO,CAAC;IAAE,QAAQ,EAAE,OAAO,CAAC;IAAC,SAAS,EAAE,OAAO,CAAC;IAAC,cAAc,EAAE,OAAO,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAA;CAAE,CAAC,CAgB1G;;;;;aAnhBa,MAAM;;;;gBACN,MAAM,EAAE;;;;;;UAKR,MAAM;;;;aACN,MAAM;;;;kBACN,OAAO,GAAG,IAAI;;;;mBACd,MAAM;;;;sBACN,MAAM;;;;qBACN,MAAM;;;;qBACN,MAAM,EAAE;;;;uBACR,MAAM,EAAE;;;;;;cAKR,GAAG,CAAC,MAAM,CAAC;;;;oBACX,MAAM;;;;YACN,MAAM"}
package/dist/detect.d.ts DELETED
@@ -1,33 +0,0 @@
1
- /**
2
- * Detect lockfile type from content and/or path
3
- *
4
- * Content is the primary signal - we actually parse the content to verify
5
- * it's a valid lockfile of the detected type. This prevents spoofing attacks
6
- * where malicious content contains detection markers in strings/comments.
7
- *
8
- * Path is only used as a fallback hint when content is not provided.
9
- *
10
- * @param {Object} options - Detection options
11
- * @param {string} [options.path] - Path to the lockfile (optional hint)
12
- * @param {string} [options.content] - Lockfile content (primary signal)
13
- * @returns {LockfileType}
14
- * @throws {Error} If unable to detect lockfile type
15
- */
16
- export function detectType({ path, content }?: {
17
- path?: string | undefined;
18
- content?: string | undefined;
19
- }): LockfileType;
20
- /**
21
- * @typedef {'npm' | 'pnpm' | 'yarn-classic' | 'yarn-berry'} LockfileType
22
- */
23
- /**
24
- * Lockfile type constants
25
- */
26
- export const Type: Readonly<{
27
- NPM: "npm";
28
- PNPM: "pnpm";
29
- YARN_CLASSIC: "yarn-classic";
30
- YARN_BERRY: "yarn-berry";
31
- }>;
32
- export type LockfileType = "npm" | "pnpm" | "yarn-classic" | "yarn-berry";
33
- //# sourceMappingURL=detect.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"detect.d.ts","sourceRoot":"","sources":["../src/detect.js"],"names":[],"mappings":"AA6FA;;;;;;;;;;;;;;GAcG;AACH,+CALG;IAAyB,IAAI;IACJ,OAAO;CAChC,GAAU,YAAY,CAgDxB;AArJD;;GAEG;AAEH;;GAEG;AACH;;;;;GAKG;2BAXU,KAAK,GAAG,MAAM,GAAG,cAAc,GAAG,YAAY"}
package/dist/index.d.ts DELETED
@@ -1,72 +0,0 @@
1
- /**
2
- * Parse lockfile from path (auto-detect type)
3
- * @param {string} path - Path to lockfile
4
- * @param {Object} [options] - Parser options
5
- * @returns {AsyncGenerator<Dependency>}
6
- */
7
- export function fromPath(path: string, options?: Object): AsyncGenerator<Dependency>;
8
- /**
9
- * Parse lockfile from string (auto-detect or use options.type)
10
- * @param {string} content - Lockfile content
11
- * @param {Object} [options] - Parser options
12
- * @param {string} [options.path] - Path hint for type detection
13
- * @param {LockfileType} [options.type] - Explicit type (skip detection)
14
- * @returns {Generator<Dependency>}
15
- */
16
- export function fromString(content: string, options?: {
17
- path?: string | undefined;
18
- type?: import("./detect.js").LockfileType | undefined;
19
- }): Generator<Dependency>;
20
- /**
21
- * Try to parse lockfile from path (returns Result)
22
- * @param {string} path - Path to lockfile
23
- * @param {ParseOptions} [options] - Parser options
24
- * @returns {Promise<import('./result.js').Result<AsyncGenerator<Dependency>>>}
25
- */
26
- export function tryFromPath(path: string, options?: ParseOptions): Promise<import("./result.js").Result<AsyncGenerator<Dependency>>>;
27
- /**
28
- * Try to parse lockfile from string (returns Result)
29
- * @param {string} content - Lockfile content
30
- * @param {ParseOptions} [options] - Parser options
31
- * @returns {import('./result.js').Result<Generator<Dependency>>}
32
- */
33
- export function tryFromString(content: string, options?: ParseOptions): import("./result.js").Result<Generator<Dependency>>;
34
- /**
35
- * Parse yarn.lock (auto-detect classic vs berry)
36
- * @param {string} content - Lockfile content
37
- * @param {Object} [options] - Parser options
38
- * @returns {Generator<Dependency>}
39
- */
40
- export function fromYarnLock(content: string, options?: Object): Generator<Dependency>;
41
- /**
42
- * Collect all dependencies into an array
43
- * @param {string} pathOrContent - Path to lockfile or content string
44
- * @param {Object} [options] - Parser options
45
- * @returns {Promise<Dependency[]>}
46
- */
47
- export function collect(pathOrContent: string, options?: Object): Promise<Dependency[]>;
48
- export type LockfileType = import("./detect.js").LockfileType;
49
- export type Dependency = import("./parsers/npm.js").Dependency;
50
- export type ParseOptions = {
51
- /**
52
- * - Path hint for type detection
53
- */
54
- path?: string;
55
- /**
56
- * - Explicit type (skip detection)
57
- */
58
- type?: LockfileType;
59
- };
60
- import { Type } from './detect.js';
61
- import { detectType } from './detect.js';
62
- import { Ok } from './result.js';
63
- import { Err } from './result.js';
64
- import { fromPackageLock } from './parsers/index.js';
65
- import { fromPnpmLock } from './parsers/index.js';
66
- import { fromYarnClassicLock } from './parsers/index.js';
67
- import { fromYarnBerryLock } from './parsers/index.js';
68
- import { FlatlockSet } from './set.js';
69
- export { Type, detectType, Ok, Err, fromPackageLock, fromPnpmLock, fromYarnClassicLock, fromYarnBerryLock, FlatlockSet };
70
- export { compare, compareAll, getAvailableParsers } from "./compare.js";
71
- export { parseNpmKey, parsePnpmKey, parseYarnBerryKey, parseYarnClassicKey } from "./parsers/index.js";
72
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.js"],"names":[],"mappings":"AAgCA;;;;;GAKG;AACH,+BAJW,MAAM,YACN,MAAM,GACJ,cAAc,CAAC,UAAU,CAAC,CAOtC;AAED;;;;;;;GAOG;AACH,oCANW,MAAM,YAEd;IAAyB,IAAI;IACE,IAAI;CACnC,GAAU,SAAS,CAAC,UAAU,CAAC,CA0BjC;AAED;;;;;GAKG;AACH,kCAJW,MAAM,YACN,YAAY,GACV,OAAO,CAAC,OAAO,aAAa,EAAE,MAAM,CAAC,cAAc,CAAC,UAAU,CAAC,CAAC,CAAC,CAS7E;AAED;;;;;GAKG;AACH,uCAJW,MAAM,YACN,YAAY,GACV,OAAO,aAAa,EAAE,MAAM,CAAC,SAAS,CAAC,UAAU,CAAC,CAAC,CAW/D;AAED;;;;;GAKG;AACH,sCAJW,MAAM,YACN,MAAM,GACJ,SAAS,CAAC,UAAU,CAAC,CAUjC;AAED;;;;;GAKG;AACH,uCAJW,MAAM,YACN,MAAM,GACJ,OAAO,CAAC,UAAU,EAAE,CAAC,CAmBjC;2BA3Ia,OAAO,aAAa,EAAE,YAAY;yBAClC,OAAO,kBAAkB,EAAE,UAAU;;;;;WAIrC,MAAM;;;;WACN,YAAY;;qBAhBO,aAAa;2BAAb,aAAa;mBAOtB,aAAa;oBAAb,aAAa;gCAD9B,oBAAoB;6BAApB,oBAAoB;oCAApB,oBAAoB;kCAApB,oBAAoB;4BAEC,UAAU"}
@@ -1,5 +0,0 @@
1
- export { fromPackageLock, parseLockfileKey as parseNpmKey } from "./npm.js";
2
- export { fromPnpmLock, parseLockfileKey as parsePnpmKey } from "./pnpm.js";
3
- export { fromYarnBerryLock, parseLockfileKey as parseYarnBerryKey, parseResolution as parseYarnBerryResolution } from "./yarn-berry.js";
4
- export { fromYarnClassicLock, parseLockfileKey as parseYarnClassicKey, parseYarnClassic } from "./yarn-classic.js";
5
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/parsers/index.js"],"names":[],"mappings":""}
@@ -1,109 +0,0 @@
1
- /** @typedef {import('./types.js').Dependency} Dependency */
2
- /**
3
- * LIMITATION: Workspace symlinks are not yielded
4
- *
5
- * npm workspaces create two entries in package-lock.json:
6
- * 1. packages/<workspace-path> → has version (workspace definition)
7
- * 2. node_modules/<pkg-name> → link:true, NO version (symlink to #1)
8
- *
9
- * Arborist resolves #2 to get version from #1. This parser does not.
10
- * Entries with link:true but no version are skipped.
11
- *
12
- * To include workspace packages, users should use @npmcli/arborist directly.
13
- */
14
- /**
15
- * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
16
- * !! WARNING: DO NOT MODIFY THIS FUNCTION !!
17
- * !! AI AGENTS (Claude, Copilot, etc.): DO NOT TOUCH THIS CODE !!
18
- * !! !!
19
- * !! This is PATH parsing, NOT spec parsing. It extracts package names from !!
20
- * !! filesystem paths like "node_modules/@scope/name", NOT from package !!
21
- * !! specs like "@scope/name@^1.0.0". !!
22
- * !! !!
23
- * !! npm-package-arg (npa) is for SPEC parsing. This is PATH parsing. !!
24
- * !! They are different things. Do not "improve" this with npa. !!
25
- * !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
26
- *
27
- * Extract package name from npm lockfile path.
28
- *
29
- * Paths in package-lock.json follow this grammar:
30
- * path := (node_modules/<pkg>)+
31
- * | <workspace>/<path>
32
- * | <workspace>/<path>/(node_modules/<pkg>)+
33
- *
34
- * pkg := name (unscoped)
35
- * | @scope/name (scoped)
36
- *
37
- * @param {string} path - Lockfile path key
38
- * @returns {string} Package name
39
- *
40
- * @example
41
- * // Simple unscoped package
42
- * parseLockfileKey('node_modules/lodash')
43
- * // => 'lodash'
44
- *
45
- * @example
46
- * // Scoped package
47
- * parseLockfileKey('node_modules/@babel/core')
48
- * // => '@babel/core'
49
- *
50
- * @example
51
- * // Nested dependency (hoisted conflict resolution)
52
- * parseLockfileKey('node_modules/foo/node_modules/bar')
53
- * // => 'bar'
54
- *
55
- * @example
56
- * // Nested scoped dependency
57
- * parseLockfileKey('node_modules/foo/node_modules/@scope/bar')
58
- * // => '@scope/bar'
59
- *
60
- * @example
61
- * // Deeply nested dependency
62
- * parseLockfileKey('node_modules/a/node_modules/b/node_modules/c')
63
- * // => 'c'
64
- *
65
- * @example
66
- * // Deeply nested scoped dependency
67
- * parseLockfileKey('node_modules/a/node_modules/@types/node')
68
- * // => '@types/node'
69
- *
70
- * @example
71
- * // Workspace package path (definition)
72
- * parseLockfileKey('packages/my-lib')
73
- * // => 'my-lib'
74
- *
75
- * @example
76
- * // Workspace nested dependency
77
- * parseLockfileKey('packages/my-lib/node_modules/lodash')
78
- * // => 'lodash'
79
- *
80
- * @example
81
- * // Workspace nested scoped dependency
82
- * parseLockfileKey('packages/my-lib/node_modules/@types/react')
83
- * // => '@types/react'
84
- *
85
- * @example
86
- * // Package with hyphenated name
87
- * parseLockfileKey('node_modules/string-width')
88
- * // => 'string-width'
89
- *
90
- * @example
91
- * // Scoped package with hyphenated name
92
- * parseLockfileKey('node_modules/@emotion/styled')
93
- * // => '@emotion/styled'
94
- *
95
- * @example
96
- * // Complex nested path
97
- * parseLockfileKey('node_modules/@babel/core/node_modules/@babel/helper-compilation-targets')
98
- * // => '@babel/helper-compilation-targets'
99
- */
100
- export function parseLockfileKey(path: string): string;
101
- /**
102
- * Parse npm package-lock.json (v1, v2, v3)
103
- * @param {string | object} input - Lockfile content string or pre-parsed object
104
- * @param {Object} [_options] - Parser options (unused, reserved for future use)
105
- * @returns {Generator<Dependency>}
106
- */
107
- export function fromPackageLock(input: string | object, _options?: Object): Generator<Dependency>;
108
- export type Dependency = import("./types.js").Dependency;
109
- //# sourceMappingURL=npm.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"npm.d.ts","sourceRoot":"","sources":["../../src/parsers/npm.js"],"names":[],"mappings":"AAAA,4DAA4D;AAE5D;;;;;;;;;;;GAWG;AAEH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqFG;AACH,uCA/DW,MAAM,GACJ,MAAM,CAoElB;AAED;;;;;GAKG;AACH,uCAJW,MAAM,GAAG,MAAM,aACf,MAAM,GACJ,SAAS,CAAC,UAAU,CAAC,CA6BjC;yBA9Ia,OAAO,YAAY,EAAE,UAAU"}
@@ -1,136 +0,0 @@
1
- /**
2
- * @fileoverview Version detection for pnpm lockfiles
3
- *
4
- * Detects the era and version of pnpm lockfiles including:
5
- * - shrinkwrap.yaml (v3/v4) from 2016-2019
6
- * - pnpm-lock.yaml v5.x (2019-2022)
7
- * - pnpm-lock.yaml v6.0 (2023)
8
- * - pnpm-lock.yaml v9.0 (2024+)
9
- *
10
- * @module flatlock/parsers/pnpm/detect
11
- */
12
- /**
13
- * @typedef {'shrinkwrap'|'v5'|'v5-inline'|'v6'|'v9'|'unknown'} LockfileEra
14
- */
15
- /**
16
- * @typedef {Object} DetectedVersion
17
- * @property {LockfileEra} era - The lockfile era/format family
18
- * @property {string|number} version - The raw version from the lockfile
19
- * @property {boolean} isShrinkwrap - True if this is a shrinkwrap.yaml file
20
- */
21
- /**
22
- * Detect the version and era of a pnpm lockfile.
23
- *
24
- * Version detection rules:
25
- * - If `shrinkwrapVersion` exists: shrinkwrap era (v3/v4)
26
- * - If `lockfileVersion` is a number: v5 era
27
- * - If `lockfileVersion` is '5.4-inlineSpecifiers': v5-inline era
28
- * - If `lockfileVersion` starts with '6': v6 era
29
- * - If `lockfileVersion` starts with '9': v9 era
30
- *
31
- * @param {Object} lockfile - Parsed pnpm lockfile object
32
- * @param {string|number} [lockfile.lockfileVersion] - The lockfile version field
33
- * @param {number} [lockfile.shrinkwrapVersion] - The shrinkwrap version field (v3/v4)
34
- * @param {number} [lockfile.shrinkwrapMinorVersion] - Minor version for shrinkwrap
35
- * @returns {DetectedVersion} The detected version information
36
- *
37
- * @example
38
- * // shrinkwrap.yaml v3
39
- * detectVersion({ shrinkwrapVersion: 3 })
40
- * // => { era: 'shrinkwrap', version: 3, isShrinkwrap: true }
41
- *
42
- * @example
43
- * // pnpm-lock.yaml v5.4
44
- * detectVersion({ lockfileVersion: 5.4 })
45
- * // => { era: 'v5', version: 5.4, isShrinkwrap: false }
46
- *
47
- * @example
48
- * // pnpm-lock.yaml v6.0
49
- * detectVersion({ lockfileVersion: '6.0' })
50
- * // => { era: 'v6', version: '6.0', isShrinkwrap: false }
51
- *
52
- * @example
53
- * // pnpm-lock.yaml v9.0
54
- * detectVersion({ lockfileVersion: '9.0' })
55
- * // => { era: 'v9', version: '9.0', isShrinkwrap: false }
56
- */
57
- export function detectVersion(lockfile: {
58
- lockfileVersion?: string | number | undefined;
59
- shrinkwrapVersion?: number | undefined;
60
- shrinkwrapMinorVersion?: number | undefined;
61
- }): DetectedVersion;
62
- /**
63
- * Check if a lockfile uses the v6+ package key format (name@version).
64
- *
65
- * v5 and earlier use: /name/version or /@scope/name/version
66
- * v6+ use: /name@version or /@scope/name@version
67
- * v9+ use: name@version (no leading slash)
68
- *
69
- * @param {DetectedVersion} detected - The detected version info
70
- * @returns {boolean} True if the lockfile uses @ separator for name@version
71
- *
72
- * @example
73
- * usesAtSeparator({ era: 'v5', version: 5.4 }) // => false
74
- * usesAtSeparator({ era: 'v6', version: '6.0' }) // => true
75
- * usesAtSeparator({ era: 'v9', version: '9.0' }) // => true
76
- */
77
- export function usesAtSeparator(detected: DetectedVersion): boolean;
78
- /**
79
- * Check if a lockfile uses the packages/snapshots split (v9+).
80
- *
81
- * v9 separates package metadata (packages) from dependency relationships (snapshots).
82
- *
83
- * @param {DetectedVersion} detected - The detected version info
84
- * @returns {boolean} True if the lockfile has packages/snapshots split
85
- *
86
- * @example
87
- * usesSnapshotsSplit({ era: 'v6', version: '6.0' }) // => false
88
- * usesSnapshotsSplit({ era: 'v9', version: '9.0' }) // => true
89
- */
90
- export function usesSnapshotsSplit(detected: DetectedVersion): boolean;
91
- /**
92
- * Check if a lockfile uses inline specifiers.
93
- *
94
- * v5.4-inlineSpecifiers and v6+ use inline specifiers in importers.
95
- * Earlier versions have a separate `specifiers` block.
96
- *
97
- * @param {DetectedVersion} detected - The detected version info
98
- * @returns {boolean} True if specifiers are inlined
99
- *
100
- * @example
101
- * usesInlineSpecifiers({ era: 'v5', version: 5.4 }) // => false
102
- * usesInlineSpecifiers({ era: 'v5-inline', version: '5.4-inlineSpecifiers' }) // => true
103
- * usesInlineSpecifiers({ era: 'v6', version: '6.0' }) // => true
104
- */
105
- export function usesInlineSpecifiers(detected: DetectedVersion): boolean;
106
- /**
107
- * Check if package keys have a leading slash.
108
- *
109
- * v5 and v6 use leading slash: /name/version or /name@version
110
- * v9 omits leading slash: name@version
111
- *
112
- * @param {DetectedVersion} detected - The detected version info
113
- * @returns {boolean} True if package keys have leading slash
114
- *
115
- * @example
116
- * hasLeadingSlash({ era: 'v5', version: 5.4 }) // => true
117
- * hasLeadingSlash({ era: 'v6', version: '6.0' }) // => true
118
- * hasLeadingSlash({ era: 'v9', version: '9.0' }) // => false
119
- */
120
- export function hasLeadingSlash(detected: DetectedVersion): boolean;
121
- export type LockfileEra = "shrinkwrap" | "v5" | "v5-inline" | "v6" | "v9" | "unknown";
122
- export type DetectedVersion = {
123
- /**
124
- * - The lockfile era/format family
125
- */
126
- era: LockfileEra;
127
- /**
128
- * - The raw version from the lockfile
129
- */
130
- version: string | number;
131
- /**
132
- * - True if this is a shrinkwrap.yaml file
133
- */
134
- isShrinkwrap: boolean;
135
- };
136
- //# sourceMappingURL=detect.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"detect.d.ts","sourceRoot":"","sources":["../../../src/parsers/pnpm/detect.js"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH;;GAEG;AAEH;;;;;GAKG;AAEH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmCG;AACH,wCAzBG;IAAiC,eAAe;IACtB,iBAAiB;IACjB,sBAAsB;CAChD,GAAU,eAAe,CAyF3B;AAED;;;;;;;;;;;;;;GAcG;AACH,0CARW,eAAe,GACb,OAAO,CASnB;AAED;;;;;;;;;;;GAWG;AACH,6CAPW,eAAe,GACb,OAAO,CAQnB;AAED;;;;;;;;;;;;;GAaG;AACH,+CARW,eAAe,GACb,OAAO,CASnB;AAED;;;;;;;;;;;;;GAaG;AACH,0CARW,eAAe,GACb,OAAO,CASnB;0BAxLY,YAAY,GAAC,IAAI,GAAC,WAAW,GAAC,IAAI,GAAC,IAAI,GAAC,SAAS;;;;;SAKhD,WAAW;;;;aACX,MAAM,GAAC,MAAM;;;;kBACb,OAAO"}
@@ -1,120 +0,0 @@
1
- /**
2
- * Parse pnpm package spec to extract name and version.
3
- *
4
- * This is the unified parser that auto-detects the format based on the spec pattern.
5
- * It supports all pnpm lockfile versions without requiring version context.
6
- *
7
- * Detection heuristics:
8
- * 1. If spec contains '(' -> v6+ format (peer deps in parentheses)
9
- * 2. If spec contains '@' after position 0 and no '/' after the '@' -> v6+ format
10
- * 3. Otherwise -> v5 or earlier format (slash separator)
11
- *
12
- * @param {string} spec - Package spec from pnpm lockfile
13
- * @returns {{ name: string | null, version: string | null }}
14
- *
15
- * @example
16
- * // v5 format - unscoped package
17
- * parseSpec('/lodash/4.17.21')
18
- * // => { name: 'lodash', version: '4.17.21' }
19
- *
20
- * @example
21
- * // v5 format - scoped package
22
- * parseSpec('/@babel/core/7.23.0')
23
- * // => { name: '@babel/core', version: '7.23.0' }
24
- *
25
- * @example
26
- * // v5 format - with peer dependency suffix (underscore)
27
- * parseSpec('/styled-jsx/3.0.9_react@17.0.2')
28
- * // => { name: 'styled-jsx', version: '3.0.9' }
29
- *
30
- * @example
31
- * // v6 format - unscoped package (with leading slash)
32
- * parseSpec('/lodash@4.17.21')
33
- * // => { name: 'lodash', version: '4.17.21' }
34
- *
35
- * @example
36
- * // v6 format - scoped package
37
- * parseSpec('/@babel/core@7.23.0')
38
- * // => { name: '@babel/core', version: '7.23.0' }
39
- *
40
- * @example
41
- * // v9 format - unscoped package (no leading slash)
42
- * parseSpec('lodash@4.17.21')
43
- * // => { name: 'lodash', version: '4.17.21' }
44
- *
45
- * @example
46
- * // v9 format - scoped package (no leading slash)
47
- * parseSpec('@babel/core@7.23.0')
48
- * // => { name: '@babel/core', version: '7.23.0' }
49
- *
50
- * @example
51
- * // v9 format - with peer dependency suffix (parentheses)
52
- * parseSpec('@babel/core@7.23.0(@types/node@20.0.0)')
53
- * // => { name: '@babel/core', version: '7.23.0' }
54
- *
55
- * @example
56
- * // v9 format - multiple peer dependencies
57
- * parseSpec('@testing-library/react@14.0.0(react-dom@18.2.0)(react@18.2.0)')
58
- * // => { name: '@testing-library/react', version: '14.0.0' }
59
- *
60
- * @example
61
- * // Shrinkwrap v3/v4 format - with peer suffix (slash)
62
- * parseSpec('/foo/1.0.0/bar@2.0.0')
63
- * // => { name: 'foo', version: '1.0.0' }
64
- *
65
- * @example
66
- * // link: protocol - skipped (returns null)
67
- * parseSpec('link:packages/my-pkg')
68
- * // => { name: null, version: null }
69
- *
70
- * @example
71
- * // file: protocol - skipped (returns null)
72
- * parseSpec('file:../local-package')
73
- * // => { name: null, version: null }
74
- *
75
- * @example
76
- * // Null input
77
- * parseSpec(null)
78
- * // => { name: null, version: null }
79
- *
80
- * @example
81
- * // Prerelease version
82
- * parseSpec('@verdaccio/ui-theme@6.0.0-6-next.50')
83
- * // => { name: '@verdaccio/ui-theme', version: '6.0.0-6-next.50' }
84
- */
85
- export function parseSpec(spec: string): {
86
- name: string | null;
87
- version: string | null;
88
- };
89
- /**
90
- * Extract package name from pnpm lockfile key.
91
- * Wraps parseSpec to return just the name (consistent with other parsers).
92
- *
93
- * @param {string} key - pnpm lockfile key
94
- * @returns {string | null} Package name
95
- *
96
- * @example
97
- * parseLockfileKey('/@babel/core@7.23.0') // => '@babel/core'
98
- * parseLockfileKey('/lodash/4.17.21') // => 'lodash'
99
- */
100
- export function parseLockfileKey(key: string): string | null;
101
- /**
102
- * Parse pnpm lockfile (shrinkwrap.yaml, pnpm-lock.yaml v5.x, v6, v9)
103
- *
104
- * @param {string | object} input - Lockfile content string or pre-parsed object
105
- * @param {Object} [_options] - Parser options (unused, reserved for future use)
106
- * @returns {Generator<Dependency>}
107
- *
108
- * @example
109
- * // Parse from string
110
- * const deps = [...fromPnpmLock(yamlContent)];
111
- *
112
- * @example
113
- * // Parse from pre-parsed object
114
- * const lockfile = yaml.load(content);
115
- * const deps = [...fromPnpmLock(lockfile)];
116
- */
117
- export function fromPnpmLock(input: string | object, _options?: Object): Generator<Dependency>;
118
- export { detectVersion } from "./detect.js";
119
- export type Dependency = import("../types.js").Dependency;
120
- //# sourceMappingURL=index.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/parsers/pnpm/index.js"],"names":[],"mappings":"AA2BA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAmFG;AACH,gCAzEW,MAAM,GACJ;IAAE,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAAA;CAAE,CA+H3D;AAED;;;;;;;;;;GAUG;AACH,sCAPW,MAAM,GACJ,MAAM,GAAG,IAAI,CAQzB;AAED;;;;;;;;;;;;;;;GAeG;AACH,oCAbW,MAAM,GAAG,MAAM,aACf,MAAM,GACJ,SAAS,CAAC,UAAU,CAAC,CAoGjC;;yBA5Qa,OAAO,aAAa,EAAE,UAAU"}
@@ -1,5 +0,0 @@
1
- export { detectVersion, hasLeadingSlash, usesAtSeparator, usesInlineSpecifiers, usesSnapshotsSplit } from "./detect.js";
2
- export { extractPeerSuffix, hasPeerSuffix, parseSpecShrinkwrap } from "./shrinkwrap.js";
3
- export { extractPeerSuffixV5, hasPeerSuffixV5, parseSpecV5 } from "./v5.js";
4
- export { extractPeerSuffixV6Plus, hasPeerSuffixV6Plus, parsePeerDependencies, parseSpecV6Plus } from "./v6plus.js";
5
- //# sourceMappingURL=internal.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"internal.d.ts","sourceRoot":"","sources":["../../../src/parsers/pnpm/internal.js"],"names":[],"mappings":""}