@savvy-web/silk 1.3.6 → 1.3.7
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/changesets-changelog.cjs +780 -451
- package/changesets-changelog.d.cts +555 -92
- package/changesets-changelog.d.ts +555 -92
- package/changesets-markdownlint.cjs +780 -451
- package/changesets-markdownlint.d.cts +555 -92
- package/changesets-markdownlint.d.ts +555 -92
- package/package.json +4 -4
- package/packages/silk-effects/dist/dev/pkg/changesets/api/linter.cjs +12 -10
- package/packages/silk-effects/dist/dev/pkg/changesets/api/linter.js +9 -7
- package/packages/silk-effects/dist/dev/pkg/changesets/index.cjs +23 -10
- package/packages/silk-effects/dist/dev/pkg/changesets/index.js +17 -10
- package/packages/silk-effects/dist/dev/pkg/changesets/markdownlint/rules/dependency-table-format.cjs +3 -3
- package/packages/silk-effects/dist/dev/pkg/changesets/markdownlint/rules/dependency-table-format.js +1 -1
- package/packages/silk-effects/dist/dev/pkg/changesets/remark/presets.cjs +1 -1
- package/packages/silk-effects/dist/dev/pkg/changesets/remark/presets.js +1 -1
- package/packages/silk-effects/dist/dev/pkg/changesets/schemas/dependency-table.cjs +12 -1
- package/packages/silk-effects/dist/dev/pkg/changesets/schemas/dependency-table.js +12 -2
- package/packages/silk-effects/dist/dev/pkg/changesets/services/deps-regen.cjs +331 -0
- package/packages/silk-effects/dist/dev/pkg/changesets/services/deps-regen.js +327 -0
- package/tsconfig/node/dist/tsconfig.tsbuildinfo +1 -1
package/changesets-changelog.cjs
CHANGED
|
@@ -43578,7 +43578,7 @@ const handle = {
|
|
|
43578
43578
|
* @import {Join} from 'mdast-util-to-markdown'
|
|
43579
43579
|
*/
|
|
43580
43580
|
/** @type {Array<Join>} */
|
|
43581
|
-
const join$
|
|
43581
|
+
const join$8 = [joinDefaults];
|
|
43582
43582
|
/** @type {Join} */
|
|
43583
43583
|
function joinDefaults(left, right, parent, state) {
|
|
43584
43584
|
if (right.type === "code" && formatCodeAsIndented(right, state) && (left.type === "list" || left.type === right.type && formatCodeAsIndented(left, state))) return false;
|
|
@@ -46423,7 +46423,7 @@ function toMarkdown(tree, options) {
|
|
|
46423
46423
|
handle: void 0,
|
|
46424
46424
|
indentLines,
|
|
46425
46425
|
indexStack: [],
|
|
46426
|
-
join: [...join$
|
|
46426
|
+
join: [...join$8],
|
|
46427
46427
|
options: {},
|
|
46428
46428
|
safe: safeBound,
|
|
46429
46429
|
stack: [],
|
|
@@ -59761,6 +59761,16 @@ const DependencyActionSchema = effect.Schema.Literal("added", "updated", "remove
|
|
|
59761
59761
|
*/
|
|
59762
59762
|
const DependencyTableTypeSchema = effect.Schema.Literal("dependency", "devDependency", "peerDependency", "optionalDependency", "workspace", "config");
|
|
59763
59763
|
/**
|
|
59764
|
+
* The canonical accepted-value pattern for a dependency-table From/To cell:
|
|
59765
|
+
* the em-dash sentinel (U+2014), a bare/`~`/`^` semver, or — as a last-resort
|
|
59766
|
+
* fallback when a `catalog:`/`workspace:` specifier could not be resolved to a
|
|
59767
|
+
* concrete version — a pnpm protocol string. Non-overlapping alternatives keep
|
|
59768
|
+
* this free of polynomial backtracking (CodeQL).
|
|
59769
|
+
*
|
|
59770
|
+
* @public
|
|
59771
|
+
*/
|
|
59772
|
+
const VERSION_RE = /^(\u2014|[~^]?\d+\.\d+\.\d+(?:[-+.][\w.+-]+)?|(?:catalog|workspace|npm|jsr|file|link|portal):[^\s|]+)$/;
|
|
59773
|
+
/**
|
|
59764
59774
|
* Version string or em dash (U+2014) sentinel for added/removed entries.
|
|
59765
59775
|
*
|
|
59766
59776
|
* @remarks
|
|
@@ -59786,7 +59796,7 @@ const DependencyTableTypeSchema = effect.Schema.Literal("dependency", "devDepend
|
|
|
59786
59796
|
*
|
|
59787
59797
|
* @public
|
|
59788
59798
|
*/
|
|
59789
|
-
const VersionOrEmptySchema = effect.Schema.String.pipe(effect.Schema.pattern(
|
|
59799
|
+
const VersionOrEmptySchema = effect.Schema.String.pipe(effect.Schema.pattern(VERSION_RE));
|
|
59790
59800
|
/**
|
|
59791
59801
|
* Schema for a single dependency table row.
|
|
59792
59802
|
*
|
|
@@ -61634,6 +61644,38 @@ const ContentStructureRule$1 = lintRule("remark-lint:changeset-content-structure
|
|
|
61634
61644
|
});
|
|
61635
61645
|
});
|
|
61636
61646
|
//#endregion
|
|
61647
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/remark/rules/dependency-table-format.js
|
|
61648
|
+
/** @internal */
|
|
61649
|
+
const EM_DASH$3 = "—";
|
|
61650
|
+
const DependencyTableFormatRule$1 = lintRule("remark-lint:changeset-dependency-table-format", (tree, file) => {
|
|
61651
|
+
visit(tree, "heading", (node, index) => {
|
|
61652
|
+
if (node.depth !== 2) return;
|
|
61653
|
+
if (toString(node).toLowerCase() !== "dependencies") return;
|
|
61654
|
+
if (index === void 0) return;
|
|
61655
|
+
const content = [];
|
|
61656
|
+
for (let i = index + 1; i < tree.children.length; i++) {
|
|
61657
|
+
const child = tree.children[i];
|
|
61658
|
+
if (child.type === "heading") break;
|
|
61659
|
+
content.push(child);
|
|
61660
|
+
}
|
|
61661
|
+
const tables = content.filter((n) => n.type === "table");
|
|
61662
|
+
if (tables.length === 0) {
|
|
61663
|
+
file.message(`Dependencies section must contain a table, not a list or paragraph. See: ${RULE_DOCS.CSH005}`, node);
|
|
61664
|
+
return;
|
|
61665
|
+
}
|
|
61666
|
+
const table = tables[0];
|
|
61667
|
+
try {
|
|
61668
|
+
const rows = parseDependencyTable(table);
|
|
61669
|
+
for (const row of rows) {
|
|
61670
|
+
if (row.action === "added" && row.from !== EM_DASH$3) file.message(`'from' must be '\u2014' when action is 'added' (got '${row.from}'). See: ${RULE_DOCS.CSH005}`, table);
|
|
61671
|
+
if (row.action === "removed" && row.to !== EM_DASH$3) file.message(`'to' must be '\u2014' when action is 'removed' (got '${row.to}'). See: ${RULE_DOCS.CSH005}`, table);
|
|
61672
|
+
}
|
|
61673
|
+
} catch (error) {
|
|
61674
|
+
file.message(`${error instanceof Error ? error.message : String(error)}. See: ${RULE_DOCS.CSH005}`, table);
|
|
61675
|
+
}
|
|
61676
|
+
});
|
|
61677
|
+
});
|
|
61678
|
+
//#endregion
|
|
61637
61679
|
//#region ../silk-effects/dist/dev/pkg/changesets/remark/rules/heading-hierarchy.js
|
|
61638
61680
|
const HeadingHierarchyRule$1 = lintRule("remark-lint:changeset-heading-hierarchy", (tree, file) => {
|
|
61639
61681
|
let prevDepth = 0;
|
|
@@ -61730,7 +61772,7 @@ function stripFrontmatter(content) {
|
|
|
61730
61772
|
/**
|
|
61731
61773
|
* Class-based API wrapper for changeset linting.
|
|
61732
61774
|
*
|
|
61733
|
-
* Provides a static class interface that runs all remark-lint rules
|
|
61775
|
+
* Provides a static class interface that runs all five remark-lint rules
|
|
61734
61776
|
* against changeset markdown files and returns structured diagnostics.
|
|
61735
61777
|
*
|
|
61736
61778
|
* @internal
|
|
@@ -61738,9 +61780,9 @@ function stripFrontmatter(content) {
|
|
|
61738
61780
|
/**
|
|
61739
61781
|
* Static class for linting changeset markdown files.
|
|
61740
61782
|
*
|
|
61741
|
-
* Runs the
|
|
61742
|
-
* content-structure, uncategorized-content) against
|
|
61743
|
-
* and returns structured {@link LintMessage} diagnostics.
|
|
61783
|
+
* Runs the five remark-lint rules (heading-hierarchy, required-sections,
|
|
61784
|
+
* content-structure, dependency-table-format, uncategorized-content) against
|
|
61785
|
+
* changeset markdown and returns structured {@link LintMessage} diagnostics.
|
|
61744
61786
|
*
|
|
61745
61787
|
* @remarks
|
|
61746
61788
|
* This class implements the pre-validation layer of the three-layer
|
|
@@ -61826,7 +61868,7 @@ var ChangesetLinter = class ChangesetLinter {
|
|
|
61826
61868
|
*
|
|
61827
61869
|
* @remarks
|
|
61828
61870
|
* Reads the file synchronously, strips YAML frontmatter, and runs all
|
|
61829
|
-
*
|
|
61871
|
+
* five lint rules. The file path is preserved in each returned
|
|
61830
61872
|
* {@link LintMessage} for error reporting.
|
|
61831
61873
|
*
|
|
61832
61874
|
* @param filePath - Absolute or relative path to the changeset `.md` file
|
|
@@ -61840,7 +61882,7 @@ var ChangesetLinter = class ChangesetLinter {
|
|
|
61840
61882
|
* Validate a markdown string directly.
|
|
61841
61883
|
*
|
|
61842
61884
|
* @remarks
|
|
61843
|
-
* Strips YAML frontmatter (if present) and runs all
|
|
61885
|
+
* Strips YAML frontmatter (if present) and runs all five lint rules
|
|
61844
61886
|
* against the remaining content. This method is useful for validating
|
|
61845
61887
|
* changeset content that is already in memory, such as in test suites
|
|
61846
61888
|
* or editor integrations.
|
|
@@ -61852,7 +61894,7 @@ var ChangesetLinter = class ChangesetLinter {
|
|
|
61852
61894
|
*/
|
|
61853
61895
|
static validateContent(content, filePath = "<input>") {
|
|
61854
61896
|
const body = stripFrontmatter(content);
|
|
61855
|
-
return unified().use(remarkParse).use(remarkStringify).use(HeadingHierarchyRule$1).use(RequiredSectionsRule$1).use(ContentStructureRule$1).use(UncategorizedContentRule$1).processSync(body).messages.map((msg) => ({
|
|
61897
|
+
return unified().use(remarkParse).use(remarkGfm).use(remarkStringify).use(HeadingHierarchyRule$1).use(RequiredSectionsRule$1).use(ContentStructureRule$1).use(DependencyTableFormatRule$1).use(UncategorizedContentRule$1).processSync(body).messages.map((msg) => ({
|
|
61856
61898
|
file: filePath,
|
|
61857
61899
|
/* v8 ignore next 3 -- ruleId/line/column fallbacks; remark-lint always provides these */
|
|
61858
61900
|
rule: msg.ruleId ?? msg.source ?? "unknown",
|
|
@@ -77373,7 +77415,7 @@ function configErrorFromParseError(parseError, configPath) {
|
|
|
77373
77415
|
* Each shape carries a private cache keyed by absolute project dir so
|
|
77374
77416
|
* repeat `inspect`/`classify` calls reuse the materialized state.
|
|
77375
77417
|
*/
|
|
77376
|
-
function makeShape$
|
|
77418
|
+
function makeShape$4(reader, discovery, fs) {
|
|
77377
77419
|
const cache = /* @__PURE__ */ new Map();
|
|
77378
77420
|
const inspect = (cwd) => effect.Effect.gen(function* () {
|
|
77379
77421
|
const projectDir = (0, node_path.resolve)(cwd);
|
|
@@ -77503,7 +77545,7 @@ function classifyOne(inspected, path) {
|
|
|
77503
77545
|
* @public
|
|
77504
77546
|
*/
|
|
77505
77547
|
const ConfigInspectorLive = effect.Layer.effect(ConfigInspector, effect.Effect.gen(function* () {
|
|
77506
|
-
return makeShape$
|
|
77548
|
+
return makeShape$4(yield* ChangesetConfigReader, yield* WorkspaceDiscovery, yield* _effect_platform.FileSystem.FileSystem);
|
|
77507
77549
|
}));
|
|
77508
77550
|
/**
|
|
77509
77551
|
* Test factory — build a {@link ConfigInspector} that returns a fixed
|
|
@@ -77726,7 +77768,7 @@ function resolveBaseBranch(opts) {
|
|
|
77726
77768
|
effect.Effect.catchAll(() => effect.Effect.succeed(opts.configBaseBranch))
|
|
77727
77769
|
);
|
|
77728
77770
|
}
|
|
77729
|
-
function makeShape$
|
|
77771
|
+
function makeShape$3(inspector) {
|
|
77730
77772
|
const analyzeBranch = (cwd, opts) => effect.Effect.gen(function* () {
|
|
77731
77773
|
const inspected = yield* inspector.inspect(cwd);
|
|
77732
77774
|
const baseBranch = yield* resolveBaseBranch({
|
|
@@ -77796,7 +77838,7 @@ function makeShape$2(inspector) {
|
|
|
77796
77838
|
* @public
|
|
77797
77839
|
*/
|
|
77798
77840
|
const BranchAnalyzerLive = effect.Layer.effect(BranchAnalyzer, effect.Effect.gen(function* () {
|
|
77799
|
-
return makeShape$
|
|
77841
|
+
return makeShape$3(yield* ConfigInspector);
|
|
77800
77842
|
}));
|
|
77801
77843
|
/**
|
|
77802
77844
|
* Test factory — build a {@link BranchAnalyzer} that returns a fixed
|
|
@@ -77853,6 +77895,714 @@ const ChangelogServiceBase = effect.Context.Tag("ChangelogService")();
|
|
|
77853
77895
|
*/
|
|
77854
77896
|
var ChangelogService = class extends ChangelogServiceBase {};
|
|
77855
77897
|
//#endregion
|
|
77898
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/utils/dep-diff.js
|
|
77899
|
+
const EM_DASH$2 = "—";
|
|
77900
|
+
const DEP_TYPE_MAP = [
|
|
77901
|
+
["dependencies", "dependency"],
|
|
77902
|
+
["devDependencies", "devDependency"],
|
|
77903
|
+
["peerDependencies", "peerDependency"],
|
|
77904
|
+
["optionalDependencies", "optionalDependency"]
|
|
77905
|
+
];
|
|
77906
|
+
function diffOneRecord(before, after, type) {
|
|
77907
|
+
const rows = [];
|
|
77908
|
+
const seen = /* @__PURE__ */ new Set();
|
|
77909
|
+
for (const [name, beforeVersion] of Object.entries(before)) {
|
|
77910
|
+
seen.add(name);
|
|
77911
|
+
const afterVersion = after[name];
|
|
77912
|
+
if (afterVersion === void 0) rows.push({
|
|
77913
|
+
dependency: name,
|
|
77914
|
+
type,
|
|
77915
|
+
action: "removed",
|
|
77916
|
+
from: beforeVersion,
|
|
77917
|
+
to: EM_DASH$2
|
|
77918
|
+
});
|
|
77919
|
+
else if (afterVersion !== beforeVersion) rows.push({
|
|
77920
|
+
dependency: name,
|
|
77921
|
+
type,
|
|
77922
|
+
action: "updated",
|
|
77923
|
+
from: beforeVersion,
|
|
77924
|
+
to: afterVersion
|
|
77925
|
+
});
|
|
77926
|
+
}
|
|
77927
|
+
for (const [name, afterVersion] of Object.entries(after)) {
|
|
77928
|
+
if (seen.has(name)) continue;
|
|
77929
|
+
rows.push({
|
|
77930
|
+
dependency: name,
|
|
77931
|
+
type,
|
|
77932
|
+
action: "added",
|
|
77933
|
+
from: EM_DASH$2,
|
|
77934
|
+
to: afterVersion
|
|
77935
|
+
});
|
|
77936
|
+
}
|
|
77937
|
+
return rows;
|
|
77938
|
+
}
|
|
77939
|
+
/**
|
|
77940
|
+
* Diff two workspace snapshots and return per-package dependency-table rows.
|
|
77941
|
+
*
|
|
77942
|
+
* @param before - Snapshot at the older ref (typically the merge base). Pass
|
|
77943
|
+
* `null` for workspace packages that did not exist at the older ref — every
|
|
77944
|
+
* declared dep is then reported as `"added"`.
|
|
77945
|
+
* @param after - Snapshot at the newer ref (typically the working tree).
|
|
77946
|
+
* @returns One {@link WorkspaceDependencyDiff} entry per workspace package
|
|
77947
|
+
* that has at least one row. Packages with no changes are omitted.
|
|
77948
|
+
*
|
|
77949
|
+
* @public
|
|
77950
|
+
*/
|
|
77951
|
+
function computeWorkspaceDependencyDiffs(beforeSnapshots, afterSnapshots) {
|
|
77952
|
+
const beforeByName = new Map(beforeSnapshots.map((s) => [s.name, s]));
|
|
77953
|
+
const result = [];
|
|
77954
|
+
for (const after of afterSnapshots) {
|
|
77955
|
+
const before = beforeByName.get(after.name);
|
|
77956
|
+
const rows = [];
|
|
77957
|
+
for (const [field, type] of DEP_TYPE_MAP) {
|
|
77958
|
+
const beforeRecord = before?.[field] ?? {};
|
|
77959
|
+
const afterRecord = after[field];
|
|
77960
|
+
rows.push(...diffOneRecord(beforeRecord, afterRecord, type));
|
|
77961
|
+
}
|
|
77962
|
+
if (rows.length > 0) result.push({
|
|
77963
|
+
package: after.name,
|
|
77964
|
+
relativePath: after.relativePath,
|
|
77965
|
+
rows: sortDependencyRows(rows)
|
|
77966
|
+
});
|
|
77967
|
+
}
|
|
77968
|
+
return result;
|
|
77969
|
+
}
|
|
77970
|
+
//#endregion
|
|
77971
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/utils/publishability.js
|
|
77972
|
+
/**
|
|
77973
|
+
* Publishability helpers for the changeset CLI commands.
|
|
77974
|
+
*
|
|
77975
|
+
* @remarks
|
|
77976
|
+
* Provides `listPublishablePackageNames`, a convenience wrapper around
|
|
77977
|
+
* {@link SilkPublishability} that returns a `Set<string>` of
|
|
77978
|
+
* publishable package names. Used by the `deps detect` and `deps regen`
|
|
77979
|
+
* commands to filter out workspace packages whose dependency changes
|
|
77980
|
+
* would never reach a release.
|
|
77981
|
+
*
|
|
77982
|
+
*/
|
|
77983
|
+
/**
|
|
77984
|
+
* Compute the set of currently-publishable workspace package names.
|
|
77985
|
+
*
|
|
77986
|
+
* @remarks
|
|
77987
|
+
* Uses the currently-active {@link SilkPublishability} — wire the
|
|
77988
|
+
* {@link SilkPublishabilityDetectorLive} layer to get silk semantics.
|
|
77989
|
+
*
|
|
77990
|
+
* @param packages - The workspace packages to evaluate
|
|
77991
|
+
* @returns An Effect yielding a `Set` of publishable package names
|
|
77992
|
+
*
|
|
77993
|
+
* @public
|
|
77994
|
+
*/
|
|
77995
|
+
function listPublishablePackageNames(packages) {
|
|
77996
|
+
return effect.Effect.gen(function* () {
|
|
77997
|
+
const detector = yield* PublishabilityDetector;
|
|
77998
|
+
const names = /* @__PURE__ */ new Set();
|
|
77999
|
+
for (const pkg of packages) if ((yield* detector.detect(pkg, pkg.path)).length > 0) names.add(pkg.name);
|
|
78000
|
+
return names;
|
|
78001
|
+
});
|
|
78002
|
+
}
|
|
78003
|
+
//#endregion
|
|
78004
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/utils/worktree-snapshot.js
|
|
78005
|
+
/**
|
|
78006
|
+
* Shared helpers for `deps detect` and `deps regen` — both need to read
|
|
78007
|
+
* workspace package snapshots from the live working tree (the "after"
|
|
78008
|
+
* side of a dep diff that isn't pinned to a git ref) and to resolve the
|
|
78009
|
+
* merge-base for the default `--from` ref.
|
|
78010
|
+
*
|
|
78011
|
+
* @remarks
|
|
78012
|
+
* `WorkspaceSnapshotReader` covers the git-ref side via `git show`. This
|
|
78013
|
+
* module is the working-tree counterpart — staged and unstaged
|
|
78014
|
+
* `package.json` edits show up here, matching `analyze-branch`'s
|
|
78015
|
+
* coverage of the working tree.
|
|
78016
|
+
*
|
|
78017
|
+
* @internal
|
|
78018
|
+
*/
|
|
78019
|
+
/**
|
|
78020
|
+
* Run `git merge-base <base> HEAD`, returning the SHA. Errors propagate
|
|
78021
|
+
* as {@link GitError}.
|
|
78022
|
+
*
|
|
78023
|
+
* @internal
|
|
78024
|
+
*/
|
|
78025
|
+
function gitMergeBase(cwd, base) {
|
|
78026
|
+
return effect.Effect.try({
|
|
78027
|
+
try: () => (0, node_child_process.execFileSync)("git", [
|
|
78028
|
+
"merge-base",
|
|
78029
|
+
base,
|
|
78030
|
+
"HEAD"
|
|
78031
|
+
], {
|
|
78032
|
+
cwd,
|
|
78033
|
+
encoding: "utf8",
|
|
78034
|
+
stdio: [
|
|
78035
|
+
"ignore",
|
|
78036
|
+
"pipe",
|
|
78037
|
+
"pipe"
|
|
78038
|
+
]
|
|
78039
|
+
}).trim(),
|
|
78040
|
+
catch: (error) => {
|
|
78041
|
+
const stderr = error.stderr;
|
|
78042
|
+
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
78043
|
+
return new GitError$1({
|
|
78044
|
+
command: `git merge-base ${base} HEAD`,
|
|
78045
|
+
cwd,
|
|
78046
|
+
reason: text.trim() || (error.message ?? String(error))
|
|
78047
|
+
});
|
|
78048
|
+
}
|
|
78049
|
+
});
|
|
78050
|
+
}
|
|
78051
|
+
/**
|
|
78052
|
+
* Normalize a pnpm-workspace.yaml glob entry for filesystem expansion.
|
|
78053
|
+
*
|
|
78054
|
+
* `packages/**` collapses to `packages/*` (retains the wildcard so the
|
|
78055
|
+
* caller hits the directory-listing path); `packages/*` and a literal
|
|
78056
|
+
* `packages/foo` are passed through unchanged.
|
|
78057
|
+
*
|
|
78058
|
+
* Returning the literal-path form for `packages/**` (i.e., `"packages"`)
|
|
78059
|
+
* would route the caller through the "no wildcards" branch and silently
|
|
78060
|
+
* skip every child workspace.
|
|
78061
|
+
*
|
|
78062
|
+
* @internal
|
|
78063
|
+
*/
|
|
78064
|
+
function normalizeWorkspaceGlob(glob) {
|
|
78065
|
+
return glob.replace(/\/\*\*$/, "/*");
|
|
78066
|
+
}
|
|
78067
|
+
/**
|
|
78068
|
+
* Read every workspace package's `package.json` from the live working
|
|
78069
|
+
* tree, returning {@link WorkspaceSnapshot} entries matching the shape
|
|
78070
|
+
* `WorkspaceSnapshotReader.snapshotAt` produces for git refs.
|
|
78071
|
+
*
|
|
78072
|
+
* @remarks
|
|
78073
|
+
* Falls back to root-only when `pnpm-workspace.yaml` is missing or
|
|
78074
|
+
* unparseable. Uses `node:fs.readdirSync` for directory expansion
|
|
78075
|
+
* (portable across platforms — `execFileSync("ls")` is not).
|
|
78076
|
+
*
|
|
78077
|
+
* @internal
|
|
78078
|
+
*/
|
|
78079
|
+
function snapshotFromWorktree(cwd) {
|
|
78080
|
+
const snapshots = [];
|
|
78081
|
+
const dirs = /* @__PURE__ */ new Set([cwd]);
|
|
78082
|
+
for (const dir of expandWorkspaceDirs(cwd)) dirs.add(dir);
|
|
78083
|
+
for (const dir of dirs) try {
|
|
78084
|
+
const pkgJson = JSON.parse((0, node_fs.readFileSync)((0, node_path.join)(dir, "package.json"), "utf8"));
|
|
78085
|
+
if (!pkgJson.name) continue;
|
|
78086
|
+
const rel = dir === cwd ? "." : dir.slice(cwd.length + 1);
|
|
78087
|
+
snapshots.push({
|
|
78088
|
+
name: pkgJson.name,
|
|
78089
|
+
relativePath: rel,
|
|
78090
|
+
version: pkgJson.version ?? "0.0.0",
|
|
78091
|
+
dependencies: pkgJson.dependencies ?? {},
|
|
78092
|
+
devDependencies: pkgJson.devDependencies ?? {},
|
|
78093
|
+
peerDependencies: pkgJson.peerDependencies ?? {},
|
|
78094
|
+
optionalDependencies: pkgJson.optionalDependencies ?? {}
|
|
78095
|
+
});
|
|
78096
|
+
} catch {}
|
|
78097
|
+
return snapshots;
|
|
78098
|
+
}
|
|
78099
|
+
function expandWorkspaceDirs(cwd) {
|
|
78100
|
+
let yaml;
|
|
78101
|
+
try {
|
|
78102
|
+
yaml = (0, node_fs.readFileSync)((0, node_path.join)(cwd, "pnpm-workspace.yaml"), "utf8");
|
|
78103
|
+
} catch {
|
|
78104
|
+
return [];
|
|
78105
|
+
}
|
|
78106
|
+
const dirs = [];
|
|
78107
|
+
const lines = yaml.split(/\r?\n/);
|
|
78108
|
+
let inPackagesBlock = false;
|
|
78109
|
+
for (const line of lines) {
|
|
78110
|
+
if (/^\s*#/.test(line)) continue;
|
|
78111
|
+
if (/^\s*packages\s*:\s*$/.test(line)) {
|
|
78112
|
+
inPackagesBlock = true;
|
|
78113
|
+
continue;
|
|
78114
|
+
}
|
|
78115
|
+
if (!inPackagesBlock) continue;
|
|
78116
|
+
const m = line.match(/^\s+-\s+["']?(.+?)["']?\s*$/);
|
|
78117
|
+
if (m) {
|
|
78118
|
+
const glob = normalizeWorkspaceGlob(m[1]);
|
|
78119
|
+
if (glob.includes("*") || glob.includes("?")) {
|
|
78120
|
+
const prefix = glob.includes("/") ? glob.slice(0, glob.lastIndexOf("/") + 1) : "";
|
|
78121
|
+
let entries = [];
|
|
78122
|
+
try {
|
|
78123
|
+
entries = (0, node_fs.readdirSync)((0, node_path.join)(cwd, prefix || "."));
|
|
78124
|
+
} catch {
|
|
78125
|
+
continue;
|
|
78126
|
+
}
|
|
78127
|
+
const regex = new RegExp(`^${glob.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, "[^/]*").replace(/\?/g, "[^/]")}$`);
|
|
78128
|
+
for (const entry of entries) {
|
|
78129
|
+
const candidate = prefix ? `${prefix}${entry}` : entry;
|
|
78130
|
+
if (regex.test(candidate)) dirs.push((0, node_path.join)(cwd, candidate));
|
|
78131
|
+
}
|
|
78132
|
+
} else dirs.push((0, node_path.join)(cwd, glob));
|
|
78133
|
+
} else if (line.length > 0 && !line.startsWith(" ") && !line.startsWith(" ")) inPackagesBlock = false;
|
|
78134
|
+
}
|
|
78135
|
+
return dirs;
|
|
78136
|
+
}
|
|
78137
|
+
//#endregion
|
|
78138
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/services/workspace-snapshot.js
|
|
78139
|
+
/**
|
|
78140
|
+
* @internal
|
|
78141
|
+
*/
|
|
78142
|
+
const WorkspaceSnapshotReaderBase = effect.Context.Tag("WorkspaceSnapshotReader")();
|
|
78143
|
+
/**
|
|
78144
|
+
* Effect service tag for {@link WorkspaceSnapshotReaderShape}.
|
|
78145
|
+
*
|
|
78146
|
+
* @public
|
|
78147
|
+
*/
|
|
78148
|
+
var WorkspaceSnapshotReader = class extends WorkspaceSnapshotReaderBase {};
|
|
78149
|
+
function runGitShow(cwd, ref, path) {
|
|
78150
|
+
return effect.Effect.try({
|
|
78151
|
+
try: () => (0, node_child_process.execFileSync)("git", ["show", `${ref}:${path}`], {
|
|
78152
|
+
cwd,
|
|
78153
|
+
encoding: "utf8",
|
|
78154
|
+
stdio: [
|
|
78155
|
+
"ignore",
|
|
78156
|
+
"pipe",
|
|
78157
|
+
"pipe"
|
|
78158
|
+
]
|
|
78159
|
+
}),
|
|
78160
|
+
catch: (error) => {
|
|
78161
|
+
const stderr = error.stderr;
|
|
78162
|
+
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
78163
|
+
if (/exists on disk, but not in|does not exist|unknown revision|bad object/.test(text)) return new GitError$1({
|
|
78164
|
+
command: `git show ${ref}:${path}`,
|
|
78165
|
+
cwd,
|
|
78166
|
+
reason: "PATH_NOT_AT_REF"
|
|
78167
|
+
});
|
|
78168
|
+
return new GitError$1({
|
|
78169
|
+
command: `git show ${ref}:${path}`,
|
|
78170
|
+
cwd,
|
|
78171
|
+
reason: text.trim() || (error.message ?? String(error))
|
|
78172
|
+
});
|
|
78173
|
+
}
|
|
78174
|
+
}).pipe(effect.Effect.catchTag("GitError", (err) => err.reason === "PATH_NOT_AT_REF" ? effect.Effect.succeed(null) : effect.Effect.fail(err)));
|
|
78175
|
+
}
|
|
78176
|
+
/**
|
|
78177
|
+
* Parse a minimal `pnpm-workspace.yaml` (`packages:` list only). Tolerant
|
|
78178
|
+
* of comments and varied indentation; rejects on missing `packages:` key.
|
|
78179
|
+
*/
|
|
78180
|
+
function parseWorkspaceGlobs(yamlText) {
|
|
78181
|
+
const lines = yamlText.split(/\r?\n/);
|
|
78182
|
+
const globs = [];
|
|
78183
|
+
let inPackagesBlock = false;
|
|
78184
|
+
for (const line of lines) {
|
|
78185
|
+
if (/^\s*#/.test(line)) continue;
|
|
78186
|
+
if (/^\s*packages\s*:\s*$/.test(line)) {
|
|
78187
|
+
inPackagesBlock = true;
|
|
78188
|
+
continue;
|
|
78189
|
+
}
|
|
78190
|
+
if (inPackagesBlock) {
|
|
78191
|
+
const match = line.match(/^\s+-\s+["']?(.+?)["']?\s*$/);
|
|
78192
|
+
if (match) {
|
|
78193
|
+
globs.push(match[1]);
|
|
78194
|
+
continue;
|
|
78195
|
+
}
|
|
78196
|
+
if (line.length > 0 && !line.startsWith(" ") && !line.startsWith(" ")) inPackagesBlock = false;
|
|
78197
|
+
}
|
|
78198
|
+
}
|
|
78199
|
+
return globs;
|
|
78200
|
+
}
|
|
78201
|
+
function toSnapshot(pkg, relativePath) {
|
|
78202
|
+
if (!pkg.name) return null;
|
|
78203
|
+
return {
|
|
78204
|
+
name: pkg.name,
|
|
78205
|
+
relativePath,
|
|
78206
|
+
version: pkg.version ?? "0.0.0",
|
|
78207
|
+
dependencies: pkg.dependencies ?? {},
|
|
78208
|
+
devDependencies: pkg.devDependencies ?? {},
|
|
78209
|
+
peerDependencies: pkg.peerDependencies ?? {},
|
|
78210
|
+
optionalDependencies: pkg.optionalDependencies ?? {}
|
|
78211
|
+
};
|
|
78212
|
+
}
|
|
78213
|
+
/**
|
|
78214
|
+
* Expand a workspace glob like `packages/*` or `apps/web` against the
|
|
78215
|
+
* directories present at the given git ref. We can't `globSync` here
|
|
78216
|
+
* (the directories may not be on disk at this ref); instead we use
|
|
78217
|
+
* `git ls-tree` to enumerate paths.
|
|
78218
|
+
*/
|
|
78219
|
+
function expandGlobAtRef(cwd, ref, glob) {
|
|
78220
|
+
return effect.Effect.gen(function* () {
|
|
78221
|
+
const cleanGlob = glob.replace(/\/\*\*$/, "/*");
|
|
78222
|
+
if (!cleanGlob.includes("*") && !cleanGlob.includes("?")) return [cleanGlob];
|
|
78223
|
+
const prefix = cleanGlob.includes("/") ? cleanGlob.slice(0, cleanGlob.lastIndexOf("/") + 1) : "";
|
|
78224
|
+
const entries = (yield* effect.Effect.try({
|
|
78225
|
+
try: () => (0, node_child_process.execFileSync)("git", [
|
|
78226
|
+
"ls-tree",
|
|
78227
|
+
"--name-only",
|
|
78228
|
+
ref,
|
|
78229
|
+
prefix
|
|
78230
|
+
], {
|
|
78231
|
+
cwd,
|
|
78232
|
+
encoding: "utf8",
|
|
78233
|
+
stdio: [
|
|
78234
|
+
"ignore",
|
|
78235
|
+
"pipe",
|
|
78236
|
+
"pipe"
|
|
78237
|
+
]
|
|
78238
|
+
}),
|
|
78239
|
+
catch: (error) => {
|
|
78240
|
+
const stderr = error.stderr;
|
|
78241
|
+
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
78242
|
+
return new GitError$1({
|
|
78243
|
+
command: `git ls-tree ${ref} ${prefix}`,
|
|
78244
|
+
cwd,
|
|
78245
|
+
reason: text.trim() || (error.message ?? String(error))
|
|
78246
|
+
});
|
|
78247
|
+
}
|
|
78248
|
+
})).split(/\r?\n/).map((s) => s.trim()).filter((s) => s.length > 0);
|
|
78249
|
+
const regex = new RegExp(`^${cleanGlob.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, "[^/]*").replace(/\?/g, "[^/]")}$`);
|
|
78250
|
+
return entries.filter((e) => regex.test(e));
|
|
78251
|
+
});
|
|
78252
|
+
}
|
|
78253
|
+
function makeShape$2() {
|
|
78254
|
+
const cache = /* @__PURE__ */ new Map();
|
|
78255
|
+
const snapshotAt = (cwd, ref) => effect.Effect.gen(function* () {
|
|
78256
|
+
const cacheKey = `${cwd}::${ref}`;
|
|
78257
|
+
const cached = cache.get(cacheKey);
|
|
78258
|
+
if (cached) return cached;
|
|
78259
|
+
const wsYaml = yield* runGitShow(cwd, ref, "pnpm-workspace.yaml");
|
|
78260
|
+
const globs = wsYaml ? parseWorkspaceGlobs(wsYaml) : [];
|
|
78261
|
+
const dirs = [];
|
|
78262
|
+
for (const glob of globs) {
|
|
78263
|
+
const expanded = yield* expandGlobAtRef(cwd, ref, glob);
|
|
78264
|
+
for (const d of expanded) if (!dirs.includes(d)) dirs.push(d);
|
|
78265
|
+
}
|
|
78266
|
+
if (!dirs.includes(".")) dirs.unshift(".");
|
|
78267
|
+
const snapshots = [];
|
|
78268
|
+
for (const dir of dirs) {
|
|
78269
|
+
const pkgText = yield* runGitShow(cwd, ref, dir === "." ? "package.json" : `${dir}/package.json`);
|
|
78270
|
+
if (!pkgText) continue;
|
|
78271
|
+
let parsed;
|
|
78272
|
+
try {
|
|
78273
|
+
parsed = JSON.parse(pkgText);
|
|
78274
|
+
} catch {
|
|
78275
|
+
continue;
|
|
78276
|
+
}
|
|
78277
|
+
const snap = toSnapshot(parsed, dir);
|
|
78278
|
+
if (snap) snapshots.push(snap);
|
|
78279
|
+
}
|
|
78280
|
+
cache.set(cacheKey, snapshots);
|
|
78281
|
+
return snapshots;
|
|
78282
|
+
});
|
|
78283
|
+
return { snapshotAt };
|
|
78284
|
+
}
|
|
78285
|
+
/**
|
|
78286
|
+
* Production layer for {@link WorkspaceSnapshotReader}.
|
|
78287
|
+
*
|
|
78288
|
+
* @public
|
|
78289
|
+
*/
|
|
78290
|
+
const WorkspaceSnapshotReaderLive = effect.Layer.succeed(WorkspaceSnapshotReader, makeShape$2());
|
|
78291
|
+
//#endregion
|
|
78292
|
+
//#region ../silk-effects/dist/dev/pkg/changesets/services/deps-regen.js
|
|
78293
|
+
/**
|
|
78294
|
+
* `Changesets.DepsRegen` service — lift the `deps regen` / `deps detect`
|
|
78295
|
+
* orchestration out of the CLI into a `Context.Tag` service with a
|
|
78296
|
+
* `plan()` / `execute()` split.
|
|
78297
|
+
*
|
|
78298
|
+
* @remarks
|
|
78299
|
+
* `plan()` computes the cumulative dependency diff (merge-base → working
|
|
78300
|
+
* tree by default, or between two explicit refs), resolves `catalog:` /
|
|
78301
|
+
* `workspace:` specifiers to concrete versions, drops `devDependency`
|
|
78302
|
+
* rows (unless `includeDevDeps`), and returns a complete {@link RegenPlan}
|
|
78303
|
+
* (target filenames + stale-changeset deletes) WITHOUT touching the
|
|
78304
|
+
* filesystem. `execute()` applies a plan — writing the fresh changesets
|
|
78305
|
+
* first, then deleting the stale pure-dependency ones (so an interrupted
|
|
78306
|
+
* run loses nothing and is safely re-runnable).
|
|
78307
|
+
*
|
|
78308
|
+
* This is the single source of truth for regen/detect: the CLI commands
|
|
78309
|
+
* and MCP tools are thin adapters over this service.
|
|
78310
|
+
*
|
|
78311
|
+
* @see {@link DepsRegen} for the service tag
|
|
78312
|
+
* @see {@link DepsRegenLive} for the production layer
|
|
78313
|
+
*
|
|
78314
|
+
*/
|
|
78315
|
+
/** The em-dash sentinel (U+2014) used for added ("from") / removed ("to") cells. */
|
|
78316
|
+
const EM_DASH$1 = "—";
|
|
78317
|
+
/** Whether a From/To cell holds a pnpm protocol specifier that could resolve to a version. */
|
|
78318
|
+
const isProtocol = (v) => /^(?:catalog|workspace|npm|jsr|file|link|portal):/.test(v);
|
|
78319
|
+
/**
|
|
78320
|
+
* Resolve protocol From/To cells to concrete versions (raw-string fallback
|
|
78321
|
+
* when unresolved or on resolver error), leave em-dash sentinels untouched,
|
|
78322
|
+
* then optionally drop `devDependency` rows, and re-sort.
|
|
78323
|
+
*
|
|
78324
|
+
* @param diff - One workspace package's dependency-table rows.
|
|
78325
|
+
* @param keepDevDeps - When `true`, retain `devDependency` rows; otherwise
|
|
78326
|
+
* drop them unconditionally (the regen default).
|
|
78327
|
+
* @returns An Effect yielding the transformed {@link WorkspaceDependencyDiff}.
|
|
78328
|
+
*
|
|
78329
|
+
* @public
|
|
78330
|
+
*/
|
|
78331
|
+
const resolveDiffRows = (diff, keepDevDeps = false) => effect.Effect.gen(function* () {
|
|
78332
|
+
const resolver = yield* CatalogResolver;
|
|
78333
|
+
const resolveCell = (dep, value) => isProtocol(value) ? resolver.resolveSpecifier(dep, value).pipe(effect.Effect.map((opt) => effect.Option.getOrElse(opt, () => value)), effect.Effect.catchAll((error) => effect.Effect.logWarning(`DepsRegen: catalog resolution failed for "${dep}" (${value}); keeping raw specifier: ${String(error)}`).pipe(effect.Effect.as(value)))) : effect.Effect.succeed(value);
|
|
78334
|
+
const rows = [];
|
|
78335
|
+
for (const row of diff.rows) {
|
|
78336
|
+
if (!keepDevDeps && row.type === "devDependency") continue;
|
|
78337
|
+
const from = row.from === EM_DASH$1 ? EM_DASH$1 : yield* resolveCell(row.dependency, row.from);
|
|
78338
|
+
const to = row.to === EM_DASH$1 ? EM_DASH$1 : yield* resolveCell(row.dependency, row.to);
|
|
78339
|
+
rows.push({
|
|
78340
|
+
...row,
|
|
78341
|
+
from,
|
|
78342
|
+
to
|
|
78343
|
+
});
|
|
78344
|
+
}
|
|
78345
|
+
return {
|
|
78346
|
+
...diff,
|
|
78347
|
+
rows: sortDependencyRows(rows)
|
|
78348
|
+
};
|
|
78349
|
+
});
|
|
78350
|
+
const ADJECTIVES = [
|
|
78351
|
+
"brave",
|
|
78352
|
+
"clever",
|
|
78353
|
+
"swift",
|
|
78354
|
+
"silver",
|
|
78355
|
+
"lucky",
|
|
78356
|
+
"happy",
|
|
78357
|
+
"calm",
|
|
78358
|
+
"bright",
|
|
78359
|
+
"quiet",
|
|
78360
|
+
"wild"
|
|
78361
|
+
];
|
|
78362
|
+
const NOUNS = [
|
|
78363
|
+
"dogs",
|
|
78364
|
+
"cats",
|
|
78365
|
+
"wolves",
|
|
78366
|
+
"foxes",
|
|
78367
|
+
"cups",
|
|
78368
|
+
"ships",
|
|
78369
|
+
"trees",
|
|
78370
|
+
"owls",
|
|
78371
|
+
"cranes",
|
|
78372
|
+
"hills"
|
|
78373
|
+
];
|
|
78374
|
+
const VERBS = [
|
|
78375
|
+
"laugh",
|
|
78376
|
+
"dream",
|
|
78377
|
+
"fly",
|
|
78378
|
+
"sing",
|
|
78379
|
+
"dance",
|
|
78380
|
+
"wander",
|
|
78381
|
+
"soar",
|
|
78382
|
+
"rest",
|
|
78383
|
+
"leap",
|
|
78384
|
+
"ponder"
|
|
78385
|
+
];
|
|
78386
|
+
function pickRandomTriplet() {
|
|
78387
|
+
return `${ADJECTIVES[Math.floor(Math.random() * ADJECTIVES.length)]}-${NOUNS[Math.floor(Math.random() * NOUNS.length)]}-${VERBS[Math.floor(Math.random() * VERBS.length)]}`;
|
|
78388
|
+
}
|
|
78389
|
+
/**
|
|
78390
|
+
* Pick a `<adjective>-<noun>-<verb>` filename slug that does not collide
|
|
78391
|
+
* with an existing `.changeset/*.md` OR with a slug already claimed
|
|
78392
|
+
* earlier in the same {@link RegenPlan.toWrite} computation. `plan()`
|
|
78393
|
+
* never writes to disk, so `existsSync` alone cannot see slugs chosen
|
|
78394
|
+
* moments earlier in the same call — the `chosen` set closes that gap.
|
|
78395
|
+
* The triplet space is 1,000 combinations, so a busy repo can plausibly
|
|
78396
|
+
* exhaust it across runs; fall back to a timestamp suffix after 20
|
|
78397
|
+
* unlucky picks.
|
|
78398
|
+
*
|
|
78399
|
+
* @param changesetDir - Directory checked via `existsSync` for on-disk collisions.
|
|
78400
|
+
* @param chosen - Basenames (without extension) already picked within this plan;
|
|
78401
|
+
* the picked candidate is added to this set before returning.
|
|
78402
|
+
* @internal
|
|
78403
|
+
*/
|
|
78404
|
+
function randomFilename(changesetDir, chosen) {
|
|
78405
|
+
for (let i = 0; i < 20; i++) {
|
|
78406
|
+
const candidate = pickRandomTriplet();
|
|
78407
|
+
if (!chosen.has(candidate) && !(0, node_fs.existsSync)((0, node_path.join)(changesetDir, `${candidate}.md`))) {
|
|
78408
|
+
chosen.add(candidate);
|
|
78409
|
+
return candidate;
|
|
78410
|
+
}
|
|
78411
|
+
}
|
|
78412
|
+
let attempt = 0;
|
|
78413
|
+
let fallback = `${pickRandomTriplet()}-${Date.now()}`;
|
|
78414
|
+
while (chosen.has(fallback) || (0, node_fs.existsSync)((0, node_path.join)(changesetDir, `${fallback}.md`))) fallback = `${pickRandomTriplet()}-${Date.now()}-${++attempt}`;
|
|
78415
|
+
chosen.add(fallback);
|
|
78416
|
+
return fallback;
|
|
78417
|
+
}
|
|
78418
|
+
/**
|
|
78419
|
+
* Strict detection of "pure dependency changesets" per the documented
|
|
78420
|
+
* rules: single-package frontmatter, single `## Dependencies` heading,
|
|
78421
|
+
* no other body content beyond that section.
|
|
78422
|
+
*
|
|
78423
|
+
* @param content - Raw `.changeset/*.md` file contents.
|
|
78424
|
+
* @returns `{ isPure, package }` — `isPure` is `true` only for a
|
|
78425
|
+
* single-package, Dependencies-only changeset; `package` is the sole
|
|
78426
|
+
* frontmatter package name (or `null` when not pure).
|
|
78427
|
+
*
|
|
78428
|
+
* @public
|
|
78429
|
+
*/
|
|
78430
|
+
function isPureDependencyChangeset(content) {
|
|
78431
|
+
const fmMatch = content.match(/^---\n([\s\S]*?)\n---\n?([\s\S]*)$/);
|
|
78432
|
+
if (!fmMatch) return {
|
|
78433
|
+
isPure: false,
|
|
78434
|
+
package: null
|
|
78435
|
+
};
|
|
78436
|
+
const frontmatter = fmMatch[1];
|
|
78437
|
+
const body = (fmMatch[2] ?? "").trim();
|
|
78438
|
+
const fmLines = frontmatter.split(/\r?\n/).filter((l) => l.trim().length > 0 && !/^\s*#/.test(l));
|
|
78439
|
+
if (fmLines.length !== 1) return {
|
|
78440
|
+
isPure: false,
|
|
78441
|
+
package: null
|
|
78442
|
+
};
|
|
78443
|
+
const pkgMatch = fmLines[0].match(/^\s*["']?([^"':\s]+)["']?\s*:\s*([a-z]+)\s*$/);
|
|
78444
|
+
if (!pkgMatch) return {
|
|
78445
|
+
isPure: false,
|
|
78446
|
+
package: null
|
|
78447
|
+
};
|
|
78448
|
+
const pkg = pkgMatch[1];
|
|
78449
|
+
const bodyTrimmed = body.replace(/^\s+/, "");
|
|
78450
|
+
if (!/^## Dependencies\b/.test(bodyTrimmed)) return {
|
|
78451
|
+
isPure: false,
|
|
78452
|
+
package: null
|
|
78453
|
+
};
|
|
78454
|
+
if ((bodyTrimmed.match(/^## /gm) ?? []).length !== 1) return {
|
|
78455
|
+
isPure: false,
|
|
78456
|
+
package: null
|
|
78457
|
+
};
|
|
78458
|
+
if (/^# /m.test(bodyTrimmed)) return {
|
|
78459
|
+
isPure: false,
|
|
78460
|
+
package: null
|
|
78461
|
+
};
|
|
78462
|
+
return {
|
|
78463
|
+
isPure: true,
|
|
78464
|
+
package: pkg
|
|
78465
|
+
};
|
|
78466
|
+
}
|
|
78467
|
+
function listChangesetFiles(changesetDir) {
|
|
78468
|
+
if (!(0, node_fs.existsSync)(changesetDir)) return [];
|
|
78469
|
+
return (0, node_fs.readdirSync)(changesetDir).filter((f) => f.endsWith(".md") && f !== "README.md").map((f) => (0, node_path.join)(changesetDir, f));
|
|
78470
|
+
}
|
|
78471
|
+
function findPureDependencyChangesets(changesetDir) {
|
|
78472
|
+
const result = [];
|
|
78473
|
+
for (const file of listChangesetFiles(changesetDir)) {
|
|
78474
|
+
let content;
|
|
78475
|
+
try {
|
|
78476
|
+
content = (0, node_fs.readFileSync)(file, "utf8");
|
|
78477
|
+
} catch {
|
|
78478
|
+
continue;
|
|
78479
|
+
}
|
|
78480
|
+
const detection = isPureDependencyChangeset(content);
|
|
78481
|
+
if (detection.isPure && detection.package) result.push({
|
|
78482
|
+
file,
|
|
78483
|
+
package: detection.package
|
|
78484
|
+
});
|
|
78485
|
+
}
|
|
78486
|
+
return result;
|
|
78487
|
+
}
|
|
78488
|
+
function findMixedDependencyChangesets(changesetDir) {
|
|
78489
|
+
const result = [];
|
|
78490
|
+
for (const file of listChangesetFiles(changesetDir)) {
|
|
78491
|
+
let content;
|
|
78492
|
+
try {
|
|
78493
|
+
content = (0, node_fs.readFileSync)(file, "utf8");
|
|
78494
|
+
} catch {
|
|
78495
|
+
continue;
|
|
78496
|
+
}
|
|
78497
|
+
if (/^## Dependencies\b/m.test(content) && !isPureDependencyChangeset(content).isPure) result.push(file);
|
|
78498
|
+
}
|
|
78499
|
+
return result;
|
|
78500
|
+
}
|
|
78501
|
+
/**
|
|
78502
|
+
* Render a single-package, patch-bump changeset for a diff whose rows have
|
|
78503
|
+
* already been resolved/filtered by {@link resolveDiffRows}.
|
|
78504
|
+
*/
|
|
78505
|
+
function renderChangesetContent(diff) {
|
|
78506
|
+
return `${`---\n"${diff.package}": patch\n---`}\n\n## Dependencies\n\n${serializeDependencyTableToMarkdown([...diff.rows])}\n`;
|
|
78507
|
+
}
|
|
78508
|
+
/**
|
|
78509
|
+
* @internal
|
|
78510
|
+
*/
|
|
78511
|
+
const DepsRegenBase = effect.Context.Tag("Changesets/DepsRegen")();
|
|
78512
|
+
/**
|
|
78513
|
+
* Effect service tag for {@link DepsRegenShape}.
|
|
78514
|
+
*
|
|
78515
|
+
* @example
|
|
78516
|
+
* ```typescript
|
|
78517
|
+
* import { Effect } from "effect";
|
|
78518
|
+
* import { Changesets } from "@savvy-web/silk-effects";
|
|
78519
|
+
*
|
|
78520
|
+
* const program = Effect.gen(function* () {
|
|
78521
|
+
* const svc = yield* Changesets.DepsRegen;
|
|
78522
|
+
* const plan = yield* svc.plan({ cwd: process.cwd() });
|
|
78523
|
+
* return yield* svc.execute(plan);
|
|
78524
|
+
* });
|
|
78525
|
+
* ```
|
|
78526
|
+
*
|
|
78527
|
+
* @public
|
|
78528
|
+
*/
|
|
78529
|
+
var DepsRegen = class extends DepsRegenBase {};
|
|
78530
|
+
/**
|
|
78531
|
+
* Build a {@link DepsRegenShape} that closes over already-resolved service
|
|
78532
|
+
* implementations, keeping the public `plan`/`execute` signatures
|
|
78533
|
+
* requirement-free (`R = never`).
|
|
78534
|
+
*/
|
|
78535
|
+
function makeShape$1(reader, inspector, discovery, resolver, detector) {
|
|
78536
|
+
const provideResolver = effect.Layer.succeed(CatalogResolver, resolver);
|
|
78537
|
+
const provideDetector = effect.Layer.succeed(PublishabilityDetector, detector);
|
|
78538
|
+
const plan = (options) => effect.Effect.gen(function* () {
|
|
78539
|
+
const resolvedCwd = (0, node_path.resolve)(options.cwd);
|
|
78540
|
+
const changesetDir = (0, node_path.join)(resolvedCwd, ".changeset");
|
|
78541
|
+
let fromRef = options.from;
|
|
78542
|
+
if (!fromRef) {
|
|
78543
|
+
let baseBranch = options.base;
|
|
78544
|
+
if (!baseBranch) baseBranch = (yield* inspector.inspect(resolvedCwd).pipe(effect.Effect.catchTag("ConfigurationError", () => effect.Effect.succeed({ baseBranch: "main" })))).baseBranch;
|
|
78545
|
+
fromRef = yield* gitMergeBase(resolvedCwd, baseBranch);
|
|
78546
|
+
}
|
|
78547
|
+
const rawDiffs = computeWorkspaceDependencyDiffs(yield* reader.snapshotAt(resolvedCwd, fromRef), options.to ? yield* reader.snapshotAt(resolvedCwd, options.to) : snapshotFromWorktree(resolvedCwd));
|
|
78548
|
+
const targetPkg = options.package;
|
|
78549
|
+
const publishable = yield* listPublishablePackageNames(yield* discovery.listPackages(resolvedCwd)).pipe(effect.Effect.provide(provideDetector));
|
|
78550
|
+
const keepDevDeps = options.includeDevDeps === true;
|
|
78551
|
+
const scoped = targetPkg ? rawDiffs.filter((d) => d.package === targetPkg) : rawDiffs.filter((d) => publishable.has(d.package));
|
|
78552
|
+
const resolved = [];
|
|
78553
|
+
for (const diff of scoped) {
|
|
78554
|
+
const next = yield* resolveDiffRows(diff, keepDevDeps).pipe(effect.Effect.provide(provideResolver));
|
|
78555
|
+
if (next.rows.length > 0) resolved.push(next);
|
|
78556
|
+
}
|
|
78557
|
+
const existingPure = findPureDependencyChangesets(changesetDir);
|
|
78558
|
+
const skippedMixed = findMixedDependencyChangesets(changesetDir);
|
|
78559
|
+
const toDelete = targetPkg ? existingPure.filter((p) => p.package === targetPkg) : existingPure.filter((p) => publishable.has(p.package));
|
|
78560
|
+
const chosenFilenames = /* @__PURE__ */ new Set();
|
|
78561
|
+
return {
|
|
78562
|
+
toDelete,
|
|
78563
|
+
toWrite: resolved.map((diff) => ({
|
|
78564
|
+
file: (0, node_path.join)(changesetDir, `${randomFilename(changesetDir, chosenFilenames)}.md`),
|
|
78565
|
+
package: diff.package,
|
|
78566
|
+
diff
|
|
78567
|
+
})),
|
|
78568
|
+
skippedMixed
|
|
78569
|
+
};
|
|
78570
|
+
});
|
|
78571
|
+
const execute = (plan) => effect.Effect.sync(() => {
|
|
78572
|
+
const deleted = [];
|
|
78573
|
+
const written = [];
|
|
78574
|
+
for (const entry of plan.toWrite) {
|
|
78575
|
+
(0, node_fs.writeFileSync)(entry.file, renderChangesetContent(entry.diff));
|
|
78576
|
+
written.push(entry.file);
|
|
78577
|
+
}
|
|
78578
|
+
for (const entry of plan.toDelete) try {
|
|
78579
|
+
(0, node_fs.unlinkSync)(entry.file);
|
|
78580
|
+
deleted.push(entry.file);
|
|
78581
|
+
} catch {}
|
|
78582
|
+
return {
|
|
78583
|
+
deleted,
|
|
78584
|
+
written,
|
|
78585
|
+
skippedMixed: plan.skippedMixed
|
|
78586
|
+
};
|
|
78587
|
+
});
|
|
78588
|
+
return {
|
|
78589
|
+
plan,
|
|
78590
|
+
execute
|
|
78591
|
+
};
|
|
78592
|
+
}
|
|
78593
|
+
/**
|
|
78594
|
+
* Live layer for {@link DepsRegen}.
|
|
78595
|
+
*
|
|
78596
|
+
* Requires {@link WorkspaceSnapshotReader}, {@link ConfigInspector},
|
|
78597
|
+
* `WorkspaceDiscovery`, `CatalogResolver`, and `PublishabilityDetector`
|
|
78598
|
+
* (the last three from `workspaces-effect`).
|
|
78599
|
+
*
|
|
78600
|
+
* @public
|
|
78601
|
+
*/
|
|
78602
|
+
const DepsRegenLive = effect.Layer.effect(DepsRegen, effect.Effect.gen(function* () {
|
|
78603
|
+
return makeShape$1(yield* WorkspaceSnapshotReader, yield* ConfigInspector, yield* WorkspaceDiscovery, yield* CatalogResolver, yield* PublishabilityDetector);
|
|
78604
|
+
}));
|
|
78605
|
+
//#endregion
|
|
77856
78606
|
//#region ../silk-effects/dist/dev/pkg/changesets/utils/jsonpath.js
|
|
77857
78607
|
/**
|
|
77858
78608
|
* Tokenize a JSONPath string into segments.
|
|
@@ -102968,7 +103718,7 @@ const ReleasePlannerBase = effect.Context.Tag("ReleasePlanner")();
|
|
|
102968
103718
|
/** Effect service tag for the release planner. @public */
|
|
102969
103719
|
var ReleasePlanner = class extends ReleasePlannerBase {};
|
|
102970
103720
|
/** Build the service shape over a resolved {@link ConfigInspector}. */
|
|
102971
|
-
function makeShape
|
|
103721
|
+
function makeShape(inspector) {
|
|
102972
103722
|
const plan = (root) => effect.Effect.tryPromise({
|
|
102973
103723
|
try: () => getReleasePlan(root),
|
|
102974
103724
|
catch: (e) => new ReleasePlanError({
|
|
@@ -102992,7 +103742,7 @@ function makeShape$1(inspector) {
|
|
|
102992
103742
|
}
|
|
102993
103743
|
/** Production layer. Requires {@link ConfigInspector} (used by `apply`). @public */
|
|
102994
103744
|
const ReleasePlannerLive = effect.Layer.effect(ReleasePlanner, effect.Effect.gen(function* () {
|
|
102995
|
-
return makeShape
|
|
103745
|
+
return makeShape(yield* ConfigInspector);
|
|
102996
103746
|
}));
|
|
102997
103747
|
/**
|
|
102998
103748
|
* Test factory — supply fixed results for any subset of methods. Unsupplied
|
|
@@ -103177,160 +103927,6 @@ function applyEffect(root, dryRun, inspector) {
|
|
|
103177
103927
|
});
|
|
103178
103928
|
}
|
|
103179
103929
|
//#endregion
|
|
103180
|
-
//#region ../silk-effects/dist/dev/pkg/changesets/services/workspace-snapshot.js
|
|
103181
|
-
/**
|
|
103182
|
-
* @internal
|
|
103183
|
-
*/
|
|
103184
|
-
const WorkspaceSnapshotReaderBase = effect.Context.Tag("WorkspaceSnapshotReader")();
|
|
103185
|
-
/**
|
|
103186
|
-
* Effect service tag for {@link WorkspaceSnapshotReaderShape}.
|
|
103187
|
-
*
|
|
103188
|
-
* @public
|
|
103189
|
-
*/
|
|
103190
|
-
var WorkspaceSnapshotReader = class extends WorkspaceSnapshotReaderBase {};
|
|
103191
|
-
function runGitShow(cwd, ref, path) {
|
|
103192
|
-
return effect.Effect.try({
|
|
103193
|
-
try: () => (0, node_child_process.execFileSync)("git", ["show", `${ref}:${path}`], {
|
|
103194
|
-
cwd,
|
|
103195
|
-
encoding: "utf8",
|
|
103196
|
-
stdio: [
|
|
103197
|
-
"ignore",
|
|
103198
|
-
"pipe",
|
|
103199
|
-
"pipe"
|
|
103200
|
-
]
|
|
103201
|
-
}),
|
|
103202
|
-
catch: (error) => {
|
|
103203
|
-
const stderr = error.stderr;
|
|
103204
|
-
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
103205
|
-
if (/exists on disk, but not in|does not exist|unknown revision|bad object/.test(text)) return new GitError$1({
|
|
103206
|
-
command: `git show ${ref}:${path}`,
|
|
103207
|
-
cwd,
|
|
103208
|
-
reason: "PATH_NOT_AT_REF"
|
|
103209
|
-
});
|
|
103210
|
-
return new GitError$1({
|
|
103211
|
-
command: `git show ${ref}:${path}`,
|
|
103212
|
-
cwd,
|
|
103213
|
-
reason: text.trim() || (error.message ?? String(error))
|
|
103214
|
-
});
|
|
103215
|
-
}
|
|
103216
|
-
}).pipe(effect.Effect.catchTag("GitError", (err) => err.reason === "PATH_NOT_AT_REF" ? effect.Effect.succeed(null) : effect.Effect.fail(err)));
|
|
103217
|
-
}
|
|
103218
|
-
/**
|
|
103219
|
-
* Parse a minimal `pnpm-workspace.yaml` (`packages:` list only). Tolerant
|
|
103220
|
-
* of comments and varied indentation; rejects on missing `packages:` key.
|
|
103221
|
-
*/
|
|
103222
|
-
function parseWorkspaceGlobs(yamlText) {
|
|
103223
|
-
const lines = yamlText.split(/\r?\n/);
|
|
103224
|
-
const globs = [];
|
|
103225
|
-
let inPackagesBlock = false;
|
|
103226
|
-
for (const line of lines) {
|
|
103227
|
-
if (/^\s*#/.test(line)) continue;
|
|
103228
|
-
if (/^\s*packages\s*:\s*$/.test(line)) {
|
|
103229
|
-
inPackagesBlock = true;
|
|
103230
|
-
continue;
|
|
103231
|
-
}
|
|
103232
|
-
if (inPackagesBlock) {
|
|
103233
|
-
const match = line.match(/^\s+-\s+["']?(.+?)["']?\s*$/);
|
|
103234
|
-
if (match) {
|
|
103235
|
-
globs.push(match[1]);
|
|
103236
|
-
continue;
|
|
103237
|
-
}
|
|
103238
|
-
if (line.length > 0 && !line.startsWith(" ") && !line.startsWith(" ")) inPackagesBlock = false;
|
|
103239
|
-
}
|
|
103240
|
-
}
|
|
103241
|
-
return globs;
|
|
103242
|
-
}
|
|
103243
|
-
function toSnapshot(pkg, relativePath) {
|
|
103244
|
-
if (!pkg.name) return null;
|
|
103245
|
-
return {
|
|
103246
|
-
name: pkg.name,
|
|
103247
|
-
relativePath,
|
|
103248
|
-
version: pkg.version ?? "0.0.0",
|
|
103249
|
-
dependencies: pkg.dependencies ?? {},
|
|
103250
|
-
devDependencies: pkg.devDependencies ?? {},
|
|
103251
|
-
peerDependencies: pkg.peerDependencies ?? {},
|
|
103252
|
-
optionalDependencies: pkg.optionalDependencies ?? {}
|
|
103253
|
-
};
|
|
103254
|
-
}
|
|
103255
|
-
/**
|
|
103256
|
-
* Expand a workspace glob like `packages/*` or `apps/web` against the
|
|
103257
|
-
* directories present at the given git ref. We can't `globSync` here
|
|
103258
|
-
* (the directories may not be on disk at this ref); instead we use
|
|
103259
|
-
* `git ls-tree` to enumerate paths.
|
|
103260
|
-
*/
|
|
103261
|
-
function expandGlobAtRef(cwd, ref, glob) {
|
|
103262
|
-
return effect.Effect.gen(function* () {
|
|
103263
|
-
const cleanGlob = glob.replace(/\/\*\*$/, "/*");
|
|
103264
|
-
if (!cleanGlob.includes("*") && !cleanGlob.includes("?")) return [cleanGlob];
|
|
103265
|
-
const prefix = cleanGlob.includes("/") ? cleanGlob.slice(0, cleanGlob.lastIndexOf("/") + 1) : "";
|
|
103266
|
-
const entries = (yield* effect.Effect.try({
|
|
103267
|
-
try: () => (0, node_child_process.execFileSync)("git", [
|
|
103268
|
-
"ls-tree",
|
|
103269
|
-
"--name-only",
|
|
103270
|
-
ref,
|
|
103271
|
-
prefix
|
|
103272
|
-
], {
|
|
103273
|
-
cwd,
|
|
103274
|
-
encoding: "utf8",
|
|
103275
|
-
stdio: [
|
|
103276
|
-
"ignore",
|
|
103277
|
-
"pipe",
|
|
103278
|
-
"pipe"
|
|
103279
|
-
]
|
|
103280
|
-
}),
|
|
103281
|
-
catch: (error) => {
|
|
103282
|
-
const stderr = error.stderr;
|
|
103283
|
-
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
103284
|
-
return new GitError$1({
|
|
103285
|
-
command: `git ls-tree ${ref} ${prefix}`,
|
|
103286
|
-
cwd,
|
|
103287
|
-
reason: text.trim() || (error.message ?? String(error))
|
|
103288
|
-
});
|
|
103289
|
-
}
|
|
103290
|
-
})).split(/\r?\n/).map((s) => s.trim()).filter((s) => s.length > 0);
|
|
103291
|
-
const regex = new RegExp(`^${cleanGlob.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, "[^/]*").replace(/\?/g, "[^/]")}$`);
|
|
103292
|
-
return entries.filter((e) => regex.test(e));
|
|
103293
|
-
});
|
|
103294
|
-
}
|
|
103295
|
-
function makeShape() {
|
|
103296
|
-
const cache = /* @__PURE__ */ new Map();
|
|
103297
|
-
const snapshotAt = (cwd, ref) => effect.Effect.gen(function* () {
|
|
103298
|
-
const cacheKey = `${cwd}::${ref}`;
|
|
103299
|
-
const cached = cache.get(cacheKey);
|
|
103300
|
-
if (cached) return cached;
|
|
103301
|
-
const wsYaml = yield* runGitShow(cwd, ref, "pnpm-workspace.yaml");
|
|
103302
|
-
const globs = wsYaml ? parseWorkspaceGlobs(wsYaml) : [];
|
|
103303
|
-
const dirs = [];
|
|
103304
|
-
for (const glob of globs) {
|
|
103305
|
-
const expanded = yield* expandGlobAtRef(cwd, ref, glob);
|
|
103306
|
-
for (const d of expanded) if (!dirs.includes(d)) dirs.push(d);
|
|
103307
|
-
}
|
|
103308
|
-
if (!dirs.includes(".")) dirs.unshift(".");
|
|
103309
|
-
const snapshots = [];
|
|
103310
|
-
for (const dir of dirs) {
|
|
103311
|
-
const pkgText = yield* runGitShow(cwd, ref, dir === "." ? "package.json" : `${dir}/package.json`);
|
|
103312
|
-
if (!pkgText) continue;
|
|
103313
|
-
let parsed;
|
|
103314
|
-
try {
|
|
103315
|
-
parsed = JSON.parse(pkgText);
|
|
103316
|
-
} catch {
|
|
103317
|
-
continue;
|
|
103318
|
-
}
|
|
103319
|
-
const snap = toSnapshot(parsed, dir);
|
|
103320
|
-
if (snap) snapshots.push(snap);
|
|
103321
|
-
}
|
|
103322
|
-
cache.set(cacheKey, snapshots);
|
|
103323
|
-
return snapshots;
|
|
103324
|
-
});
|
|
103325
|
-
return { snapshotAt };
|
|
103326
|
-
}
|
|
103327
|
-
/**
|
|
103328
|
-
* Production layer for {@link WorkspaceSnapshotReader}.
|
|
103329
|
-
*
|
|
103330
|
-
* @public
|
|
103331
|
-
*/
|
|
103332
|
-
const WorkspaceSnapshotReaderLive = effect.Layer.succeed(WorkspaceSnapshotReader, makeShape());
|
|
103333
|
-
//#endregion
|
|
103334
103930
|
//#region ../silk-effects/dist/dev/pkg/changesets/categories/types.js
|
|
103335
103931
|
/**
|
|
103336
103932
|
* Section category schema and type definitions.
|
|
@@ -103647,246 +104243,6 @@ const AppliedReleaseSchema = effect.Schema.Struct({
|
|
|
103647
104243
|
versionFileUpdates: effect.Schema.Array(VersionFileUpdateRecordSchema)
|
|
103648
104244
|
}).annotations({ identifier: "AppliedRelease" });
|
|
103649
104245
|
//#endregion
|
|
103650
|
-
//#region ../silk-effects/dist/dev/pkg/changesets/utils/dep-diff.js
|
|
103651
|
-
const EM_DASH$2 = "—";
|
|
103652
|
-
const DEP_TYPE_MAP = [
|
|
103653
|
-
["dependencies", "dependency"],
|
|
103654
|
-
["devDependencies", "devDependency"],
|
|
103655
|
-
["peerDependencies", "peerDependency"],
|
|
103656
|
-
["optionalDependencies", "optionalDependency"]
|
|
103657
|
-
];
|
|
103658
|
-
function diffOneRecord(before, after, type) {
|
|
103659
|
-
const rows = [];
|
|
103660
|
-
const seen = /* @__PURE__ */ new Set();
|
|
103661
|
-
for (const [name, beforeVersion] of Object.entries(before)) {
|
|
103662
|
-
seen.add(name);
|
|
103663
|
-
const afterVersion = after[name];
|
|
103664
|
-
if (afterVersion === void 0) rows.push({
|
|
103665
|
-
dependency: name,
|
|
103666
|
-
type,
|
|
103667
|
-
action: "removed",
|
|
103668
|
-
from: beforeVersion,
|
|
103669
|
-
to: EM_DASH$2
|
|
103670
|
-
});
|
|
103671
|
-
else if (afterVersion !== beforeVersion) rows.push({
|
|
103672
|
-
dependency: name,
|
|
103673
|
-
type,
|
|
103674
|
-
action: "updated",
|
|
103675
|
-
from: beforeVersion,
|
|
103676
|
-
to: afterVersion
|
|
103677
|
-
});
|
|
103678
|
-
}
|
|
103679
|
-
for (const [name, afterVersion] of Object.entries(after)) {
|
|
103680
|
-
if (seen.has(name)) continue;
|
|
103681
|
-
rows.push({
|
|
103682
|
-
dependency: name,
|
|
103683
|
-
type,
|
|
103684
|
-
action: "added",
|
|
103685
|
-
from: EM_DASH$2,
|
|
103686
|
-
to: afterVersion
|
|
103687
|
-
});
|
|
103688
|
-
}
|
|
103689
|
-
return rows;
|
|
103690
|
-
}
|
|
103691
|
-
/**
|
|
103692
|
-
* Diff two workspace snapshots and return per-package dependency-table rows.
|
|
103693
|
-
*
|
|
103694
|
-
* @param before - Snapshot at the older ref (typically the merge base). Pass
|
|
103695
|
-
* `null` for workspace packages that did not exist at the older ref — every
|
|
103696
|
-
* declared dep is then reported as `"added"`.
|
|
103697
|
-
* @param after - Snapshot at the newer ref (typically the working tree).
|
|
103698
|
-
* @returns One {@link WorkspaceDependencyDiff} entry per workspace package
|
|
103699
|
-
* that has at least one row. Packages with no changes are omitted.
|
|
103700
|
-
*
|
|
103701
|
-
* @public
|
|
103702
|
-
*/
|
|
103703
|
-
function computeWorkspaceDependencyDiffs(beforeSnapshots, afterSnapshots) {
|
|
103704
|
-
const beforeByName = new Map(beforeSnapshots.map((s) => [s.name, s]));
|
|
103705
|
-
const result = [];
|
|
103706
|
-
for (const after of afterSnapshots) {
|
|
103707
|
-
const before = beforeByName.get(after.name);
|
|
103708
|
-
const rows = [];
|
|
103709
|
-
for (const [field, type] of DEP_TYPE_MAP) {
|
|
103710
|
-
const beforeRecord = before?.[field] ?? {};
|
|
103711
|
-
const afterRecord = after[field];
|
|
103712
|
-
rows.push(...diffOneRecord(beforeRecord, afterRecord, type));
|
|
103713
|
-
}
|
|
103714
|
-
if (rows.length > 0) result.push({
|
|
103715
|
-
package: after.name,
|
|
103716
|
-
relativePath: after.relativePath,
|
|
103717
|
-
rows: sortDependencyRows(rows)
|
|
103718
|
-
});
|
|
103719
|
-
}
|
|
103720
|
-
return result;
|
|
103721
|
-
}
|
|
103722
|
-
//#endregion
|
|
103723
|
-
//#region ../silk-effects/dist/dev/pkg/changesets/utils/publishability.js
|
|
103724
|
-
/**
|
|
103725
|
-
* Publishability helpers for the changeset CLI commands.
|
|
103726
|
-
*
|
|
103727
|
-
* @remarks
|
|
103728
|
-
* Provides `listPublishablePackageNames`, a convenience wrapper around
|
|
103729
|
-
* {@link SilkPublishability} that returns a `Set<string>` of
|
|
103730
|
-
* publishable package names. Used by the `deps detect` and `deps regen`
|
|
103731
|
-
* commands to filter out workspace packages whose dependency changes
|
|
103732
|
-
* would never reach a release.
|
|
103733
|
-
*
|
|
103734
|
-
*/
|
|
103735
|
-
/**
|
|
103736
|
-
* Compute the set of currently-publishable workspace package names.
|
|
103737
|
-
*
|
|
103738
|
-
* @remarks
|
|
103739
|
-
* Uses the currently-active {@link SilkPublishability} — wire the
|
|
103740
|
-
* {@link SilkPublishabilityDetectorLive} layer to get silk semantics.
|
|
103741
|
-
*
|
|
103742
|
-
* @param packages - The workspace packages to evaluate
|
|
103743
|
-
* @returns An Effect yielding a `Set` of publishable package names
|
|
103744
|
-
*
|
|
103745
|
-
* @public
|
|
103746
|
-
*/
|
|
103747
|
-
function listPublishablePackageNames(packages) {
|
|
103748
|
-
return effect.Effect.gen(function* () {
|
|
103749
|
-
const detector = yield* PublishabilityDetector;
|
|
103750
|
-
const names = /* @__PURE__ */ new Set();
|
|
103751
|
-
for (const pkg of packages) if ((yield* detector.detect(pkg, pkg.path)).length > 0) names.add(pkg.name);
|
|
103752
|
-
return names;
|
|
103753
|
-
});
|
|
103754
|
-
}
|
|
103755
|
-
//#endregion
|
|
103756
|
-
//#region ../silk-effects/dist/dev/pkg/changesets/utils/worktree-snapshot.js
|
|
103757
|
-
/**
|
|
103758
|
-
* Shared helpers for `deps detect` and `deps regen` — both need to read
|
|
103759
|
-
* workspace package snapshots from the live working tree (the "after"
|
|
103760
|
-
* side of a dep diff that isn't pinned to a git ref) and to resolve the
|
|
103761
|
-
* merge-base for the default `--from` ref.
|
|
103762
|
-
*
|
|
103763
|
-
* @remarks
|
|
103764
|
-
* `WorkspaceSnapshotReader` covers the git-ref side via `git show`. This
|
|
103765
|
-
* module is the working-tree counterpart — staged and unstaged
|
|
103766
|
-
* `package.json` edits show up here, matching `analyze-branch`'s
|
|
103767
|
-
* coverage of the working tree.
|
|
103768
|
-
*
|
|
103769
|
-
* @internal
|
|
103770
|
-
*/
|
|
103771
|
-
/**
|
|
103772
|
-
* Run `git merge-base <base> HEAD`, returning the SHA. Errors propagate
|
|
103773
|
-
* as {@link GitError}.
|
|
103774
|
-
*
|
|
103775
|
-
* @internal
|
|
103776
|
-
*/
|
|
103777
|
-
function gitMergeBase(cwd, base) {
|
|
103778
|
-
return effect.Effect.try({
|
|
103779
|
-
try: () => (0, node_child_process.execFileSync)("git", [
|
|
103780
|
-
"merge-base",
|
|
103781
|
-
base,
|
|
103782
|
-
"HEAD"
|
|
103783
|
-
], {
|
|
103784
|
-
cwd,
|
|
103785
|
-
encoding: "utf8",
|
|
103786
|
-
stdio: [
|
|
103787
|
-
"ignore",
|
|
103788
|
-
"pipe",
|
|
103789
|
-
"pipe"
|
|
103790
|
-
]
|
|
103791
|
-
}).trim(),
|
|
103792
|
-
catch: (error) => {
|
|
103793
|
-
const stderr = error.stderr;
|
|
103794
|
-
const text = typeof stderr === "string" ? stderr : stderr?.toString() ?? "";
|
|
103795
|
-
return new GitError$1({
|
|
103796
|
-
command: `git merge-base ${base} HEAD`,
|
|
103797
|
-
cwd,
|
|
103798
|
-
reason: text.trim() || (error.message ?? String(error))
|
|
103799
|
-
});
|
|
103800
|
-
}
|
|
103801
|
-
});
|
|
103802
|
-
}
|
|
103803
|
-
/**
|
|
103804
|
-
* Normalize a pnpm-workspace.yaml glob entry for filesystem expansion.
|
|
103805
|
-
*
|
|
103806
|
-
* `packages/**` collapses to `packages/*` (retains the wildcard so the
|
|
103807
|
-
* caller hits the directory-listing path); `packages/*` and a literal
|
|
103808
|
-
* `packages/foo` are passed through unchanged.
|
|
103809
|
-
*
|
|
103810
|
-
* Returning the literal-path form for `packages/**` (i.e., `"packages"`)
|
|
103811
|
-
* would route the caller through the "no wildcards" branch and silently
|
|
103812
|
-
* skip every child workspace.
|
|
103813
|
-
*
|
|
103814
|
-
* @internal
|
|
103815
|
-
*/
|
|
103816
|
-
function normalizeWorkspaceGlob(glob) {
|
|
103817
|
-
return glob.replace(/\/\*\*$/, "/*");
|
|
103818
|
-
}
|
|
103819
|
-
/**
|
|
103820
|
-
* Read every workspace package's `package.json` from the live working
|
|
103821
|
-
* tree, returning {@link WorkspaceSnapshot} entries matching the shape
|
|
103822
|
-
* `WorkspaceSnapshotReader.snapshotAt` produces for git refs.
|
|
103823
|
-
*
|
|
103824
|
-
* @remarks
|
|
103825
|
-
* Falls back to root-only when `pnpm-workspace.yaml` is missing or
|
|
103826
|
-
* unparseable. Uses `node:fs.readdirSync` for directory expansion
|
|
103827
|
-
* (portable across platforms — `execFileSync("ls")` is not).
|
|
103828
|
-
*
|
|
103829
|
-
* @internal
|
|
103830
|
-
*/
|
|
103831
|
-
function snapshotFromWorktree(cwd) {
|
|
103832
|
-
const snapshots = [];
|
|
103833
|
-
const dirs = /* @__PURE__ */ new Set([cwd]);
|
|
103834
|
-
for (const dir of expandWorkspaceDirs(cwd)) dirs.add(dir);
|
|
103835
|
-
for (const dir of dirs) try {
|
|
103836
|
-
const pkgJson = JSON.parse((0, node_fs.readFileSync)((0, node_path.join)(dir, "package.json"), "utf8"));
|
|
103837
|
-
if (!pkgJson.name) continue;
|
|
103838
|
-
const rel = dir === cwd ? "." : dir.slice(cwd.length + 1);
|
|
103839
|
-
snapshots.push({
|
|
103840
|
-
name: pkgJson.name,
|
|
103841
|
-
relativePath: rel,
|
|
103842
|
-
version: pkgJson.version ?? "0.0.0",
|
|
103843
|
-
dependencies: pkgJson.dependencies ?? {},
|
|
103844
|
-
devDependencies: pkgJson.devDependencies ?? {},
|
|
103845
|
-
peerDependencies: pkgJson.peerDependencies ?? {},
|
|
103846
|
-
optionalDependencies: pkgJson.optionalDependencies ?? {}
|
|
103847
|
-
});
|
|
103848
|
-
} catch {}
|
|
103849
|
-
return snapshots;
|
|
103850
|
-
}
|
|
103851
|
-
function expandWorkspaceDirs(cwd) {
|
|
103852
|
-
let yaml;
|
|
103853
|
-
try {
|
|
103854
|
-
yaml = (0, node_fs.readFileSync)((0, node_path.join)(cwd, "pnpm-workspace.yaml"), "utf8");
|
|
103855
|
-
} catch {
|
|
103856
|
-
return [];
|
|
103857
|
-
}
|
|
103858
|
-
const dirs = [];
|
|
103859
|
-
const lines = yaml.split(/\r?\n/);
|
|
103860
|
-
let inPackagesBlock = false;
|
|
103861
|
-
for (const line of lines) {
|
|
103862
|
-
if (/^\s*#/.test(line)) continue;
|
|
103863
|
-
if (/^\s*packages\s*:\s*$/.test(line)) {
|
|
103864
|
-
inPackagesBlock = true;
|
|
103865
|
-
continue;
|
|
103866
|
-
}
|
|
103867
|
-
if (!inPackagesBlock) continue;
|
|
103868
|
-
const m = line.match(/^\s+-\s+["']?(.+?)["']?\s*$/);
|
|
103869
|
-
if (m) {
|
|
103870
|
-
const glob = normalizeWorkspaceGlob(m[1]);
|
|
103871
|
-
if (glob.includes("*") || glob.includes("?")) {
|
|
103872
|
-
const prefix = glob.includes("/") ? glob.slice(0, glob.lastIndexOf("/") + 1) : "";
|
|
103873
|
-
let entries = [];
|
|
103874
|
-
try {
|
|
103875
|
-
entries = (0, node_fs.readdirSync)((0, node_path.join)(cwd, prefix || "."));
|
|
103876
|
-
} catch {
|
|
103877
|
-
continue;
|
|
103878
|
-
}
|
|
103879
|
-
const regex = new RegExp(`^${glob.replace(/[.+^${}()|[\]\\]/g, "\\$&").replace(/\*/g, "[^/]*").replace(/\?/g, "[^/]")}$`);
|
|
103880
|
-
for (const entry of entries) {
|
|
103881
|
-
const candidate = prefix ? `${prefix}${entry}` : entry;
|
|
103882
|
-
if (regex.test(candidate)) dirs.push((0, node_path.join)(cwd, candidate));
|
|
103883
|
-
}
|
|
103884
|
-
} else dirs.push((0, node_path.join)(cwd, glob));
|
|
103885
|
-
} else if (line.length > 0 && !line.startsWith(" ") && !line.startsWith(" ")) inPackagesBlock = false;
|
|
103886
|
-
}
|
|
103887
|
-
return dirs;
|
|
103888
|
-
}
|
|
103889
|
-
//#endregion
|
|
103890
104246
|
//#region ../silk-effects/dist/dev/pkg/changesets/markdownlint/rules/utils.js
|
|
103891
104247
|
/**
|
|
103892
104248
|
* Get the heading level (1-6) from an `atxHeading` token.
|
|
@@ -104007,7 +104363,7 @@ const ContentStructureRule = {
|
|
|
104007
104363
|
};
|
|
104008
104364
|
//#endregion
|
|
104009
104365
|
//#region ../silk-effects/dist/dev/pkg/changesets/markdownlint/rules/dependency-table-format.js
|
|
104010
|
-
const EM_DASH
|
|
104366
|
+
const EM_DASH = "—";
|
|
104011
104367
|
const VALID_TYPES = /* @__PURE__ */ new Set([
|
|
104012
104368
|
"dependency",
|
|
104013
104369
|
"devDependency",
|
|
@@ -104028,7 +104384,6 @@ const EXPECTED_HEADERS = [
|
|
|
104028
104384
|
"from",
|
|
104029
104385
|
"to"
|
|
104030
104386
|
];
|
|
104031
|
-
const VERSION_RE = /^(\u2014|[~^]?\d+\.\d+\.\d+(?:[-+.][\w.+-]*)?)$/;
|
|
104032
104387
|
/**
|
|
104033
104388
|
* Extract text from a `tableHeader` or `tableData` cell token.
|
|
104034
104389
|
*
|
|
@@ -104060,7 +104415,7 @@ function getRowCells(row) {
|
|
|
104060
104415
|
*
|
|
104061
104416
|
* @public
|
|
104062
104417
|
*/
|
|
104063
|
-
const DependencyTableFormatRule
|
|
104418
|
+
const DependencyTableFormatRule = {
|
|
104064
104419
|
names: ["changeset-dependency-table-format", "CSH005"],
|
|
104065
104420
|
description: "Dependencies section must contain a valid dependency table",
|
|
104066
104421
|
tags: ["changeset"],
|
|
@@ -104158,11 +104513,11 @@ const DependencyTableFormatRule$1 = {
|
|
|
104158
104513
|
lineNumber: row.startLine,
|
|
104159
104514
|
detail: `Invalid 'to' value '${to}'. Must be a semver string or em dash (\u2014). See: ${RULE_DOCS.CSH005}`
|
|
104160
104515
|
});
|
|
104161
|
-
if (action === "added" && from !== EM_DASH
|
|
104516
|
+
if (action === "added" && from !== EM_DASH) onError({
|
|
104162
104517
|
lineNumber: row.startLine,
|
|
104163
104518
|
detail: `'from' must be '\u2014' when action is 'added' (got '${from}'). See: ${RULE_DOCS.CSH005}`
|
|
104164
104519
|
});
|
|
104165
|
-
if (action === "removed" && to !== EM_DASH
|
|
104520
|
+
if (action === "removed" && to !== EM_DASH) onError({
|
|
104166
104521
|
lineNumber: row.startLine,
|
|
104167
104522
|
detail: `'to' must be '\u2014' when action is 'removed' (got '${to}'). See: ${RULE_DOCS.CSH005}`
|
|
104168
104523
|
});
|
|
@@ -104342,7 +104697,7 @@ const SilkChangesetsRules = [
|
|
|
104342
104697
|
RequiredSectionsRule,
|
|
104343
104698
|
ContentStructureRule,
|
|
104344
104699
|
UncategorizedContentRule,
|
|
104345
|
-
DependencyTableFormatRule
|
|
104700
|
+
DependencyTableFormatRule
|
|
104346
104701
|
];
|
|
104347
104702
|
//#endregion
|
|
104348
104703
|
//#region ../silk-effects/dist/dev/pkg/changesets/remark/plugins/aggregate-dependency-tables.js
|
|
@@ -104387,38 +104742,6 @@ const AggregateDependencyTablesPlugin = () => {
|
|
|
104387
104742
|
};
|
|
104388
104743
|
};
|
|
104389
104744
|
//#endregion
|
|
104390
|
-
//#region ../silk-effects/dist/dev/pkg/changesets/remark/rules/dependency-table-format.js
|
|
104391
|
-
/** @internal */
|
|
104392
|
-
const EM_DASH = "—";
|
|
104393
|
-
const DependencyTableFormatRule = lintRule("remark-lint:changeset-dependency-table-format", (tree, file) => {
|
|
104394
|
-
visit(tree, "heading", (node, index) => {
|
|
104395
|
-
if (node.depth !== 2) return;
|
|
104396
|
-
if (toString(node).toLowerCase() !== "dependencies") return;
|
|
104397
|
-
if (index === void 0) return;
|
|
104398
|
-
const content = [];
|
|
104399
|
-
for (let i = index + 1; i < tree.children.length; i++) {
|
|
104400
|
-
const child = tree.children[i];
|
|
104401
|
-
if (child.type === "heading") break;
|
|
104402
|
-
content.push(child);
|
|
104403
|
-
}
|
|
104404
|
-
const tables = content.filter((n) => n.type === "table");
|
|
104405
|
-
if (tables.length === 0) {
|
|
104406
|
-
file.message(`Dependencies section must contain a table, not a list or paragraph. See: ${RULE_DOCS.CSH005}`, node);
|
|
104407
|
-
return;
|
|
104408
|
-
}
|
|
104409
|
-
const table = tables[0];
|
|
104410
|
-
try {
|
|
104411
|
-
const rows = parseDependencyTable(table);
|
|
104412
|
-
for (const row of rows) {
|
|
104413
|
-
if (row.action === "added" && row.from !== EM_DASH) file.message(`'from' must be '\u2014' when action is 'added' (got '${row.from}'). See: ${RULE_DOCS.CSH005}`, table);
|
|
104414
|
-
if (row.action === "removed" && row.to !== EM_DASH) file.message(`'to' must be '\u2014' when action is 'removed' (got '${row.to}'). See: ${RULE_DOCS.CSH005}`, table);
|
|
104415
|
-
}
|
|
104416
|
-
} catch (error) {
|
|
104417
|
-
file.message(`${error instanceof Error ? error.message : String(error)}. See: ${RULE_DOCS.CSH005}`, table);
|
|
104418
|
-
}
|
|
104419
|
-
});
|
|
104420
|
-
});
|
|
104421
|
-
//#endregion
|
|
104422
104745
|
//#region ../silk-effects/dist/dev/pkg/changesets/remark/presets.js
|
|
104423
104746
|
/**
|
|
104424
104747
|
* Remark preset collections for changeset lint rules and transform plugins.
|
|
@@ -104472,7 +104795,7 @@ const SilkChangesetPreset = [
|
|
|
104472
104795
|
RequiredSectionsRule$1,
|
|
104473
104796
|
ContentStructureRule$1,
|
|
104474
104797
|
UncategorizedContentRule$1,
|
|
104475
|
-
DependencyTableFormatRule
|
|
104798
|
+
DependencyTableFormatRule$1
|
|
104476
104799
|
];
|
|
104477
104800
|
/**
|
|
104478
104801
|
* Ordered array of all transform plugins in the correct execution order.
|
|
@@ -104568,12 +104891,15 @@ const changelogFunctions = (/* @__PURE__ */ __exportAll({
|
|
|
104568
104891
|
DeduplicateItemsPlugin: () => DeduplicateItemsPlugin,
|
|
104569
104892
|
DependencyActionSchema: () => DependencyActionSchema,
|
|
104570
104893
|
DependencyTable: () => DependencyTable,
|
|
104571
|
-
DependencyTableFormatRule: () => DependencyTableFormatRule,
|
|
104894
|
+
DependencyTableFormatRule: () => DependencyTableFormatRule$1,
|
|
104572
104895
|
DependencyTableRowSchema: () => DependencyTableRowSchema,
|
|
104573
104896
|
DependencyTableSchema: () => DependencyTableSchema,
|
|
104574
104897
|
DependencyTableTypeSchema: () => DependencyTableTypeSchema,
|
|
104575
104898
|
DependencyTypeSchema: () => DependencyTypeSchema,
|
|
104576
104899
|
DependencyUpdateSchema: () => DependencyUpdateSchema,
|
|
104900
|
+
DepsRegen: () => DepsRegen,
|
|
104901
|
+
DepsRegenBase: () => DepsRegenBase,
|
|
104902
|
+
DepsRegenLive: () => DepsRegenLive,
|
|
104577
104903
|
FileStatusSchema: () => FileStatusSchema,
|
|
104578
104904
|
GitError: () => GitError$1,
|
|
104579
104905
|
GitErrorBase: () => GitErrorBase,
|
|
@@ -104597,7 +104923,7 @@ const changelogFunctions = (/* @__PURE__ */ __exportAll({
|
|
|
104597
104923
|
MarkdownService: () => MarkdownService,
|
|
104598
104924
|
MarkdownServiceBase: () => MarkdownServiceBase,
|
|
104599
104925
|
MarkdownlintContentStructureRule: () => ContentStructureRule,
|
|
104600
|
-
MarkdownlintDependencyTableFormatRule: () => DependencyTableFormatRule
|
|
104926
|
+
MarkdownlintDependencyTableFormatRule: () => DependencyTableFormatRule,
|
|
104601
104927
|
MarkdownlintHeadingHierarchyRule: () => HeadingHierarchyRule,
|
|
104602
104928
|
MarkdownlintRequiredSectionsRule: () => RequiredSectionsRule,
|
|
104603
104929
|
MarkdownlintUncategorizedContentRule: () => UncategorizedContentRule,
|
|
@@ -104626,6 +104952,7 @@ const changelogFunctions = (/* @__PURE__ */ __exportAll({
|
|
|
104626
104952
|
UncategorizedContentRule: () => UncategorizedContentRule$1,
|
|
104627
104953
|
UrlOrMarkdownLinkSchema: () => UrlOrMarkdownLinkSchema,
|
|
104628
104954
|
UsernameSchema: () => UsernameSchema,
|
|
104955
|
+
VERSION_RE: () => VERSION_RE,
|
|
104629
104956
|
VersionFileConfigSchema: () => VersionFileConfigSchema,
|
|
104630
104957
|
VersionFileError: () => VersionFileError,
|
|
104631
104958
|
VersionFileErrorBase: () => VersionFileErrorBase,
|
|
@@ -104640,11 +104967,13 @@ const changelogFunctions = (/* @__PURE__ */ __exportAll({
|
|
|
104640
104967
|
changelogFunctions: () => changelogFunctions$1,
|
|
104641
104968
|
computeWorkspaceDependencyDiffs: () => computeWorkspaceDependencyDiffs,
|
|
104642
104969
|
gitMergeBase: () => gitMergeBase,
|
|
104970
|
+
isPureDependencyChangeset: () => isPureDependencyChangeset,
|
|
104643
104971
|
listPublishablePackageNames: () => listPublishablePackageNames,
|
|
104644
104972
|
makeBranchAnalyzerTest: () => makeBranchAnalyzerTest,
|
|
104645
104973
|
makeConfigInspectorTest: () => makeConfigInspectorTest,
|
|
104646
104974
|
makeGitHubTest: () => makeGitHubTest,
|
|
104647
104975
|
makeReleasePlannerTest: () => makeReleasePlannerTest,
|
|
104976
|
+
resolveDiffRows: () => resolveDiffRows,
|
|
104648
104977
|
serializeDependencyTableToMarkdown: () => serializeDependencyTableToMarkdown,
|
|
104649
104978
|
snapshotFromWorktree: () => snapshotFromWorktree
|
|
104650
104979
|
})).changelogFunctions;
|