@onlineapps/cookbook-core 2.1.3 → 2.1.4

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@onlineapps/cookbook-core",
3
- "version": "2.1.3",
3
+ "version": "2.1.4",
4
4
  "description": "Core cookbook parsing and validation - lightweight foundation for workflow definitions",
5
5
  "main": "src/index.js",
6
6
  "scripts": {
@@ -249,53 +249,48 @@ function validateSemantics(cookbook, version) {
249
249
  stepIds.add(stepId);
250
250
  }
251
251
 
252
- // Check nested steps
253
- if (step.steps) {
254
- step.steps.forEach((nested, idx) =>
255
- checkStep(nested, `${path}.steps[${idx}]`)
252
+ // Check nested steps - V2: all nested steps are objects keyed by step_id
253
+ if (step.steps && typeof step.steps === 'object') {
254
+ Object.entries(step.steps).forEach(([nestedKey, nested]) =>
255
+ checkStep(nested, `${path}.steps.${nestedKey}`)
256
256
  );
257
257
  }
258
- if (step.body) {
259
- step.body.forEach((nested, idx) =>
260
- checkStep(nested, `${path}.body[${idx}]`)
258
+ if (step.body && typeof step.body === 'object') {
259
+ Object.entries(step.body).forEach(([nestedKey, nested]) =>
260
+ checkStep(nested, `${path}.body.${nestedKey}`)
261
261
  );
262
262
  }
263
- if (step.branches) {
264
- step.branches.forEach((branch, idx) => {
265
- if (branch.steps) {
266
- branch.steps.forEach((nested, jdx) =>
267
- checkStep(nested, `${path}.branches[${idx}].steps[${jdx}]`)
268
- );
269
- }
263
+ if (step.branches && typeof step.branches === 'object') {
264
+ Object.entries(step.branches).forEach(([branchKey, branch]) => {
265
+ checkStep(branch, `${path}.branches.${branchKey}`);
270
266
  });
271
267
  }
272
268
  if (step.cases) {
273
269
  Object.keys(step.cases).forEach(caseKey => {
274
270
  const caseVal = step.cases[caseKey];
275
- if (caseVal.steps) {
276
- caseVal.steps.forEach((nested, idx) =>
277
- checkStep(nested, `${path}.cases.${caseKey}.steps[${idx}]`)
278
- );
279
- }
271
+ checkStep(caseVal, `${path}.cases.${caseKey}`);
280
272
  });
281
273
  }
282
274
  }
283
275
 
284
- // Check all steps
276
+ // Check all steps - V2: steps is an OBJECT keyed by step_id, NOT an array
285
277
  if (cookbook.steps) {
286
- cookbook.steps.forEach((step, idx) =>
287
- checkStep(step, `steps[${idx}]`)
278
+ if (Array.isArray(cookbook.steps)) {
279
+ throw new CookbookValidationError('V1 FORMAT BANNED! steps must be an object keyed by step_id, not an array');
280
+ }
281
+ Object.entries(cookbook.steps).forEach(([stepKey, step]) =>
282
+ checkStep(step, `steps.${stepKey}`)
288
283
  );
289
284
  }
290
285
 
291
286
  // Check dependencies exist
292
287
  if (version === '2.0' && cookbook.steps) {
293
- cookbook.steps.forEach((step, idx) => {
288
+ Object.entries(cookbook.steps).forEach(([stepKey, step]) => {
294
289
  if (step.depends_on) {
295
290
  step.depends_on.forEach(dep => {
296
291
  if (!stepIds.has(dep)) {
297
292
  throw new CookbookValidationError(
298
- `Step ${idx} depends on non-existent step_id '${dep}'`
293
+ `Step '${stepKey}' depends on non-existent step_id '${dep}'`
299
294
  );
300
295
  }
301
296
  });