rman 2.0.0-beta.2 → 2.0.0-beta.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (164) hide show
  1. package/README.md +2 -12
  2. package/{plugins/node/augmentation/rman.augmentation.d.ts → builtins/platforms/node/augmentation/rmanrc.augmentation.d.ts} +4 -5
  3. package/{plugins → builtins/platforms}/node/augmentation/system-info.augmentation.js +1 -1
  4. package/{plugins → builtins/platforms}/node/commands/ci.command.d.ts +5 -3
  5. package/{plugins → builtins/platforms}/node/commands/ci.command.js +6 -5
  6. package/{plugins → builtins/platforms}/node/commands/clean.command.d.ts +6 -4
  7. package/{plugins → builtins/platforms}/node/commands/clean.command.js +6 -5
  8. package/builtins/platforms/node/index.d.ts +8 -0
  9. package/builtins/platforms/node/index.js +8 -0
  10. package/{plugins → builtins/platforms}/node/node-config.interface.d.ts +1 -2
  11. package/{plugins → builtins/platforms}/node/node-manifest.provider.d.ts +3 -3
  12. package/{plugins → builtins/platforms}/node/node-manifest.provider.js +3 -3
  13. package/{plugins → builtins/platforms}/node/node.platform.d.ts +3 -3
  14. package/{plugins → builtins/platforms}/node/services/ci.service.d.ts +3 -3
  15. package/{plugins → builtins/platforms}/node/services/ci.service.js +4 -4
  16. package/{plugins → builtins/platforms}/node/services/clean.service.d.ts +3 -3
  17. package/{plugins → builtins/platforms}/node/services/clean.service.js +3 -3
  18. package/{plugins → builtins/platforms}/node/services/publish.service.d.ts +4 -4
  19. package/{plugins → builtins/platforms}/node/services/publish.service.js +5 -5
  20. package/{plugins → builtins/platforms}/node/services/version-plan.service.d.ts +3 -3
  21. package/{plugins → builtins/platforms}/node/services/version-plan.service.js +2 -2
  22. package/builtins/presets/index.d.ts +15 -0
  23. package/builtins/presets/index.js +57 -0
  24. package/builtins/presets/node.d.ts +16 -0
  25. package/builtins/presets/node.js +57 -0
  26. package/{services → builtins/publish-targets/docker}/docker-publish.service.d.ts +6 -6
  27. package/{services → builtins/publish-targets/docker}/docker-publish.service.js +9 -9
  28. package/{targets → builtins/publish-targets/docker}/docker.target.d.ts +6 -5
  29. package/{targets → builtins/publish-targets/docker}/docker.target.js +1 -1
  30. package/builtins/publish-targets/docker/index.d.ts +2 -0
  31. package/builtins/publish-targets/docker/index.js +2 -0
  32. package/builtins/publish-targets/npm/index.d.ts +2 -0
  33. package/builtins/publish-targets/npm/index.js +2 -0
  34. package/{plugins/node → builtins/publish-targets/npm}/npm-publish-target.d.ts +4 -4
  35. package/{plugins/node → builtins/publish-targets/npm}/npm-publish-target.js +4 -5
  36. package/cli.d.ts +3 -0
  37. package/cli.js +16 -7
  38. package/commands/changelog.command.d.ts +106 -2
  39. package/commands/changelog.command.js +40 -0
  40. package/commands/config.command.js +23 -5
  41. package/commands/lint.command.d.ts +176 -0
  42. package/commands/lint.command.js +34 -0
  43. package/commands/list.command.js +1 -1
  44. package/commands/publish.command.d.ts +1 -1
  45. package/commands/publish.command.js +1 -1
  46. package/commands/run.command.js +1 -1
  47. package/commands/version.command.d.ts +16 -3
  48. package/commands/version.command.js +143 -9
  49. package/commands.d.ts +1 -1
  50. package/commands.js +1 -1
  51. package/constants.js +1 -1
  52. package/core/application.d.ts +10 -10
  53. package/core/application.js +28 -11
  54. package/core/{package.d.ts → classes/package.d.ts} +12 -4
  55. package/core/{package.js → classes/package.js} +17 -1
  56. package/core/{repository.d.ts → classes/repository.d.ts} +22 -36
  57. package/core/{repository.js → classes/repository.js} +112 -241
  58. package/core/{service.d.ts → classes/service.d.ts} +2 -2
  59. package/core/classes/workspace.d.ts +275 -0
  60. package/core/classes/workspace.js +537 -0
  61. package/core/command-builder.js +17 -1
  62. package/core/config/config-file-scope.d.ts +107 -0
  63. package/core/config/config-file-scope.js +226 -0
  64. package/core/config/config-interpolator.d.ts +164 -0
  65. package/core/config/config-interpolator.js +577 -0
  66. package/core/config/config-paths.d.ts +65 -0
  67. package/core/config/config-paths.js +78 -0
  68. package/core/config/config-reader.d.ts +192 -0
  69. package/core/config/config-reader.js +727 -0
  70. package/core/{merge-config.js → config/merge-config.js} +4 -8
  71. package/core/{custom-command.d.ts → interfaces/custom-command.d.ts} +5 -5
  72. package/core/{manifest.d.ts → interfaces/manifest.d.ts} +3 -3
  73. package/core/{manifest.js → interfaces/manifest.js} +2 -2
  74. package/core/{plugin.d.ts → interfaces/plugin.d.ts} +44 -27
  75. package/core/{plugin.js → interfaces/plugin.js} +48 -10
  76. package/core/{publish-target.d.ts → interfaces/publish-target.d.ts} +24 -12
  77. package/core/{publish-target.js → interfaces/publish-target.js} +16 -3
  78. package/core/{run-step.d.ts → interfaces/run-step.d.ts} +4 -4
  79. package/core/plugin-loader.d.ts +11 -51
  80. package/core/plugin-loader.js +21 -202
  81. package/index.d.ts +29 -28
  82. package/index.js +20 -46
  83. package/interfaces/config-scope.interface.d.ts +223 -0
  84. package/interfaces/config-scope.interface.js +1 -0
  85. package/interfaces/rman-config.interface.d.ts +100 -5
  86. package/interfaces/rman-config.interface.js +17 -0
  87. package/package.json +2 -1
  88. package/services/change-hash.service.d.ts +40 -6
  89. package/services/change-hash.service.js +90 -11
  90. package/services/changelog.service.d.ts +31 -3
  91. package/services/changelog.service.js +448 -65
  92. package/services/config-service.d.ts +8 -0
  93. package/services/config-service.js +3 -0
  94. package/services/exec.service.d.ts +2 -2
  95. package/services/exec.service.js +1 -1
  96. package/services/github-release.service.d.ts +3 -3
  97. package/services/github-release.service.js +3 -3
  98. package/services/import.service.d.ts +2 -2
  99. package/services/import.service.js +1 -1
  100. package/services/list.service.d.ts +9 -7
  101. package/services/list.service.js +2 -2
  102. package/services/run.service.d.ts +15 -11
  103. package/services/run.service.js +62 -18
  104. package/services/system-info.d.ts +1 -1
  105. package/services/version-plan.service.d.ts +8 -4
  106. package/services/version-plan.service.js +54 -21
  107. package/services/version.service.d.ts +5 -5
  108. package/services/version.service.js +7 -4
  109. package/services.d.ts +1 -1
  110. package/services.js +1 -1
  111. package/utils/branch-guard.d.ts +1 -1
  112. package/utils/color-yaml.d.ts +8 -0
  113. package/utils/color-yaml.js +86 -0
  114. package/utils/git.d.ts +26 -0
  115. package/utils/git.js +65 -0
  116. package/utils/logger.d.ts +1 -1
  117. package/utils/package-filter.d.ts +8 -1
  118. package/utils/package-filter.js +7 -0
  119. package/utils/printable-config.d.ts +8 -0
  120. package/utils/printable-config.js +45 -0
  121. package/utils/progress-panel.d.ts +9 -0
  122. package/utils/progress-panel.js +23 -1
  123. package/utils/release-version.d.ts +1 -1
  124. package/utils/run-options.js +1 -1
  125. package/utils/version-group.d.ts +31 -0
  126. package/utils/version-group.js +43 -0
  127. package/commands/changed.command.d.ts +0 -80
  128. package/commands/changed.command.js +0 -36
  129. package/core/config.d.ts +0 -530
  130. package/core/config.js +0 -1123
  131. package/core/core-services.d.ts +0 -14
  132. package/core/core-services.js +0 -30
  133. package/core/core-targets.d.ts +0 -14
  134. package/core/core-targets.js +0 -16
  135. package/core/extends-config.d.ts +0 -35
  136. package/core/extends-config.js +0 -129
  137. package/core/load-config-module.d.ts +0 -28
  138. package/core/load-config-module.js +0 -42
  139. package/core/workspace.d.ts +0 -119
  140. package/core/workspace.js +0 -124
  141. package/plugins/builtins.d.ts +0 -44
  142. package/plugins/builtins.js +0 -33
  143. package/plugins/detect.d.ts +0 -78
  144. package/plugins/detect.js +0 -70
  145. package/plugins/node/index.d.ts +0 -29
  146. package/plugins/node/index.js +0 -40
  147. /package/{core/run-step.js → builtins/platforms/node/augmentation/rmanrc.augmentation.js} +0 -0
  148. /package/{plugins → builtins/platforms}/node/augmentation/system-info.augmentation.d.ts +0 -0
  149. /package/{plugins → builtins/platforms}/node/node-config.interface.js +0 -0
  150. /package/{plugins → builtins/platforms}/node/node.platform.js +0 -0
  151. /package/{plugins → builtins/platforms}/node/utils/workspace-range.d.ts +0 -0
  152. /package/{plugins → builtins/platforms}/node/utils/workspace-range.js +0 -0
  153. /package/{plugins/node/utils → builtins/publish-targets/npm}/npm-view.d.ts +0 -0
  154. /package/{plugins/node/utils → builtins/publish-targets/npm}/npm-view.js +0 -0
  155. /package/core/{registry.d.ts → classes/registry.d.ts} +0 -0
  156. /package/core/{registry.js → classes/registry.js} +0 -0
  157. /package/core/{service.js → classes/service.js} +0 -0
  158. /package/core/{version-scheme.d.ts → classes/version-scheme.d.ts} +0 -0
  159. /package/core/{version-scheme.js → classes/version-scheme.js} +0 -0
  160. /package/core/{merge-config.d.ts → config/merge-config.d.ts} +0 -0
  161. /package/core/{resolve-target.d.ts → config/resolve-config-target.d.ts} +0 -0
  162. /package/core/{resolve-target.js → config/resolve-config-target.js} +0 -0
  163. /package/core/{custom-command.js → interfaces/custom-command.js} +0 -0
  164. /package/{plugins/node/augmentation/rman.augmentation.js → core/interfaces/run-step.js} +0 -0
package/README.md CHANGED
@@ -86,7 +86,6 @@ worked examples of every single command, see **[docs/cli-rman.md](https://github
86
86
  | [`test`](#rman-test) | Alias for `run test`. |
87
87
  | [`exec <command..>`](#rman-exec-command) | Runs an arbitrary shell command in each package. |
88
88
  | [`config`](#rman-config) | Prints the effective `.rmanrc` config for the current directory's package. |
89
- | [`changed`](#rman-changed) | Shows which packages the next `version` run would bump. |
90
89
  | [`diff [package]`](#rman-diff-package) | Shows the git diff since a package's (or the repo's) last release tag. |
91
90
  | [`changelog`](#rman-changelog) | Generates a changelog per package from unreleased commits. |
92
91
  | [`version [bump]`](#rman-version-bump) | Bumps versions of changed packages (and their dependents). |
@@ -141,7 +140,7 @@ rman list --json # full detail as JSON
141
140
  rman list --parseable # location::name::version::PRIVATE::STATUS lines, for scripting
142
141
  rman list --toposort # dependencies before dependents, instead of directory order
143
142
  rman list --graph # dependency graph as a JSON adjacency list
144
- rman list --changed # only packages changed since the last publish
143
+ rman list --changed # only packages you have touched but not pushed
145
144
  rman list --changed-since HEAD~5
146
145
  rman list --scope '@myorg/*' --ignore '*-internal'
147
146
  ```
@@ -165,7 +164,7 @@ Runs an npm script in each package, in dependency order by default.
165
164
  ```bash
166
165
  rman run build
167
166
  rman run lint --topo=false # independent packages, alphabetical order, no dependency waiting
168
- rman run test --changed # only in packages changed since the last publish
167
+ rman run test --changed # only in packages you have touched but not pushed
169
168
  rman run build --changed-since v1.2.0
170
169
  rman run build --parallel 4 # at most 4 packages at once
171
170
  rman run build --parallel false # serially, one at a time
@@ -216,15 +215,6 @@ rman config --from-root # the repository root's own config instead
216
215
  rman config --json | jq .run
217
216
  ```
218
217
 
219
- ### `rman changed`
220
-
221
- Shows which packages the next `rman version` run would bump, without changing anything.
222
-
223
- ```bash
224
- rman changed
225
- rman changed --json
226
- ```
227
-
228
218
  ### `rman diff [package]`
229
219
 
230
220
  Shows the git diff since a package's (or the whole repository's) last release tag.
@@ -1,5 +1,4 @@
1
- import type cleanCommand from '../commands/clean.command.js';
2
- import type { CleanExtraKeys } from '../commands/clean.command.js';
1
+ import type { cleanCommand, CleanExtraKeys } from '../commands/clean.command.js';
3
2
  import type { NodeConfigKeys, RmanNodeConfig } from '../node-config.interface.js';
4
3
  import type { CiService } from '../services/ci.service.js';
5
4
  /**
@@ -16,7 +15,7 @@ import type { CiService } from '../services/ci.service.js';
16
15
  * (`augmentSystemInfo()`, `augmentManifest()`, ...); this file is imported by the plugin's entry
17
16
  * point purely so a consumer's compiler loads it.
18
17
  */
19
- declare module '../../../interfaces/rman-config.interface.js' {
18
+ declare module '../../../../interfaces/rman-config.interface.js' {
20
19
  /**
21
20
  * The `.rmanrc` keys that only mean something in a Node repository - merged into the core's own
22
21
  * key list, so `pkg.config.clean` is typed wherever it is read (`CleanService` included) without
@@ -49,7 +48,7 @@ declare module '../../../interfaces/rman-config.interface.js' {
49
48
  * declared in `publish.command.ts` was reachable only by re-declaring it - which now reads as two
50
49
  * interfaces of one name and is refused. Each interface is augmented where it lives.
51
50
  */
52
- declare module '../../../commands/publish.command.js' {
51
+ declare module '../../../../commands/publish.command.js' {
53
52
  /**
54
53
  * The `npm` publish target's own `publish.*` block, declared the way the core's `docker` target
55
54
  * declares `publish.docker` - through the slot `publish` contributes, rather than into a central
@@ -68,7 +67,7 @@ declare module '../../../commands/publish.command.js' {
68
67
  * runtime half is `augmentSystemInfo()` in the file beside this one, called when the built-in is
69
68
  * registered rather than at import, so a repository that never named it reports no npm.
70
69
  */
71
- declare module '../../../services/system-info.js' {
70
+ declare module '../../../../services/system-info.js' {
72
71
  namespace SystemInfo {
73
72
  type PackageManager = CiService.PackageManager;
74
73
  interface Options {
@@ -1,4 +1,4 @@
1
- import { SystemInfo as OrgSystemInfo } from '../../../services/system-info.js';
1
+ import { SystemInfo as OrgSystemInfo } from '../../../../services/system-info.js';
2
2
  /**
3
3
  * Adds the npm half of `SystemInfo` to rman's own types.
4
4
  *
@@ -1,4 +1,4 @@
1
- import type { ArgsOf } from '../../../index.js';
1
+ import type { ArgsOf } from '../../../../index.js';
2
2
  /** Hoisted out of the metadata literal so the handler can be annotated against them - see
3
3
  * `RmanConfig.ArgsOf` for why an inferred `argv` and the metadata's own typo checking cannot both
4
4
  * work in one signature. */
@@ -67,8 +67,10 @@ type Args = ArgsOf<typeof config, typeof COMMAND>;
67
67
  * The repository arrives through `app` when the factory runs (in `cli.ts`, after `Repository.create`
68
68
  * has attached one), rather than through a `CommandContext` per invocation.
69
69
  */
70
- declare const ciCommand: (app: import("../../../index.js").RmanApplication) => {
70
+ export declare const ciCommand: (app: import("../../../../index.js").RmanApplication) => {
71
71
  command: "ci";
72
+ /** npm's alone: it installs through a Node package manager, from a Node lockfile. */
73
+ platforms: string[];
72
74
  describe: string;
73
75
  /** Read, not owned: `packageManager` is a root-level key this package declares in
74
76
  * `NodeConfigKeys`, and the `npm` publish target reads it too. */
@@ -128,4 +130,4 @@ declare const ciCommand: (app: import("../../../index.js").RmanApplication) => {
128
130
  }[];
129
131
  handler: (args: Args) => Promise<void>;
130
132
  };
131
- export default ciCommand;
133
+ export {};
@@ -1,6 +1,6 @@
1
- import { declareCommand } from '../../../interfaces/rman-config.interface.js';
2
- import { assertAllowedBranch, branchGuardOptions, readBranchGuardOptions } from '../../../utils/branch-guard.js';
3
- import { packageFilterOptions, readPackageFilterOptions } from '../../../utils/package-filter.js';
1
+ import { declareCommand } from '../../../../interfaces/rman-config.interface.js';
2
+ import { assertAllowedBranch, branchGuardOptions, readBranchGuardOptions } from '../../../../utils/branch-guard.js';
3
+ import { packageFilterOptions, readPackageFilterOptions } from '../../../../utils/package-filter.js';
4
4
  import { CiService } from '../services/ci.service.js';
5
5
  /** Hoisted out of the metadata literal so the handler can be annotated against them - see
6
6
  * `RmanConfig.ArgsOf` for why an inferred `argv` and the metadata's own typo checking cannot both
@@ -35,10 +35,12 @@ const config = {
35
35
  * The repository arrives through `app` when the factory runs (in `cli.ts`, after `Repository.create`
36
36
  * has attached one), rather than through a `CommandContext` per invocation.
37
37
  */
38
- const ciCommand = declareCommand(app => {
38
+ export const ciCommand = declareCommand(app => {
39
39
  const repository = app.repository;
40
40
  return {
41
41
  command: COMMAND,
42
+ /** npm's alone: it installs through a Node package manager, from a Node lockfile. */
43
+ platforms: ['node'],
42
44
  describe: 'Deletes node_modules and lockfiles in every package, then reinstalls from scratch',
43
45
  /** Read, not owned: `packageManager` is a root-level key this package declares in
44
46
  * `NodeConfigKeys`, and the `npm` publish target reads it too. */
@@ -56,4 +58,3 @@ const ciCommand = declareCommand(app => {
56
58
  },
57
59
  };
58
60
  });
59
- export default ciCommand;
@@ -1,5 +1,5 @@
1
- import type { ConfigValue } from '../../../core/config.js';
2
- import type { ArgsOf } from '../../../index.js';
1
+ import type { ArgsOf } from '../../../../index.js';
2
+ import type { ConfigValue } from '../../../../interfaces/rman-config.interface.js';
3
3
  /** Hoisted for `ArgsOf` - see `ci.command.ts` and `RmanConfig.ArgsOf`. */
4
4
  declare const COMMAND: "clean";
5
5
  declare const config: {
@@ -91,8 +91,10 @@ type Args = ArgsOf<typeof config, typeof COMMAND>;
91
91
  * Declared the same way `ci` is - see that file for why a plugin uses `declareCommand` rather than
92
92
  * `registerCommand`.
93
93
  */
94
- declare const cleanCommand: (app: import("../../../index.js").RmanApplication) => {
94
+ export declare const cleanCommand: (app: import("../../../../index.js").RmanApplication) => {
95
95
  command: "clean";
96
+ /** npm's alone: it deletes TypeScript build output, which no other ecosystem has. */
97
+ platforms: string[];
96
98
  describe: string;
97
99
  /**
98
100
  * **No `configKeys`, because `clean` is this command's *own* key now** - derived from the
@@ -180,4 +182,4 @@ declare const cleanCommand: (app: import("../../../index.js").RmanApplication) =
180
182
  })[];
181
183
  handler: (args: Args) => Promise<void>;
182
184
  };
183
- export default cleanCommand;
185
+ export {};
@@ -1,6 +1,6 @@
1
- import { declareCommand } from '../../../interfaces/rman-config.interface.js';
2
- import { assertAllowedBranch, branchGuardOptions, readBranchGuardOptions } from '../../../utils/branch-guard.js';
3
- import { fromRootOption, packageFilterOptions, readPackageFilterOptions } from '../../../utils/package-filter.js';
1
+ import { declareCommand } from '../../../../interfaces/rman-config.interface.js';
2
+ import { assertAllowedBranch, branchGuardOptions, readBranchGuardOptions } from '../../../../utils/branch-guard.js';
3
+ import { fromRootOption, packageFilterOptions, readPackageFilterOptions } from '../../../../utils/package-filter.js';
4
4
  import { CleanService } from '../services/clean.service.js';
5
5
  /** Hoisted for `ArgsOf` - see `ci.command.ts` and `RmanConfig.ArgsOf`. */
6
6
  const COMMAND = 'clean';
@@ -35,10 +35,12 @@ const config = {
35
35
  * Declared the same way `ci` is - see that file for why a plugin uses `declareCommand` rather than
36
36
  * `registerCommand`.
37
37
  */
38
- const cleanCommand = declareCommand(app => {
38
+ export const cleanCommand = declareCommand(app => {
39
39
  const repository = app.repository;
40
40
  return {
41
41
  command: COMMAND,
42
+ /** npm's alone: it deletes TypeScript build output, which no other ecosystem has. */
43
+ platforms: ['node'],
42
44
  describe: 'Removes compiled TypeScript output and any extra files/dirs configured via .rmanrc "clean"',
43
45
  /**
44
46
  * **No `configKeys`, because `clean` is this command's *own* key now** - derived from the
@@ -70,4 +72,3 @@ const cleanCommand = declareCommand(app => {
70
72
  },
71
73
  };
72
74
  });
73
- export default cleanCommand;
@@ -0,0 +1,8 @@
1
+ export * from './augmentation/rmanrc.augmentation.js';
2
+ export * from './augmentation/system-info.augmentation.js';
3
+ export * from './commands/ci.command.js';
4
+ export * from './commands/clean.command.js';
5
+ export * from './node.platform.js';
6
+ export * from './node-config.interface.js';
7
+ export * from './node-manifest.provider.js';
8
+ export * from './utils/workspace-range.js';
@@ -0,0 +1,8 @@
1
+ export * from './augmentation/rmanrc.augmentation.js';
2
+ export * from './augmentation/system-info.augmentation.js';
3
+ export * from './commands/ci.command.js';
4
+ export * from './commands/clean.command.js';
5
+ export * from './node.platform.js';
6
+ export * from './node-config.interface.js';
7
+ export * from './node-manifest.provider.js';
8
+ export * from './utils/workspace-range.js';
@@ -1,5 +1,4 @@
1
- import type { ConfigValue } from '../../core/config.js';
2
- import type { RmanConfig, ScopedVars } from '../../interfaces/rman-config.interface.js';
1
+ import type { ConfigValue, RmanConfig, ScopedVars } from '../../../interfaces/rman-config.interface.js';
3
2
  import type { CiService } from './services/ci.service.js';
4
3
  /**
5
4
  * The `.rmanrc` keys that only mean something because the repository is a Node one.
@@ -1,6 +1,6 @@
1
- import type { ManifestProvider } from '../../core/manifest.js';
2
- import { Manifest } from '../../core/manifest.js';
3
- import type { Package } from '../../core/package.js';
1
+ import type { Package } from '../../../core/classes/package.js';
2
+ import type { ManifestProvider } from '../../../core/interfaces/manifest.js';
3
+ import { Manifest } from '../../../core/interfaces/manifest.js';
4
4
  export declare class NodeManifestProvider implements ManifestProvider {
5
5
  name: string;
6
6
  fileName: string;
@@ -1,8 +1,8 @@
1
1
  import fs from 'node:fs';
2
2
  import path from 'node:path';
3
- import { Manifest } from '../../core/manifest.js';
4
- import { stampVersionConstant } from '../../utils/version-stamp.js';
5
- import { npmViewVersion } from './utils/npm-view.js';
3
+ import { Manifest } from '../../../core/interfaces/manifest.js';
4
+ import { stampVersionConstant } from '../../../utils/version-stamp.js';
5
+ import { npmViewVersion } from '../../publish-targets/npm/npm-view.js';
6
6
  import { parseWorkspaceRange } from './utils/workspace-range.js';
7
7
  export class NodeManifestProvider {
8
8
  name = 'node';
@@ -1,6 +1,6 @@
1
- import type { Package } from '../../core/package.js';
2
- import type { Platform } from '../../core/plugin.js';
3
- import type { RunService } from '../../services/run.service.js';
1
+ import type { Package } from '../../../core/classes/package.js';
2
+ import type { Platform } from '../../../core/interfaces/plugin.js';
3
+ import type { RunService } from '../../../services/run.service.js';
4
4
  import { NodeManifestProvider } from './node-manifest.provider.js';
5
5
  import { NodeVersionPlanService } from './services/version-plan.service.js';
6
6
  export declare class NodePlatform implements Platform {
@@ -1,6 +1,6 @@
1
- import type { Repository } from '../../../core/repository.js';
2
- import type { LogLevel } from '../../../utils/logger.js';
3
- import type { PackageFilterOptions } from '../../../utils/package-filter.js';
1
+ import type { Repository } from '../../../../core/classes/repository.js';
2
+ import type { LogLevel } from '../../../../utils/logger.js';
3
+ import type { PackageFilterOptions } from '../../../../utils/package-filter.js';
4
4
  export declare namespace CiService {
5
5
  /**
6
6
  * The package managers this plugin knows how to drive, and the `choices` both `ci --package-manager`
@@ -1,10 +1,10 @@
1
1
  import fs from 'node:fs/promises';
2
2
  import path from 'node:path';
3
3
  import colors from 'ansi-colors';
4
- import { exec } from '../../../utils/exec.js';
5
- import { Logger, resolveRootLogLevel } from '../../../utils/logger.js';
6
- import { filterPackages } from '../../../utils/package-filter.js';
7
- import { formatDuration, ProgressPanel } from '../../../utils/progress-panel.js';
4
+ import { exec } from '../../../../utils/exec.js';
5
+ import { Logger, resolveRootLogLevel } from '../../../../utils/logger.js';
6
+ import { filterPackages } from '../../../../utils/package-filter.js';
7
+ import { formatDuration, ProgressPanel } from '../../../../utils/progress-panel.js';
8
8
  export var CiService;
9
9
  (function (CiService) {
10
10
  /**
@@ -1,6 +1,6 @@
1
- import type { Repository } from '../../../core/repository.js';
2
- import type { LogLevel } from '../../../utils/logger.js';
3
- import type { PackageFilterOptions } from '../../../utils/package-filter.js';
1
+ import type { Repository } from '../../../../core/classes/repository.js';
2
+ import type { LogLevel } from '../../../../utils/logger.js';
3
+ import type { PackageFilterOptions } from '../../../../utils/package-filter.js';
4
4
  export declare namespace CleanService {
5
5
  interface Options extends PackageFilterOptions {
6
6
  /** Show the live progress panel. Default true; auto-disabled when stdout isn't a TTY. */
@@ -2,9 +2,9 @@ import fs from 'node:fs';
2
2
  import path from 'node:path';
3
3
  import colors from 'ansi-colors';
4
4
  import fg from 'fast-glob';
5
- import { Logger, resolveRootLogLevel } from '../../../utils/logger.js';
6
- import { filterPackages } from '../../../utils/package-filter.js';
7
- import { ProgressPanel } from '../../../utils/progress-panel.js';
5
+ import { Logger, resolveRootLogLevel } from '../../../../utils/logger.js';
6
+ import { filterPackages } from '../../../../utils/package-filter.js';
7
+ import { ProgressPanel } from '../../../../utils/progress-panel.js';
8
8
  export var CleanService;
9
9
  (function (CleanService) {
10
10
  /**
@@ -1,7 +1,7 @@
1
- import type { Package } from '../../../core/package.js';
2
- import type { Repository } from '../../../core/repository.js';
3
- import type { PackageFilterOptions } from '../../../utils/package-filter.js';
4
- import { type NpmPackageView } from '../utils/npm-view.js';
1
+ import type { Package } from '../../../../core/classes/package.js';
2
+ import type { Repository } from '../../../../core/classes/repository.js';
3
+ import type { PackageFilterOptions } from '../../../../utils/package-filter.js';
4
+ import { type NpmPackageView } from '../../../publish-targets/npm/npm-view.js';
5
5
  import { CiService } from './ci.service.js';
6
6
  export declare namespace PublishService {
7
7
  /** Injectable registry lookup - mainly for tests, so they don't depend on network access or a
@@ -16,12 +16,12 @@
16
16
  */
17
17
  import fs from 'node:fs';
18
18
  import path from 'node:path';
19
- import { exec } from '../../../utils/exec.js';
20
- import { GitHelper } from '../../../utils/git.js';
21
- import { filterPackages } from '../../../utils/package-filter.js';
22
- import { isCalendarVersion } from '../../../utils/release-version.js';
19
+ import { exec } from '../../../../utils/exec.js';
20
+ import { GitHelper } from '../../../../utils/git.js';
21
+ import { filterPackages } from '../../../../utils/package-filter.js';
22
+ import { isCalendarVersion } from '../../../../utils/release-version.js';
23
+ import { npmViewPackage } from '../../../publish-targets/npm/npm-view.js';
23
24
  import { DEPENDENCY_KEYS } from '../node-manifest.provider.js';
24
- import { npmViewPackage } from '../utils/npm-view.js';
25
25
  import { parseWorkspaceRange, resolveWorkspaceRange } from '../utils/workspace-range.js';
26
26
  import { CiService } from './ci.service.js';
27
27
  function preparePublishManifest(pkg, publishDir, packagesByName) {
@@ -1,6 +1,6 @@
1
- import type { Package } from '../../../core/package.js';
2
- import { VersionPlanService } from '../../../services/version-plan.service.js';
3
- import type { GitHelper } from '../../../utils/git.js';
1
+ import type { Package } from '../../../../core/classes/package.js';
2
+ import { VersionPlanService } from '../../../../services/version-plan.service.js';
3
+ import type { GitHelper } from '../../../../utils/git.js';
4
4
  /**
5
5
  * How a release is planned for an npm repository.
6
6
  *
@@ -1,5 +1,5 @@
1
- import { ChangeHashService } from '../../../services/change-hash.service.js';
2
- import { VersionPlanService } from '../../../services/version-plan.service.js';
1
+ import { ChangeHashService } from '../../../../services/change-hash.service.js';
2
+ import { VersionPlanService } from '../../../../services/version-plan.service.js';
3
3
  /**
4
4
  * How a release is planned for an npm repository.
5
5
  *
@@ -0,0 +1,15 @@
1
+ /**
2
+ * **Where the presets are.** `ConfigReader` resolves `extends: "rman:<name>"` against this.
3
+ */
4
+ export declare const PRESETS_DIR: string;
5
+ /** Every preset rman ships, read off the directory rather than written down again. */
6
+ export declare function presetNames(): string[];
7
+ /**
8
+ * **The presets rman ships, laid underneath every repository's own config.**
9
+ *
10
+ * A repository writing nothing at all still gets these, exactly as if its `.rmanrc` had opened with
11
+ * `extends: ['rman:node']` - so `rman list` finds the workspace and `rman clean` exists without a
12
+ * config file having to say so. A repository naming one itself changes nothing: the key appends, and
13
+ * a technology already present by name is skipped.
14
+ */
15
+ export declare const DEFAULT_PRESETS: readonly string[];
@@ -0,0 +1,57 @@
1
+ import fs from 'node:fs';
2
+ import path from 'node:path';
3
+ import { fileURLToPath } from 'node:url';
4
+ /**
5
+ * **Where the presets are.** `ConfigReader` resolves `extends: "rman:<name>"` against this.
6
+ */
7
+ /* **The directory says where it is, rather than the reader computing a path to it.** It was
8
+ * `path.resolve(dirname(config-reader), '..', 'presets')` - two relative hops between two files
9
+ * that nothing keeps in step, and moving either one breaks it silently at *runtime*: measured, the
10
+ * `core/config/` + `builtins/presets/` reorganization left every repository answering
11
+ * `"presets" has no preset "node". rman ships: node.` - a message that named the preset it had
12
+ * just failed to find, because the list behind it was a hardcoded `['node']` somewhere else again.
13
+ * `tsc` cannot see a path built with `path.resolve`, so only a run says. */
14
+ export const PRESETS_DIR = path.dirname(fileURLToPath(import.meta.url));
15
+ /** Every preset rman ships, read off the directory rather than written down again. */
16
+ /* One `readdirSync`, on an error path only - `_resolvePreset` asks after a lookup already failed.
17
+ * Reading the directory is what keeps the message true: the hardcoded list it replaces could say
18
+ * `node` while `node.js` was not where the resolver looked. `index` is this file. */
19
+ export function presetNames() {
20
+ try {
21
+ return [
22
+ ...new Set(fs
23
+ .readdirSync(PRESETS_DIR)
24
+ .filter(f => /\.(js|ts)$/.test(f) && !/\.d\.ts$/.test(f))
25
+ .map(f => f.replace(/\.(js|ts)$/, ''))
26
+ .filter(n => n !== 'index')),
27
+ ].sort();
28
+ }
29
+ catch {
30
+ return [];
31
+ }
32
+ }
33
+ /**
34
+ * **The presets rman ships, laid underneath every repository's own config.**
35
+ *
36
+ * A repository writing nothing at all still gets these, exactly as if its `.rmanrc` had opened with
37
+ * `extends: ['rman:node']` - so `rman list` finds the workspace and `rman clean` exists without a
38
+ * config file having to say so. A repository naming one itself changes nothing: the key appends, and
39
+ * a technology already present by name is skipped.
40
+ */
41
+ /* **Names, not imports, and that is load-bearing rather than tidy.** A preset's module pulls in a
42
+ * platform, its commands and its services, and one of those services extends a core service - so a
43
+ * static import from `core/` closes the cycle that stopped the *built* CLI dead on every command
44
+ * (`Cannot access 'VersionPlanService' before initialization`, invisible to the suite, which is why
45
+ * `npm run smoke` exists). `ConfigReader` resolves these through the same dynamic `import()` an
46
+ * `extends: "rman:node"` goes through, so this file stays a list of strings and imports nothing.
47
+ *
48
+ * **This replaced detection**, which asked each built-in "is this directory yours?" before turning
49
+ * anything on, and merged the matching preset underneath. What that bought was a repository not
50
+ * growing a technology's commands unasked; what it cost was a catalogue module, a `Builtin` type, a
51
+ * per-directory memo and a gate that had to decide what counts as having "said something". The
52
+ * platform answers the same question now - `manifestProvider.read` is what detection asked - and it
53
+ * answers it from the ordinary registry, once loaded. The cost, stated rather than hidden: a
54
+ * repository of some other technology carries node's `clean` and `ci` in `rman --help`, and
55
+ * `rman info` reports npm's tooling. Split this list's presets in two - the platform apart from the
56
+ * commands - if that ever stops being acceptable. */
57
+ export const DEFAULT_PRESETS = ['node'];
@@ -0,0 +1,16 @@
1
+ import type { RmanConfig } from '../../interfaces/rman-config.interface.js';
2
+ /**
3
+ * **The `node` preset** - everything rman knows about the npm ecosystem, as a config.
4
+ *
5
+ * ```yaml
6
+ * # .rmanrc.yml
7
+ * extends: node
8
+ * ```
9
+ *
10
+ * It contributes the technology (how a `package.json` is read, where `workspaces` point, how
11
+ * versions are planned), the two commands that are npm's alone (`clean`, `ci`), and the `npm`
12
+ * publish target. A polyglot repository names several: `extends: ['node', 'cargo']` holds both,
13
+ * because every key here appends.
14
+ */
15
+ export declare function nodePreset(): RmanConfig;
16
+ export default nodePreset;
@@ -0,0 +1,57 @@
1
+ import { definePlatform } from '../../core/interfaces/plugin.js';
2
+ import { defineConfig } from '../../interfaces/rman-config.interface.js';
3
+ import { augmentSystemInfo, ciCommand, cleanCommand, NodePlatform } from '../platforms/node/index.js';
4
+ import { NpmPublishTarget } from '../publish-targets/npm/index.js';
5
+ /**
6
+ * **The `node` preset** - everything rman knows about the npm ecosystem, as a config.
7
+ *
8
+ * ```yaml
9
+ * # .rmanrc.yml
10
+ * extends: node
11
+ * ```
12
+ *
13
+ * It contributes the technology (how a `package.json` is read, where `workspaces` point, how
14
+ * versions are planned), the two commands that are npm's alone (`clean`, `ci`), and the `npm`
15
+ * publish target. A polyglot repository names several: `extends: ['node', 'cargo']` holds both,
16
+ * because every key here appends.
17
+ */
18
+ /* **A config rather than a plugin, and that is the whole shape of a preset.** `commands` and
19
+ * `publishTargets` were already config keys; `platforms` is one now, so a technology arrives the
20
+ * same way everything else does. What used to need a `Builtin` type, a name that looked like a glob
21
+ * and an expansion step is `extends` and nothing else.
22
+ *
23
+ * **A function, so nothing here happens until a repository asks for it.** `augmentSystemInfo()`
24
+ * mutates the core's own `SystemInfo` in place, so running it at import time would have `rman info`
25
+ * report npm's tooling in a Cargo repository that never named this preset. `extends` imports the
26
+ * module it names and calls this; a repository that names something else never reaches it. */
27
+ export function nodePreset() {
28
+ augmentSystemInfo();
29
+ return defineConfig({
30
+ platforms: [(nodePlatform ??= definePlatform(new NodePlatform()))],
31
+ commands: [ciCommand, cleanCommand],
32
+ publishTargets: [(npmTarget ??= new NpmPublishTarget())],
33
+ });
34
+ }
35
+ export default nodePreset;
36
+ /**
37
+ * **One instance of each across every call, so calling this preset twice contributes one of each.**
38
+ *
39
+ * A repository writing `extends: 'rman:node'` is read *and* gets the same preset laid under it by
40
+ * default, which is ordinary rather than a mistake - the contribution keys append and drop a
41
+ * duplicate **by identity** (`appendList`). The two commands are module consts, so they dedup on
42
+ * their own; anything this factory `new`s does not, and both of these have been that at some point.
43
+ *
44
+ * - **The target announced itself loudly.** Two of them reached `publish`, which refuses two
45
+ * targets declaring one option name, and it died with `Publish targets "npm" and "npm" both
46
+ * declare an option named "packageManager"` - the guard working exactly as intended, on a
47
+ * collision with itself.
48
+ * - **The platform does not, and that is the one to watch.** `_addPlatform` dedups by *name*, so a
49
+ * second `node` platform never reaches `context.platforms` and nothing resolves differently. What
50
+ * it does is put the same technology in `config.platforms` twice - visible only in `rman config`
51
+ * and to whoever iterates the key - plus an `augmentSystemInfo()` and a `new NodePlatform()` per
52
+ * read. Caught by the identity spec in `docs-api.spec.ts` rather than by anything failing.
53
+ *
54
+ * **A new preset has to do the same for anything it constructs.**
55
+ */
56
+ let npmTarget;
57
+ let nodePlatform;
@@ -1,11 +1,11 @@
1
- import { type PublishTarget } from '../core/publish-target.js';
2
- import { Service } from '../core/service.js';
3
- import { type PackageFilterOptions } from '../utils/package-filter.js';
1
+ import { Service } from '../../../core/classes/service.js';
2
+ import { type PublishTarget } from '../../../core/interfaces/publish-target.js';
3
+ import { type PackageFilterOptions } from '../../../utils/package-filter.js';
4
4
  /**
5
5
  * The name this target answers to in `publish.target` and `--target`.
6
6
  *
7
7
  * Declared beside the implementation rather than in `publish-target.ts`: the seam is general and
8
- * must not know any one target's name, and the adapter in `targets/docker.target.ts` reads it from
8
+ * must not know any one target's name, and the adapter in `builtins/publish-targets/docker/docker.target.ts` reads it from
9
9
  * here, which keeps the dependency pointing one way.
10
10
  */
11
11
  export declare const DOCKER_TARGET = "docker";
@@ -31,7 +31,7 @@ export declare class DockerPublishService extends Service {
31
31
  /**
32
32
  * Publishes every `'publish'` entry in `plan`: one `docker login` and one `docker buildx create`
33
33
  * up front (each package's own build reuses them), then per package a single `docker buildx
34
- * build --push` using that package's `publish.docker` config (platforms, named build-contexts,
34
+ * build --push` using that package's `publish.docker` config (architectures, named build-contexts,
35
35
  * build-args, an optional `cwd` override). A package's `publish.docker.readme` file (default
36
36
  * `DOCKER_README.md`), if present, updates the DockerHub repo description afterward. A package's
37
37
  * own failure doesn't stop unrelated packages elsewhere in the plan.
@@ -66,7 +66,7 @@ export declare namespace DockerPublishService {
66
66
  image?: string;
67
67
  }
68
68
  }
69
- declare module '../core/service.js' {
69
+ declare module '../../../core/classes/service.js' {
70
70
  interface ServiceMap {
71
71
  dockerPublish: DockerPublishService;
72
72
  }
@@ -2,16 +2,16 @@ import { execFile } from 'node:child_process';
2
2
  import fs from 'node:fs';
3
3
  import path from 'node:path';
4
4
  import { promisify } from 'node:util';
5
- import { targetsOf } from '../core/publish-target.js';
6
- import { Service } from '../core/service.js';
7
- import { exec } from '../utils/exec.js';
8
- import { GitHelper } from '../utils/git.js';
9
- import { filterPackages } from '../utils/package-filter.js';
5
+ import { Service } from '../../../core/classes/service.js';
6
+ import { targetsOf } from '../../../core/interfaces/publish-target.js';
7
+ import { exec } from '../../../utils/exec.js';
8
+ import { GitHelper } from '../../../utils/git.js';
9
+ import { filterPackages } from '../../../utils/package-filter.js';
10
10
  /**
11
11
  * The name this target answers to in `publish.target` and `--target`.
12
12
  *
13
13
  * Declared beside the implementation rather than in `publish-target.ts`: the seam is general and
14
- * must not know any one target's name, and the adapter in `targets/docker.target.ts` reads it from
14
+ * must not know any one target's name, and the adapter in `builtins/publish-targets/docker/docker.target.ts` reads it from
15
15
  * here, which keeps the dependency pointing one way.
16
16
  */
17
17
  export const DOCKER_TARGET = 'docker';
@@ -94,7 +94,7 @@ export class DockerPublishService extends Service {
94
94
  /**
95
95
  * Publishes every `'publish'` entry in `plan`: one `docker login` and one `docker buildx create`
96
96
  * up front (each package's own build reuses them), then per package a single `docker buildx
97
- * build --push` using that package's `publish.docker` config (platforms, named build-contexts,
97
+ * build --push` using that package's `publish.docker` config (architectures, named build-contexts,
98
98
  * build-args, an optional `cwd` override). A package's `publish.docker.readme` file (default
99
99
  * `DOCKER_README.md`), if present, updates the DockerHub repo description afterward. A package's
100
100
  * own failure doesn't stop unrelated packages elsewhere in the plan.
@@ -172,10 +172,10 @@ async function dockerLogin(app, cwd) {
172
172
  async function buildAndPush(repository, entry) {
173
173
  const pkg = entry.package;
174
174
  const docker = pkg.config.publish.docker;
175
- const platforms = docker.platforms?.length ? docker.platforms : ['linux/amd64'];
175
+ const architectures = docker.architectures?.length ? docker.architectures : ['linux/amd64'];
176
176
  const dockerfile = path.resolve(pkg.dirname, docker.dockerfile || 'Dockerfile');
177
177
  const cwd = docker.cwd ? path.resolve(repository.dirname, docker.cwd) : pkg.dirname;
178
- const args = ['buildx', 'build', '--platform', platforms.join(',')];
178
+ const args = ['buildx', 'build', '--platform', architectures.join(',')];
179
179
  for (const [name, dir] of Object.entries(docker.buildContexts ?? {})) {
180
180
  args.push('--build-context', `${name}="${path.resolve(pkg.dirname, dir)}"`);
181
181
  }
@@ -1,6 +1,5 @@
1
- import type { ConfigValue } from '../core/config.js';
2
- import type { PublishTarget } from '../core/publish-target.js';
3
- import type { ScopedVars } from '../interfaces/rman-config.interface.js';
1
+ import type { PublishTarget } from '../../../core/interfaces/publish-target.js';
2
+ import type { ConfigValue, ScopedVars } from '../../../interfaces/rman-config.interface.js';
4
3
  /**
5
4
  * **`publish.docker.*`** - this target's own config block, declared here rather than centrally.
6
5
  *
@@ -23,8 +22,10 @@ export interface DockerPublishOptionsKeys {
23
22
  image: ConfigValue<string>;
24
23
  /** Relative to the package's own directory. Default `"Dockerfile"`. */
25
24
  dockerfile?: ConfigValue<string>;
26
- /** Default `["linux/amd64"]`. */
27
- platforms?: ConfigValue<string[]>;
25
+ /**
26
+ * The architectures to build for - `docker buildx build --platform`. Default `["linux/amd64"]`.
27
+ */
28
+ architectures?: ConfigValue<string[]>;
28
29
  /** Build `cwd` override, relative to the repository root - only needed when the Dockerfile's
29
30
  * own `COPY`/`ADD` paths expect something other than the package's own directory (rare). */
30
31
  cwd?: ConfigValue<string>;