vyriy 0.3.9 → 0.4.1

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 (190) hide show
  1. package/README.md +75 -179
  2. package/bin/vyriy.js +2 -2
  3. package/cli/args.js +29 -0
  4. package/cli/cli.d.ts +2 -2
  5. package/cli/cli.js +18 -69
  6. package/cli/index.d.ts +1 -1
  7. package/cli/index.js +1 -1
  8. package/cli/types.d.ts +12 -3
  9. package/commands/check-env.d.ts +2 -0
  10. package/commands/check-env.js +65 -0
  11. package/commands/create/index.d.ts +2 -0
  12. package/commands/create/index.js +121 -0
  13. package/commands/create/plan/index.d.ts +4 -0
  14. package/commands/create/plan/index.js +3 -0
  15. package/commands/create/plan/plan.d.ts +9 -0
  16. package/commands/create/plan/plan.js +34 -0
  17. package/commands/create/plan/question.d.ts +2 -0
  18. package/commands/create/plan/question.js +25 -0
  19. package/commands/create/plan/types.d.ts +14 -0
  20. package/commands/create/preset/api.d.ts +2 -0
  21. package/commands/create/preset/api.js +168 -0
  22. package/commands/create/preset/base.d.ts +2 -0
  23. package/commands/create/preset/base.js +195 -0
  24. package/commands/create/preset/gql.d.ts +2 -0
  25. package/commands/create/preset/gql.js +16 -0
  26. package/commands/create/preset/index.d.ts +17 -0
  27. package/commands/create/preset/index.js +20 -0
  28. package/commands/create/preset/library.d.ts +2 -0
  29. package/commands/create/preset/library.js +252 -0
  30. package/commands/create/preset/mfe.d.ts +2 -0
  31. package/commands/create/preset/mfe.js +16 -0
  32. package/commands/create/preset/rest.d.ts +2 -0
  33. package/commands/create/preset/rest.js +16 -0
  34. package/commands/create/preset/spa.d.ts +2 -0
  35. package/commands/create/preset/spa.js +16 -0
  36. package/commands/create/preset/ssg.d.ts +2 -0
  37. package/commands/create/preset/ssg.js +16 -0
  38. package/commands/create/preset/ssr.d.ts +2 -0
  39. package/commands/create/preset/ssr.js +16 -0
  40. package/commands/create/preset/types.d.ts +15 -0
  41. package/commands/create/prompt/conflict-strategy.d.ts +5 -0
  42. package/commands/create/prompt/conflict-strategy.js +22 -0
  43. package/commands/create/prompt/index.d.ts +7 -0
  44. package/commands/create/prompt/index.js +6 -0
  45. package/commands/create/prompt/preset.d.ts +4 -0
  46. package/commands/create/prompt/preset.js +11 -0
  47. package/commands/create/prompt/prompt.d.ts +2 -0
  48. package/commands/create/prompt/prompt.js +4 -0
  49. package/commands/create/prompt/provider.d.ts +2 -0
  50. package/commands/create/prompt/provider.js +13 -0
  51. package/commands/create/prompt/resolve-option.d.ts +6 -0
  52. package/commands/create/prompt/resolve-option.js +8 -0
  53. package/commands/create/prompt/scope.d.ts +2 -0
  54. package/commands/create/prompt/scope.js +2 -0
  55. package/commands/create/prompt/types.d.ts +4 -0
  56. package/commands/dist.d.ts +2 -0
  57. package/commands/{publish/publish.js → dist.js} +22 -9
  58. package/commands/help.d.ts +3 -0
  59. package/commands/help.js +24 -0
  60. package/commands/index.d.ts +5 -0
  61. package/commands/index.js +5 -0
  62. package/commands/{publish/types.d.ts → types.d.ts} +18 -4
  63. package/commands/version.d.ts +2 -0
  64. package/commands/version.js +6 -0
  65. package/package.json +20 -588
  66. package/bin/vyriy.d.ts +0 -2
  67. package/checks/node/index.d.ts +0 -2
  68. package/checks/node/index.js +0 -1
  69. package/checks/node/node.d.ts +0 -2
  70. package/checks/node/node.js +0 -22
  71. package/checks/node/types.d.ts +0 -11
  72. package/checks/yarn/index.d.ts +0 -2
  73. package/checks/yarn/index.js +0 -1
  74. package/checks/yarn/types.d.ts +0 -7
  75. package/checks/yarn/yarn.d.ts +0 -2
  76. package/checks/yarn/yarn.js +0 -40
  77. package/cli/args/args.js +0 -40
  78. package/cli/args/index.d.ts +0 -2
  79. package/cli/args/index.js +0 -1
  80. package/cli/args/types.d.ts +0 -24
  81. package/commands/doctor/doctor.d.ts +0 -2
  82. package/commands/doctor/doctor.js +0 -9
  83. package/commands/doctor/index.d.ts +0 -2
  84. package/commands/doctor/index.js +0 -1
  85. package/commands/doctor/types.d.ts +0 -8
  86. package/commands/init/index.d.ts +0 -2
  87. package/commands/init/index.js +0 -1
  88. package/commands/init/init.d.ts +0 -2
  89. package/commands/init/init.js +0 -7
  90. package/commands/init/types.d.ts +0 -5
  91. package/commands/new/index.d.ts +0 -2
  92. package/commands/new/index.js +0 -1
  93. package/commands/new/new.d.ts +0 -3
  94. package/commands/new/new.js +0 -189
  95. package/commands/new/types.d.ts +0 -15
  96. package/commands/publish/index.d.ts +0 -2
  97. package/commands/publish/index.js +0 -1
  98. package/commands/publish/publish.d.ts +0 -2
  99. package/doctor/checkCorepack.d.ts +0 -2
  100. package/doctor/checkCorepack.js +0 -24
  101. package/doctor/checkGit.d.ts +0 -2
  102. package/doctor/checkGit.js +0 -23
  103. package/doctor/checkNodeVersion.d.ts +0 -5
  104. package/doctor/checkNodeVersion.js +0 -24
  105. package/doctor/checkYarn.d.ts +0 -10
  106. package/doctor/checkYarn.js +0 -45
  107. package/doctor/createDoctorReport.d.ts +0 -2
  108. package/doctor/createDoctorReport.js +0 -17
  109. package/doctor/index.d.ts +0 -7
  110. package/doctor/index.js +0 -6
  111. package/doctor/printDoctorReport.d.ts +0 -2
  112. package/doctor/printDoctorReport.js +0 -42
  113. package/doctor/types.d.ts +0 -25
  114. package/file-plan/createFilePlan.d.ts +0 -4
  115. package/file-plan/createFilePlan.js +0 -29
  116. package/file-plan/index.d.ts +0 -4
  117. package/file-plan/index.js +0 -3
  118. package/file-plan/printFilePlan.d.ts +0 -2
  119. package/file-plan/printFilePlan.js +0 -44
  120. package/file-plan/types.d.ts +0 -12
  121. package/file-plan/writeFilePlan.d.ts +0 -2
  122. package/file-plan/writeFilePlan.js +0 -12
  123. package/index.d.ts +0 -12
  124. package/index.js +0 -12
  125. package/presets/agentsTemplate.d.ts +0 -1
  126. package/presets/agentsTemplate.js +0 -105
  127. package/presets/base/createBaseFiles.d.ts +0 -3
  128. package/presets/base/createBaseFiles.js +0 -307
  129. package/presets/config.d.ts +0 -28
  130. package/presets/config.js +0 -7
  131. package/presets/createProjectFiles.d.ts +0 -2
  132. package/presets/createProjectFiles.js +0 -8
  133. package/presets/index.d.ts +0 -2
  134. package/presets/index.js +0 -1
  135. package/presets/library/createLibraryUiFiles.d.ts +0 -3
  136. package/presets/library/createLibraryUiFiles.js +0 -127
  137. package/presets/packages/createPackageFiles.d.ts +0 -3
  138. package/presets/packages/createPackageFiles.js +0 -39
  139. package/presets/packages/createPackageManifest.d.ts +0 -7
  140. package/presets/packages/createPackageManifest.js +0 -13
  141. package/presets/types.d.ts +0 -3
  142. package/presets/workspaces/createWorkspaceFiles.d.ts +0 -3
  143. package/presets/workspaces/createWorkspaceFiles.js +0 -98
  144. package/project-plan/api/api.d.ts +0 -6
  145. package/project-plan/api/api.js +0 -44
  146. package/project-plan/api/index.d.ts +0 -2
  147. package/project-plan/api/index.js +0 -1
  148. package/project-plan/api/types.d.ts +0 -11
  149. package/project-plan/ci/ci.d.ts +0 -3
  150. package/project-plan/ci/ci.js +0 -20
  151. package/project-plan/ci/index.d.ts +0 -2
  152. package/project-plan/ci/index.js +0 -1
  153. package/project-plan/ci/types.d.ts +0 -6
  154. package/project-plan/create/create.d.ts +0 -2
  155. package/project-plan/create/create.js +0 -129
  156. package/project-plan/create/index.d.ts +0 -2
  157. package/project-plan/create/index.js +0 -1
  158. package/project-plan/create/types.d.ts +0 -13
  159. package/project-plan/index.d.ts +0 -6
  160. package/project-plan/index.js +0 -5
  161. package/project-plan/kind/index.d.ts +0 -2
  162. package/project-plan/kind/index.js +0 -1
  163. package/project-plan/kind/kind.d.ts +0 -2
  164. package/project-plan/kind/kind.js +0 -1
  165. package/project-plan/kind/types.d.ts +0 -2
  166. package/project-plan/print/index.d.ts +0 -2
  167. package/project-plan/print/index.js +0 -1
  168. package/project-plan/print/print.d.ts +0 -2
  169. package/project-plan/print/print.js +0 -47
  170. package/project-plan/print/types.d.ts +0 -2
  171. package/project-plan/types.d.ts +0 -46
  172. package/prompts/project-plan/index.d.ts +0 -2
  173. package/prompts/project-plan/index.js +0 -1
  174. package/prompts/project-plan/project-plan.d.ts +0 -2
  175. package/prompts/project-plan/project-plan.js +0 -198
  176. package/prompts/project-plan/types.d.ts +0 -18
  177. package/shared/commandExists.d.ts +0 -2
  178. package/shared/commandExists.js +0 -10
  179. package/shared/execCommand.d.ts +0 -2
  180. package/shared/execCommand.js +0 -7
  181. package/shared/fileExists.d.ts +0 -2
  182. package/shared/fileExists.js +0 -10
  183. package/shared/index.d.ts +0 -6
  184. package/shared/index.js +0 -5
  185. package/shared/runCommand.d.ts +0 -9
  186. package/shared/runCommand.js +0 -34
  187. package/shared/semver.d.ts +0 -1
  188. package/shared/semver.js +0 -4
  189. package/shared/types.d.ts +0 -12
  190. /package/cli/{args/args.d.ts → args.d.ts} +0 -0
package/README.md CHANGED
@@ -1,222 +1,118 @@
1
1
  # vyriy
2
2
 
3
- Interactive project master for calm cloud-ready applications.
3
+ Interactive project master for Vyriy projects.
4
4
 
5
5
  ## Purpose
6
6
 
7
- `vyriy` is the user-facing CLI entry point for the Vyriy ecosystem.
8
-
9
- The CLI checks the local environment, runs a small project wizard, creates a normalized `VyriyProjectPlan`, builds generated project files in memory, prints a file plan, and writes only files that are safe to create or explicitly allowed to overwrite.
10
-
11
- For a detailed map of CLI choices, diagrams, current generated files, and next
12
- generator targets, see [PROJECT-MASTER.md](./PROJECT-MASTER.md).
7
+ `vyriy` is a CLI tool that scaffolds new projects with Vyriy configuration
8
+ presets, validates the local environment, merges optional provider files, and
9
+ prepares packages for publishing.
13
10
 
14
11
  ## Install
15
12
 
16
- Install globally:
13
+ With npm:
17
14
 
18
15
  ```bash
19
- npm i -g vyriy
16
+ npm install -g vyriy
20
17
  ```
21
18
 
22
- Or run the package temporarily:
19
+ With Yarn:
23
20
 
24
21
  ```bash
25
- npx vyriy new my-app
26
- yarn dlx vyriy new my-app
22
+ yarn global add vyriy
27
23
  ```
28
24
 
29
- ## Commands
25
+ ## Usage
30
26
 
31
27
  ```bash
32
- vyriy new
33
- vyriy new my-app
34
- vyriy .
35
- vyriy init
36
- vyriy doctor
37
- vyriy publish
38
- vyriy --dry-run
39
- vyriy --yes
40
- vyriy --no-install
41
- vyriy --no-verify
42
- vyriy --install-only
43
- vyriy --verify
44
- vyriy --overwrite
45
- vyriy --skip-existing
46
- vyriy --help
47
- vyriy --version
28
+ vyriy [name] Create a new Vyriy project
29
+ vyriy . Initialise a new Vyriy project in the current directory
30
+ vyriy --help, -h Show help
31
+ vyriy --version, -v Show version
32
+ vyriy --check-env, -c Check local environment (Node.js and Yarn versions)
33
+ vyriy --dist, -d Prepare dist package metadata without publishing to npm
34
+ vyriy --dry-run Print the merged file plan without writing project files
35
+ vyriy --overwrite Overwrite existing generated paths
36
+ vyriy --skip-existing Leave existing generated paths untouched
37
+ vyriy --no-install Create files without installing dependencies
38
+ vyriy --no-verify Install dependencies without running checks
48
39
  ```
49
40
 
50
- ### `vyriy`
51
-
52
- Runs the same flow as `vyriy new`.
53
-
54
- ### `vyriy new [name]`
55
-
56
- Starts the project planning wizard, prints the project summary and file plan, writes generated files when no unresolved conflicts exist, installs dependencies, and runs generated project checks.
57
-
58
- If `name` is provided, it is used as the default project name and target directory.
59
-
60
- ### `vyriy init`
61
-
62
- Starts the same planning wizard for the current directory.
63
-
64
- The current directory name is used as the default project name.
65
-
66
- ### `vyriy .`
67
-
68
- Alias for `vyriy init`.
69
-
70
- ### `vyriy doctor`
71
-
72
- Runs environment checks only.
73
-
74
- Current checks:
75
-
76
- - Node.js `>=24`
77
- - Corepack availability
78
- - Yarn `>=4`
79
- - Git availability
80
-
81
- Node.js is fatal when unsupported. Yarn and Git are warnings so generation can continue without silently installing tools or initializing Git.
82
-
83
- ### `vyriy publish`
84
-
85
- Prepares compiled `dist` package metadata for publishing without running `npm publish`.
86
-
87
- Use it after TypeScript emits package files into `dist`, for example from a `build:dist` script.
88
-
89
- ## Flags
90
-
91
- ### `--dry-run`
92
-
93
- Prints the doctor report, project summary, and file plan without writing files, installing dependencies, or running checks.
94
-
95
- ### `--no-install`
96
-
97
- Writes generated files but skips `yarn install` and `yarn check`.
98
-
99
- ### `--no-verify`
100
-
101
- Writes generated files and runs `yarn install`, but skips `yarn check`.
102
-
103
- ### `--install-only`
104
-
105
- Alias for `--no-verify`.
106
-
107
- ### `--verify`
108
-
109
- Explicitly enables `yarn check`. This is already the default unless `--no-install`, `--no-verify`, or `--install-only` is passed.
110
-
111
- ### `--yes`
112
-
113
- Uses default wizard answers and avoids prompts where possible. In non-interactive mode, the default preset is `empty` with no CI/CD provider. It does not overwrite existing files unless `--overwrite` is also passed.
114
-
115
- ### `--overwrite`
41
+ ## Commands
116
42
 
117
- Marks existing generated paths as overwrite candidates and writes them.
43
+ ### `create` (default)
118
44
 
119
- ### `--skip-existing`
45
+ The interactive wizard collects project details and writes the scaffold:
120
46
 
121
- Marks existing generated paths as skipped and leaves them untouched.
47
+ 1. Project name and description
48
+ 2. Target directory
49
+ 3. Preset selection
50
+ 4. Package scope (for package-based presets)
51
+ 5. CI/CD provider when the preset offers one
52
+ 6. Deploy provider when the preset offers one
53
+ 7. Confirmation (`y` to continue)
122
54
 
123
- `--overwrite` and `--skip-existing` cannot be used together.
55
+ The generated file set is built from the selected preset and then merged with
56
+ the selected CI/CD and deploy provider files. Later entries override earlier
57
+ entries with the same path.
124
58
 
125
- ## Wizard
59
+ When generated paths already exist, use `--overwrite` or `--skip-existing` to
60
+ avoid the interactive conflict prompt. Without either flag, `vyriy` asks whether
61
+ to overwrite existing files, skip them, or abort.
126
62
 
127
- The wizard collects:
63
+ ### `--check-env`
128
64
 
129
- - project name
130
- - target directory
131
- - package scope
132
- - description
133
- - project preset
134
- - API style for API-capable presets
135
- - CI/CD provider
136
- - infrastructure provider
137
- - confirmation
65
+ Validates Node.js and Yarn versions against the engine requirements declared in
66
+ `package.json`.
138
67
 
139
- After confirmation, the CLI prints the project plan, creates generated files in memory, builds a conflict-aware file plan, writes the accepted file plan, runs `yarn install`, and runs `yarn check`.
68
+ ### `--dist`
140
69
 
141
- Presets do not write to disk directly.
70
+ Prepares every package inside the `dist/` directory for npm publishing:
142
71
 
143
- Generated projects always include `AGENTS.md` based on the shared Vyriy package agent guide.
72
+ - Strips dev-only fields from `package.json`
73
+ - Builds the `exports` map from compiled JS files
74
+ - Copies README, LICENSE, and AGENTS.md
75
+ - Makes bin files executable
144
76
 
145
- ## Project Presets
77
+ ## Presets
146
78
 
147
- Supported presets:
79
+ Registered presets:
148
80
 
149
- - `empty`
150
- - `library`
151
- - `api`
152
- - `ssr`
153
- - `ssg`
154
- - `csr`
155
- - `fullstack`
156
- - `mfe`
81
+ | Key | Description |
82
+ | --------- | --------------------------------------------- |
83
+ | `base` | Minimal monorepo with config only |
84
+ | `library` | Workspaces layout with a sample React package |
85
+ | `api` | Backend API workspace with server/build setup |
157
86
 
158
- The preset is the concrete future generated setup. The project kind is the broader architecture category. The infrastructure choice is selected separately: Docker is the default local/container shape, while AWS selects CDK plus Lambda/API Gateway for API-capable presets.
87
+ Presets in progress:
159
88
 
160
- The `mfe` preset uses OpenMFE as the default MFE contract shape. There is no separate `openmfe` preset unless a future use case proves that split is useful.
89
+ | Key | Direction |
90
+ | ------ | ------------------------------ |
91
+ | `rest` | REST API project |
92
+ | `gql` | GraphQL API project |
93
+ | `ssr` | Server-side rendering project |
94
+ | `ssg` | Static site generation project |
95
+ | `spa` | Single-page application |
96
+ | `mfe` | Micro-frontend project |
161
97
 
162
- Workspace kinds describe deployment intent: `ui` is universal UI output, `api` is Docker-oriented, `lambda` is the AWS API runtime, `fargate` is an AWS container runtime, and `stack` contains AWS infrastructure.
98
+ Only registered presets are selectable by the wizard today. In-progress presets
99
+ exist as source modules and are expected to become selectable as their generated
100
+ project shape is finalized.
163
101
 
164
- Examples:
102
+ ## Providers
165
103
 
166
- - `csr` -> `csr`
167
- - `ssr` -> `ssr`
168
- - `ssg` -> `ssg`
169
- - `mfe` -> `mfe`
170
- - `fullstack` -> `fullstack`
104
+ Provider selections add files to the generated project.
171
105
 
172
- ## Public API
106
+ | Preset | CI/CD providers | Deploy providers |
107
+ | --------- | ------------------ | ---------------- |
108
+ | `base` | `gitlab`, `github` | none |
109
+ | `library` | `gitlab`, `github` | none |
110
+ | `api` | `gitlab`, `github` | none |
173
111
 
174
- The package exports the CLI runner, command helpers, doctor checks, file-plan utilities, generated preset files, prompt helper, and project-plan utilities.
112
+ ## API
175
113
 
176
114
  ```ts
177
- import {
178
- askProjectPlan,
179
- checkNodeVersion,
180
- checkYarnVersion,
181
- createDoctorReport,
182
- createFilePlan,
183
- createProjectFiles,
184
- createApiPlan,
185
- createCiPlan,
186
- createProjectPlanFromPreset,
187
- getProjectKindFromPreset,
188
- parseArgs,
189
- printProjectPlan,
190
- writeFilePlan,
191
- runDoctorCommand,
192
- runInitCommand,
193
- runNewCommand,
194
- runVyriyCli,
195
- } from 'vyriy';
196
- ```
197
-
198
- ## Project Plan
199
-
200
- The central model is `VyriyProjectPlan`.
201
-
202
- It includes:
115
+ import { cli } from 'vyriy';
203
116
 
204
- - project identity: `projectName`, `targetDirectory`, `packageScope`, `description`
205
- - architecture: `preset`, `projectKind`
206
- - selected features
207
- - CI/CD planning: enabled state, providers, and validation pipelines
208
- - API planning for API-capable presets: REST or GraphQL API style
209
- - future package plans
210
- - future workspace plans
211
-
212
- This model is intentionally useful before files are written. It gives generator steps a stable contract to build from.
213
-
214
- ## Current Non-Goals
215
-
216
- The CLI does not yet:
217
-
218
- - initialize Git
219
- - run `yarn install`
220
- - generate AWS CDK stacks
221
- - generate Docker files
222
- - generate React, OpenMFE, API, or service workspaces
117
+ await cli(process.argv.slice(2));
118
+ ```
package/bin/vyriy.js CHANGED
@@ -1,3 +1,3 @@
1
1
  #!/usr/bin/env node
2
- import { runVyriyCli } from '../cli/index.js';
3
- await runVyriyCli(process.argv.slice(2));
2
+ import { cli } from '../cli/index.js';
3
+ await cli(process.argv.slice(2));
package/cli/args.js ADDED
@@ -0,0 +1,29 @@
1
+ export const parseArgs = (args) => {
2
+ if (args.includes('--help') || args.includes('-h')) {
3
+ return { type: 'help' };
4
+ }
5
+ if (args.includes('--version') || args.includes('-v')) {
6
+ return { type: 'version' };
7
+ }
8
+ if (args.includes('--dist') || args.includes('-d')) {
9
+ return { type: 'dist' };
10
+ }
11
+ if (args.includes('--check-env') || args.includes('-c')) {
12
+ return { type: 'check-env' };
13
+ }
14
+ const dryRun = args.includes('--dry-run');
15
+ const overwrite = args.includes('--overwrite');
16
+ const skipExisting = args.includes('--skip-existing');
17
+ const install = !args.includes('--no-install');
18
+ const verify = install && !args.includes('--no-verify');
19
+ const directory = args.find((arg) => !arg.startsWith('-')) ?? '';
20
+ return {
21
+ type: 'create',
22
+ directory,
23
+ dryRun,
24
+ overwrite,
25
+ skipExisting,
26
+ install,
27
+ verify,
28
+ };
29
+ };
package/cli/cli.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { RunVyriyCli } from './types.js';
2
- export declare const runVyriyCli: RunVyriyCli;
1
+ import type { Cli } from './types.js';
2
+ export declare const cli: Cli;
package/cli/cli.js CHANGED
@@ -1,79 +1,28 @@
1
- import { runDoctorCommand } from '../commands/doctor/index.js';
2
- import { runInitCommand } from '../commands/init/index.js';
3
- import { runNewCommand } from '../commands/new/index.js';
4
- import { runPublishCommand } from '../commands/publish/index.js';
5
- import packageJson from '../package.json' with { type: 'json' };
6
- import { parseArgs } from './args/index.js';
7
- const helpText = `Vyriy Project Master
8
-
9
- Usage:
10
- vyriy new [name] Create a new Vyriy project
11
- vyriy init Initialize the current directory
12
- vyriy . Initialize the current directory
13
- vyriy doctor Check local environment
14
- vyriy publish Prepare dist package metadata without publishing to npm
15
- vyriy --yes, -y Use defaults where possible (empty preset)
16
- vyriy --dry-run Print checks and file plan without writing
17
- vyriy --overwrite Overwrite existing generated paths
18
- vyriy --skip-existing Leave existing generated paths untouched
19
- vyriy --no-install Create files without installing dependencies
20
- vyriy --no-verify Install dependencies without running checks
21
- vyriy --install-only Alias for --no-verify
22
- vyriy --verify Explicitly enable generated project checks
23
- vyriy --help, -h Show help
24
- vyriy --version, -v Show version
25
-
26
- Examples:
27
- vyriy new my-app
28
- vyriy .
29
- vyriy init`;
30
- export const runVyriyCli = async (args = [], { output = console } = {}) => {
1
+ import { parseArgs } from './args.js';
2
+ import { help, version, dist, checkEnv, create } from '../commands/index.js';
3
+ export const cli = async (args = []) => {
31
4
  const command = parseArgs(args);
32
- let code = 0;
33
5
  switch (command.type) {
34
- case 'new':
35
- code = await runNewCommand({
36
- dryRun: command.dryRun,
37
- install: command.install,
38
- output,
39
- overwrite: command.overwrite,
40
- projectName: command.projectName,
41
- skipExisting: command.skipExisting,
42
- verify: command.verify,
43
- yes: command.yes,
44
- });
6
+ case 'help':
7
+ process.exitCode = await help();
45
8
  break;
46
- case 'init':
47
- code = await runInitCommand({
48
- dryRun: command.dryRun,
49
- install: command.install,
50
- output,
51
- overwrite: command.overwrite,
52
- skipExisting: command.skipExisting,
53
- verify: command.verify,
54
- yes: command.yes,
55
- });
9
+ case 'version':
10
+ process.exitCode = await version();
56
11
  break;
57
- case 'doctor': {
58
- const result = await runDoctorCommand({ output });
59
- code = result.code;
12
+ case 'dist':
13
+ process.exitCode = await dist();
60
14
  break;
61
- }
62
- case 'publish':
63
- code = await runPublishCommand();
15
+ case 'check-env': {
16
+ process.exitCode = await checkEnv();
64
17
  break;
65
- case 'help':
66
- output.log(helpText);
67
- break;
68
- case 'version':
69
- output.log(packageJson.version);
18
+ }
19
+ case 'create':
20
+ process.exitCode = await create(command);
70
21
  break;
71
- case 'unknown':
72
- output.error(`Unknown command: ${command.command}\n`);
73
- output.error(helpText);
74
- code = 1;
22
+ default:
23
+ console.error(`Unknown command.\n`);
24
+ await help();
25
+ process.exitCode = 1;
75
26
  break;
76
27
  }
77
- process.exitCode = code;
78
- return code;
79
28
  };
package/cli/index.d.ts CHANGED
@@ -1,3 +1,3 @@
1
- export * from './args/index.js';
1
+ export * from './args.js';
2
2
  export * from './cli.js';
3
3
  export type * from './types.js';
package/cli/index.js CHANGED
@@ -1,2 +1,2 @@
1
- export * from './args/index.js';
1
+ export * from './args.js';
2
2
  export * from './cli.js';
package/cli/types.d.ts CHANGED
@@ -1,4 +1,13 @@
1
- export type RunVyriyCliOptions = {
2
- readonly output?: Pick<typeof console, 'log' | 'error'>;
1
+ export type Command = {
2
+ readonly type: 'help' | 'version' | 'dist' | 'check-env';
3
+ } | {
4
+ readonly type: 'create';
5
+ readonly directory: string;
6
+ readonly dryRun: boolean;
7
+ readonly overwrite: boolean;
8
+ readonly skipExisting: boolean;
9
+ readonly install: boolean;
10
+ readonly verify: boolean;
3
11
  };
4
- export type RunVyriyCli = (args?: readonly string[], options?: RunVyriyCliOptions) => Promise<number>;
12
+ export type ParseArgs = (args: readonly string[]) => Command;
13
+ export type Cli = (args?: readonly string[]) => Promise<void>;
@@ -0,0 +1,2 @@
1
+ import { Command } from './types.js';
2
+ export declare const checkEnv: Command;
@@ -0,0 +1,65 @@
1
+ import { exec as processExec } from 'node:child_process';
2
+ import { promisify } from 'node:util';
3
+ import packageJson from '../package.json' with { type: 'json' };
4
+ const exec = promisify(processExec);
5
+ const node = () => {
6
+ const majorVersion = Number.parseInt(process.versions.node.split('.')[0]);
7
+ const minimumMajorVersion = Number.parseInt(packageJson.engines.node.match(/(\d+)/)?.[0]);
8
+ if (majorVersion && majorVersion >= minimumMajorVersion) {
9
+ return {
10
+ ok: true,
11
+ version: process.versions.node,
12
+ message: `Node.js ${majorVersion}`,
13
+ };
14
+ }
15
+ return {
16
+ ok: false,
17
+ version: process.versions.node,
18
+ message: `Vyriy requires Node.js >= ${minimumMajorVersion}.\n\nCurrent version: ${process.versions.node}\n\nPlease upgrade Node.js and run the command again.`,
19
+ };
20
+ };
21
+ const yarn = async () => {
22
+ const minimumMajorVersion = Number.parseInt(packageJson.packageManager.match(/(\d+)/)?.[0]);
23
+ let currentVersion;
24
+ try {
25
+ const { stdout } = await exec('yarn --version');
26
+ currentVersion = stdout.trim();
27
+ }
28
+ catch {
29
+ return {
30
+ ok: false,
31
+ message: `Yarn was not found.\n\nVyriy requires Yarn >= ${minimumMajorVersion}.\n\nTry:\n corepack enable\n yarn set version stable`,
32
+ };
33
+ }
34
+ const majorVersion = Number.parseInt(currentVersion.match(/(\d+)/)?.[0]);
35
+ if (majorVersion && majorVersion >= minimumMajorVersion) {
36
+ return {
37
+ ok: true,
38
+ message: `Yarn ${currentVersion}`,
39
+ };
40
+ }
41
+ return {
42
+ ok: false,
43
+ message: `Vyriy requires Yarn >= ${minimumMajorVersion}.\n\nCurrent version: ${currentVersion}\n\nTry:\n corepack enable\n yarn set version stable`,
44
+ };
45
+ };
46
+ export const checkEnv = async () => {
47
+ const nodeResults = node();
48
+ console.log('Check env:');
49
+ if (nodeResults.ok) {
50
+ console.log(' ', nodeResults.message);
51
+ }
52
+ else {
53
+ console.error(nodeResults.message);
54
+ return 1;
55
+ }
56
+ const yarnResults = await yarn();
57
+ if (yarnResults.ok) {
58
+ console.log(' ', yarnResults.message);
59
+ }
60
+ else {
61
+ console.error(yarnResults.message);
62
+ return 1;
63
+ }
64
+ return 0;
65
+ };
@@ -0,0 +1,2 @@
1
+ import { Create } from '../types.js';
2
+ export declare const create: Create;
@@ -0,0 +1,121 @@
1
+ import { cwd } from 'node:process';
2
+ import { basename, dirname, resolve } from 'node:path';
3
+ import { existsSync, mkdirSync, writeFileSync } from 'node:fs';
4
+ import { exec as processExec } from 'node:child_process';
5
+ import { promisify } from 'node:util';
6
+ import { checkEnv } from '../check-env.js';
7
+ import { plan } from './plan/index.js';
8
+ import { conflictStrategy as promptConflictStrategy } from './prompt/index.js';
9
+ import { presets } from './preset/index.js';
10
+ const exec = promisify(processExec);
11
+ const getProviderFiles = (providers, provider) => provider === undefined ? {} : (providers[provider] ?? {});
12
+ const isPresetName = (preset) => preset in presets;
13
+ const mergeFiles = (planOption) => {
14
+ if (!isPresetName(planOption.preset)) {
15
+ return undefined;
16
+ }
17
+ const preset = presets[planOption.preset].preset;
18
+ return {
19
+ ...preset.files(planOption),
20
+ ...getProviderFiles(preset.ci, planOption.ci),
21
+ ...getProviderFiles(preset.deploy, planOption.deploy),
22
+ };
23
+ };
24
+ const getSortedFileNames = (files) => Object.keys(files).sort();
25
+ const logFilePlan = (target, files) => {
26
+ console.log(`\nFile plan (${target}):`);
27
+ console.log(' ', getSortedFileNames(files).join('\n '));
28
+ };
29
+ const getExistingFiles = (target, files) => {
30
+ const existingFiles = getSortedFileNames(files).filter((file) => existsSync(resolve(target, file)));
31
+ if (existingFiles.length) {
32
+ console.log('\nExisting files found:\n');
33
+ existingFiles.forEach((file) => console.log(' ', file));
34
+ }
35
+ return existingFiles;
36
+ };
37
+ const resolveConflictStrategy = async (filesExist, overwrite, skipExisting) => {
38
+ if (!filesExist || overwrite || skipExisting) {
39
+ return { overwrite, skipExisting };
40
+ }
41
+ const strategy = await promptConflictStrategy();
42
+ if (strategy) {
43
+ return strategy;
44
+ }
45
+ console.error('\nCannot continue without a conflict strategy.\n');
46
+ console.error('Use one of:\n\n vyriy --overwrite\n vyriy --skip-existing\n vyriy --dry-run');
47
+ return undefined;
48
+ };
49
+ const writeFiles = (target, files, overwrite) => {
50
+ console.log(`\nFile creating (${target}):`);
51
+ getSortedFileNames(files).forEach((file) => {
52
+ if (!existsSync(resolve(target, file)) || overwrite) {
53
+ console.log(' ', file);
54
+ const filePath = resolve(target, file);
55
+ mkdirSync(dirname(filePath), { recursive: true });
56
+ writeFileSync(filePath, files[file]);
57
+ }
58
+ });
59
+ };
60
+ export const create = async (options) => {
61
+ const { directory, dryRun, overwrite, skipExisting, install, verify } = options;
62
+ const checkEnvCode = await checkEnv();
63
+ if (checkEnvCode) {
64
+ return checkEnvCode;
65
+ }
66
+ const cliPath = cwd();
67
+ let dirName = 'app';
68
+ let appPath = resolve(cliPath, dirName);
69
+ if (directory) {
70
+ if (directory === '.') {
71
+ dirName = basename(cliPath);
72
+ appPath = cliPath;
73
+ }
74
+ else {
75
+ dirName = directory;
76
+ appPath = resolve(cwd(), dirName);
77
+ }
78
+ }
79
+ const planOption = await plan(dirName, appPath);
80
+ if (planOption) {
81
+ const { target } = planOption;
82
+ const files = mergeFiles(planOption);
83
+ if (!files) {
84
+ console.error(`Unknown preset: ${planOption.preset}`);
85
+ return 1;
86
+ }
87
+ if (dryRun) {
88
+ logFilePlan(target, files);
89
+ return 0;
90
+ }
91
+ console.log(`\nFile checking (${target})...`);
92
+ const existingFiles = getExistingFiles(target, files);
93
+ const conflictStrategy = await resolveConflictStrategy(Boolean(existingFiles.length), overwrite, skipExisting);
94
+ if (!conflictStrategy) {
95
+ return 1;
96
+ }
97
+ writeFiles(target, files, conflictStrategy.overwrite);
98
+ if (install) {
99
+ console.log('Installing dependencies...');
100
+ await exec(`yarn --cwd ${target} set version berry`);
101
+ await exec(`yarn --cwd ${target} install`);
102
+ }
103
+ else {
104
+ console.log('Installing dependencies... SKIPPED');
105
+ console.log('Running checks... SKIPPED');
106
+ console.log('\nProject files were created.');
107
+ return 0;
108
+ }
109
+ if (verify) {
110
+ console.log('Running checks...');
111
+ await exec(`yarn --cwd ${target} check`);
112
+ }
113
+ else {
114
+ console.log('Running checks... SKIPPED');
115
+ console.log('\nProject files were created.');
116
+ return 0;
117
+ }
118
+ return 0;
119
+ }
120
+ return 1;
121
+ };
@@ -0,0 +1,4 @@
1
+ export * from './plan.js';
2
+ export * from '../prompt/index.js';
3
+ export * from './question.js';
4
+ export type * from './types.js';
@@ -0,0 +1,3 @@
1
+ export * from './plan.js';
2
+ export * from '../prompt/index.js';
3
+ export * from './question.js';