@elevasis/core 0.1.0 → 0.2.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 (34) hide show
  1. package/dist/index.js +195 -3
  2. package/dist/organization-model/index.js +195 -3
  3. package/package.json +1 -1
  4. package/src/__tests__/template-foundations-compatibility.test.ts +95 -14
  5. package/src/auth/multi-tenancy/types.ts +2 -1
  6. package/src/execution/engine/__tests__/fixtures/test-agents.ts +4 -4
  7. package/src/execution/engine/index.ts +5 -19
  8. package/src/execution/engine/tools/platform/index.ts +9 -33
  9. package/src/execution/engine/tools/registry.ts +109 -2
  10. package/src/execution/engine/tools/tool-maps.ts +88 -0
  11. package/src/organization-model/README.md +19 -4
  12. package/src/organization-model/__tests__/graph.test.ts +612 -0
  13. package/src/organization-model/__tests__/resolve.test.ts +208 -0
  14. package/src/organization-model/defaults.ts +1 -1
  15. package/src/organization-model/organization-graph.mdx +262 -0
  16. package/src/organization-model/organization-model.mdx +257 -0
  17. package/src/organization-model/resolve.ts +26 -2
  18. package/src/organization-model/schema.ts +203 -1
  19. package/src/platform/constants/versions.ts +1 -1
  20. package/src/platform/registry/__tests__/resource-registry.integration.test.ts +24 -0
  21. package/src/platform/registry/__tests__/resource-registry.test.ts +63 -0
  22. package/src/platform/registry/resource-registry.ts +98 -10
  23. package/src/projects/api-schemas.ts +2 -1
  24. package/src/reference/_generated/contracts.md +1044 -0
  25. package/src/reference/glossary.md +88 -0
  26. package/src/server.ts +2 -3
  27. package/src/execution/engine/tools/platform/resource-invocation/__tests__/edge-cases.test.ts +0 -507
  28. package/src/execution/engine/tools/platform/resource-invocation/__tests__/resource-invocation-service.test.ts +0 -500
  29. package/src/execution/engine/tools/platform/resource-invocation/__tests__/tool.test.ts +0 -555
  30. package/src/execution/engine/tools/platform/resource-invocation/dynamic-tool.ts +0 -94
  31. package/src/execution/engine/tools/platform/resource-invocation/index.ts +0 -14
  32. package/src/execution/engine/tools/platform/resource-invocation/resource-invocation-service.ts +0 -147
  33. package/src/execution/engine/tools/platform/resource-invocation/tool.ts +0 -115
  34. package/src/execution/engine/tools/platform/resource-invocation/types.ts +0 -31
@@ -143,6 +143,85 @@ export class ResourceRegistry {
143
143
  }
144
144
  }
145
145
 
146
+ /**
147
+ * Get the remote resource IDs currently registered for an organization.
148
+ * Used to validate redeployments against the post-swap state before any
149
+ * live registry mutation occurs.
150
+ */
151
+ private getRemoteResourceIds(orgName: string): Set<string> {
152
+ const prefix = `${orgName}/`
153
+ const remoteIds = new Set<string>()
154
+ for (const key of this.remoteResources.keys()) {
155
+ if (key.startsWith(prefix)) {
156
+ remoteIds.add(key.slice(prefix.length))
157
+ }
158
+ }
159
+ return remoteIds
160
+ }
161
+
162
+ /**
163
+ * Build the "static + surviving" baseline for registration validation.
164
+ * On redeploy, this strips the currently remote-owned resources and
165
+ * deployment-owned metadata so validation reflects the state after swap.
166
+ */
167
+ private buildRegistrationBase(orgName: string): DeploymentSpec | undefined {
168
+ const existingOrg = this.registry[orgName]
169
+ if (!existingOrg) return undefined
170
+
171
+ const remoteIds = this.getRemoteResourceIds(orgName)
172
+ if (remoteIds.size === 0) return existingOrg
173
+
174
+ const relationships = existingOrg.relationships
175
+ ? Object.fromEntries(Object.entries(existingOrg.relationships).filter(([resourceId]) => !remoteIds.has(resourceId)))
176
+ : undefined
177
+
178
+ return {
179
+ ...existingOrg,
180
+ version: existingOrg.version ?? '0.0.0',
181
+ workflows: (existingOrg.workflows ?? []).filter((w) => !remoteIds.has(w.config.resourceId)),
182
+ agents: (existingOrg.agents ?? []).filter((a) => !remoteIds.has(a.config.resourceId)),
183
+ triggers: undefined,
184
+ integrations: undefined,
185
+ humanCheckpoints: undefined,
186
+ externalResources: undefined,
187
+ relationships: relationships && Object.keys(relationships).length > 0 ? relationships : undefined
188
+ }
189
+ }
190
+
191
+ /**
192
+ * Validate the registry state that would exist after registration succeeds.
193
+ * This runs before any live mutation so invalid redeploys preserve the
194
+ * currently active remote resources.
195
+ */
196
+ private validateRegistrationCandidate(orgName: string, incoming: DeploymentSpec): void {
197
+ const base = this.buildRegistrationBase(orgName)
198
+
199
+ const candidate: DeploymentSpec = base
200
+ ? {
201
+ ...base,
202
+ version: incoming.version ?? base.version ?? '0.0.0',
203
+ workflows: [...(base.workflows ?? []), ...(incoming.workflows ?? [])],
204
+ agents: [...(base.agents ?? []), ...(incoming.agents ?? [])],
205
+ triggers: incoming.triggers,
206
+ integrations: incoming.integrations,
207
+ humanCheckpoints: incoming.humanCheckpoints,
208
+ externalResources: incoming.externalResources,
209
+ relationships: incoming.relationships
210
+ ? {
211
+ ...(base.relationships ?? {}),
212
+ ...incoming.relationships
213
+ }
214
+ : base.relationships
215
+ }
216
+ : {
217
+ ...incoming,
218
+ version: incoming.version ?? '0.0.0'
219
+ }
220
+
221
+ validateDeploymentSpec(orgName, candidate)
222
+ validateRelationships(orgName, candidate)
223
+ }
224
+
146
225
  /**
147
226
  * Get a resource definition by ID
148
227
  * Returns full definition (WorkflowDefinition or AgentDefinition)
@@ -281,16 +360,13 @@ export class ResourceRegistry {
281
360
  }
282
361
  }
283
362
 
284
- // If redeploying (some resources already registered as remote for this org), clean up first
285
- if (this.isRemote(orgName)) {
286
- this.unregisterOrganization(orgName)
287
- }
288
-
289
- // Check for conflicts with static (non-remote) resources in the existing org
290
- const existingOrg = this.registry[orgName]
291
- if (existingOrg) {
292
- const staticWorkflowIds = new Set((existingOrg.workflows ?? []).map((w) => w.config.resourceId))
293
- const staticAgentIds = new Set((existingOrg.agents ?? []).map((a) => a.config.resourceId))
363
+ // Check for conflicts against the static/surviving org state.
364
+ // On redeploy, current remote resources are excluded so a deployment can
365
+ // legitimately replace its own resource IDs without colliding with itself.
366
+ const validationBase = this.buildRegistrationBase(orgName)
367
+ if (validationBase) {
368
+ const staticWorkflowIds = new Set((validationBase.workflows ?? []).map((w) => w.config.resourceId))
369
+ const staticAgentIds = new Set((validationBase.agents ?? []).map((a) => a.config.resourceId))
294
370
 
295
371
  for (const id of incomingIds) {
296
372
  if (staticWorkflowIds.has(id) || staticAgentIds.has(id)) {
@@ -301,7 +377,19 @@ export class ResourceRegistry {
301
377
  }
302
378
  }
303
379
 
380
+ // Validate the merged deployment shape before mutating the live registry.
381
+ // This keeps the current deployment intact if a redeploy introduces
382
+ // invalid relationships or other registry-level validation failures.
383
+ this.validateRegistrationCandidate(orgName, org)
384
+
385
+ // If redeploying (some resources already registered as remote for this org), clean up only
386
+ // after validation succeeds so a failed redeploy preserves the current remote resources.
387
+ if (this.isRemote(orgName)) {
388
+ this.unregisterOrganization(orgName)
389
+ }
390
+
304
391
  // Merge incoming resources into the org (or create new org entry)
392
+ const existingOrg = this.registry[orgName]
305
393
  if (existingOrg) {
306
394
  existingOrg.workflows = [...(existingOrg.workflows ?? []), ...(org.workflows ?? [])]
307
395
  existingOrg.agents = [...(existingOrg.agents ?? []), ...(org.agents ?? [])]
@@ -101,7 +101,8 @@ export const UpdateProjectRequestSchema = z
101
101
 
102
102
  export const GetProjectsQuerySchema = z
103
103
  .object({
104
- kind: ProjectKindSchema.optional()
104
+ kind: ProjectKindSchema.optional(),
105
+ status: ProjectStatusSchema.optional()
105
106
  })
106
107
  .strict()
107
108