@toa.io/norm 1.0.0-alpha.320 → 1.0.0-alpha.322

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/CHANGELOG.md CHANGED
@@ -3,6 +3,20 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ # [1.0.0-alpha.322](https://github.com/toa-io/toa/compare/v1.0.0-alpha.321...v1.0.0-alpha.322) (2026-09-29)
7
+
8
+ ### Features
9
+
10
+ * **continuity:** give back what a continued effect was answered on an earlier attempt ([507145b](https://github.com/toa-io/toa/commit/507145beb635dad3d948b74630e34858537bf8ef))
11
+
12
+
13
+ # [1.0.0-alpha.321](https://github.com/toa-io/toa/compare/v1.0.0-alpha.320...v1.0.0-alpha.321) (2026-09-28)
14
+
15
+ ### Features
16
+
17
+ * **core:** let an operation declared unchained begin a chain of its own ([6d94324](https://github.com/toa-io/toa/commit/6d94324cb43ff4b12e1bc267d81498445b40a02e))
18
+
19
+
6
20
  # [1.0.0-alpha.320](https://github.com/toa-io/toa/compare/v1.0.0-alpha.319...v1.0.0-alpha.320) (2026-09-28)
7
21
 
8
22
  **Note:** Version bump only for package @toa.io/norm
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@toa.io/norm",
3
- "version": "1.0.0-alpha.320",
3
+ "version": "1.0.0-alpha.322",
4
4
  "type": "module",
5
5
  "description": "Toa declarations normalization and validation",
6
6
  "author": "temich <tema.gurtovoy@gmail.com>",
@@ -21,12 +21,12 @@
21
21
  "test": "echo \"Error: run tests from root\" && exit 1"
22
22
  },
23
23
  "dependencies": {
24
- "@toa.io/core": "1.0.0-alpha.320",
25
- "@toa.io/definitions": "1.0.0-alpha.320",
24
+ "@toa.io/core": "1.0.0-alpha.322",
25
+ "@toa.io/definitions": "1.0.0-alpha.322",
26
26
  "@toa.io/generic": "1.0.0-alpha.311",
27
- "@toa.io/prototype": "1.0.0-alpha.319",
27
+ "@toa.io/prototype": "1.0.0-alpha.322",
28
28
  "@toa.io/schemas": "1.0.0-alpha.311",
29
29
  "fast-glob": "3.3.3"
30
30
  },
31
- "gitHead": "5ef92ab939a596e4ac820965c59c015820eba7b2"
31
+ "gitHead": "ef65352a8bd7bc0ef400fcc8cde0e19a3bb92199"
32
32
  }
@@ -13,6 +13,7 @@ const SHORTCUTS = {
13
13
  stash: '@toa.io/extensions.stash',
14
14
  storages: '@toa.io/extensions.storages',
15
15
  cadence: '@toa.io/extensions.cadence',
16
+ continuity: '@toa.io/extensions.continuity',
16
17
  introspection: '@toa.io/extensions.introspection',
17
18
  telemetry: '@toa.io/extensions.telemetry'
18
19
  }
@@ -101,7 +101,7 @@ properties:
101
101
  type: object
102
102
  propertyNames:
103
103
  not:
104
- enum: [id, VERSION, CREATED, UPDATED, DELETED, REGION, TRAILERS]
104
+ enum: [id, VERSION, CREATED, UPDATED, DELETED, REGION, TRAILERS, DISCARD]
105
105
  migrations:
106
106
  type: array
107
107
  items:
@@ -166,6 +166,9 @@ properties:
166
166
  stateful:
167
167
  # served by every process under an address of its own, which a call names; see documentation/stateful.md
168
168
  type: boolean
169
+ unchained:
170
+ # every call begins a chain of its own, so a circle through it is refused by neither rule; see documentation/cycles.md
171
+ type: boolean
169
172
  stream:
170
173
  # the input property that carries a stream, read as its caller writes it; see documentation/streams.md
171
174
  $ref: "#/definitions/name"
@@ -25,9 +25,11 @@ export const validate = async (manifest) => {
25
25
  const entity = (manifest) => {
26
26
  const { properties, required, blank } = manifest.entity
27
27
 
28
- // what an algorithm writes beside the record for the event of its commit; never stored
29
- if (properties.TRAILERS !== undefined)
30
- throw new Error("System property 'TRAILERS' cannot be declared")
28
+ // what an algorithm writes beside the record: for the event of its commit, and to have
29
+ // nothing of it committed; neither is ever stored
30
+ for (const name of ['TRAILERS', 'DISCARD'])
31
+ if (properties[name] !== undefined)
32
+ throw new Error(`System property '${name}' cannot be declared`)
31
33
 
32
34
  for (const name of required ?? [])
33
35
  if (properties[name] === undefined)
package/src/shortcuts.js CHANGED
@@ -49,6 +49,7 @@ export const SHORTCUTS = {
49
49
  storages: '@toa.io/extensions.storages',
50
50
  telemetry: '@toa.io/extensions.telemetry',
51
51
  cadence: '@toa.io/extensions.cadence',
52
+ continuity: '@toa.io/extensions.continuity',
52
53
  convergence: '@toa.io/extensions.convergence',
53
54
  introspection: '@toa.io/extensions.introspection'
54
55
  }
@@ -122,6 +122,13 @@ describe('entity', () => {
122
122
  /System property 'TRAILERS' cannot be declared/.test(error.message)
123
123
  )
124
124
  })
125
+
126
+ it('should not declare DISCARD', async () => {
127
+ manifest.entity.properties.DISCARD = { type: 'boolean' }
128
+ await assert.rejects(validate(manifest), (error) =>
129
+ /System property 'DISCARD' cannot be declared/.test(error.message)
130
+ )
131
+ })
125
132
  })
126
133
 
127
134
  describe('required', () => {
@@ -160,6 +167,13 @@ describe('entity', () => {
160
167
  /must NOT be valid/.test(error.message)
161
168
  )
162
169
  })
170
+
171
+ it('should not name DISCARD', async () => {
172
+ manifest.entity.blank = { DISCARD: true }
173
+ await assert.rejects(validate(manifest), (error) =>
174
+ /must NOT be valid/.test(error.message)
175
+ )
176
+ })
163
177
  })
164
178
  })
165
179
 
@@ -383,6 +397,24 @@ describe('stateful', () => {
383
397
  })
384
398
  })
385
399
 
400
+ describe('unchained', () => {
401
+ it('should be allowed on an operation', async () => {
402
+ const [operation] = Object.values(manifest.operations)
403
+
404
+ operation.unchained = true
405
+
406
+ await assert.doesNotReject(validate(manifest))
407
+ })
408
+
409
+ it('should be a boolean', async () => {
410
+ const [operation] = Object.values(manifest.operations)
411
+
412
+ operation.unchained = 'yes'
413
+
414
+ await assert.rejects(validate(manifest), (error) => /must be boolean/.test(error.message))
415
+ })
416
+ })
417
+
386
418
  describe('stream', () => {
387
419
  beforeEach(() => {
388
420
  manifest.operations.read = {
@@ -16,6 +16,8 @@ export type Operation = {
16
16
  query?: boolean
17
17
  /** served by every process under an address of its own, which a call to it names */
18
18
  stateful?: boolean
19
+ /** every call begins a chain of its own */
20
+ unchained?: boolean
19
21
  /** the input property that carries a stream, read as its caller writes it */
20
22
  stream?: string
21
23
  }