@component-compass/cli 0.0.2 → 0.0.4
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/cli.js +5 -1
- package/dist/cli.js.map +1 -1
- package/dist/commands/init.js +1 -3
- package/dist/commands/init.js.map +1 -1
- package/dist/commands/scan.d.ts +13 -1
- package/dist/commands/scan.js +192 -72
- package/dist/commands/scan.js.map +1 -1
- package/dist/composition-rollup.d.ts +16 -14
- package/dist/composition-rollup.js +33 -43
- package/dist/composition-rollup.js.map +1 -1
- package/dist/config/loader.js +5 -9
- package/dist/config/loader.js.map +1 -1
- package/dist/config/schema.d.ts +2 -15
- package/dist/config/schema.js.map +1 -1
- package/dist/envelope/index.d.ts +0 -9
- package/dist/envelope/index.js +1 -46
- package/dist/envelope/index.js.map +1 -1
- package/dist/identity.d.ts +19 -17
- package/dist/identity.js +42 -21
- package/dist/identity.js.map +1 -1
- package/dist/index.d.ts +2 -0
- package/dist/index.js +1 -0
- package/dist/index.js.map +1 -1
- package/dist/local-index/detect-react.d.ts +2 -1
- package/dist/local-index/detect-react.js +269 -72
- package/dist/local-index/detect-react.js.map +1 -1
- package/dist/local-index/detect-vue.d.ts +15 -1
- package/dist/local-index/detect-vue.js +130 -107
- package/dist/local-index/detect-vue.js.map +1 -1
- package/dist/local-index/detect-wc.d.ts +7 -1
- package/dist/local-index/detect-wc.js +56 -60
- package/dist/local-index/detect-wc.js.map +1 -1
- package/dist/local-index/index.d.ts +12 -4
- package/dist/local-index/index.js +40 -25
- package/dist/local-index/index.js.map +1 -1
- package/dist/manifest/barrel-parser.d.ts +10 -0
- package/dist/manifest/barrel-parser.js +11 -0
- package/dist/manifest/barrel-parser.js.map +1 -1
- package/dist/manifest/derived-manifest-stub.d.ts +16 -7
- package/dist/manifest/derived-manifest-stub.js +43 -7
- package/dist/manifest/derived-manifest-stub.js.map +1 -1
- package/dist/manifest/lazy-resolver.d.ts +52 -34
- package/dist/manifest/lazy-resolver.js +269 -69
- package/dist/manifest/lazy-resolver.js.map +1 -1
- package/dist/occurrences.d.ts +4 -4
- package/dist/occurrences.js +49 -9
- package/dist/occurrences.js.map +1 -1
- package/dist/parse-by-ext.d.ts +21 -0
- package/dist/parse-by-ext.js +53 -0
- package/dist/parse-by-ext.js.map +1 -0
- package/dist/reporter/index.d.ts +27 -28
- package/dist/reporter/index.js +99 -58
- package/dist/reporter/index.js.map +1 -1
- package/dist/reporter/stdout.js +4 -4
- package/dist/reporter/stdout.js.map +1 -1
- package/dist/rollup.d.ts +13 -6
- package/dist/rollup.js +9 -6
- package/dist/rollup.js.map +1 -1
- package/dist/scan/cem-index.d.ts +38 -0
- package/dist/scan/cem-index.js +139 -0
- package/dist/scan/cem-index.js.map +1 -0
- package/dist/scan/git-mtime.d.ts +2 -0
- package/dist/scan/git-mtime.js +22 -0
- package/dist/scan/git-mtime.js.map +1 -0
- package/dist/scan/meta.d.ts +5 -0
- package/dist/scan/meta.js +58 -0
- package/dist/scan/meta.js.map +1 -0
- package/dist/scan/stamp-deprecated.d.ts +16 -0
- package/dist/scan/stamp-deprecated.js +33 -0
- package/dist/scan/stamp-deprecated.js.map +1 -0
- package/dist/scan/stamp-version.d.ts +18 -0
- package/dist/scan/stamp-version.js +94 -0
- package/dist/scan/stamp-version.js.map +1 -0
- package/dist/seeds.d.ts +20 -19
- package/dist/seeds.js +136 -68
- package/dist/seeds.js.map +1 -1
- package/dist/types.d.ts +2 -5
- package/dist/util/git.d.ts +8 -0
- package/dist/util/git.js +73 -0
- package/dist/util/git.js.map +1 -1
- package/dist/util/progress.d.ts +21 -0
- package/dist/util/progress.js +54 -0
- package/dist/util/progress.js.map +1 -0
- package/dist/walker/files.d.ts +1 -0
- package/dist/walker/files.js +11 -5
- package/dist/walker/files.js.map +1 -1
- package/dist/workspace/build-graph.d.ts +2 -0
- package/dist/workspace/build-graph.js +117 -0
- package/dist/workspace/build-graph.js.map +1 -0
- package/dist/workspace/declared-deps.d.ts +5 -0
- package/dist/workspace/declared-deps.js +42 -0
- package/dist/workspace/declared-deps.js.map +1 -0
- package/dist/workspace/find-owning-package.d.ts +8 -0
- package/dist/workspace/find-owning-package.js +69 -0
- package/dist/workspace/find-owning-package.js.map +1 -0
- package/dist/workspace/index.d.ts +4 -0
- package/dist/workspace/index.js +4 -0
- package/dist/workspace/index.js.map +1 -0
- package/dist/workspace/types.d.ts +46 -0
- package/dist/workspace/types.js +13 -0
- package/dist/workspace/types.js.map +1 -0
- package/package.json +15 -7
- package/schema/config.schema.json +2 -24
- package/dist/config/tag-rules.d.ts +0 -2
- package/dist/config/tag-rules.js +0 -34
- package/dist/config/tag-rules.js.map +0 -1
- package/dist/local-index/walker.d.ts +0 -11
- package/dist/local-index/walker.js +0 -47
- package/dist/local-index/walker.js.map +0 -1
- package/dist/manifest/diagnostic-filter.d.ts +0 -12
- package/dist/manifest/diagnostic-filter.js +0 -23
- package/dist/manifest/diagnostic-filter.js.map +0 -1
package/dist/seeds.js
CHANGED
|
@@ -1,13 +1,12 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Builds per-component seeds from a resolver-emitted snapshot
|
|
3
|
-
* parser-emitted occurrences
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
* (that is merged separately during rollup).
|
|
2
|
+
* Builds per-component seeds from a resolver-emitted snapshot and
|
|
3
|
+
* parser-emitted occurrences. Seeds are the per-component input to
|
|
4
|
+
* `rollupOccurrencesToComponents`: they carry identity and manifest enrichment
|
|
5
|
+
* but no occurrence data (that is merged separately during rollup).
|
|
7
6
|
*
|
|
8
7
|
* Pure function; no I/O.
|
|
9
8
|
*/
|
|
10
|
-
import {
|
|
9
|
+
import { relative, isAbsolute } from "node:path";
|
|
11
10
|
import { manifestComponentToOutput } from "./reporter/index.js";
|
|
12
11
|
import { computeOutputIdentity, computeStableId, computeStableIdFromComponentId, } from "./identity.js";
|
|
13
12
|
/**
|
|
@@ -15,61 +14,152 @@ import { computeOutputIdentity, computeStableId, computeStableIdFromComponentId,
|
|
|
15
14
|
* ComponentSeeds.
|
|
16
15
|
*
|
|
17
16
|
* Two sources contribute:
|
|
18
|
-
* 1.
|
|
19
|
-
*
|
|
20
|
-
* 2.
|
|
21
|
-
*
|
|
22
|
-
*
|
|
17
|
+
* 1. Components observed in parser walks — carry `modulePath` from the
|
|
18
|
+
* resolver and surface with `manifest: null` initially.
|
|
19
|
+
* 2. Snapshotted components — full enrichment via `manifestComponentToOutput`,
|
|
20
|
+
* labelled with the snapshot entry's `enrichmentSource`. Snapshot entries
|
|
21
|
+
* have NO `modulePath` (manifests don't carry that info), so their stable
|
|
22
|
+
* id differs from the parser-emitted seed for the same logical component.
|
|
23
|
+
* To avoid emitting a ghost component, we attach the snapshot's manifest
|
|
24
|
+
* enrichment to a matching parser-emitted seed when the match is
|
|
25
|
+
* unambiguous (exactly one parser seed with `{kind, packageName,
|
|
26
|
+
* exportName-or-tagName}`). Ambiguous matches fall through to a
|
|
27
|
+
* snapshot-only seed.
|
|
23
28
|
*
|
|
24
|
-
*
|
|
25
|
-
*
|
|
26
|
-
* Scope derivation follows the three-lane model in identity.ts:
|
|
27
|
-
* - local → source.type === "local"
|
|
28
|
-
* - ds → external + derivedTags.length > 0
|
|
29
|
-
* - external → external + no matching tag rules
|
|
29
|
+
* Scope derivation: "local" for source.type === "local"; "external" otherwise.
|
|
30
|
+
* DS-grouping is the web app's responsibility — CC emits two scopes only.
|
|
30
31
|
*/
|
|
31
|
-
export function buildComponentSeeds(snapshot, parseResults,
|
|
32
|
+
export function buildComponentSeeds(snapshot, parseResults, localIndex, repoRoot, workspaceGraph) {
|
|
32
33
|
const seedsById = new Map();
|
|
33
|
-
// 1.
|
|
34
|
+
// 1. Parser-emitted components first. These carry `modulePath` for
|
|
35
|
+
// resolver-driven externals and are the ones occurrences hash against.
|
|
36
|
+
for (const result of parseResults) {
|
|
37
|
+
for (const occ of result.occurrences) {
|
|
38
|
+
// Normalise local filePaths: parsers emit absolute paths; the local index
|
|
39
|
+
// uses repo-root-relative POSIX paths. Relativise here so the stable id
|
|
40
|
+
// matches the one produced for seeds built from the local index.
|
|
41
|
+
const componentId = repoRoot && occ.componentId.source.type === "local" && isAbsolute(occ.componentId.source.filePath)
|
|
42
|
+
? {
|
|
43
|
+
...occ.componentId,
|
|
44
|
+
source: {
|
|
45
|
+
type: "local",
|
|
46
|
+
filePath: relative(repoRoot, occ.componentId.source.filePath).replace(/\\/g, "/"),
|
|
47
|
+
},
|
|
48
|
+
}
|
|
49
|
+
: occ.componentId;
|
|
50
|
+
const id = computeStableIdFromComponentId(componentId);
|
|
51
|
+
if (seedsById.has(id))
|
|
52
|
+
continue;
|
|
53
|
+
const isLocal = componentId.source.type === "local";
|
|
54
|
+
let definitionLoc;
|
|
55
|
+
if (isLocal && localIndex) {
|
|
56
|
+
let match;
|
|
57
|
+
if (componentId.kind === "custom-element") {
|
|
58
|
+
match = localIndex.byTag.get(componentId.tagName);
|
|
59
|
+
}
|
|
60
|
+
else {
|
|
61
|
+
const path = componentId.source.type === "local" ? componentId.source.filePath : "";
|
|
62
|
+
const defs = localIndex.byPath.get(path) ?? [];
|
|
63
|
+
const exportName = componentId.export;
|
|
64
|
+
match = defs.find((d) => d.exportName === exportName);
|
|
65
|
+
}
|
|
66
|
+
if (match?.loc) {
|
|
67
|
+
definitionLoc = { line: match.loc.line, column: match.loc.column };
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
const identity = computeOutputIdentity({
|
|
71
|
+
componentId,
|
|
72
|
+
repoId: "",
|
|
73
|
+
...(workspaceGraph !== undefined ? { workspaceGraph } : {}),
|
|
74
|
+
...(definitionLoc !== undefined ? { definitionLoc } : {}),
|
|
75
|
+
});
|
|
76
|
+
seedsById.set(id, { id, identity, manifest: null, deprecated: false });
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
// 2. Snapshotted components. Snapshot entries lack `modulePath`, so their
|
|
80
|
+
// stable id won't collide with the parser-emitted seed even when they
|
|
81
|
+
// describe the same logical component. Instead of hashing, look up by
|
|
82
|
+
// `{kind, packageName, exportName-or-tagName}` and attach the manifest
|
|
83
|
+
// enrichment to that parser seed. Only merge when exactly one parser
|
|
84
|
+
// seed matches — multiple matches (e.g. two subpaths both exporting
|
|
85
|
+
// `default`) are ambiguous, so fall through to a snapshot-only seed.
|
|
34
86
|
for (const entry of snapshot) {
|
|
35
87
|
const componentId = indexedToComponentId(entry.component);
|
|
36
|
-
const
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
88
|
+
const manifest = manifestComponentToOutput(entry.component, entry.enrichmentSource);
|
|
89
|
+
const mergeTarget = findUnambiguousMergeTarget(seedsById, componentId);
|
|
90
|
+
if (mergeTarget !== null) {
|
|
91
|
+
mergeTarget.manifest = manifest;
|
|
92
|
+
mergeTarget.deprecated = false;
|
|
93
|
+
continue;
|
|
94
|
+
}
|
|
41
95
|
const identity = computeOutputIdentity({
|
|
42
96
|
componentId,
|
|
43
|
-
via,
|
|
44
|
-
derivedTags,
|
|
45
97
|
repoId: "",
|
|
98
|
+
...(workspaceGraph !== undefined ? { workspaceGraph } : {}),
|
|
46
99
|
});
|
|
47
100
|
const id = computeStableId(identity);
|
|
48
|
-
|
|
49
|
-
|
|
101
|
+
if (seedsById.has(id))
|
|
102
|
+
continue;
|
|
103
|
+
seedsById.set(id, { id, identity, manifest, deprecated: false });
|
|
50
104
|
}
|
|
51
|
-
//
|
|
52
|
-
//
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
105
|
+
// 3. Local definitions that were never referenced in any occurrence.
|
|
106
|
+
// These must still appear in components[] so they can serve as
|
|
107
|
+
// owner-edge targets in the composition graph.
|
|
108
|
+
if (localIndex) {
|
|
109
|
+
for (const [, defs] of localIndex.byPath) {
|
|
110
|
+
for (const def of defs) {
|
|
111
|
+
const id = computeStableIdFromComponentId(def.componentId);
|
|
112
|
+
if (seedsById.has(id))
|
|
113
|
+
continue;
|
|
114
|
+
const definitionLoc = def.loc !== undefined
|
|
115
|
+
? { line: def.loc.line, column: def.loc.column }
|
|
116
|
+
: undefined;
|
|
117
|
+
const identity = computeOutputIdentity({
|
|
118
|
+
componentId: def.componentId,
|
|
119
|
+
repoId: "",
|
|
120
|
+
...(workspaceGraph !== undefined ? { workspaceGraph } : {}),
|
|
121
|
+
...(definitionLoc !== undefined ? { definitionLoc } : {}),
|
|
122
|
+
});
|
|
123
|
+
seedsById.set(id, { id, identity, manifest: null, deprecated: false });
|
|
124
|
+
}
|
|
69
125
|
}
|
|
70
126
|
}
|
|
71
127
|
return [...seedsById.values()];
|
|
72
128
|
}
|
|
129
|
+
/**
|
|
130
|
+
* Find a parser-emitted seed whose logical identity matches the snapshot's
|
|
131
|
+
* `ComponentId`, ignoring `modulePath` (snapshot entries don't carry it).
|
|
132
|
+
*
|
|
133
|
+
* The match is intentionally narrowed to **unambiguous** cases: if two or more
|
|
134
|
+
* parser seeds share the same `{kind, packageName, exportName/tagName}` (e.g.
|
|
135
|
+
* two subpaths of one package both exporting `default`), we cannot safely pick
|
|
136
|
+
* one to enrich, so we return null and let the caller fall through to a
|
|
137
|
+
* snapshot-only seed.
|
|
138
|
+
*/
|
|
139
|
+
function findUnambiguousMergeTarget(seeds, candidate) {
|
|
140
|
+
if (candidate.source.type !== "external")
|
|
141
|
+
return null;
|
|
142
|
+
const candidatePackage = candidate.source.package;
|
|
143
|
+
let match = null;
|
|
144
|
+
for (const seed of seeds.values()) {
|
|
145
|
+
if (seed.identity.kind !== candidate.kind)
|
|
146
|
+
continue;
|
|
147
|
+
if (seed.identity.packageName !== candidatePackage)
|
|
148
|
+
continue;
|
|
149
|
+
if (candidate.kind === "custom-element") {
|
|
150
|
+
if (seed.identity.tagName !== candidate.tagName)
|
|
151
|
+
continue;
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
if (seed.identity.exportName !== candidate.export)
|
|
155
|
+
continue;
|
|
156
|
+
}
|
|
157
|
+
if (match !== null)
|
|
158
|
+
return null; // ambiguous — bail out
|
|
159
|
+
match = seed;
|
|
160
|
+
}
|
|
161
|
+
return match;
|
|
162
|
+
}
|
|
73
163
|
/**
|
|
74
164
|
* Convert an `IndexedComponent` to a `ComponentId` for use with
|
|
75
165
|
* `computeOutputIdentity`. `IndexedComponent` extends `ManifestComponent`
|
|
@@ -89,26 +179,4 @@ function indexedToComponentId(c) {
|
|
|
89
179
|
source: c.source,
|
|
90
180
|
};
|
|
91
181
|
}
|
|
92
|
-
/**
|
|
93
|
-
* Infer a default `via` for a snapshotted seed based on component kind.
|
|
94
|
-
* Only `via.kind` is consumed by `computeOutputIdentity`; the required
|
|
95
|
-
* `specifier`/`import` fields on `direct-import` are not meaningful for
|
|
96
|
-
* zero-occurrence seeds and are left as empty strings.
|
|
97
|
-
*/
|
|
98
|
-
function defaultVia(c) {
|
|
99
|
-
if (c.kind === "custom-element") {
|
|
100
|
-
return { kind: "html-tag" };
|
|
101
|
-
}
|
|
102
|
-
return { kind: "direct-import", specifier: "", import: "" };
|
|
103
|
-
}
|
|
104
|
-
/**
|
|
105
|
-
* Infer a default `via` for an occurrence-observed seed based on the
|
|
106
|
-
* component's kind. Used when seeding a component that has no snapshot entry.
|
|
107
|
-
*/
|
|
108
|
-
function defaultViaForKind(c) {
|
|
109
|
-
if (c.kind === "custom-element") {
|
|
110
|
-
return { kind: "html-tag" };
|
|
111
|
-
}
|
|
112
|
-
return { kind: "direct-import", specifier: "", import: "" };
|
|
113
|
-
}
|
|
114
182
|
//# sourceMappingURL=seeds.js.map
|
package/dist/seeds.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"seeds.js","sourceRoot":"","sources":["../src/seeds.ts"],"names":[],"mappings":"AAAA
|
|
1
|
+
{"version":3,"file":"seeds.js","sourceRoot":"","sources":["../src/seeds.ts"],"names":[],"mappings":"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"}
|
package/dist/types.d.ts
CHANGED
|
@@ -1,16 +1,13 @@
|
|
|
1
1
|
export type { Loc, WarningCode, Warning } from "@component-compass/plugin-core";
|
|
2
|
-
export type { TagRule } from "./config/schema.js";
|
|
3
|
-
import type { TagRule } from "./config/schema.js";
|
|
4
2
|
export type ResolvedConfig = {
|
|
5
3
|
configPath: string;
|
|
6
4
|
configDir: string;
|
|
7
|
-
repoId
|
|
8
|
-
packageScopes: string[];
|
|
5
|
+
repoId?: string;
|
|
9
6
|
include: string[];
|
|
10
7
|
exclude: string[];
|
|
11
8
|
captureValues: boolean;
|
|
12
9
|
output: string;
|
|
10
|
+
gitignore: boolean;
|
|
13
11
|
tsconfigPath?: string;
|
|
14
12
|
aliases?: Record<string, string[]>;
|
|
15
|
-
tagRules?: TagRule[];
|
|
16
13
|
};
|
package/dist/util/git.d.ts
CHANGED
|
@@ -1 +1,9 @@
|
|
|
1
|
+
export type MTimeRange = {
|
|
2
|
+
firstCommitAt: string;
|
|
3
|
+
lastCommitAt: string;
|
|
4
|
+
};
|
|
5
|
+
export declare function readFileMTimes(root: string, paths: string[]): Promise<Map<string, MTimeRange>>;
|
|
1
6
|
export declare function readGitCommit(root: string): Promise<string | undefined>;
|
|
7
|
+
export declare function readInitialCommit(root: string): Promise<string | undefined>;
|
|
8
|
+
export declare function readGitRemote(root: string): Promise<string | null>;
|
|
9
|
+
export declare function readGitBranch(root: string): Promise<string | null>;
|
package/dist/util/git.js
CHANGED
|
@@ -1,6 +1,50 @@
|
|
|
1
1
|
import { execFile } from "node:child_process";
|
|
2
2
|
import { promisify } from "node:util";
|
|
3
3
|
const exec = promisify(execFile);
|
|
4
|
+
export async function readFileMTimes(root, paths) {
|
|
5
|
+
if (paths.length === 0)
|
|
6
|
+
return new Map();
|
|
7
|
+
const out = new Map();
|
|
8
|
+
// git log --reverse interleaves commits oldest-first. Marker line precedes
|
|
9
|
+
// each commit's file list. Walk linearly: track currentDate, then bucket
|
|
10
|
+
// each named path into first (set once) / last (overwrite each commit).
|
|
11
|
+
// Known fidelity gaps: shallow clones cap firstCommitAt at the depth boundary;
|
|
12
|
+
// renames without --follow stop at the rename. Both documented in the spec.
|
|
13
|
+
try {
|
|
14
|
+
const args = [
|
|
15
|
+
"-c",
|
|
16
|
+
"core.quotePath=false",
|
|
17
|
+
"log",
|
|
18
|
+
"--reverse",
|
|
19
|
+
"--name-only",
|
|
20
|
+
"--format=__CC_COMMIT__ %aI",
|
|
21
|
+
"--",
|
|
22
|
+
...paths,
|
|
23
|
+
];
|
|
24
|
+
const { stdout } = await exec("git", args, {
|
|
25
|
+
cwd: root,
|
|
26
|
+
maxBuffer: 64 * 1024 * 1024,
|
|
27
|
+
});
|
|
28
|
+
let currentDate = null;
|
|
29
|
+
for (const line of stdout.split("\n")) {
|
|
30
|
+
if (line.startsWith("__CC_COMMIT__ ")) {
|
|
31
|
+
currentDate = line.slice("__CC_COMMIT__ ".length).trim();
|
|
32
|
+
}
|
|
33
|
+
else if (line.trim() && currentDate) {
|
|
34
|
+
const p = line.trim();
|
|
35
|
+
const existing = out.get(p);
|
|
36
|
+
if (existing)
|
|
37
|
+
existing.lastCommitAt = currentDate;
|
|
38
|
+
else
|
|
39
|
+
out.set(p, { firstCommitAt: currentDate, lastCommitAt: currentDate });
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
catch {
|
|
44
|
+
// git failure or buffer overflow — return whatever's accumulated (or empty).
|
|
45
|
+
}
|
|
46
|
+
return out;
|
|
47
|
+
}
|
|
4
48
|
export async function readGitCommit(root) {
|
|
5
49
|
try {
|
|
6
50
|
const { stdout } = await exec("git", ["rev-parse", "HEAD"], { cwd: root });
|
|
@@ -10,4 +54,33 @@ export async function readGitCommit(root) {
|
|
|
10
54
|
return undefined;
|
|
11
55
|
}
|
|
12
56
|
}
|
|
57
|
+
export async function readInitialCommit(root) {
|
|
58
|
+
try {
|
|
59
|
+
const { stdout } = await exec("git", ["rev-list", "--max-parents=0", "HEAD"], { cwd: root });
|
|
60
|
+
return stdout.trim().split("\n")[0];
|
|
61
|
+
}
|
|
62
|
+
catch {
|
|
63
|
+
return undefined;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
export async function readGitRemote(root) {
|
|
67
|
+
try {
|
|
68
|
+
const { stdout } = await exec("git", ["config", "--get", "remote.origin.url"], { cwd: root });
|
|
69
|
+
return stdout.trim() || null;
|
|
70
|
+
}
|
|
71
|
+
catch {
|
|
72
|
+
return null;
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
export async function readGitBranch(root) {
|
|
76
|
+
try {
|
|
77
|
+
const { stdout } = await exec("git", ["rev-parse", "--abbrev-ref", "HEAD"], { cwd: root });
|
|
78
|
+
const branch = stdout.trim();
|
|
79
|
+
// "HEAD" means detached HEAD state — not a named branch.
|
|
80
|
+
return branch === "HEAD" ? null : branch || null;
|
|
81
|
+
}
|
|
82
|
+
catch {
|
|
83
|
+
return null;
|
|
84
|
+
}
|
|
85
|
+
}
|
|
13
86
|
//# sourceMappingURL=git.js.map
|
package/dist/util/git.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"git.js","sourceRoot":"","sources":["../../src/util/git.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,QAAQ,EAAE,MAAM,oBAAoB,CAAC;AAC9C,OAAO,EAAE,SAAS,EAAE,MAAM,WAAW,CAAC;AAEtC,MAAM,IAAI,GAAG,SAAS,CAAC,QAAQ,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"git.js","sourceRoot":"","sources":["../../src/util/git.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Rate-limited progress reporter for the scan loop. Emits a single line on
|
|
3
|
+
* stderr — rewriting in place when stderr is a TTY, appending one line per
|
|
4
|
+
* tick otherwise (CI logs).
|
|
5
|
+
*
|
|
6
|
+
* Rate limit: emit when either ≥50 ticks have happened since the last emit
|
|
7
|
+
* OR ≥250ms have elapsed. Tuned so the line moves smoothly on TTYs without
|
|
8
|
+
* spamming non-TTY logs.
|
|
9
|
+
*/
|
|
10
|
+
export type ProgressOptions = {
|
|
11
|
+
total: number;
|
|
12
|
+
writer: (s: string) => void;
|
|
13
|
+
isTTY: boolean;
|
|
14
|
+
/** Verb prefix in the rendered line (default: "Scanned"). */
|
|
15
|
+
label?: string;
|
|
16
|
+
};
|
|
17
|
+
export type Progress = {
|
|
18
|
+
tick(): void;
|
|
19
|
+
done(): void;
|
|
20
|
+
};
|
|
21
|
+
export declare function createProgress(opts: ProgressOptions): Progress;
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Rate-limited progress reporter for the scan loop. Emits a single line on
|
|
3
|
+
* stderr — rewriting in place when stderr is a TTY, appending one line per
|
|
4
|
+
* tick otherwise (CI logs).
|
|
5
|
+
*
|
|
6
|
+
* Rate limit: emit when either ≥50 ticks have happened since the last emit
|
|
7
|
+
* OR ≥250ms have elapsed. Tuned so the line moves smoothly on TTYs without
|
|
8
|
+
* spamming non-TTY logs.
|
|
9
|
+
*/
|
|
10
|
+
const COUNT_THRESHOLD = 50;
|
|
11
|
+
const TIME_THRESHOLD_MS = 250;
|
|
12
|
+
export function createProgress(opts) {
|
|
13
|
+
const start = Date.now();
|
|
14
|
+
let processed = 0;
|
|
15
|
+
let lastEmitCount = -1; // forces emission on the first tick
|
|
16
|
+
let lastEmitTime = 0;
|
|
17
|
+
const label = opts.label ?? "Scanned";
|
|
18
|
+
function emit() {
|
|
19
|
+
const pct = opts.total > 0 ? ((processed / opts.total) * 100).toFixed(1) : "0.0";
|
|
20
|
+
const elapsedS = ((Date.now() - start) / 1000).toFixed(1);
|
|
21
|
+
const body = `${label} ${processed} / ${opts.total} files (${pct}%) — ${elapsedS}s elapsed`;
|
|
22
|
+
if (opts.isTTY) {
|
|
23
|
+
opts.writer(`\r${body}\x1b[K`);
|
|
24
|
+
}
|
|
25
|
+
else {
|
|
26
|
+
opts.writer(`${body}\n`);
|
|
27
|
+
}
|
|
28
|
+
lastEmitCount = processed;
|
|
29
|
+
lastEmitTime = Date.now();
|
|
30
|
+
}
|
|
31
|
+
return {
|
|
32
|
+
tick() {
|
|
33
|
+
processed += 1;
|
|
34
|
+
// sinceEmit counts the current tick, so the COUNT_THRESHOLDth tick since
|
|
35
|
+
// the last emit fires this branch (e.g. with threshold 50: emit at the
|
|
36
|
+
// 1st tick, then at the 50th, 99th, …). Always emit on the final tick
|
|
37
|
+
// so the bar shows 100% before the next phase starts.
|
|
38
|
+
const sinceEmit = processed - lastEmitCount;
|
|
39
|
+
const elapsedSinceEmit = Date.now() - lastEmitTime;
|
|
40
|
+
if (lastEmitCount === -1 ||
|
|
41
|
+
sinceEmit >= COUNT_THRESHOLD - 1 ||
|
|
42
|
+
elapsedSinceEmit >= TIME_THRESHOLD_MS ||
|
|
43
|
+
processed === opts.total) {
|
|
44
|
+
emit();
|
|
45
|
+
}
|
|
46
|
+
},
|
|
47
|
+
done() {
|
|
48
|
+
if (opts.isTTY && lastEmitCount > 0) {
|
|
49
|
+
opts.writer("\r\x1b[K");
|
|
50
|
+
}
|
|
51
|
+
},
|
|
52
|
+
};
|
|
53
|
+
}
|
|
54
|
+
//# sourceMappingURL=progress.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"progress.js","sourceRoot":"","sources":["../../src/util/progress.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAeH,MAAM,eAAe,GAAG,EAAE,CAAC;AAC3B,MAAM,iBAAiB,GAAG,GAAG,CAAC;AAE9B,MAAM,UAAU,cAAc,CAAC,IAAqB;IAClD,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IACzB,IAAI,SAAS,GAAG,CAAC,CAAC;IAClB,IAAI,aAAa,GAAG,CAAC,CAAC,CAAC,CAAC,oCAAoC;IAC5D,IAAI,YAAY,GAAG,CAAC,CAAC;IAErB,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,IAAI,SAAS,CAAC;IAEtC,SAAS,IAAI;QACX,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,SAAS,GAAG,IAAI,CAAC,KAAK,CAAC,GAAG,GAAG,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;QACjF,MAAM,QAAQ,GAAG,CAAC,CAAC,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,CAAC,GAAG,IAAI,CAAC,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC;QAC1D,MAAM,IAAI,GAAG,GAAG,KAAK,IAAI,SAAS,MAAM,IAAI,CAAC,KAAK,WAAW,GAAG,QAAQ,QAAQ,WAAW,CAAC;QAC5F,IAAI,IAAI,CAAC,KAAK,EAAE,CAAC;YACf,IAAI,CAAC,MAAM,CAAC,KAAK,IAAI,QAAQ,CAAC,CAAC;QACjC,CAAC;aAAM,CAAC;YACN,IAAI,CAAC,MAAM,CAAC,GAAG,IAAI,IAAI,CAAC,CAAC;QAC3B,CAAC;QACD,aAAa,GAAG,SAAS,CAAC;QAC1B,YAAY,GAAG,IAAI,CAAC,GAAG,EAAE,CAAC;IAC5B,CAAC;IAED,OAAO;QACL,IAAI;YACF,SAAS,IAAI,CAAC,CAAC;YACf,yEAAyE;YACzE,uEAAuE;YACvE,sEAAsE;YACtE,sDAAsD;YACtD,MAAM,SAAS,GAAG,SAAS,GAAG,aAAa,CAAC;YAC5C,MAAM,gBAAgB,GAAG,IAAI,CAAC,GAAG,EAAE,GAAG,YAAY,CAAC;YACnD,IACE,aAAa,KAAK,CAAC,CAAC;gBACpB,SAAS,IAAI,eAAe,GAAG,CAAC;gBAChC,gBAAgB,IAAI,iBAAiB;gBACrC,SAAS,KAAK,IAAI,CAAC,KAAK,EACxB,CAAC;gBACD,IAAI,EAAE,CAAC;YACT,CAAC;QACH,CAAC;QACD,IAAI;YACF,IAAI,IAAI,CAAC,KAAK,IAAI,aAAa,GAAG,CAAC,EAAE,CAAC;gBACpC,IAAI,CAAC,MAAM,CAAC,UAAU,CAAC,CAAC;YAC1B,CAAC;QACH,CAAC;KACF,CAAC;AACJ,CAAC"}
|
package/dist/walker/files.d.ts
CHANGED
package/dist/walker/files.js
CHANGED
|
@@ -1,12 +1,18 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { globby } from "globby";
|
|
2
2
|
export async function walkFiles(opts) {
|
|
3
|
-
|
|
3
|
+
// `dot: false` skips `.next/`, `.nuxt/`, `.turbo/`, etc. unless the user
|
|
4
|
+
// explicitly globs them in. `gitignore: true` is the default at the config
|
|
5
|
+
// layer; the explicit knob exists so users can opt out for WIP scans of
|
|
6
|
+
// untracked work. `suppressErrors` silences EACCES on unreadable dirs
|
|
7
|
+
// (vendored fixtures, transient OS turds) — the walker keeps going.
|
|
8
|
+
return globby(opts.include, {
|
|
4
9
|
cwd: opts.root,
|
|
5
|
-
nodir: true,
|
|
6
|
-
absolute: true,
|
|
7
10
|
ignore: opts.exclude,
|
|
11
|
+
gitignore: opts.gitignore,
|
|
8
12
|
dot: false,
|
|
13
|
+
absolute: true,
|
|
14
|
+
onlyFiles: true,
|
|
15
|
+
suppressErrors: true,
|
|
9
16
|
});
|
|
10
|
-
return matched;
|
|
11
17
|
}
|
|
12
18
|
//# sourceMappingURL=files.js.map
|
package/dist/walker/files.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"files.js","sourceRoot":"","sources":["../../src/walker/files.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,
|
|
1
|
+
{"version":3,"file":"files.js","sourceRoot":"","sources":["../../src/walker/files.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAC;AAShC,MAAM,CAAC,KAAK,UAAU,SAAS,CAAC,IAAiB;IAC/C,yEAAyE;IACzE,2EAA2E;IAC3E,wEAAwE;IACxE,sEAAsE;IACtE,oEAAoE;IACpE,OAAO,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE;QAC1B,GAAG,EAAE,IAAI,CAAC,IAAI;QACd,MAAM,EAAE,IAAI,CAAC,OAAO;QACpB,SAAS,EAAE,IAAI,CAAC,SAAS;QACzB,GAAG,EAAE,KAAK;QACV,QAAQ,EAAE,IAAI;QACd,SAAS,EAAE,IAAI;QACf,cAAc,EAAE,IAAI;KACrB,CAAC,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Build a workspace graph from a repository root.
|
|
3
|
+
*
|
|
4
|
+
* Two independent steps:
|
|
5
|
+
* - sniffPackageManager: lockfile-based; sets graph.packageManager. Always
|
|
6
|
+
* runs; returns "unknown" when no lockfile is found.
|
|
7
|
+
* - detectWorkspacePackages: pnpm-workspace.yaml → package.json#workspaces →
|
|
8
|
+
* empty array. Independent of step 1.
|
|
9
|
+
*
|
|
10
|
+
* Glob expansion uses globby (already a CLI dep).
|
|
11
|
+
* Pure; no I/O beyond config-file reads.
|
|
12
|
+
*/
|
|
13
|
+
import { existsSync, readFileSync } from "node:fs";
|
|
14
|
+
import { join, resolve } from "node:path";
|
|
15
|
+
import { globbySync } from "globby";
|
|
16
|
+
import * as yaml from "js-yaml";
|
|
17
|
+
export function buildWorkspaceGraph(rootPath) {
|
|
18
|
+
const absRoot = resolve(rootPath);
|
|
19
|
+
const rootPkgJsonPath = join(absRoot, "package.json");
|
|
20
|
+
const rootPkg = readJsonSafely(rootPkgJsonPath) ?? {};
|
|
21
|
+
const rootPackageName = typeof rootPkg.name === "string" ? rootPkg.name : "<unnamed>";
|
|
22
|
+
return {
|
|
23
|
+
packageManager: sniffPackageManager(absRoot),
|
|
24
|
+
rootPath: absRoot,
|
|
25
|
+
rootPackageName,
|
|
26
|
+
packages: detectWorkspacePackages(absRoot, rootPkg),
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
function sniffPackageManager(absRoot) {
|
|
30
|
+
if (existsSync(join(absRoot, "pnpm-lock.yaml")))
|
|
31
|
+
return "pnpm";
|
|
32
|
+
if (existsSync(join(absRoot, "package-lock.json")))
|
|
33
|
+
return "npm";
|
|
34
|
+
if (existsSync(join(absRoot, "yarn.lock")))
|
|
35
|
+
return "yarn";
|
|
36
|
+
return "unknown";
|
|
37
|
+
}
|
|
38
|
+
function detectWorkspacePackages(absRoot, rootPkg) {
|
|
39
|
+
// pnpm-workspace.yaml wins when both configs present.
|
|
40
|
+
const pnpmYamlPath = join(absRoot, "pnpm-workspace.yaml");
|
|
41
|
+
if (existsSync(pnpmYamlPath)) {
|
|
42
|
+
const yamlContent = readFileSync(pnpmYamlPath, "utf8");
|
|
43
|
+
let parsed;
|
|
44
|
+
try {
|
|
45
|
+
parsed = yaml.load(yamlContent);
|
|
46
|
+
}
|
|
47
|
+
catch {
|
|
48
|
+
parsed = null;
|
|
49
|
+
}
|
|
50
|
+
const globs = isWorkspaceYaml(parsed) ? parsed.packages : [];
|
|
51
|
+
return expandPackages(absRoot, globs);
|
|
52
|
+
}
|
|
53
|
+
// package.json#workspaces (array or object form).
|
|
54
|
+
const workspaces = rootPkg.workspaces;
|
|
55
|
+
if (Array.isArray(workspaces)) {
|
|
56
|
+
return expandPackages(absRoot, workspaces);
|
|
57
|
+
}
|
|
58
|
+
if (workspaces &&
|
|
59
|
+
typeof workspaces === "object" &&
|
|
60
|
+
Array.isArray(workspaces.packages)) {
|
|
61
|
+
return expandPackages(absRoot, workspaces.packages);
|
|
62
|
+
}
|
|
63
|
+
// No workspace config → single-package repo.
|
|
64
|
+
return [];
|
|
65
|
+
}
|
|
66
|
+
function expandPackages(absRoot, entries) {
|
|
67
|
+
if (entries.length === 0)
|
|
68
|
+
return [];
|
|
69
|
+
// Split literal paths from globs: globby (fast-glob) treats a bare "foo"
|
|
70
|
+
// as "foo/**" and returns subdirectories instead of foo itself, so literal
|
|
71
|
+
// workspace entries must be resolved directly.
|
|
72
|
+
const literals = [];
|
|
73
|
+
const globs = [];
|
|
74
|
+
for (const e of entries) {
|
|
75
|
+
if (/[*?[\]{}]/.test(e))
|
|
76
|
+
globs.push(e);
|
|
77
|
+
else
|
|
78
|
+
literals.push(e);
|
|
79
|
+
}
|
|
80
|
+
const matched = literals.map((p) => resolve(absRoot, p));
|
|
81
|
+
if (globs.length > 0) {
|
|
82
|
+
matched.push(...globbySync(globs, {
|
|
83
|
+
cwd: absRoot,
|
|
84
|
+
onlyDirectories: true,
|
|
85
|
+
absolute: true,
|
|
86
|
+
suppressErrors: true,
|
|
87
|
+
}));
|
|
88
|
+
}
|
|
89
|
+
const packages = [];
|
|
90
|
+
const seenNames = new Set();
|
|
91
|
+
for (const dir of matched) {
|
|
92
|
+
const pkgJson = readJsonSafely(join(dir, "package.json"));
|
|
93
|
+
if (!pkgJson)
|
|
94
|
+
continue;
|
|
95
|
+
if (typeof pkgJson.name !== "string" || pkgJson.name.length === 0)
|
|
96
|
+
continue;
|
|
97
|
+
if (seenNames.has(pkgJson.name))
|
|
98
|
+
continue;
|
|
99
|
+
seenNames.add(pkgJson.name);
|
|
100
|
+
packages.push({ name: pkgJson.name, absolutePath: dir, packageJson: pkgJson });
|
|
101
|
+
}
|
|
102
|
+
return packages;
|
|
103
|
+
}
|
|
104
|
+
function readJsonSafely(path) {
|
|
105
|
+
try {
|
|
106
|
+
return JSON.parse(readFileSync(path, "utf8"));
|
|
107
|
+
}
|
|
108
|
+
catch {
|
|
109
|
+
return null;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
function isWorkspaceYaml(p) {
|
|
113
|
+
return (typeof p === "object" &&
|
|
114
|
+
p !== null &&
|
|
115
|
+
Array.isArray(p.packages));
|
|
116
|
+
}
|
|
117
|
+
//# sourceMappingURL=build-graph.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"build-graph.js","sourceRoot":"","sources":["../../src/workspace/build-graph.ts"],"names":[],"mappings":"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"}
|