@decohere/scaffold 0.0.1-dev.125 → 0.0.1-dev.18

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 (264) hide show
  1. package/package.json +9 -19
  2. package/src/add-api.action.ts +25 -0
  3. package/src/add-api.command.ts +31 -0
  4. package/src/add.command.ts +20 -0
  5. package/src/add.module.ts +11 -0
  6. package/src/cli.ts +4 -0
  7. package/src/create.command.ts +20 -0
  8. package/src/create.module.ts +11 -0
  9. package/src/domain/prompt.ts +50 -0
  10. package/{types/src/index.d.ts → src/index.ts} +0 -4
  11. package/src/models/compose.model.ts +205 -0
  12. package/src/models/config-yaml.model.ts +83 -0
  13. package/src/models/const.ts +20 -0
  14. package/src/models/dev-container.model.ts +136 -0
  15. package/src/models/docker-image.model.ts +343 -0
  16. package/src/models/env-file.model.ts +45 -0
  17. package/src/models/gitignore.model.ts +35 -0
  18. package/src/models/launch-json.model.ts +60 -0
  19. package/src/models/package-json.model.ts +169 -0
  20. package/src/models/project.model.ts +141 -0
  21. package/{types/src/models/source-file.d.ts → src/models/source-file.ts} +6 -4
  22. package/src/models/tsconfig.model.ts +29 -0
  23. package/src/models/vitest-config.model.ts +26 -0
  24. package/src/models/vscode-settings.model.ts +24 -0
  25. package/src/program.ts +63 -0
  26. package/{types/src/resolve-target-dir.d.ts → src/resolve-target-dir.ts} +4 -1
  27. package/src/services/scaffold.service.ts +89 -0
  28. package/src/version.ts +56 -0
  29. package/src/webapi/api-name.ts +73 -0
  30. package/src/webapi/cli-options.ts +56 -0
  31. package/{types/src/webapi/const.d.ts → src/webapi/const.ts} +21 -9
  32. package/src/webapi/create-api.ts +275 -0
  33. package/src/webapi/devcontainer/host-scripts.ts +35 -0
  34. package/src/webapi/features/auth.feature.ts +454 -0
  35. package/src/webapi/features/auth0-cli.ts +421 -0
  36. package/src/webapi/features/biome-format.ts +34 -0
  37. package/src/webapi/features/database.feature.ts +522 -0
  38. package/src/webapi/features/finalize.feature.ts +112 -0
  39. package/src/webapi/features/postman.feature.ts +287 -0
  40. package/src/webapi/models/api-package-json.model.ts +60 -0
  41. package/src/webapi/models/auth-config.model.ts +36 -0
  42. package/src/webapi/models/controller-source-file.model.ts +232 -0
  43. package/{es6/src/webapi/models/github-ci.model.js → src/webapi/models/github-ci.model.ts} +29 -27
  44. package/src/webapi/models/main-source-file.model.ts +208 -0
  45. package/src/webapi/models/production-dockerfile.model.ts +162 -0
  46. package/src/webapi/models/sample-files.model.ts +45 -0
  47. package/src/webapi/models/webapi-image.model.ts +21 -0
  48. package/src/webapi/postman/hello-openapi.ts +92 -0
  49. package/src/webapi/postman/local-view.ts +195 -0
  50. package/src/webapi/postman/openapi-to-postman.ts +208 -0
  51. package/src/webapi/workspace-readme.ts +192 -0
  52. package/src/webapi.action.ts +22 -0
  53. package/src/webapi.command.ts +41 -0
  54. package/tests/auth-postman.wiring.spec.ts +263 -0
  55. package/tests/auth0-cli.spec.ts +232 -0
  56. package/tests/biome-format.spec.ts +49 -0
  57. package/tests/cli.integration.spec.ts +658 -0
  58. package/tests/compose.model.spec.ts +51 -0
  59. package/tests/container-image.model.spec.ts +162 -0
  60. package/tests/dev-container.model.spec.ts +29 -0
  61. package/tests/devcontainer-base-image.spec.ts +32 -0
  62. package/tests/hello-di-inject.scaffold.spec.ts +18 -0
  63. package/tests/hello-route.contract.spec.ts +94 -0
  64. package/tests/package-json.order.spec.ts +59 -0
  65. package/tests/postman-from-openapi.spec.ts +197 -0
  66. package/tests/seed-devcontainer-templates.ts +40 -0
  67. package/tests/webapi/devcontainer/codebase-rag-mcp.spec.ts +96 -0
  68. package/LICENSE +0 -15
  69. package/commonjs/src/add-api.action.js +0 -37
  70. package/commonjs/src/add-api.command.js +0 -39
  71. package/commonjs/src/add.command.js +0 -22
  72. package/commonjs/src/add.module.js +0 -24
  73. package/commonjs/src/auth0-configure.action.js +0 -28
  74. package/commonjs/src/auth0-configure.command.js +0 -24
  75. package/commonjs/src/auth0-login.action.js +0 -28
  76. package/commonjs/src/auth0-login.command.js +0 -23
  77. package/commonjs/src/auth0.command.js +0 -22
  78. package/commonjs/src/auth0.module.js +0 -28
  79. package/commonjs/src/cli.js +0 -8
  80. package/commonjs/src/create.command.js +0 -22
  81. package/commonjs/src/create.module.js +0 -24
  82. package/commonjs/src/domain/prompt.js +0 -62
  83. package/commonjs/src/index.js +0 -48
  84. package/commonjs/src/models/compose.model.js +0 -258
  85. package/commonjs/src/models/config-yaml.model.js +0 -86
  86. package/commonjs/src/models/const.js +0 -30
  87. package/commonjs/src/models/dev-container.model.js +0 -172
  88. package/commonjs/src/models/docker-image.model.js +0 -277
  89. package/commonjs/src/models/env-file.model.js +0 -48
  90. package/commonjs/src/models/gitignore.model.js +0 -48
  91. package/commonjs/src/models/launch-json.model.js +0 -70
  92. package/commonjs/src/models/package-json.model.js +0 -156
  93. package/commonjs/src/models/project.model.js +0 -132
  94. package/commonjs/src/models/source-file.js +0 -4
  95. package/commonjs/src/models/tsconfig.model.js +0 -32
  96. package/commonjs/src/models/vitest-config.model.js +0 -33
  97. package/commonjs/src/models/vscode-settings.model.js +0 -29
  98. package/commonjs/src/program.js +0 -64
  99. package/commonjs/src/resolve-target-dir.js +0 -17
  100. package/commonjs/src/services/scaffold.service.js +0 -60
  101. package/commonjs/src/version.js +0 -55
  102. package/commonjs/src/webapi/api-name.js +0 -93
  103. package/commonjs/src/webapi/auth0-commands.js +0 -250
  104. package/commonjs/src/webapi/authorize-scopes.js +0 -79
  105. package/commonjs/src/webapi/cli-options.js +0 -99
  106. package/commonjs/src/webapi/const.js +0 -54
  107. package/commonjs/src/webapi/create-api.js +0 -265
  108. package/commonjs/src/webapi/devcontainer/codebase-rag-mcp.js +0 -164
  109. package/commonjs/src/webapi/devcontainer/codebase-rag-mcp.ts +0 -182
  110. package/commonjs/src/webapi/devcontainer/host-scripts.js +0 -50
  111. package/commonjs/src/webapi/devcontainer/templates/codebase-rag.env.example +0 -3
  112. package/commonjs/src/webapi/devcontainer/templates/initialize.sh +0 -169
  113. package/commonjs/src/webapi/devcontainer/templates/post-create.sh +0 -35
  114. package/commonjs/src/webapi/devcontainer/templates/post-start.sh +0 -65
  115. package/commonjs/src/webapi/devcontainer/templates/tty-prompt.sh +0 -38
  116. package/commonjs/src/webapi/features/auth.feature.js +0 -408
  117. package/commonjs/src/webapi/features/auth0-cli.js +0 -472
  118. package/commonjs/src/webapi/features/biome-format.js +0 -47
  119. package/commonjs/src/webapi/features/database.feature.js +0 -433
  120. package/commonjs/src/webapi/features/finalize.feature.js +0 -93
  121. package/commonjs/src/webapi/features/postman.feature.js +0 -322
  122. package/commonjs/src/webapi/models/api-package-json.model.js +0 -58
  123. package/commonjs/src/webapi/models/auth-config.model.js +0 -24
  124. package/commonjs/src/webapi/models/controller-source-file.model.js +0 -190
  125. package/commonjs/src/webapi/models/github-ci.model.js +0 -193
  126. package/commonjs/src/webapi/models/main-source-file.model.js +0 -165
  127. package/commonjs/src/webapi/models/production-dockerfile.model.js +0 -75
  128. package/commonjs/src/webapi/models/sample-files.model.js +0 -58
  129. package/commonjs/src/webapi/models/webapi-image.model.js +0 -25
  130. package/commonjs/src/webapi/postman/hello-openapi.js +0 -173
  131. package/commonjs/src/webapi/postman/local-view.js +0 -182
  132. package/commonjs/src/webapi/postman/openapi-to-postman.js +0 -238
  133. package/commonjs/src/webapi/workspace-readme.js +0 -109
  134. package/commonjs/src/webapi.action.js +0 -28
  135. package/commonjs/src/webapi.command.js +0 -43
  136. package/es6/src/add-api.action.js +0 -27
  137. package/es6/src/add-api.command.js +0 -29
  138. package/es6/src/add.command.js +0 -12
  139. package/es6/src/add.module.js +0 -14
  140. package/es6/src/auth0-configure.action.js +0 -18
  141. package/es6/src/auth0-configure.command.js +0 -14
  142. package/es6/src/auth0-login.action.js +0 -18
  143. package/es6/src/auth0-login.command.js +0 -13
  144. package/es6/src/auth0.command.js +0 -12
  145. package/es6/src/auth0.module.js +0 -18
  146. package/es6/src/cli.js +0 -4
  147. package/es6/src/create.command.js +0 -12
  148. package/es6/src/create.module.js +0 -14
  149. package/es6/src/domain/prompt.js +0 -41
  150. package/es6/src/index.js +0 -9
  151. package/es6/src/models/compose.model.js +0 -254
  152. package/es6/src/models/config-yaml.model.js +0 -74
  153. package/es6/src/models/const.js +0 -20
  154. package/es6/src/models/dev-container.model.js +0 -162
  155. package/es6/src/models/docker-image.model.js +0 -235
  156. package/es6/src/models/env-file.model.js +0 -44
  157. package/es6/src/models/gitignore.model.js +0 -38
  158. package/es6/src/models/launch-json.model.js +0 -60
  159. package/es6/src/models/package-json.model.js +0 -141
  160. package/es6/src/models/project.model.js +0 -117
  161. package/es6/src/models/source-file.js +0 -1
  162. package/es6/src/models/tsconfig.model.js +0 -22
  163. package/es6/src/models/vitest-config.model.js +0 -23
  164. package/es6/src/models/vscode-settings.model.js +0 -19
  165. package/es6/src/program.js +0 -50
  166. package/es6/src/resolve-target-dir.js +0 -7
  167. package/es6/src/services/scaffold.service.js +0 -50
  168. package/es6/src/version.js +0 -34
  169. package/es6/src/webapi/api-name.js +0 -57
  170. package/es6/src/webapi/auth0-commands.js +0 -185
  171. package/es6/src/webapi/authorize-scopes.js +0 -55
  172. package/es6/src/webapi/cli-options.js +0 -34
  173. package/es6/src/webapi/const.js +0 -21
  174. package/es6/src/webapi/create-api.js +0 -245
  175. package/es6/src/webapi/devcontainer/codebase-rag-mcp.js +0 -154
  176. package/es6/src/webapi/devcontainer/codebase-rag-mcp.ts +0 -182
  177. package/es6/src/webapi/devcontainer/host-scripts.js +0 -29
  178. package/es6/src/webapi/devcontainer/templates/codebase-rag.env.example +0 -3
  179. package/es6/src/webapi/devcontainer/templates/initialize.sh +0 -169
  180. package/es6/src/webapi/devcontainer/templates/post-create.sh +0 -35
  181. package/es6/src/webapi/devcontainer/templates/post-start.sh +0 -65
  182. package/es6/src/webapi/devcontainer/templates/tty-prompt.sh +0 -38
  183. package/es6/src/webapi/features/auth.feature.js +0 -357
  184. package/es6/src/webapi/features/auth0-cli.js +0 -406
  185. package/es6/src/webapi/features/biome-format.js +0 -40
  186. package/es6/src/webapi/features/database.feature.js +0 -423
  187. package/es6/src/webapi/features/finalize.feature.js +0 -83
  188. package/es6/src/webapi/features/postman.feature.js +0 -256
  189. package/es6/src/webapi/models/api-package-json.model.js +0 -53
  190. package/es6/src/webapi/models/auth-config.model.js +0 -20
  191. package/es6/src/webapi/models/controller-source-file.model.js +0 -181
  192. package/es6/src/webapi/models/main-source-file.model.js +0 -161
  193. package/es6/src/webapi/models/production-dockerfile.model.js +0 -66
  194. package/es6/src/webapi/models/sample-files.model.js +0 -40
  195. package/es6/src/webapi/models/webapi-image.model.js +0 -18
  196. package/es6/src/webapi/postman/hello-openapi.js +0 -166
  197. package/es6/src/webapi/postman/local-view.js +0 -167
  198. package/es6/src/webapi/postman/openapi-to-postman.js +0 -179
  199. package/es6/src/webapi/workspace-readme.js +0 -88
  200. package/es6/src/webapi.action.js +0 -18
  201. package/es6/src/webapi.command.js +0 -33
  202. package/types/src/add-api.action.d.ts +0 -13
  203. package/types/src/add-api.command.d.ts +0 -7
  204. package/types/src/add.command.d.ts +0 -6
  205. package/types/src/add.module.d.ts +0 -14
  206. package/types/src/auth0-configure.action.d.ts +0 -7
  207. package/types/src/auth0-configure.command.d.ts +0 -6
  208. package/types/src/auth0-login.action.d.ts +0 -4
  209. package/types/src/auth0-login.command.d.ts +0 -6
  210. package/types/src/auth0.command.d.ts +0 -6
  211. package/types/src/auth0.module.d.ts +0 -18
  212. package/types/src/cli.d.ts +0 -2
  213. package/types/src/create.command.d.ts +0 -6
  214. package/types/src/create.module.d.ts +0 -14
  215. package/types/src/domain/prompt.d.ts +0 -4
  216. package/types/src/models/compose.model.d.ts +0 -73
  217. package/types/src/models/config-yaml.model.d.ts +0 -27
  218. package/types/src/models/const.d.ts +0 -20
  219. package/types/src/models/dev-container.model.d.ts +0 -49
  220. package/types/src/models/docker-image.model.d.ts +0 -90
  221. package/types/src/models/env-file.model.d.ts +0 -16
  222. package/types/src/models/gitignore.model.d.ts +0 -9
  223. package/types/src/models/launch-json.model.d.ts +0 -7
  224. package/types/src/models/package-json.model.d.ts +0 -36
  225. package/types/src/models/project.model.d.ts +0 -60
  226. package/types/src/models/tsconfig.model.d.ts +0 -5
  227. package/types/src/models/vitest-config.model.d.ts +0 -5
  228. package/types/src/models/vscode-settings.model.d.ts +0 -7
  229. package/types/src/program.d.ts +0 -8
  230. package/types/src/services/scaffold.service.d.ts +0 -22
  231. package/types/src/version.d.ts +0 -6
  232. package/types/src/webapi/api-name.d.ts +0 -14
  233. package/types/src/webapi/auth0-commands.d.ts +0 -11
  234. package/types/src/webapi/authorize-scopes.d.ts +0 -7
  235. package/types/src/webapi/cli-options.d.ts +0 -6
  236. package/types/src/webapi/create-api.d.ts +0 -15
  237. package/types/src/webapi/devcontainer/codebase-rag-mcp.d.ts +0 -32
  238. package/types/src/webapi/devcontainer/codebase-rag-mcp.ts +0 -182
  239. package/types/src/webapi/devcontainer/host-scripts.d.ts +0 -7
  240. package/types/src/webapi/devcontainer/templates/codebase-rag.env.example +0 -3
  241. package/types/src/webapi/devcontainer/templates/initialize.sh +0 -169
  242. package/types/src/webapi/devcontainer/templates/post-create.sh +0 -35
  243. package/types/src/webapi/devcontainer/templates/post-start.sh +0 -65
  244. package/types/src/webapi/devcontainer/templates/tty-prompt.sh +0 -38
  245. package/types/src/webapi/features/auth.feature.d.ts +0 -10
  246. package/types/src/webapi/features/auth0-cli.d.ts +0 -84
  247. package/types/src/webapi/features/biome-format.d.ts +0 -5
  248. package/types/src/webapi/features/database.feature.d.ts +0 -7
  249. package/types/src/webapi/features/finalize.feature.d.ts +0 -2
  250. package/types/src/webapi/features/postman.feature.d.ts +0 -16
  251. package/types/src/webapi/models/api-package-json.model.d.ts +0 -18
  252. package/types/src/webapi/models/auth-config.model.d.ts +0 -26
  253. package/types/src/webapi/models/controller-source-file.model.d.ts +0 -46
  254. package/types/src/webapi/models/github-ci.model.d.ts +0 -9
  255. package/types/src/webapi/models/main-source-file.model.d.ts +0 -54
  256. package/types/src/webapi/models/production-dockerfile.model.d.ts +0 -18
  257. package/types/src/webapi/models/sample-files.model.d.ts +0 -7
  258. package/types/src/webapi/models/webapi-image.model.d.ts +0 -12
  259. package/types/src/webapi/postman/hello-openapi.d.ts +0 -19
  260. package/types/src/webapi/postman/local-view.d.ts +0 -17
  261. package/types/src/webapi/postman/openapi-to-postman.d.ts +0 -62
  262. package/types/src/webapi/workspace-readme.d.ts +0 -18
  263. package/types/src/webapi.action.d.ts +0 -14
  264. package/types/src/webapi.command.d.ts +0 -11
@@ -1,14 +0,0 @@
1
- import { ModuleManifest } from "@decohere/devkit/cli";
2
- import { AddCommand } from "./add.command.js";
3
- import { AddApiAction } from "./add-api.action.js";
4
- import { AddApiCommand } from "./add-api.command.js";
5
- export class AddModule extends ModuleManifest {
6
- id = "add";
7
- command = AddCommand;
8
- commands = {
9
- api: AddApiCommand
10
- };
11
- actions = {
12
- api: AddApiAction
13
- };
14
- }
@@ -1,18 +0,0 @@
1
- function _ts_decorate(decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- }
7
- import { injectable } from "@decohere/crucible/decorators";
8
- import { ActionResponse } from "@decohere/devkit/cli";
9
- import { runAuth0Configure } from "./webapi/auth0-commands.js";
10
- export class Auth0ConfigureAction {
11
- async run(options) {
12
- runAuth0Configure(typeof options.d === "string" ? options.d : ".");
13
- return ActionResponse.Success("configure");
14
- }
15
- }
16
- Auth0ConfigureAction = _ts_decorate([
17
- injectable()
18
- ], Auth0ConfigureAction);
@@ -1,14 +0,0 @@
1
- import { DecohereCommand } from "@decohere/devkit/cli";
2
- import { Auth0ConfigureAction } from "./auth0-configure.action.js";
3
- export class Auth0ConfigureCommand extends DecohereCommand {
4
- get actions() {
5
- return [
6
- Auth0ConfigureAction
7
- ];
8
- }
9
- constructor(name){
10
- super(name);
11
- this.description("Update Auth0 API permissions and Postman SPA from @Authorize in this workspace");
12
- this.option("-d <directory>", "Workspace directory (default: current directory)", ".");
13
- }
14
- }
@@ -1,18 +0,0 @@
1
- function _ts_decorate(decorators, target, key, desc) {
2
- var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
3
- if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
4
- else for(var i = decorators.length - 1; i >= 0; i--)if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
5
- return c > 3 && r && Object.defineProperty(target, key, r), r;
6
- }
7
- import { injectable } from "@decohere/crucible/decorators";
8
- import { ActionResponse } from "@decohere/devkit/cli";
9
- import { runAuth0Login } from "./webapi/auth0-commands.js";
10
- export class Auth0LoginAction {
11
- async run() {
12
- runAuth0Login();
13
- return ActionResponse.Success("login");
14
- }
15
- }
16
- Auth0LoginAction = _ts_decorate([
17
- injectable()
18
- ], Auth0LoginAction);
@@ -1,13 +0,0 @@
1
- import { DecohereCommand } from "@decohere/devkit/cli";
2
- import { Auth0LoginAction } from "./auth0-login.action.js";
3
- export class Auth0LoginCommand extends DecohereCommand {
4
- get actions() {
5
- return [
6
- Auth0LoginAction
7
- ];
8
- }
9
- constructor(name){
10
- super(name);
11
- this.description("Authenticate the Auth0 CLI (device URL; tokens persist on the host)");
12
- }
13
- }
@@ -1,12 +0,0 @@
1
- import { DecohereCommand } from "@decohere/devkit/cli";
2
- export class Auth0Command extends DecohereCommand {
3
- constructor(commands, handler){
4
- super(Auth0Command);
5
- this.description("Log in to Auth0 and update a scaffolded client");
6
- this.exitOverride();
7
- this.registerSubcommand(commands, handler);
8
- }
9
- run(_actions, _options) {
10
- return this.help();
11
- }
12
- }
@@ -1,18 +0,0 @@
1
- import { ModuleManifest } from "@decohere/devkit/cli";
2
- import { Auth0Command } from "./auth0.command.js";
3
- import { Auth0ConfigureAction } from "./auth0-configure.action.js";
4
- import { Auth0ConfigureCommand } from "./auth0-configure.command.js";
5
- import { Auth0LoginAction } from "./auth0-login.action.js";
6
- import { Auth0LoginCommand } from "./auth0-login.command.js";
7
- export class Auth0Module extends ModuleManifest {
8
- id = "auth0";
9
- command = Auth0Command;
10
- commands = {
11
- login: Auth0LoginCommand,
12
- configure: Auth0ConfigureCommand
13
- };
14
- actions = {
15
- login: Auth0LoginAction,
16
- configure: Auth0ConfigureAction
17
- };
18
- }
package/es6/src/cli.js DELETED
@@ -1,4 +0,0 @@
1
- #!/usr/bin/env node
2
- import { runCli } from "./program.js";
3
- // Exit as soon as the command is done, without waiting for handles it left open.
4
- process.exit(await runCli());
@@ -1,12 +0,0 @@
1
- import { DecohereCommand } from "@decohere/devkit/cli";
2
- export class CreateCommand extends DecohereCommand {
3
- constructor(commands, handler){
4
- super(CreateCommand);
5
- this.description("Create a new Decohere workspace");
6
- this.exitOverride();
7
- this.registerSubcommand(commands, handler);
8
- }
9
- run(_actions, _options) {
10
- return this.help();
11
- }
12
- }
@@ -1,14 +0,0 @@
1
- import { ModuleManifest } from "@decohere/devkit/cli";
2
- import { CreateCommand } from "./create.command.js";
3
- import { WebapiAction } from "./webapi.action.js";
4
- import { WebapiCommand } from "./webapi.command.js";
5
- export class CreateModule extends ModuleManifest {
6
- id = "create";
7
- command = CreateCommand;
8
- commands = {
9
- webapi: WebapiCommand
10
- };
11
- actions = {
12
- webapi: WebapiAction
13
- };
14
- }
@@ -1,41 +0,0 @@
1
- import { createInterface } from "node:readline";
2
- // readline/promises rl.question() has a race condition with piped (non-TTY) stdin
3
- // in Node ≥ 22: after the first line is read, stdin emits 'end', readline closes,
4
- // and all subsequent question() calls resolve to "".
5
- // Fix: use the async-iterator API, which buffers all lines before the close event fires.
6
- let _rl = null;
7
- let _lines = null;
8
- function getLines() {
9
- if (_lines == null) {
10
- _rl = createInterface({
11
- input: process.stdin,
12
- terminal: false
13
- });
14
- _lines = _rl[Symbol.asyncIterator]();
15
- }
16
- return _lines;
17
- }
18
- /** Release stdin so the process can exit after interactive prompts. */ export function closePrompt() {
19
- _rl?.close();
20
- _rl = null;
21
- _lines = null;
22
- }
23
- async function readLine(prompt) {
24
- process.stdout.write(prompt);
25
- const { value, done } = await getLines().next();
26
- return done ? "" : value.trim();
27
- }
28
- export async function ask(question, fallback = "") {
29
- const answer = await readLine(question);
30
- return answer || fallback;
31
- }
32
- export async function pick(label, items, display) {
33
- console.log(label.trimEnd());
34
- for (const [i, item] of items.entries()){
35
- console.log(` ${i + 1}. ${display(item)}`);
36
- }
37
- const answer = await readLine(" > ");
38
- const idx = Number.parseInt(answer, 10);
39
- if (Number.isNaN(idx) || idx < 1 || idx > items.length) return null;
40
- return items[idx - 1];
41
- }
package/es6/src/index.js DELETED
@@ -1,9 +0,0 @@
1
- export { AddModule } from "./add.module.js";
2
- export { AddApiAction } from "./add-api.action.js";
3
- export { Auth0Module } from "./auth0.module.js";
4
- export { Auth0ConfigureAction } from "./auth0-configure.action.js";
5
- export { Auth0LoginAction } from "./auth0-login.action.js";
6
- export { CreateModule } from "./create.module.js";
7
- export { runCli } from "./program.js";
8
- export { scaffoldApi } from "./webapi/create-api.js";
9
- export { WebapiAction } from "./webapi.action.js";
@@ -1,254 +0,0 @@
1
- import { readFileSync } from "node:fs";
2
- import { isMap, isSeq, parseDocument } from "yaml";
3
- import { WELL_KNOWN_FILES } from "./const.js";
4
- /**
5
- * Live builder for `docker-compose.yml`.
6
- *
7
- * Features call `addService` / `addVolume` / `addNetwork` in their scaffold phases.
8
- * Loaded with `fromFile` (`decohere add api`), additions merge into the existing file:
9
- * services, networks and volumes already there are left untouched, comments kept.
10
- */ export class DockerCompose {
11
- key = WELL_KNOWN_FILES.DOCKER_COMPOSE;
12
- _projectName;
13
- _headerComments = [];
14
- _services = new Map();
15
- _volumes = new Set();
16
- _networks = new Map();
17
- _envFiles = [];
18
- _existing;
19
- /** Load an existing compose file so `decohere add api` can merge into it. */ static fromFile(absolutePath) {
20
- const compose = new DockerCompose();
21
- compose._existing = parseDocument(readFileSync(absolutePath, "utf8"));
22
- return compose;
23
- }
24
- /** True when the service is defined (in the loaded file or added since). */ hasService(name) {
25
- return this._services.has(name) || this._existing?.hasIn([
26
- "services",
27
- name
28
- ]) === true;
29
- }
30
- /** Compose project name (`name:` top-level) — isolates containers/volumes. */ setProjectName(name) {
31
- this._projectName = name;
32
- return this;
33
- }
34
- /** File-level `#` comments rendered above `name:` / `services:`. */ addHeaderComment(...lines) {
35
- this._headerComments.push(...lines);
36
- return this;
37
- }
38
- addService(name, config) {
39
- this._services.set(name, config);
40
- return this;
41
- }
42
- files() {
43
- return [
44
- {
45
- filePath: ".devcontainer/docker-compose.yml",
46
- content: this.getContent()
47
- }
48
- ];
49
- }
50
- addVolume(name) {
51
- this._volumes.add(name);
52
- return this;
53
- }
54
- addNetwork(key, network) {
55
- this._networks.set(key, network);
56
- return this;
57
- }
58
- /** Append an env_file path to an existing service. */ addEnvFile(serviceName, filePath) {
59
- // A service already in the loaded file wins over an `addService` of the same name.
60
- const svc = this._existing?.hasIn([
61
- "services",
62
- serviceName
63
- ]) ? undefined : this._services.get(serviceName);
64
- if (svc) svc.env_file = [
65
- ...svc.env_file ?? [],
66
- filePath
67
- ];
68
- else this._envFiles.push([
69
- serviceName,
70
- filePath
71
- ]);
72
- return this;
73
- }
74
- getContent() {
75
- if (this._existing) return this.mergeIntoExisting(this._existing);
76
- const lines = [];
77
- for (const comment of this._headerComments){
78
- lines.push(comment.startsWith("#") ? comment : `# ${comment}`);
79
- }
80
- if (this._headerComments.length > 0) {
81
- lines.push("");
82
- }
83
- if (this._projectName) {
84
- lines.push(`name: ${this._projectName}`, "");
85
- }
86
- lines.push("services:");
87
- for (const [name, svc] of this._services){
88
- lines.push(` ${name}:`);
89
- if (svc.build) lines.push(` build: ${svc.build}`);
90
- if (svc.image) lines.push(` image: ${svc.image}`);
91
- if (svc.container_name) lines.push(` container_name: ${svc.container_name}`);
92
- if (svc.command) lines.push(` command: ${svc.command}`);
93
- if (svc.user) lines.push(` user: "${svc.user}"`);
94
- if (svc.restart) lines.push(` restart: ${svc.restart}`);
95
- if (svc.profiles && svc.profiles.length > 0) {
96
- lines.push(" profiles:");
97
- for (const p of svc.profiles)lines.push(` - ${p}`);
98
- }
99
- if (svc.env_file && svc.env_file.length > 0) {
100
- lines.push(" env_file:");
101
- for (const f of svc.env_file)lines.push(` - ${f}`);
102
- }
103
- if (svc.environment && Object.keys(svc.environment).length > 0) {
104
- lines.push(" environment:");
105
- for (const [k, v] of Object.entries(svc.environment)){
106
- lines.push(` ${k}: ${v}`);
107
- }
108
- }
109
- if (svc.ports && svc.ports.length > 0) {
110
- lines.push(" ports:");
111
- for (const p of svc.ports)lines.push(` - "${p}"`);
112
- }
113
- if (svc.volumes && svc.volumes.length > 0) {
114
- lines.push(" volumes:");
115
- for (const v of svc.volumes)lines.push(` - ${v}`);
116
- }
117
- if (svc.networks && svc.networks.length > 0) {
118
- const onlyStrings = svc.networks.every((n)=>typeof n === "string");
119
- if (onlyStrings) {
120
- lines.push(" networks:");
121
- for (const n of svc.networks)lines.push(` - ${n}`);
122
- } else {
123
- lines.push(" networks:");
124
- for (const n of svc.networks){
125
- if (typeof n === "string") {
126
- lines.push(` ${n}:`);
127
- } else {
128
- for (const [netKey, cfg] of Object.entries(n)){
129
- lines.push(` ${netKey}:`);
130
- if (cfg.aliases && cfg.aliases.length > 0) {
131
- lines.push(" aliases:");
132
- for (const a of cfg.aliases)lines.push(` - ${a}`);
133
- }
134
- }
135
- }
136
- }
137
- }
138
- }
139
- if (svc.depends_on && svc.depends_on.length > 0) {
140
- lines.push(" depends_on:");
141
- for (const d of svc.depends_on)lines.push(` - ${d}`);
142
- }
143
- if (svc.healthcheck) {
144
- const hc = svc.healthcheck;
145
- lines.push(" healthcheck:");
146
- lines.push(` test: ${JSON.stringify(hc.test)}`);
147
- if (hc.interval) lines.push(` interval: ${hc.interval}`);
148
- if (hc.timeout) lines.push(` timeout: ${hc.timeout}`);
149
- if (hc.retries != null) lines.push(` retries: ${hc.retries}`);
150
- }
151
- }
152
- if (this._networks.size > 0) {
153
- lines.push("");
154
- lines.push("networks:");
155
- for (const [key, net] of this._networks){
156
- lines.push(` ${key}:`);
157
- lines.push(` name: ${net.name}`);
158
- if (net.external) lines.push(" external: true");
159
- }
160
- }
161
- if (this._volumes.size > 0) {
162
- lines.push("");
163
- lines.push("volumes:");
164
- for (const v of this._volumes)lines.push(` ${v}:`);
165
- }
166
- return `${lines.join("\n")}\n`;
167
- }
168
- mergeIntoExisting(doc) {
169
- if (!isMap(doc.contents)) throw new Error("docker-compose.yml is not a YAML mapping");
170
- for (const line of this._headerComments){
171
- const text = line.replace(/^#\s?/, "");
172
- const before = doc.commentBefore ?? "";
173
- if (!before.includes(text)) doc.commentBefore = before ? `${before}\n ${text}` : ` ${text}`;
174
- }
175
- for (const [name, svc] of this._services){
176
- if (!doc.hasIn([
177
- "services",
178
- name
179
- ])) doc.setIn([
180
- "services",
181
- name
182
- ], doc.createNode(toComposeYaml(svc)));
183
- }
184
- for (const [service, path] of this._envFiles){
185
- if (!doc.hasIn([
186
- "services",
187
- service
188
- ])) continue;
189
- const envFiles = doc.getIn([
190
- "services",
191
- service,
192
- "env_file"
193
- ]);
194
- if (isSeq(envFiles)) {
195
- if (!envFiles.items.some((item)=>String(item) === path)) envFiles.add(path);
196
- } else if (envFiles == null) {
197
- doc.setIn([
198
- "services",
199
- service,
200
- "env_file"
201
- ], doc.createNode([
202
- path
203
- ]));
204
- } else if (String(envFiles) !== path) {
205
- doc.setIn([
206
- "services",
207
- service,
208
- "env_file"
209
- ], doc.createNode([
210
- String(envFiles),
211
- path
212
- ]));
213
- }
214
- }
215
- for (const [key, network] of this._networks){
216
- if (!doc.hasIn([
217
- "networks",
218
- key
219
- ])) doc.setIn([
220
- "networks",
221
- key
222
- ], doc.createNode(network));
223
- }
224
- for (const volume of this._volumes){
225
- if (!doc.hasIn([
226
- "volumes",
227
- volume
228
- ])) doc.setIn([
229
- "volumes",
230
- volume
231
- ], null);
232
- }
233
- return doc.toString({
234
- lineWidth: 0
235
- });
236
- }
237
- }
238
- /** Plain compose YAML shape for a service (networks with aliases become a map). */ function toComposeYaml(svc) {
239
- const { networks, ...rest } = svc;
240
- if (!networks || networks.length === 0) return rest;
241
- if (networks.every((n)=>typeof n === "string")) return {
242
- ...rest,
243
- networks
244
- };
245
- const networkMap = {};
246
- for (const network of networks){
247
- if (typeof network === "string") networkMap[network] = null;
248
- else Object.assign(networkMap, network);
249
- }
250
- return {
251
- ...rest,
252
- networks: networkMap
253
- };
254
- }
@@ -1,74 +0,0 @@
1
- import { readFileSync } from "node:fs";
2
- /**
3
- * Builder for a YAML config file (e.g. config/config.yaml or config/config.dev.yaml).
4
- *
5
- * Starts with a base section passed to the constructor. Features call
6
- * `addSection(yaml)` during their scaffold phase to append their own block.
7
- * `files()` joins all sections with a blank line separator.
8
- */ export class ConfigYaml {
9
- key;
10
- filePath;
11
- _sections = [];
12
- constructor(key, filePath, baseContent){
13
- this.key = key;
14
- this.filePath = filePath;
15
- this._sections.push(baseContent);
16
- }
17
- addSection(yaml) {
18
- this._sections.push(yaml);
19
- return this;
20
- }
21
- /** True when a datasource with this `name:` already appears in the file. */ hasDataSource(name) {
22
- return this._sections.join("\n").includes(`name: ${name}\n`);
23
- }
24
- hasDataSources() {
25
- return this._sections.join("\n").includes("dataSources:");
26
- }
27
- /**
28
- * Insert a `dataSources` list item. Used by `webapi add` so we do not write a
29
- * second top-level `database:` key (YAML last-key-wins).
30
- */ appendDataSource(item) {
31
- const current = this._sections.join("\n");
32
- this._sections.length = 0;
33
- this._sections.push(injectYamlDataSource(current, item));
34
- return this;
35
- }
36
- static fromFile(key, relativePath, absolutePath) {
37
- const content = readFileSync(absolutePath, "utf8");
38
- return new ConfigYaml(key, relativePath, content);
39
- }
40
- files() {
41
- return [
42
- {
43
- filePath: this.filePath,
44
- content: this._sections.join("\n")
45
- }
46
- ];
47
- }
48
- }
49
- /** Insert a YAML list item under `dataSources:`; append a new `database:` block if missing. */ export function injectYamlDataSource(yaml, item) {
50
- const block = item.replace(/\n$/, "");
51
- if (!yaml.includes("dataSources:")) {
52
- const prefix = yaml.trimEnd();
53
- const section = `database:\n dataSources:\n${block}\n`;
54
- return prefix.length > 0 ? `${prefix}\n\n${section}` : section;
55
- }
56
- const lines = yaml.split("\n");
57
- const dsIndex = lines.findIndex((line)=>/^\s*dataSources:\s*$/.test(line));
58
- if (dsIndex < 0) {
59
- return `${yaml.trimEnd()}\n\ndatabase:\n dataSources:\n${block}\n`;
60
- }
61
- let insertAt = lines.length;
62
- for(let i = dsIndex + 1; i < lines.length; i++){
63
- if (/^[A-Za-z]/.test(lines[i] ?? "")) {
64
- insertAt = i;
65
- break;
66
- }
67
- }
68
- const insertLines = block.split("\n");
69
- if (insertAt < lines.length && lines[insertAt - 1] !== "") {
70
- insertLines.push("");
71
- }
72
- lines.splice(insertAt, 0, ...insertLines);
73
- return lines.join("\n");
74
- }
@@ -1,20 +0,0 @@
1
- export const WELL_KNOWN_FILES = {
2
- VSCODE_SETTINGS: "VSCODE_SETTINGS",
3
- LAUNCH_JSON: "LAUNCH_JSON",
4
- DOCKER_COMPOSE: "DOCKER_COMPOSE",
5
- DEVCONTAINER_JSON: "DEVCONTAINER_JSON",
6
- DOCKERFILE: "DOCKERFILE",
7
- PRODUCTION_DOCKERFILE: "PRODUCTION_DOCKERFILE",
8
- GITHUB_CI: "GITHUB_CI",
9
- PACKAGE_JSON: "PACKAGE_JSON",
10
- API_PACKAGE_JSON: "API_PACKAGE_JSON",
11
- TSCONFIG: "TSCONFIG",
12
- VITEST_CONFIG: "VITEST_CONFIG",
13
- MAIN_TS: "MAIN_TS",
14
- CONTROLLER_TS: "CONTROLLER_TS",
15
- CONFIG_YAML: "CONFIG_YAML",
16
- CONFIG_DEV_YAML: "CONFIG_DEV_YAML",
17
- GITIGNORE: "GITIGNORE",
18
- AUTH_CONFIG: "AUTH_CONFIG",
19
- ENV_FILE: "ENV_FILE"
20
- };