declastruct 1.0.0 → 1.1.0

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 (253) hide show
  1. package/dist/.test/assets/providers/demo.provider.d.ts +32 -0
  2. package/dist/.test/assets/providers/demo.provider.js +101 -0
  3. package/dist/.test/assets/providers/demo.provider.js.map +1 -0
  4. package/dist/contract/cli/apply.d.ts +9 -0
  5. package/dist/contract/cli/apply.integration.test.js +148 -0
  6. package/dist/contract/cli/apply.integration.test.js.map +1 -0
  7. package/dist/contract/cli/apply.js +90 -0
  8. package/dist/contract/cli/apply.js.map +1 -0
  9. package/dist/contract/cli/invoke.d.ts +8 -0
  10. package/dist/contract/cli/invoke.js +58 -0
  11. package/dist/contract/cli/invoke.js.map +1 -0
  12. package/dist/contract/cli/plan.d.ts +10 -0
  13. package/dist/contract/cli/plan.integration.test.js +107 -0
  14. package/dist/contract/cli/plan.integration.test.js.map +1 -0
  15. package/dist/contract/cli/plan.js +94 -0
  16. package/dist/contract/cli/plan.js.map +1 -0
  17. package/dist/contract/sdk/index.d.ts +15 -3
  18. package/dist/contract/sdk/index.js +31 -17
  19. package/dist/contract/sdk/index.js.map +1 -1
  20. package/dist/domain.objects/ContextDeclastruct.d.ts +15 -0
  21. package/dist/{domain/DeclastructContext.js → domain.objects/ContextDeclastruct.js} +1 -1
  22. package/dist/domain.objects/ContextDeclastruct.js.map +1 -0
  23. package/dist/domain.objects/ContextDeclastruct.test.js +41 -0
  24. package/dist/domain.objects/ContextDeclastruct.test.js.map +1 -0
  25. package/dist/domain.objects/DeclastructChange.d.ts +73 -0
  26. package/dist/domain.objects/DeclastructChange.js +35 -0
  27. package/dist/domain.objects/DeclastructChange.js.map +1 -0
  28. package/dist/domain.objects/DeclastructChange.test.js +59 -0
  29. package/dist/domain.objects/DeclastructChange.test.js.map +1 -0
  30. package/dist/domain.objects/DeclastructDao.d.ts +39 -0
  31. package/dist/domain.objects/DeclastructDao.js +8 -0
  32. package/dist/domain.objects/DeclastructDao.js.map +1 -0
  33. package/dist/domain.objects/DeclastructDao.test.js +42 -0
  34. package/dist/domain.objects/DeclastructDao.test.js.map +1 -0
  35. package/dist/domain.objects/DeclastructPlan.d.ts +35 -0
  36. package/dist/domain.objects/DeclastructPlan.js +11 -0
  37. package/dist/domain.objects/DeclastructPlan.js.map +1 -0
  38. package/dist/domain.objects/DeclastructPlan.test.js +31 -0
  39. package/dist/domain.objects/DeclastructPlan.test.js.map +1 -0
  40. package/dist/domain.objects/DeclastructProvider.d.ts +30 -0
  41. package/dist/domain.objects/DeclastructProvider.js +8 -0
  42. package/dist/domain.objects/DeclastructProvider.js.map +1 -0
  43. package/dist/domain.objects/DeclastructProvider.test.js +35 -0
  44. package/dist/domain.objects/DeclastructProvider.test.js.map +1 -0
  45. package/dist/domain.objects/IsoTimestamp.d.ts +6 -0
  46. package/dist/{domain/DeclaredResource.js → domain.objects/IsoTimestamp.js} +1 -1
  47. package/dist/domain.objects/IsoTimestamp.js.map +1 -0
  48. package/dist/domain.objects/IsoTimestamp.test.js +10 -0
  49. package/dist/domain.objects/IsoTimestamp.test.js.map +1 -0
  50. package/dist/domain.operations/apply/applyChange.d.ts +14 -0
  51. package/dist/domain.operations/apply/applyChange.js +64 -0
  52. package/dist/domain.operations/apply/applyChange.js.map +1 -0
  53. package/dist/domain.operations/apply/applyChange.test.d.ts +1 -0
  54. package/dist/domain.operations/apply/applyChange.test.js +247 -0
  55. package/dist/domain.operations/apply/applyChange.test.js.map +1 -0
  56. package/dist/domain.operations/apply/applyChanges.d.ts +18 -0
  57. package/dist/domain.operations/apply/applyChanges.integration.test.d.ts +1 -0
  58. package/dist/domain.operations/apply/applyChanges.integration.test.js +291 -0
  59. package/dist/domain.operations/apply/applyChanges.integration.test.js.map +1 -0
  60. package/dist/domain.operations/apply/applyChanges.js +53 -0
  61. package/dist/domain.operations/apply/applyChanges.js.map +1 -0
  62. package/dist/domain.operations/plan/computeChange.d.ts +11 -0
  63. package/dist/domain.operations/plan/computeChange.js +78 -0
  64. package/dist/domain.operations/plan/computeChange.js.map +1 -0
  65. package/dist/domain.operations/plan/computeChange.test.d.ts +1 -0
  66. package/dist/domain.operations/plan/computeChange.test.js +67 -0
  67. package/dist/domain.operations/plan/computeChange.test.js.map +1 -0
  68. package/dist/domain.operations/plan/extractResourcesFromPlan.d.ts +8 -0
  69. package/dist/domain.operations/plan/extractResourcesFromPlan.js +17 -0
  70. package/dist/domain.operations/plan/extractResourcesFromPlan.js.map +1 -0
  71. package/dist/domain.operations/plan/getDaoByResource.d.ts +12 -0
  72. package/dist/domain.operations/plan/getDaoByResource.js +41 -0
  73. package/dist/domain.operations/plan/getDaoByResource.js.map +1 -0
  74. package/dist/domain.operations/plan/getDaoByResource.test.d.ts +1 -0
  75. package/dist/domain.operations/plan/getDaoByResource.test.js +99 -0
  76. package/dist/domain.operations/plan/getDaoByResource.test.js.map +1 -0
  77. package/dist/domain.operations/plan/hashChanges.d.ts +7 -0
  78. package/dist/domain.operations/plan/hashChanges.js +18 -0
  79. package/dist/domain.operations/plan/hashChanges.js.map +1 -0
  80. package/dist/domain.operations/plan/planChanges.d.ts +15 -0
  81. package/dist/domain.operations/plan/planChanges.integration.test.d.ts +1 -0
  82. package/dist/domain.operations/plan/planChanges.integration.test.js +197 -0
  83. package/dist/domain.operations/plan/planChanges.integration.test.js.map +1 -0
  84. package/dist/domain.operations/plan/planChanges.js +50 -0
  85. package/dist/domain.operations/plan/planChanges.js.map +1 -0
  86. package/dist/domain.operations/plan/validate.d.ts +10 -0
  87. package/dist/domain.operations/plan/validate.js +21 -0
  88. package/dist/domain.operations/plan/validate.js.map +1 -0
  89. package/dist/infra/asIsoTimestamp.d.ts +6 -0
  90. package/dist/infra/asIsoTimestamp.js +12 -0
  91. package/dist/infra/asIsoTimestamp.js.map +1 -0
  92. package/package.json +8 -15
  93. package/readme.md +48 -28
  94. package/dist/__test_assets__/getExampleContext.d.ts +0 -33
  95. package/dist/__test_assets__/getExampleContext.js +0 -87
  96. package/dist/__test_assets__/getExampleContext.js.map +0 -1
  97. package/dist/contract/commands/command.apply.d.ts +0 -6
  98. package/dist/contract/commands/command.apply.js +0 -20
  99. package/dist/contract/commands/command.apply.js.map +0 -1
  100. package/dist/contract/commands/command.plan.d.ts +0 -6
  101. package/dist/contract/commands/command.plan.js +0 -20
  102. package/dist/contract/commands/command.plan.js.map +0 -1
  103. package/dist/contract/commands/utils/resolveCommandInputs.d.ts +0 -17
  104. package/dist/contract/commands/utils/resolveCommandInputs.js +0 -23
  105. package/dist/contract/commands/utils/resolveCommandInputs.js.map +0 -1
  106. package/dist/contract/sdk/refs.d.ts +0 -2
  107. package/dist/contract/sdk/refs.js +0 -19
  108. package/dist/contract/sdk/refs.js.map +0 -1
  109. package/dist/contract/sdk/sync/apply.d.ts +0 -22
  110. package/dist/contract/sdk/sync/apply.js +0 -29
  111. package/dist/contract/sdk/sync/apply.js.map +0 -1
  112. package/dist/contract/sdk/sync/plan.d.ts +0 -22
  113. package/dist/contract/sdk/sync/plan.js +0 -30
  114. package/dist/contract/sdk/sync/plan.js.map +0 -1
  115. package/dist/domain/DeclaredResource.d.ts +0 -2
  116. package/dist/domain/DeclaredResource.js.map +0 -1
  117. package/dist/domain/DeclaredResourceReference.d.ts +0 -66
  118. package/dist/domain/DeclaredResourceReference.js +0 -42
  119. package/dist/domain/DeclaredResourceReference.js.map +0 -1
  120. package/dist/domain/DeclastructChangeProposal.d.ts +0 -61
  121. package/dist/domain/DeclastructChangeProposal.js +0 -37
  122. package/dist/domain/DeclastructChangeProposal.js.map +0 -1
  123. package/dist/domain/DeclastructContext.d.ts +0 -24
  124. package/dist/domain/DeclastructContext.js.map +0 -1
  125. package/dist/domain/DeclastructProvider.d.ts +0 -58
  126. package/dist/domain/DeclastructProvider.js +0 -3
  127. package/dist/domain/DeclastructProvider.js.map +0 -1
  128. package/dist/domain/DeclastructProviderContext.d.ts +0 -30
  129. package/dist/domain/DeclastructProviderContext.js +0 -3
  130. package/dist/domain/DeclastructProviderContext.js.map +0 -1
  131. package/dist/domain/DeclastructProviderResourceRemoteStateInterface.d.ts +0 -156
  132. package/dist/domain/DeclastructProviderResourceRemoteStateInterface.js +0 -3
  133. package/dist/domain/DeclastructProviderResourceRemoteStateInterface.js.map +0 -1
  134. package/dist/index.d.ts +0 -1
  135. package/dist/index.js +0 -18
  136. package/dist/index.js.map +0 -1
  137. package/dist/logic/actions/execute/canUpdateResource.d.ts +0 -5
  138. package/dist/logic/actions/execute/canUpdateResource.js +0 -12
  139. package/dist/logic/actions/execute/canUpdateResource.js.map +0 -1
  140. package/dist/logic/actions/execute/executeProposal.d.ts +0 -5
  141. package/dist/logic/actions/execute/executeProposal.js +0 -52
  142. package/dist/logic/actions/execute/executeProposal.js.map +0 -1
  143. package/dist/logic/actions/propose/getColoredActionToken.d.ts +0 -4
  144. package/dist/logic/actions/propose/getColoredActionToken.js +0 -22
  145. package/dist/logic/actions/propose/getColoredActionToken.js.map +0 -1
  146. package/dist/logic/actions/propose/getColoredProposalTitle.d.ts +0 -4
  147. package/dist/logic/actions/propose/getColoredProposalTitle.js +0 -34
  148. package/dist/logic/actions/propose/getColoredProposalTitle.js.map +0 -1
  149. package/dist/logic/actions/propose/proposeChangeForResource.d.ts +0 -7
  150. package/dist/logic/actions/propose/proposeChangeForResource.js +0 -65
  151. package/dist/logic/actions/propose/proposeChangeForResource.js.map +0 -1
  152. package/dist/logic/actions/propose/proposeChangeForResource.test.js +0 -48
  153. package/dist/logic/actions/propose/proposeChangeForResource.test.js.map +0 -1
  154. package/dist/logic/commands/command.apply.d.ts +0 -8
  155. package/dist/logic/commands/command.apply.js +0 -77
  156. package/dist/logic/commands/command.apply.js.map +0 -1
  157. package/dist/logic/commands/command.plan.d.ts +0 -13
  158. package/dist/logic/commands/command.plan.js +0 -155
  159. package/dist/logic/commands/command.plan.js.map +0 -1
  160. package/dist/logic/commands/execute.d.ts +0 -15
  161. package/dist/logic/commands/execute.js +0 -63
  162. package/dist/logic/commands/execute.js.map +0 -1
  163. package/dist/logic/tools/compare/castReferenceToGrokableString.d.ts +0 -16
  164. package/dist/logic/tools/compare/castReferenceToGrokableString.js +0 -66
  165. package/dist/logic/tools/compare/castReferenceToGrokableString.js.map +0 -1
  166. package/dist/logic/tools/compare/castReferenceToGrokableString.test.js +0 -111
  167. package/dist/logic/tools/compare/castReferenceToGrokableString.test.js.map +0 -1
  168. package/dist/logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.d.ts +0 -11
  169. package/dist/logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.js +0 -61
  170. package/dist/logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.js.map +0 -1
  171. package/dist/logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.test.js +0 -31
  172. package/dist/logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.test.js.map +0 -1
  173. package/dist/logic/tools/compare/resolveReferenceToCommonComparableForm.d.ts +0 -21
  174. package/dist/logic/tools/compare/resolveReferenceToCommonComparableForm.js +0 -53
  175. package/dist/logic/tools/compare/resolveReferenceToCommonComparableForm.js.map +0 -1
  176. package/dist/logic/tools/compare/resolveReferenceToCommonComparableForm.test.js +0 -31
  177. package/dist/logic/tools/compare/resolveReferenceToCommonComparableForm.test.js.map +0 -1
  178. package/dist/logic/tools/compare/resolveReferencesToCommonComparableForm.d.ts +0 -10
  179. package/dist/logic/tools/compare/resolveReferencesToCommonComparableForm.js +0 -41
  180. package/dist/logic/tools/compare/resolveReferencesToCommonComparableForm.js.map +0 -1
  181. package/dist/logic/tools/compare/resolveReferencesToCommonComparableForm.test.js +0 -174
  182. package/dist/logic/tools/compare/resolveReferencesToCommonComparableForm.test.js.map +0 -1
  183. package/dist/logic/tools/context/createDeclastructContext.d.ts +0 -10
  184. package/dist/logic/tools/context/createDeclastructContext.js +0 -12
  185. package/dist/logic/tools/context/createDeclastructContext.js.map +0 -1
  186. package/dist/logic/tools/context/destroyDeclastructContext.d.ts +0 -4
  187. package/dist/logic/tools/context/destroyDeclastructContext.js +0 -10
  188. package/dist/logic/tools/context/destroyDeclastructContext.js.map +0 -1
  189. package/dist/logic/tools/provider/castProviderContextToGlobalContext.d.ts +0 -4
  190. package/dist/logic/tools/provider/castProviderContextToGlobalContext.js +0 -10
  191. package/dist/logic/tools/provider/castProviderContextToGlobalContext.js.map +0 -1
  192. package/dist/logic/tools/provider/getProviderContextFromGlobalContextForResourceClass.d.ts +0 -13
  193. package/dist/logic/tools/provider/getProviderContextFromGlobalContextForResourceClass.js +0 -29
  194. package/dist/logic/tools/provider/getProviderContextFromGlobalContextForResourceClass.js.map +0 -1
  195. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceExecutionDependenciesForResource.d.ts +0 -13
  196. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceExecutionDependenciesForResource.js +0 -24
  197. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceExecutionDependenciesForResource.js.map +0 -1
  198. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceFromContextForResourceClass.d.ts +0 -10
  199. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceFromContextForResourceClass.js +0 -21
  200. package/dist/logic/tools/provider/getProviderResourceRemoteStateInterfaceFromContextForResourceClass.js.map +0 -1
  201. package/dist/logic/tools/reference/buildPrimaryKeyTo.d.ts +0 -5
  202. package/dist/logic/tools/reference/buildPrimaryKeyTo.js +0 -40
  203. package/dist/logic/tools/reference/buildPrimaryKeyTo.js.map +0 -1
  204. package/dist/logic/tools/reference/buildReferenceTo.d.ts +0 -28
  205. package/dist/logic/tools/reference/buildReferenceTo.js +0 -92
  206. package/dist/logic/tools/reference/buildReferenceTo.js.map +0 -1
  207. package/dist/logic/tools/reference/buildReferenceTo.test.js +0 -119
  208. package/dist/logic/tools/reference/buildReferenceTo.test.js.map +0 -1
  209. package/dist/logic/tools/reference/buildUniqueKeyTo.d.ts +0 -5
  210. package/dist/logic/tools/reference/buildUniqueKeyTo.js +0 -40
  211. package/dist/logic/tools/reference/buildUniqueKeyTo.js.map +0 -1
  212. package/dist/logic/tools/reference/defineReferenceClassOf.d.ts +0 -5
  213. package/dist/logic/tools/reference/defineReferenceClassOf.js +0 -25
  214. package/dist/logic/tools/reference/defineReferenceClassOf.js.map +0 -1
  215. package/dist/logic/tools/reference/defineReferenceKeyConstituentsOf.d.ts +0 -13
  216. package/dist/logic/tools/reference/defineReferenceKeyConstituentsOf.js +0 -36
  217. package/dist/logic/tools/reference/defineReferenceKeyConstituentsOf.js.map +0 -1
  218. package/dist/logic/tools/reference/getByReference.d.ts +0 -15
  219. package/dist/logic/tools/reference/getByReference.js +0 -55
  220. package/dist/logic/tools/reference/getByReference.js.map +0 -1
  221. package/dist/logic/tools/reference/getByReference.test.js +0 -92
  222. package/dist/logic/tools/reference/getByReference.test.js.map +0 -1
  223. package/dist/logic/tools/reference/getByReferencedPrimaryKey.d.ts +0 -6
  224. package/dist/logic/tools/reference/getByReferencedPrimaryKey.js +0 -17
  225. package/dist/logic/tools/reference/getByReferencedPrimaryKey.js.map +0 -1
  226. package/dist/logic/tools/reference/getByReferencedUniqueKey.d.ts +0 -7
  227. package/dist/logic/tools/reference/getByReferencedUniqueKey.js +0 -42
  228. package/dist/logic/tools/reference/getByReferencedUniqueKey.js.map +0 -1
  229. package/dist/logic/tools/reference/getPrimaryKeyByReference.d.ts +0 -15
  230. package/dist/logic/tools/reference/getPrimaryKeyByReference.js +0 -36
  231. package/dist/logic/tools/reference/getPrimaryKeyByReference.js.map +0 -1
  232. package/dist/logic/tools/reference/getReferenceTo.d.ts +0 -18
  233. package/dist/logic/tools/reference/getReferenceTo.js +0 -55
  234. package/dist/logic/tools/reference/getReferenceTo.js.map +0 -1
  235. package/dist/logic/tools/reference/getReferenceTo.test.js +0 -95
  236. package/dist/logic/tools/reference/getReferenceTo.test.js.map +0 -1
  237. package/dist/logic/tools/reference/getUniqueKeyByReference.d.ts +0 -15
  238. package/dist/logic/tools/reference/getUniqueKeyByReference.js +0 -36
  239. package/dist/logic/tools/reference/getUniqueKeyByReference.js.map +0 -1
  240. package/dist/logic/tools/reference/isPrimaryKeyReference.d.ts +0 -6
  241. package/dist/logic/tools/reference/isPrimaryKeyReference.js +0 -7
  242. package/dist/logic/tools/reference/isPrimaryKeyReference.js.map +0 -1
  243. package/dist/logic/tools/reference/isUniqueKeyReference.d.ts +0 -6
  244. package/dist/logic/tools/reference/isUniqueKeyReference.js +0 -7
  245. package/dist/logic/tools/reference/isUniqueKeyReference.js.map +0 -1
  246. /package/dist/{logic/actions/propose/proposeChangeForResource.test.d.ts → contract/cli/apply.integration.test.d.ts} +0 -0
  247. /package/dist/{logic/tools/compare/castReferenceToGrokableString.test.d.ts → contract/cli/plan.integration.test.d.ts} +0 -0
  248. /package/dist/{logic/tools/compare/detectDifferenceBetweenDesiredAndRemoteStateOfResource.test.d.ts → domain.objects/ContextDeclastruct.test.d.ts} +0 -0
  249. /package/dist/{logic/tools/compare/resolveReferenceToCommonComparableForm.test.d.ts → domain.objects/DeclastructChange.test.d.ts} +0 -0
  250. /package/dist/{logic/tools/compare/resolveReferencesToCommonComparableForm.test.d.ts → domain.objects/DeclastructDao.test.d.ts} +0 -0
  251. /package/dist/{logic/tools/reference/buildReferenceTo.test.d.ts → domain.objects/DeclastructPlan.test.d.ts} +0 -0
  252. /package/dist/{logic/tools/reference/getByReference.test.d.ts → domain.objects/DeclastructProvider.test.d.ts} +0 -0
  253. /package/dist/{logic/tools/reference/getReferenceTo.test.d.ts → domain.objects/IsoTimestamp.test.d.ts} +0 -0
@@ -0,0 +1,32 @@
1
+ import { DomainEntity } from 'domain-objects';
2
+ import { DeclastructDao } from '../../../domain.objects/DeclastructDao';
3
+ import { DeclastructProvider } from '../../../domain.objects/DeclastructProvider';
4
+ /**
5
+ * .what = demo resource for integration testing
6
+ */
7
+ interface DemoResource {
8
+ exid: string;
9
+ name: string;
10
+ }
11
+ declare class DemoResource extends DomainEntity<DemoResource> implements DemoResource {
12
+ static unique: readonly ["exid"];
13
+ }
14
+ /**
15
+ * .what = demo provider with on-disk persistence
16
+ * .why = enables full integration testing with real CRUD operations
17
+ */
18
+ export declare const demoProvider: DeclastructProvider<{
19
+ DemoResource: DeclastructDao<DemoResource, typeof DemoResource, any>;
20
+ }, {}>;
21
+ /**
22
+ * .what = generates a sample DemoResource with automatic unique ID
23
+ * .why = simplifies test resource creation without managing IDs manually
24
+ * .note = use resource.clone({ name: 'New Name' }) to update properties while keeping same exid
25
+ */
26
+ export declare const genSampleDemoResource: (input: {
27
+ name: string;
28
+ }) => import("domain-objects/dist/manipulation/immute/withImmute").WithImmute<DemoResource>;
29
+ /**
30
+ * .what = export DemoResource class for test usage
31
+ */
32
+ export { DemoResource };
@@ -0,0 +1,101 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.DemoResource = exports.genSampleDemoResource = exports.demoProvider = void 0;
4
+ const domain_objects_1 = require("domain-objects");
5
+ const fs_1 = require("fs");
6
+ const promises_1 = require("fs/promises");
7
+ const path_1 = require("path");
8
+ const uuid_fns_1 = require("uuid-fns");
9
+ const DeclastructProvider_1 = require("../../../domain.objects/DeclastructProvider");
10
+ class DemoResource extends domain_objects_1.DomainEntity {
11
+ }
12
+ exports.DemoResource = DemoResource;
13
+ DemoResource.unique = ['exid'];
14
+ /**
15
+ * .what = resolves file path for a resource on disk
16
+ * .why = centralizes file naming logic
17
+ */
18
+ const getResourceFilePath = (id) => {
19
+ return (0, path_1.resolve)(process.cwd(), `.test/demo/provider/.temp/${id}.json`);
20
+ };
21
+ /**
22
+ * .what = demo DAO with on-disk JSON persistence
23
+ * .why = provides real persistence for integration tests
24
+ */
25
+ const demoDao = {
26
+ get: {
27
+ byUnique: async (input) => {
28
+ const filePath = getResourceFilePath(input.exid);
29
+ // check if file exists
30
+ if (!(0, fs_1.existsSync)(filePath))
31
+ return null;
32
+ // read and parse file
33
+ const json = await (0, promises_1.readFile)(filePath, 'utf-8');
34
+ const data = JSON.parse(json);
35
+ return DemoResource.as(data);
36
+ },
37
+ byRef: async (ref) => {
38
+ // extract exid from ref
39
+ const exid = ref.exid;
40
+ if (!exid)
41
+ return null;
42
+ return demoDao.get.byUnique({ exid }, {});
43
+ },
44
+ },
45
+ set: {
46
+ finsert: async (resource) => {
47
+ const filePath = getResourceFilePath(resource.exid);
48
+ // write resource to disk
49
+ await (0, promises_1.writeFile)(filePath, JSON.stringify(resource, null, 2), 'utf-8');
50
+ return resource;
51
+ },
52
+ upsert: async (resource) => {
53
+ const filePath = getResourceFilePath(resource.exid);
54
+ // write resource to disk (overwrite if exists)
55
+ await (0, promises_1.writeFile)(filePath, JSON.stringify(resource, null, 2), 'utf-8');
56
+ return resource;
57
+ },
58
+ delete: async (ref) => {
59
+ const resource = await demoDao.get.byRef(ref, {});
60
+ if (!resource)
61
+ return;
62
+ const filePath = getResourceFilePath(resource.exid);
63
+ // remove file if it exists
64
+ if ((0, fs_1.existsSync)(filePath)) {
65
+ await (0, promises_1.rm)(filePath);
66
+ }
67
+ },
68
+ },
69
+ };
70
+ /**
71
+ * .what = demo provider with on-disk persistence
72
+ * .why = enables full integration testing with real CRUD operations
73
+ */
74
+ exports.demoProvider = new DeclastructProvider_1.DeclastructProvider({
75
+ name: 'demo-provider',
76
+ daos: { DemoResource: demoDao },
77
+ context: {},
78
+ hooks: {
79
+ beforeAll: async () => {
80
+ // ensure temp directory exists
81
+ const tempDir = (0, path_1.resolve)(process.cwd(), '.test/demo/provider/.temp');
82
+ if (!(0, fs_1.existsSync)(tempDir)) {
83
+ await (0, promises_1.mkdir)(tempDir, { recursive: true });
84
+ }
85
+ },
86
+ afterAll: async () => { },
87
+ },
88
+ });
89
+ /**
90
+ * .what = generates a sample DemoResource with automatic unique ID
91
+ * .why = simplifies test resource creation without managing IDs manually
92
+ * .note = use resource.clone({ name: 'New Name' }) to update properties while keeping same exid
93
+ */
94
+ const genSampleDemoResource = (input) => {
95
+ return DemoResource.as({
96
+ exid: (0, uuid_fns_1.getUuid)(),
97
+ name: input.name,
98
+ });
99
+ };
100
+ exports.genSampleDemoResource = genSampleDemoResource;
101
+ //# sourceMappingURL=demo.provider.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"demo.provider.js","sourceRoot":"","sources":["../../../../src/.test/assets/providers/demo.provider.ts"],"names":[],"mappings":";;;AAAA,mDAA8C;AAC9C,2BAAgC;AAChC,0CAA6D;AAC7D,+BAA+B;AAC/B,uCAAmC;AAGnC,qFAAkF;AASlF,MAAM,YAAa,SAAQ,6BAA0B;;AAwG5C,oCAAY;AAvGL,mBAAM,GAAG,CAAC,MAAM,CAAU,CAAC;AAG3C;;;GAGG;AACH,MAAM,mBAAmB,GAAG,CAAC,EAAU,EAAU,EAAE;IACjD,OAAO,IAAA,cAAO,EAAC,OAAO,CAAC,GAAG,EAAE,EAAE,6BAA6B,EAAE,OAAO,CAAC,CAAC;AACxE,CAAC,CAAC;AAEF;;;GAGG;AACH,MAAM,OAAO,GAA2D;IACtE,GAAG,EAAE;QACH,QAAQ,EAAE,KAAK,EAAE,KAAK,EAAE,EAAE;YACxB,MAAM,QAAQ,GAAG,mBAAmB,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;YAEjD,uBAAuB;YACvB,IAAI,CAAC,IAAA,eAAU,EAAC,QAAQ,CAAC;gBAAE,OAAO,IAAI,CAAC;YAEvC,sBAAsB;YACtB,MAAM,IAAI,GAAG,MAAM,IAAA,mBAAQ,EAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;YAC/C,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC;YAE9B,OAAO,YAAY,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC;QAC/B,CAAC;QACD,KAAK,EAAE,KAAK,EAAE,GAAG,EAAE,EAAE;YACnB,wBAAwB;YACxB,MAAM,IAAI,GAAI,GAAW,CAAC,IAAI,CAAC;YAC/B,IAAI,CAAC,IAAI;gBAAE,OAAO,IAAI,CAAC;YAEvB,OAAO,OAAO,CAAC,GAAG,CAAC,QAAQ,CAAC,EAAE,IAAI,EAAS,EAAE,EAAE,CAAC,CAAC;QACnD,CAAC;KACF;IACD,GAAG,EAAE;QACH,OAAO,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE;YAC1B,MAAM,QAAQ,GAAG,mBAAmB,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;YAEpD,yBAAyB;YACzB,MAAM,IAAA,oBAAS,EAAC,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC;YAEtE,OAAO,QAAQ,CAAC;QAClB,CAAC;QACD,MAAM,EAAE,KAAK,EAAE,QAAQ,EAAE,EAAE;YACzB,MAAM,QAAQ,GAAG,mBAAmB,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;YAEpD,+CAA+C;YAC/C,MAAM,IAAA,oBAAS,EAAC,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,EAAE,OAAO,CAAC,CAAC;YAEtE,OAAO,QAAQ,CAAC;QAClB,CAAC;QACD,MAAM,EAAE,KAAK,EAAE,GAAG,EAAE,EAAE;YACpB,MAAM,QAAQ,GAAG,MAAM,OAAO,CAAC,GAAG,CAAC,KAAK,CAAC,GAAG,EAAE,EAAE,CAAC,CAAC;YAClD,IAAI,CAAC,QAAQ;gBAAE,OAAO;YAEtB,MAAM,QAAQ,GAAG,mBAAmB,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC;YAEpD,2BAA2B;YAC3B,IAAI,IAAA,eAAU,EAAC,QAAQ,CAAC,EAAE,CAAC;gBACzB,MAAM,IAAA,aAAE,EAAC,QAAQ,CAAC,CAAC;YACrB,CAAC;QACH,CAAC;KACF;CACF,CAAC;AAEF;;;GAGG;AACU,QAAA,YAAY,GAAG,IAAI,yCAAmB,CAAC;IAClD,IAAI,EAAE,eAAe;IACrB,IAAI,EAAE,EAAE,YAAY,EAAE,OAAO,EAAE;IAC/B,OAAO,EAAE,EAAE;IACX,KAAK,EAAE;QACL,SAAS,EAAE,KAAK,IAAI,EAAE;YACpB,+BAA+B;YAC/B,MAAM,OAAO,GAAG,IAAA,cAAO,EAAC,OAAO,CAAC,GAAG,EAAE,EAAE,2BAA2B,CAAC,CAAC;YACpE,IAAI,CAAC,IAAA,eAAU,EAAC,OAAO,CAAC,EAAE,CAAC;gBACzB,MAAM,IAAA,gBAAK,EAAC,OAAO,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;YAC5C,CAAC;QACH,CAAC;QACD,QAAQ,EAAE,KAAK,IAAI,EAAE,GAAE,CAAC;KACzB;CACF,CAAC,CAAC;AAEH;;;;GAIG;AACI,MAAM,qBAAqB,GAAG,CAAC,KAAuB,EAAE,EAAE;IAC/D,OAAO,YAAY,CAAC,EAAE,CAAC;QACrB,IAAI,EAAE,IAAA,kBAAO,GAAE;QACf,IAAI,EAAE,KAAK,CAAC,IAAI;KACjB,CAAC,CAAC;AACL,CAAC,CAAC;AALW,QAAA,qBAAqB,yBAKhC"}
@@ -0,0 +1,9 @@
1
+ #!/usr/bin/env tsx
2
+ /**
3
+ * .what = executes the apply command to apply an infrastructure change plan
4
+ * .why = provides CLI interface for applying infrastructure changes
5
+ * .note = loads plan from file and wish file from plan.wish.uri
6
+ */
7
+ export declare const executeApplyCommand: ({ planFilePath, }: {
8
+ planFilePath: string;
9
+ }) => Promise<void>;
@@ -0,0 +1,148 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const fs_1 = require("fs");
4
+ const promises_1 = require("fs/promises");
5
+ const path_1 = require("path");
6
+ const uuid_fns_1 = require("uuid-fns");
7
+ const DeclastructPlan_1 = require("../../domain.objects/DeclastructPlan");
8
+ const apply_1 = require("./apply");
9
+ const plan_1 = require("./plan");
10
+ /**
11
+ * .what = creates an isolated wish file for a test
12
+ * .why = ensures stable resources within a single test while maintaining test isolation
13
+ */
14
+ const createIsolatedWishFile = async () => {
15
+ const tempDir = (0, path_1.resolve)(process.cwd(), '.test/.temp');
16
+ const wishPath = (0, path_1.resolve)(tempDir, `wish-${(0, uuid_fns_1.getUuid)()}.ts`);
17
+ // ensure temp directory exists
18
+ if (!(0, fs_1.existsSync)(tempDir)) {
19
+ await (0, promises_1.mkdir)(tempDir, { recursive: true });
20
+ }
21
+ const exid1 = (0, uuid_fns_1.getUuid)();
22
+ const exid2 = (0, uuid_fns_1.getUuid)();
23
+ const wishContent = `
24
+ import { DomainEntity } from 'domain-objects';
25
+ import { DeclastructProvider } from '../../src/domain.objects/DeclastructProvider';
26
+ import { DemoResource, demoProvider } from '../../src/.test/assets/providers/demo.provider';
27
+
28
+ export const getResources = async (): Promise<DomainEntity<any>[]> => {
29
+ return [
30
+ DemoResource.as({ exid: '${exid1}', name: 'First Resource' }),
31
+ DemoResource.as({ exid: '${exid2}', name: 'Second Resource' }),
32
+ ];
33
+ };
34
+
35
+ export const getProviders = async (): Promise<DeclastructProvider<any, any>[]> => {
36
+ return [demoProvider];
37
+ };
38
+ `;
39
+ await (0, promises_1.writeFile)(wishPath, wishContent, 'utf-8');
40
+ return wishPath;
41
+ };
42
+ describe('executeApplyCommand', () => {
43
+ const planFilePath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/apply.test.json');
44
+ afterEach(async () => {
45
+ // cleanup plan file after each test
46
+ if ((0, fs_1.existsSync)(planFilePath)) {
47
+ await (0, promises_1.rm)(planFilePath);
48
+ }
49
+ });
50
+ it('should apply changes from a valid plan file', async () => {
51
+ // create isolated wish file for this test
52
+ const wishFilePath = await createIsolatedWishFile();
53
+ // first generate a plan
54
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
55
+ // verify plan was created
56
+ expect((0, fs_1.existsSync)(planFilePath)).toBe(true);
57
+ // now apply the plan
58
+ await (0, apply_1.executeApplyCommand)({ planFilePath });
59
+ // verify plan still exists after apply
60
+ expect((0, fs_1.existsSync)(planFilePath)).toBe(true);
61
+ // read plan to verify structure
62
+ const planJson = await (0, promises_1.readFile)(planFilePath, 'utf-8');
63
+ const plan = new DeclastructPlan_1.DeclastructPlan(JSON.parse(planJson));
64
+ // verify plan has changes
65
+ expect(plan.changes.length).toBe(2);
66
+ });
67
+ it('should throw when plan file does not exist', async () => {
68
+ const nonexistentPlanPath = (0, path_1.resolve)(__dirname, 'nonexistent-plan.json');
69
+ await expect((0, apply_1.executeApplyCommand)({ planFilePath: nonexistentPlanPath })).rejects.toThrow('Plan file not found');
70
+ });
71
+ it('should throw when wish file referenced in plan does not exist', async () => {
72
+ // create plan with invalid wish path
73
+ const invalidPlan = {
74
+ hash: 'test-hash',
75
+ createdAt: new Date().toISOString(),
76
+ wish: { uri: '/nonexistent/wish.ts' },
77
+ changes: [],
78
+ };
79
+ await (0, promises_1.writeFile)(planFilePath, JSON.stringify(invalidPlan, null, 2));
80
+ await expect((0, apply_1.executeApplyCommand)({ planFilePath })).rejects.toThrow();
81
+ });
82
+ it('should throw when wish file does not export getProviders', async () => {
83
+ const badWishPath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/bad-apply-wish.ts');
84
+ // create bad wish file
85
+ await (0, promises_1.writeFile)(badWishPath, 'export const foo = "bar";', 'utf-8');
86
+ // create plan pointing to bad wish
87
+ const invalidPlan = {
88
+ hash: 'test-hash',
89
+ createdAt: new Date().toISOString(),
90
+ wish: { uri: badWishPath },
91
+ changes: [],
92
+ };
93
+ await (0, promises_1.writeFile)(planFilePath, JSON.stringify(invalidPlan, null, 2));
94
+ await expect((0, apply_1.executeApplyCommand)({ planFilePath })).rejects.toThrow('Wish file must export getProviders() function');
95
+ // cleanup
96
+ await (0, promises_1.rm)(badWishPath);
97
+ });
98
+ it('should successfully apply multiple CREATE actions', async () => {
99
+ // create isolated wish file for this test
100
+ const wishFilePath = await createIsolatedWishFile();
101
+ // generate plan
102
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
103
+ // spy on console to verify logging
104
+ const logSpy = jest.spyOn(console, 'info');
105
+ // apply changes
106
+ await (0, apply_1.executeApplyCommand)({ planFilePath });
107
+ // verify success logging occurred
108
+ const logCalls = logSpy.mock.calls.map((call) => call.join(' '));
109
+ const successLogs = logCalls.filter((log) => log.includes('✔'));
110
+ // should have logged success for each CREATE action
111
+ expect(successLogs.length).toBeGreaterThan(0);
112
+ // cleanup spy
113
+ logSpy.mockRestore();
114
+ });
115
+ it('should handle KEEP actions without errors', async () => {
116
+ // create isolated wish file for this test
117
+ const wishFilePath = await createIsolatedWishFile();
118
+ // generate initial plan
119
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
120
+ // apply changes
121
+ await (0, apply_1.executeApplyCommand)({ planFilePath });
122
+ // generate new plan (should now show KEEP actions)
123
+ await (0, promises_1.rm)(planFilePath);
124
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
125
+ // read new plan
126
+ const planJson = await (0, promises_1.readFile)(planFilePath, 'utf-8');
127
+ const plan = new DeclastructPlan_1.DeclastructPlan(JSON.parse(planJson));
128
+ // verify we have KEEP actions
129
+ const keepActions = plan.changes.filter((c) => c.action === 'KEEP');
130
+ expect(keepActions.length).toBe(2);
131
+ // apply again (should handle KEEP without errors)
132
+ await (0, apply_1.executeApplyCommand)({ planFilePath });
133
+ });
134
+ it('should throw when plan is stale', async () => {
135
+ // create isolated wish file for this test
136
+ const wishFilePath = await createIsolatedWishFile();
137
+ // generate initial plan
138
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
139
+ // modify the plan's hash to make it stale
140
+ const planJson = await (0, promises_1.readFile)(planFilePath, 'utf-8');
141
+ const plan = JSON.parse(planJson);
142
+ plan.hash = 'stale-hash-that-wont-match';
143
+ await (0, promises_1.writeFile)(planFilePath, JSON.stringify(plan, null, 2));
144
+ // applying stale plan should throw
145
+ await expect((0, apply_1.executeApplyCommand)({ planFilePath })).rejects.toThrow('plan is stale');
146
+ });
147
+ });
148
+ //# sourceMappingURL=apply.integration.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"apply.integration.test.js","sourceRoot":"","sources":["../../../src/contract/cli/apply.integration.test.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,90 @@
1
+ #!/usr/bin/env tsx
2
+ "use strict";
3
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
4
+ if (k2 === undefined) k2 = k;
5
+ var desc = Object.getOwnPropertyDescriptor(m, k);
6
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
7
+ desc = { enumerable: true, get: function() { return m[k]; } };
8
+ }
9
+ Object.defineProperty(o, k2, desc);
10
+ }) : (function(o, m, k, k2) {
11
+ if (k2 === undefined) k2 = k;
12
+ o[k2] = m[k];
13
+ }));
14
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
15
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
16
+ }) : function(o, v) {
17
+ o["default"] = v;
18
+ });
19
+ var __importStar = (this && this.__importStar) || function (mod) {
20
+ if (mod && mod.__esModule) return mod;
21
+ var result = {};
22
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
23
+ __setModuleDefault(result, mod);
24
+ return result;
25
+ };
26
+ var __importDefault = (this && this.__importDefault) || function (mod) {
27
+ return (mod && mod.__esModule) ? mod : { "default": mod };
28
+ };
29
+ Object.defineProperty(exports, "__esModule", { value: true });
30
+ exports.executeApplyCommand = void 0;
31
+ const bottleneck_1 = __importDefault(require("bottleneck"));
32
+ const fs_1 = require("fs");
33
+ const promises_1 = require("fs/promises");
34
+ const helpful_errors_1 = require("helpful-errors");
35
+ const path_1 = require("path");
36
+ const DeclastructPlan_1 = require("../../domain.objects/DeclastructPlan");
37
+ const applyChanges_1 = require("../../domain.operations/apply/applyChanges");
38
+ const log = console;
39
+ /**
40
+ * .what = executes the apply command to apply an infrastructure change plan
41
+ * .why = provides CLI interface for applying infrastructure changes
42
+ * .note = loads plan from file and wish file from plan.wish.uri
43
+ */
44
+ const executeApplyCommand = async ({ planFilePath, }) => {
45
+ // resolve path
46
+ const resolvedPlanPath = (0, path_1.resolve)(process.cwd(), planFilePath);
47
+ // validate plan file exists
48
+ if (!(0, fs_1.existsSync)(resolvedPlanPath)) {
49
+ throw new helpful_errors_1.BadRequestError(`Plan file not found: ${resolvedPlanPath}`);
50
+ }
51
+ log.info('🌊 declastruct apply');
52
+ log.info(` plan: ${resolvedPlanPath}`);
53
+ log.info('');
54
+ // load plan from file
55
+ const planJson = await (0, promises_1.readFile)(resolvedPlanPath, 'utf-8');
56
+ const plan = new DeclastructPlan_1.DeclastructPlan(JSON.parse(planJson));
57
+ // import wish file from plan
58
+ const wishPath = plan.wish.uri;
59
+ const wish = await Promise.resolve(`${wishPath}`).then(s => __importStar(require(s)));
60
+ // validate exports
61
+ if (typeof wish.getProviders !== 'function') {
62
+ throw new helpful_errors_1.BadRequestError('Wish file must export getProviders() function');
63
+ }
64
+ if (typeof wish.getResources !== 'function') {
65
+ throw new helpful_errors_1.BadRequestError('Wish file must export getResources() function');
66
+ }
67
+ // get resources and providers from wish file
68
+ const resources = await wish.getResources();
69
+ const providers = await wish.getProviders();
70
+ // initialize providers
71
+ log.info('✨ start providers...');
72
+ await Promise.all(providers.map((p) => p.hooks.beforeAll()));
73
+ // create context
74
+ const context = {
75
+ bottleneck: new bottleneck_1.default({ maxConcurrent: 1 }),
76
+ log,
77
+ };
78
+ // apply changes (logs emitted in real-time by applyChanges)
79
+ log.info('🪄 apply changes...');
80
+ log.info('');
81
+ const result = await (0, applyChanges_1.applyChanges)({ plan, resources, providers }, context);
82
+ // cleanup providers
83
+ log.info('✨ stop providers...');
84
+ await Promise.all(providers.map((p) => p.hooks.afterAll()));
85
+ // log summary
86
+ log.info('');
87
+ log.info(`🌊 applied ${result.appliedChanges.length} changes`);
88
+ };
89
+ exports.executeApplyCommand = executeApplyCommand;
90
+ //# sourceMappingURL=apply.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"apply.js","sourceRoot":"","sources":["../../../src/contract/cli/apply.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ /**
2
+ * .what = invokes CLI commands based on user input
3
+ * .why = provides global entry point for declastruct CLI
4
+ * .note = uses commander for argument parsing and help text
5
+ */
6
+ export declare const invoke: ({ args }: {
7
+ args: string[];
8
+ }) => Promise<void>;
@@ -0,0 +1,58 @@
1
+ "use strict";
2
+ var __importDefault = (this && this.__importDefault) || function (mod) {
3
+ return (mod && mod.__esModule) ? mod : { "default": mod };
4
+ };
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ exports.invoke = void 0;
7
+ const commander_1 = require("commander");
8
+ const package_json_1 = __importDefault(require("../../../package.json"));
9
+ const apply_1 = require("./apply");
10
+ const plan_1 = require("./plan");
11
+ const log = console;
12
+ /**
13
+ * .what = invokes CLI commands based on user input
14
+ * .why = provides global entry point for declastruct CLI
15
+ * .note = uses commander for argument parsing and help text
16
+ */
17
+ const invoke = async ({ args }) => {
18
+ const program = new commander_1.Command();
19
+ program
20
+ .name('declastruct')
21
+ .description('Declarative resource structure control')
22
+ .version(package_json_1.default.version);
23
+ program
24
+ .command('plan')
25
+ .description('Generate a change plan from a wish file')
26
+ .requiredOption('--wish <file>', 'Path to wish file')
27
+ .requiredOption('--into <file>', 'Path to output plan file')
28
+ .action(async (options) => {
29
+ try {
30
+ await (0, plan_1.executePlanCommand)({
31
+ wishFilePath: options.wish,
32
+ planFilePath: options.into,
33
+ });
34
+ }
35
+ catch (error) {
36
+ log.error('✖ Error during plan:', error);
37
+ process.exit(1);
38
+ }
39
+ });
40
+ program
41
+ .command('apply')
42
+ .description('Apply changes from a plan file')
43
+ .requiredOption('--plan <file>', 'Path to plan file')
44
+ .action(async (options) => {
45
+ try {
46
+ await (0, apply_1.executeApplyCommand)({
47
+ planFilePath: options.plan,
48
+ });
49
+ }
50
+ catch (error) {
51
+ log.error('✖ Error during apply:', error);
52
+ process.exit(1);
53
+ }
54
+ });
55
+ await program.parseAsync(args, { from: 'user' });
56
+ };
57
+ exports.invoke = invoke;
58
+ //# sourceMappingURL=invoke.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"invoke.js","sourceRoot":"","sources":["../../../src/contract/cli/invoke.ts"],"names":[],"mappings":";;;;;;AAAA,yCAAoC;AAEpC,yEAAwC;AACxC,mCAA8C;AAC9C,iCAA4C;AAE5C,MAAM,GAAG,GAAG,OAAO,CAAC;AAEpB;;;;GAIG;AACI,MAAM,MAAM,GAAG,KAAK,EAAE,EAAE,IAAI,EAAsB,EAAiB,EAAE;IAC1E,MAAM,OAAO,GAAG,IAAI,mBAAO,EAAE,CAAC;IAE9B,OAAO;SACJ,IAAI,CAAC,aAAa,CAAC;SACnB,WAAW,CAAC,wCAAwC,CAAC;SACrD,OAAO,CAAC,sBAAG,CAAC,OAAO,CAAC,CAAC;IAExB,OAAO;SACJ,OAAO,CAAC,MAAM,CAAC;SACf,WAAW,CAAC,yCAAyC,CAAC;SACtD,cAAc,CAAC,eAAe,EAAE,mBAAmB,CAAC;SACpD,cAAc,CAAC,eAAe,EAAE,0BAA0B,CAAC;SAC3D,MAAM,CAAC,KAAK,EAAE,OAAO,EAAE,EAAE;QACxB,IAAI,CAAC;YACH,MAAM,IAAA,yBAAkB,EAAC;gBACvB,YAAY,EAAE,OAAO,CAAC,IAAI;gBAC1B,YAAY,EAAE,OAAO,CAAC,IAAI;aAC3B,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,GAAG,CAAC,KAAK,CAAC,sBAAsB,EAAE,KAAK,CAAC,CAAC;YACzC,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;IACH,CAAC,CAAC,CAAC;IAEL,OAAO;SACJ,OAAO,CAAC,OAAO,CAAC;SAChB,WAAW,CAAC,gCAAgC,CAAC;SAC7C,cAAc,CAAC,eAAe,EAAE,mBAAmB,CAAC;SACpD,MAAM,CAAC,KAAK,EAAE,OAAO,EAAE,EAAE;QACxB,IAAI,CAAC;YACH,MAAM,IAAA,2BAAmB,EAAC;gBACxB,YAAY,EAAE,OAAO,CAAC,IAAI;aAC3B,CAAC,CAAC;QACL,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,GAAG,CAAC,KAAK,CAAC,uBAAuB,EAAE,KAAK,CAAC,CAAC;YAC1C,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;IACH,CAAC,CAAC,CAAC;IAEL,MAAM,OAAO,CAAC,UAAU,CAAC,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,CAAC,CAAC;AACnD,CAAC,CAAC;AAzCW,QAAA,MAAM,UAyCjB"}
@@ -0,0 +1,10 @@
1
+ #!/usr/bin/env tsx
2
+ /**
3
+ * .what = executes the plan command to generate an infrastructure change plan
4
+ * .why = provides CLI interface for planning infrastructure changes
5
+ * .note = requires wish file with getResources() and getProviders() exports
6
+ */
7
+ export declare const executePlanCommand: ({ wishFilePath, planFilePath, }: {
8
+ wishFilePath: string;
9
+ planFilePath: string;
10
+ }) => Promise<void>;
@@ -0,0 +1,107 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ Object.defineProperty(exports, "__esModule", { value: true });
26
+ const fs_1 = require("fs");
27
+ const promises_1 = require("fs/promises");
28
+ const path_1 = require("path");
29
+ const DeclastructPlan_1 = require("../../domain.objects/DeclastructPlan");
30
+ const plan_1 = require("./plan");
31
+ describe('executePlanCommand', () => {
32
+ const wishFilePath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/wish.fixture.ts');
33
+ const planFilePath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/plan.test.json');
34
+ afterEach(async () => {
35
+ // cleanup plan file after each test
36
+ if ((0, fs_1.existsSync)(planFilePath)) {
37
+ await (0, promises_1.rm)(planFilePath);
38
+ }
39
+ });
40
+ it('should generate a plan file with changes based on wish file', async () => {
41
+ // execute plan command
42
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
43
+ // verify plan file was created
44
+ expect((0, fs_1.existsSync)(planFilePath)).toBe(true);
45
+ // read and parse plan
46
+ const planJson = await (0, promises_1.readFile)(planFilePath, 'utf-8');
47
+ const plan = new DeclastructPlan_1.DeclastructPlan(JSON.parse(planJson));
48
+ // verify plan structure
49
+ expect(plan.hash).toBeDefined();
50
+ expect(plan.createdAt).toBeDefined();
51
+ expect(plan.wish.uri).toBe(wishFilePath);
52
+ expect(plan.changes.length).toBe(2);
53
+ // verify changes are all CREATE (no remote state)
54
+ plan.changes.forEach((change) => {
55
+ expect(change.action).toBe('CREATE');
56
+ expect(change.forResource.class).toBe('DemoResource');
57
+ expect(change.state.desired).toBeDefined();
58
+ expect(change.state.remote).toBeNull();
59
+ });
60
+ // verify slugs exist and are unique
61
+ const slugs = plan.changes.map((c) => c.forResource.slug);
62
+ expect(slugs.length).toBe(2);
63
+ expect(slugs[0]).toBeDefined();
64
+ expect(slugs[1]).toBeDefined();
65
+ expect(slugs[0]).not.toBe(slugs[1]);
66
+ });
67
+ it('should throw when wish file does not exist', async () => {
68
+ const nonexistentWishPath = (0, path_1.resolve)(__dirname, 'nonexistent.ts');
69
+ await expect((0, plan_1.executePlanCommand)({
70
+ wishFilePath: nonexistentWishPath,
71
+ planFilePath,
72
+ })).rejects.toThrow('Wish file not found');
73
+ });
74
+ it('should throw when wish file does not export getResources', async () => {
75
+ const badWishPath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/bad-wish.ts');
76
+ // create bad wish file
77
+ const { writeFile } = await Promise.resolve().then(() => __importStar(require('fs/promises')));
78
+ await writeFile(badWishPath, 'export const getProviders = async () => [];', 'utf-8');
79
+ await expect((0, plan_1.executePlanCommand)({ wishFilePath: badWishPath, planFilePath })).rejects.toThrow('Wish file must export getResources() function');
80
+ // cleanup
81
+ await (0, promises_1.rm)(badWishPath);
82
+ });
83
+ it('should throw when wish file does not export getProviders', async () => {
84
+ const badWishPath = (0, path_1.resolve)(process.cwd(), 'src/.test/assets/bad-wish2.ts');
85
+ // create bad wish file
86
+ const { writeFile } = await Promise.resolve().then(() => __importStar(require('fs/promises')));
87
+ await writeFile(badWishPath, 'export const getResources = async () => [];', 'utf-8');
88
+ await expect((0, plan_1.executePlanCommand)({ wishFilePath: badWishPath, planFilePath })).rejects.toThrow('Wish file must export getProviders() function');
89
+ // cleanup
90
+ await (0, promises_1.rm)(badWishPath);
91
+ });
92
+ it('should detect KEEP action when resource already exists remotely', async () => {
93
+ // first run - create resources
94
+ await (0, plan_1.executePlanCommand)({ wishFilePath, planFilePath });
95
+ // read first plan
96
+ const firstPlanJson = await (0, promises_1.readFile)(planFilePath, 'utf-8');
97
+ const firstPlan = new DeclastructPlan_1.DeclastructPlan(JSON.parse(firstPlanJson));
98
+ // verify all CREATE
99
+ expect(firstPlan.changes.every((c) => c.action === 'CREATE')).toBe(true);
100
+ // cleanup and run again
101
+ await (0, promises_1.rm)(planFilePath);
102
+ // Note: In a real integration test, we would need to actually apply the changes
103
+ // to populate remote state. For now, this test just verifies the basic flow.
104
+ // A more complete test would require mocking or actual provider state.
105
+ });
106
+ });
107
+ //# sourceMappingURL=plan.integration.test.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"plan.integration.test.js","sourceRoot":"","sources":["../../../src/contract/cli/plan.integration.test.ts"],"names":[],"mappings":"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"}