@aifabrix/builder 2.41.0 → 2.42.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 (142) hide show
  1. package/.cursor/rules/docs-rules.mdc +30 -0
  2. package/README.md +2 -2
  3. package/integration/hubspot/README.md +11 -5
  4. package/integration/hubspot/application.json +54 -0
  5. package/integration/hubspot/create-hubspot.js +9 -136
  6. package/integration/hubspot/env.template +3 -4
  7. package/integration/hubspot/hubspot-datasource-company.json +343 -5
  8. package/integration/hubspot/hubspot-datasource-contact.json +413 -5
  9. package/integration/hubspot/hubspot-datasource-deal.json +341 -4
  10. package/integration/hubspot/hubspot-datasource-users.json +116 -0
  11. package/integration/hubspot/hubspot-deploy.json +1250 -108
  12. package/integration/hubspot/hubspot-system.json +15 -32
  13. package/integration/hubspot/test-dataplane-down-tests.js +17 -16
  14. package/integration/hubspot/test-dataplane-down.js +2 -2
  15. package/jest.config.manual.js +2 -1
  16. package/lib/api/external-test.api.js +111 -0
  17. package/lib/api/index.js +42 -19
  18. package/lib/api/pipeline.api.js +66 -120
  19. package/lib/api/types/pipeline.types.js +37 -0
  20. package/lib/api/wizard-platform.api.js +61 -0
  21. package/lib/api/wizard.api.js +36 -2
  22. package/lib/app/config.js +23 -11
  23. package/lib/app/index.js +5 -3
  24. package/lib/app/prompts.js +46 -31
  25. package/lib/app/readme.js +11 -4
  26. package/lib/app/run-env-compose.js +64 -1
  27. package/lib/app/run-helpers.js +1 -1
  28. package/lib/app/show-display.js +1 -1
  29. package/lib/cli/setup-app.js +45 -14
  30. package/lib/cli/setup-credential-deployment.js +31 -6
  31. package/lib/cli/setup-dev.js +27 -0
  32. package/lib/cli/setup-environment.js +12 -4
  33. package/lib/cli/setup-external-system.js +19 -4
  34. package/lib/cli/setup-infra.js +54 -14
  35. package/lib/cli/setup-utility.js +117 -21
  36. package/lib/commands/auth-config.js +22 -12
  37. package/lib/commands/credential-env.js +162 -0
  38. package/lib/commands/credential-list.js +17 -22
  39. package/lib/commands/credential-push.js +96 -0
  40. package/lib/commands/datasource.js +77 -6
  41. package/lib/commands/dev-init.js +39 -1
  42. package/lib/commands/repair-auth-config.js +99 -0
  43. package/lib/commands/repair-datasource-keys.js +208 -0
  44. package/lib/commands/repair-datasource.js +235 -0
  45. package/lib/commands/repair-env-template.js +348 -0
  46. package/lib/commands/repair-internal.js +85 -0
  47. package/lib/commands/repair-rbac.js +158 -0
  48. package/lib/commands/repair.js +518 -0
  49. package/lib/commands/secrets-set.js +6 -0
  50. package/lib/commands/test-e2e-external.js +165 -0
  51. package/lib/commands/up-dataplane.js +90 -6
  52. package/lib/commands/upload.js +71 -40
  53. package/lib/commands/wizard-core-helpers.js +230 -5
  54. package/lib/commands/wizard-core.js +68 -29
  55. package/lib/commands/wizard-dataplane.js +1 -1
  56. package/lib/commands/wizard-entity-selection.js +43 -0
  57. package/lib/commands/wizard-headless.js +49 -5
  58. package/lib/commands/wizard-helpers.js +7 -3
  59. package/lib/commands/wizard.js +93 -64
  60. package/lib/core/config.js +7 -1
  61. package/lib/core/secrets.js +33 -12
  62. package/lib/datasource/deploy.js +12 -3
  63. package/lib/datasource/test-e2e.js +219 -0
  64. package/lib/datasource/test-integration.js +154 -0
  65. package/lib/deployment/deployer.js +7 -5
  66. package/lib/external-system/download-helpers.js +3 -1
  67. package/lib/external-system/download.js +182 -204
  68. package/lib/external-system/generator.js +204 -56
  69. package/lib/external-system/test-execution.js +2 -1
  70. package/lib/external-system/test-system-level.js +73 -0
  71. package/lib/external-system/test.js +51 -18
  72. package/lib/generator/external-controller-manifest.js +29 -2
  73. package/lib/generator/external-schema-utils.js +4 -2
  74. package/lib/generator/external.js +10 -3
  75. package/lib/generator/index.js +4 -1
  76. package/lib/generator/split-readme.js +1 -0
  77. package/lib/generator/split-variables.js +7 -1
  78. package/lib/generator/split.js +194 -54
  79. package/lib/generator/wizard-prompts-secondary.js +326 -0
  80. package/lib/generator/wizard-prompts.js +105 -106
  81. package/lib/generator/wizard-readme.js +91 -0
  82. package/lib/generator/wizard.js +180 -179
  83. package/lib/infrastructure/compose.js +11 -1
  84. package/lib/infrastructure/index.js +11 -3
  85. package/lib/infrastructure/services.js +22 -11
  86. package/lib/schema/application-schema.json +8 -5
  87. package/lib/schema/external-datasource.schema.json +49 -26
  88. package/lib/schema/external-system.schema.json +82 -6
  89. package/lib/schema/wizard-config.schema.json +23 -1
  90. package/lib/utils/api.js +38 -10
  91. package/lib/utils/auth-headers.js +8 -7
  92. package/lib/utils/compose-generator.js +1 -1
  93. package/lib/utils/compose-handlebars-helpers.js +11 -0
  94. package/lib/utils/config-format-preference.js +51 -0
  95. package/lib/utils/config-format.js +36 -0
  96. package/lib/utils/configuration-env-resolver.js +179 -0
  97. package/lib/utils/credential-display.js +83 -0
  98. package/lib/utils/credential-secrets-env.js +115 -25
  99. package/lib/utils/dataplane-pipeline-warning.js +28 -0
  100. package/lib/utils/deployment-validation-helpers.js +4 -4
  101. package/lib/utils/dev-ca-install.js +139 -0
  102. package/lib/utils/env-copy.js +23 -3
  103. package/lib/utils/error-formatters/http-status-errors.js +0 -1
  104. package/lib/utils/error-formatters/permission-errors.js +0 -1
  105. package/lib/utils/error-formatters/validation-errors.js +0 -1
  106. package/lib/utils/external-readme.js +89 -30
  107. package/lib/utils/external-system-display.js +59 -1
  108. package/lib/utils/external-system-test-helpers.js +21 -8
  109. package/lib/utils/external-system-validators.js +3 -0
  110. package/lib/utils/file-upload.js +20 -50
  111. package/lib/utils/help-builder.js +1 -0
  112. package/lib/utils/infra-status.js +50 -44
  113. package/lib/utils/local-secrets.js +5 -5
  114. package/lib/utils/paths.js +85 -4
  115. package/lib/utils/secrets-canonical.js +93 -0
  116. package/lib/utils/secrets-generator.js +20 -0
  117. package/lib/utils/secrets-helpers.js +75 -89
  118. package/lib/utils/test-log-writer.js +56 -0
  119. package/lib/utils/token-manager.js +24 -32
  120. package/lib/validation/env-template-auth.js +157 -0
  121. package/lib/validation/env-template-kv.js +41 -0
  122. package/lib/validation/external-manifest-validator.js +25 -0
  123. package/lib/validation/external-system-auth-rules.js +86 -0
  124. package/lib/validation/validate-batch.js +149 -0
  125. package/lib/validation/validate-datasource-keys-api.js +33 -0
  126. package/lib/validation/validate-display.js +94 -16
  127. package/lib/validation/validate.js +25 -12
  128. package/lib/validation/validator.js +7 -9
  129. package/lib/validation/wizard-datasource-validation.js +50 -0
  130. package/package.json +7 -2
  131. package/templates/applications/dataplane/application.yaml +1 -1
  132. package/templates/applications/dataplane/env.template +5 -5
  133. package/templates/applications/dataplane/rbac.yaml +2 -2
  134. package/templates/applications/miso-controller/env.template +1 -1
  135. package/templates/external-system/README.md.hbs +75 -22
  136. package/templates/external-system/deploy.js.hbs +4 -2
  137. package/templates/external-system/external-datasource.yaml.hbs +217 -0
  138. package/templates/external-system/external-system.json.hbs +1 -18
  139. package/templates/infra/compose.yaml.hbs +6 -0
  140. package/templates/python/docker-compose.hbs +4 -4
  141. package/templates/typescript/docker-compose.hbs +4 -4
  142. package/integration/hubspot/application.yaml +0 -37
@@ -0,0 +1,217 @@
1
+ key: "{{fullDatasourceKey}}"
2
+ displayName: "{{datasourceDisplayName}}"
3
+ description: "{{datasourceDescription}}"
4
+ systemKey: "{{systemKey}}"
5
+ entityType: "{{schemaEntityType}}"
6
+ resourceType: "{{resourceType}}"
7
+ primaryKey:
8
+ {{#each primaryKey}} - "{{this}}"
9
+ {{/each}}
10
+ enabled: true
11
+ version: "1.0.0"
12
+ fieldMappings:
13
+ {{#if dimensions}}
14
+ dimensions:
15
+ {{#each dimensions}}
16
+ {{@key}}: "{{this}}"
17
+ {{/each}}
18
+ {{else}}
19
+ dimensions: {}
20
+ # Optional: add country, department, organization for ABAC
21
+ {{/if}}
22
+ attributes:
23
+ {{#if attributes}}
24
+ {{#each attributes}}
25
+ {{@key}}:
26
+ expression: "{{this.expression}}"
27
+ type: {{this.type}}
28
+ indexed: {{#if this.indexed}}true{{else}}false{{/if}}
29
+ {{/each}}
30
+ {{else}}
31
+ id:
32
+ expression: "{{raw.id}}"
33
+ type: string
34
+ indexed: true
35
+ name:
36
+ expression: "{{raw.name}}"
37
+ type: string
38
+ indexed: false
39
+ {{/if}}
40
+ {{#if (eq systemType "openapi")}}
41
+ openapi:
42
+ enabled: true
43
+ documentKey: "{{systemKey}}-api"
44
+ operations:
45
+ list:
46
+ operationId: "list{{entityKey}}"
47
+ method: GET
48
+ path: "/{{entityKey}}"
49
+ get:
50
+ operationId: "get{{entityKey}}"
51
+ method: GET
52
+ path: "/{{entityKey}}/{id}"
53
+ autoRbac: true
54
+ {{/if}}
55
+
56
+ # --- Optional sections: uncomment or delete as needed ---
57
+ # CIP (Custom Integration Pipeline) supports: fetch, paginate, map, filter, output, pythonInline steps.
58
+ # Operations: list, get, create, update, delete. Pagination: cursor | page | offset.
59
+ {{#if (eq schemaEntityType "recordStorage")}}
60
+ # sync:
61
+ # pull:
62
+ # enabled: true
63
+ # schedule: "0 * * * *"
64
+ # capabilities: [list, get]
65
+ {{/if}}
66
+ {{#if (eq schemaEntityType "documentStorage")}}
67
+ # documentStorage:
68
+ # enabled: true
69
+ # binaryOperationRef: get
70
+ # embeddingField: content
71
+ {{/if}}
72
+ {{#if (eq schemaEntityType "vectorStore")}}
73
+ # vectorStore:
74
+ # enabled: true
75
+ # embeddingModel: "text-embedding-ada-002"
76
+ {{/if}}
77
+ {{#if (eq schemaEntityType "messageService")}}
78
+ # messageService:
79
+ # enabled: true
80
+ # channels: []
81
+ {{/if}}
82
+
83
+ # --- execution: CIP pipeline ---
84
+ # Steps: fetch (openapi/http) → paginate (cursor|page|offset) → map (useFieldMappings, inputPath) → filter (enforceAbac, expression) → output (mode: records)
85
+ # Pagination: cursor=cursorField+cursorParam | page=pageParam+pageSizeParam | offset=offsetParam+pageSizeParam
86
+ # Adjust inputPath to your API ($.results[*], $.items[*], $.value[*], etc.)
87
+ {{#if (eq schemaEntityType "recordStorage")}}
88
+ # execution:
89
+ # engine: cip
90
+ # cip:
91
+ # operations:
92
+ # list:
93
+ # enabled: true
94
+ # description: "List all records"
95
+ # steps:
96
+ # - fetch: { source: openapi, openapiRef: list, query: {} }
97
+ # - paginate: { strategy: cursor, cursorField: "$.paging.next.after", cursorParam: after, pageSize: 100, maxPages: 100 }
98
+ # # Alternative: page → pageParam, pageSizeParam | offset → offsetParam, pageSizeParam
99
+ # - map: { useFieldMappings: true, inputPath: "$.results[*]" }
100
+ # - filter: { enforceAbac: true }
101
+ # # Optional: filter.expression for SQL or JSON filter, e.g. expression: "status = 'active'"
102
+ # - output: { mode: records }
103
+ # get:
104
+ # enabled: true
105
+ # description: "Get record by ID"
106
+ # steps:
107
+ # - fetch: { source: openapi, openapiRef: get, query: {} }
108
+ # - map: { useFieldMappings: true, inputPath: "$" }
109
+ # - filter: { enforceAbac: true }
110
+ # - output: { mode: records }
111
+ # create:
112
+ # steps:
113
+ # - fetch: { source: openapi, openapiRef: create, bodyTemplate: "{{body}}" }
114
+ # - map: { useFieldMappings: true, inputPath: "$" }
115
+ # - output: { mode: records }
116
+ # update:
117
+ # steps:
118
+ # - fetch: { source: openapi, openapiRef: update, bodyTemplate: "{{body}}" }
119
+ # - map: { useFieldMappings: true, inputPath: "$" }
120
+ # - output: { mode: records }
121
+ # delete:
122
+ # steps:
123
+ # - fetch: { source: openapi, openapiRef: delete }
124
+ # - output: { mode: records }
125
+ {{/if}}
126
+ {{#if (eq schemaEntityType "documentStorage")}}
127
+ # execution:
128
+ # engine: cip
129
+ # cip:
130
+ # operations:
131
+ # list:
132
+ # enabled: true
133
+ # description: "List documents"
134
+ # steps:
135
+ # - fetch: { source: openapi, openapiRef: list, query: {} }
136
+ # - paginate: { strategy: offset, offsetParam: skip, pageSizeParam: top, pageSize: 100, maxPages: 100 }
137
+ # - map: { useFieldMappings: true, inputPath: "$.value[*]" }
138
+ # - filter: { enforceAbac: true }
139
+ # - output: { mode: records }
140
+ # get:
141
+ # enabled: true
142
+ # description: "Get document by ID"
143
+ # steps:
144
+ # - fetch: { source: openapi, openapiRef: get, query: {} }
145
+ # - map: { useFieldMappings: true, inputPath: "$" }
146
+ # - filter: { enforceAbac: true }
147
+ # - output: { mode: records }
148
+ # create:
149
+ # enabled: true
150
+ # description: "Upload document"
151
+ # steps:
152
+ # - fetch: { source: openapi, openapiRef: create, bodyTemplate: "{{fileContent}}" }
153
+ # - map: { useFieldMappings: true, inputPath: "$" }
154
+ # - output: { mode: records }
155
+ {{/if}}
156
+ {{#if (eq schemaEntityType "vectorStore")}}
157
+ # execution:
158
+ # engine: cip
159
+ # cip:
160
+ # operations:
161
+ # list:
162
+ # steps:
163
+ # - fetch: { source: openapi, openapiRef: list, query: {} }
164
+ # - map: { useFieldMappings: true, inputPath: "$" }
165
+ # - output: { mode: records }
166
+ # get:
167
+ # steps:
168
+ # - fetch: { source: openapi, openapiRef: get, query: {} }
169
+ # - map: { useFieldMappings: true, inputPath: "$" }
170
+ # - output: { mode: records }
171
+ {{/if}}
172
+ {{#if (eq schemaEntityType "messageService")}}
173
+ # execution:
174
+ # engine: cip
175
+ # cip:
176
+ # operations:
177
+ # list:
178
+ # steps:
179
+ # - fetch: { source: openapi, openapiRef: list, query: {} }
180
+ # - map: { useFieldMappings: true, inputPath: "$" }
181
+ # - output: { mode: records }
182
+ {{/if}}
183
+ {{#if (eq schemaEntityType "none")}}
184
+ # execution:
185
+ # engine: cip
186
+ # cip:
187
+ # operations:
188
+ # list:
189
+ # steps:
190
+ # - fetch: { source: openapi, openapiRef: list, query: {} }
191
+ # - map: { useFieldMappings: true, inputPath: "$" }
192
+ # - output: { mode: records }
193
+ # get:
194
+ # steps:
195
+ # - fetch: { source: openapi, openapiRef: get, query: {} }
196
+ # - map: { useFieldMappings: true, inputPath: "$" }
197
+ # - output: { mode: records }
198
+ {{/if}}
199
+
200
+ # config: ABAC cross-system filters (SQL or JSON)
201
+ # config:
202
+ # abac:
203
+ # crossSystemSql: "country = '{{actor.country}}'"
204
+ # # crossSystemJson: { "dimensions.country": { "eq": "{{actor.country}}" } }
205
+
206
+ # capabilities: [list, get, create, update, delete]
207
+
208
+ # exposed: attributes to expose via MCP/OpenAPI
209
+ # exposed:
210
+ # attributes: [id, name]
211
+
212
+ # metadataSchema: JSON Schema for raw metadata validation
213
+ # metadataSchema:
214
+ # type: object
215
+ # properties:
216
+ # id: { type: string }
217
+ # name: { type: string }
@@ -4,23 +4,7 @@
4
4
  "description": "{{systemDescription}}",
5
5
  "type": "{{systemType}}",
6
6
  "enabled": true,
7
- "authentication": {
8
- "type": "{{authType}}"{{#if (eq authType "oauth2")}},
9
- "oauth2": {
10
- "tokenUrl": "https://api.example.com/oauth/token",
11
- "clientId": "kv://{{systemKey}}-oauth2-client-id",
12
- "clientSecret": "kv://{{systemKey}}-oauth2-client-secret",
13
- "scopes": []
14
- }{{/if}}{{#if (eq authType "apikey")}},
15
- "apikey": {
16
- "headerName": "X-API-Key",
17
- "key": "kv://{{systemKey}}-api-key"
18
- }{{/if}}{{#if (eq authType "basic")}},
19
- "basic": {
20
- "username": "kv://{{systemKey}}-username",
21
- "password": "kv://{{systemKey}}-password"
22
- }{{/if}}
23
- }{{#if (eq systemType "openapi")}},
7
+ "authentication": {{{json authentication}}}{{#if (eq systemType "openapi")}},
24
8
  "openapi": {
25
9
  "documentKey": "{{systemKey}}-api",
26
10
  "autoDiscoverEntities": false
@@ -51,4 +35,3 @@
51
35
  {{/each}}
52
36
  ]{{/if}}
53
37
  }
54
-
@@ -45,6 +45,7 @@ services:
45
45
  retries: 5
46
46
  restart: unless-stopped
47
47
 
48
+ {{#if pgadmin.enabled}}
48
49
  # Optional: pgAdmin for database management
49
50
  pgadmin:
50
51
  image: dpage/pgadmin4:latest
@@ -78,7 +79,9 @@ services:
78
79
  condition: service_healthy
79
80
  networks:
80
81
  - {{networkName}}
82
+ {{/if}}
81
83
 
84
+ {{#if redisCommander.enabled}}
82
85
  # Optional: Redis Commander for Redis management
83
86
  redis-commander:
84
87
  image: rediscommander/redis-commander:latest
@@ -96,6 +99,7 @@ services:
96
99
  condition: service_healthy
97
100
  networks:
98
101
  - {{networkName}}
102
+ {{/if}}
99
103
 
100
104
  {{#if traefik.enabled}}
101
105
  # Traefik Reverse Proxy
@@ -139,9 +143,11 @@ volumes:
139
143
  {{#if (eq devId 0)}}redis_data{{else}}dev{{devId}}_redis_data{{/if}}:
140
144
  name: {{#if (eq devId 0)}}infra_redis_data{{else}}infra_dev{{devId}}_redis_data{{/if}}
141
145
  driver: local
146
+ {{#if pgadmin.enabled}}
142
147
  {{#if (eq devId 0)}}pgadmin_data{{else}}dev{{devId}}_pgadmin_data{{/if}}:
143
148
  name: {{#if (eq devId 0)}}infra_pgadmin_data{{else}}infra_dev{{devId}}_pgadmin_data{{/if}}
144
149
  driver: local
150
+ {{/if}}
145
151
 
146
152
  networks:
147
153
  {{networkName}}:
@@ -136,10 +136,10 @@ services:
136
136
  psql -d {{name}} -c "GRANT ALL ON SCHEMA public TO \"{{pgUserName name}}\";" &&
137
137
  echo 'Database "{{name}}" created successfully!'
138
138
  fi &&
139
- {{#if (isVectorDatabase name)}}
140
- psql -d {{name}} -c "CREATE EXTENSION IF NOT EXISTS vector;" &&
141
- echo 'pgvector extension enabled on "{{name}}".' &&
142
- {{/if}}
139
+ {{#each (extensionsForDb this)}}
140
+ (psql -d {{../name}} -c 'CREATE EXTENSION IF NOT EXISTS {{pgQuote this}};' || echo 'Warning: could not create extension {{this}}') &&
141
+ echo 'Extension "{{this}}" enabled on "{{../name}}".' &&
142
+ {{/each}}
143
143
  {{/each}}
144
144
  {{else}}
145
145
  echo 'Creating {{app.key}} database and user...' &&
@@ -136,10 +136,10 @@ services:
136
136
  psql -d {{name}} -c "GRANT ALL ON SCHEMA public TO \"{{pgUserName name}}\";" &&
137
137
  echo 'Database "{{name}}" created successfully!'
138
138
  fi &&
139
- {{#if (isVectorDatabase name)}}
140
- psql -d {{name}} -c "CREATE EXTENSION IF NOT EXISTS vector;" &&
141
- echo 'pgvector extension enabled on "{{name}}".' &&
142
- {{/if}}
139
+ {{#each (extensionsForDb this)}}
140
+ (psql -d {{../name}} -c 'CREATE EXTENSION IF NOT EXISTS {{pgQuote this}};' || echo 'Warning: could not create extension {{this}}') &&
141
+ echo 'Extension "{{this}}" enabled on "{{../name}}".' &&
142
+ {{/each}}
143
143
  {{/each}}
144
144
  {{else}}
145
145
  echo 'Creating {{app.key}} database and user...' &&
@@ -1,37 +0,0 @@
1
- app:
2
- key: hubspot
3
- displayName: HubSpot CRM Integration
4
- description: HubSpot CRM external system integration with companies, contacts, and deals
5
- type: external
6
- configuration:
7
- - name: HUBSPOT_API_VERSION
8
- portalInput:
9
- field: select
10
- label: HubSpot API Version
11
- placeholder: Select API version
12
- options:
13
- - v1
14
- - v2
15
- - v3
16
- validation:
17
- required: false
18
- - name: MAX_PAGE_SIZE
19
- portalInput:
20
- field: text
21
- label: Maximum Page Size
22
- placeholder: '100'
23
- validation:
24
- required: false
25
- pattern: ^[0-9]+$
26
- minLength: 1
27
- maxLength: 1000
28
- externalIntegration:
29
- schemaBasePath: ./
30
- systems:
31
- - hubspot-system.json
32
- dataSources:
33
- - hubspot-datasource-company.json
34
- - hubspot-datasource-contact.json
35
- - hubspot-datasource-deal.json
36
- autopublish: true
37
- version: 1.0.0