nervur 0.21.4 → 0.22.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.
- package/README.md +215 -158
- package/dist/browser.js +4 -3
- package/dist/cli.js +16 -0
- package/dist/{being → core/being}/being.js +10 -0
- package/dist/{being → core/being}/faculty.js +5 -2
- package/dist/{being → core/being}/index.d.ts +1 -1
- package/dist/{being → core/being}/index.js +1 -1
- package/dist/{being → core/being}/kind.d.ts +2 -0
- package/dist/{being → core/being}/kind.js +6 -0
- package/dist/{being → core/being}/types.js +1 -1
- package/dist/{browser → core/browser}/index.d.ts +6 -5
- package/dist/{browser → core/browser}/index.js +10 -10
- package/dist/{browser → core/browser}/worker.d.ts +2 -3
- package/dist/{browser → core/browser}/worker.js +8 -11
- package/dist/{cli → core/cli}/command.d.ts +4 -4
- package/dist/{cli → core/cli}/command.js +116 -66
- package/dist/{cli → core/cli}/edge.js +4 -2
- package/dist/core/cli/harbor.d.ts +25 -0
- package/dist/{cli → core/cli}/harbor.js +45 -33
- package/dist/{contract → core/contract}/index.d.ts +6 -5
- package/dist/{contract → core/contract}/index.js +8 -9
- package/dist/core/contract/link.d.ts +4 -0
- package/dist/core/contract/link.js +45 -0
- package/dist/{crypto → core/crypto}/ed25519.js +22 -14
- package/dist/core/crypto/subtle.d.ts +3 -0
- package/dist/core/crypto/subtle.js +11 -0
- package/dist/core/crypto/x25519.js +24 -0
- package/dist/core/edge/index.d.ts +164 -0
- package/dist/core/edge/index.js +739 -0
- package/dist/core/edge/kit.d.ts +2 -0
- package/dist/core/edge/kit.js +2 -0
- package/dist/core/git/http.d.ts +6 -0
- package/dist/core/git/http.js +102 -0
- package/dist/core/git/index.d.ts +5 -0
- package/dist/core/git/index.js +10 -0
- package/dist/core/git/object.d.ts +40 -0
- package/dist/core/git/object.js +103 -0
- package/dist/core/git/pack.d.ts +9 -0
- package/dist/core/git/pack.js +171 -0
- package/dist/core/git/store.d.ts +23 -0
- package/dist/core/git/store.js +120 -0
- package/dist/core/git/zlib.d.ts +6 -0
- package/dist/core/git/zlib.js +210 -0
- package/dist/core/harbor/carrying.d.ts +51 -0
- package/dist/core/harbor/carrying.js +69 -0
- package/dist/core/harbor/catalogue.d.ts +33 -0
- package/dist/core/harbor/catalogue.js +365 -0
- package/dist/core/harbor/dna.d.ts +13 -0
- package/dist/core/harbor/dna.js +120 -0
- package/dist/{harbor → core/harbor}/dock.d.ts +22 -13
- package/dist/core/harbor/dock.js +381 -0
- package/dist/core/harbor/harbor.d.ts +16 -0
- package/dist/core/harbor/harbor.js +438 -0
- package/dist/core/harbor/index.d.ts +11 -0
- package/dist/{harbor → core/harbor}/index.js +5 -5
- package/dist/core/harbor/memory.d.ts +10 -0
- package/dist/core/harbor/memory.js +25 -0
- package/dist/{harbor → core/harbor}/package.d.ts +0 -1
- package/dist/{harbor → core/harbor}/package.js +9 -9
- package/dist/core/harbor/probe.d.ts +22 -0
- package/dist/core/harbor/probe.js +15 -0
- package/dist/core/harbor/registry.d.ts +15 -0
- package/dist/{harbor → core/harbor}/registry.js +26 -10
- package/dist/core/harbor/root-line.d.ts +7 -0
- package/dist/core/harbor/root-line.js +9 -0
- package/dist/{harbor → core/harbor}/terrain.d.ts +9 -6
- package/dist/{harbor → core/harbor}/terrain.js +5 -4
- package/dist/core/http/index.d.ts +2 -0
- package/dist/{http → core/http}/index.js +3 -5
- package/dist/{line → core/line}/answer.d.ts +2 -2
- package/dist/{line → core/line}/frame.d.ts +0 -5
- package/dist/{line → core/line}/frame.js +0 -4
- package/dist/core/line/ground.js +7 -0
- package/dist/core/line/index.d.ts +4 -0
- package/dist/core/line/index.js +8 -0
- package/dist/core/line/web.d.ts +12 -0
- package/dist/{line → core/line}/web.js +13 -77
- package/dist/{node → core/node}/index.d.ts +2 -15
- package/dist/core/node/index.js +124 -0
- package/dist/{pointer → core/pointer}/bodies.d.ts +7 -5
- package/dist/core/pointer/bodies.js +118 -0
- package/dist/core/pointer/index.d.ts +2 -0
- package/dist/{pointer → core/pointer}/index.js +1 -1
- package/dist/{pointer → core/pointer}/world.d.ts +13 -9
- package/dist/{pointer → core/pointer}/world.js +31 -16
- package/dist/{proof → core/proof}/contracts.d.ts +6 -2
- package/dist/{proof → core/proof}/contracts.js +11 -10
- package/dist/core/proof/index.d.ts +3 -0
- package/dist/{proof → core/proof}/index.js +2 -2
- package/dist/core/proof/law.d.ts +25 -0
- package/dist/core/proof/law.js +715 -0
- package/dist/{tcp → core/tcp}/index.d.ts +7 -4
- package/dist/{tcp → core/tcp}/index.js +11 -62
- package/dist/{ward/ward.d.ts → core/ward/house.d.ts} +24 -10
- package/dist/core/ward/house.js +473 -0
- package/dist/core/ward/index.d.ts +5 -0
- package/dist/core/ward/index.js +7 -0
- package/dist/{ward → core/ward}/partition.d.ts +1 -0
- package/dist/{ward → core/ward}/stance.d.ts +2 -2
- package/dist/{ward → core/ward}/stance.js +5 -2
- package/dist/{ward/ward-being.d.ts → core/ward/ward.d.ts} +14 -6
- package/dist/core/ward/ward.js +140 -0
- package/dist/core.d.ts +10 -0
- package/dist/core.js +19 -0
- package/dist/defaults/dock/index.d.ts +4 -0
- package/dist/defaults/dock/index.js +11 -0
- package/dist/defaults/index.d.ts +5 -0
- package/dist/defaults/index.js +10 -0
- package/dist/defaults/memory/index.d.ts +12 -0
- package/dist/defaults/memory/index.js +39 -0
- package/dist/defaults/tcp/index.d.ts +16 -0
- package/dist/defaults/tcp/index.js +82 -0
- package/dist/defaults/ward/index.d.ts +4 -0
- package/dist/defaults/ward/index.js +11 -0
- package/dist/defaults/web/index.d.ts +15 -0
- package/dist/defaults/web/index.js +90 -0
- package/dist/edge.js +4 -3
- package/dist/index.d.ts +1 -8
- package/dist/index.js +13 -18
- package/dist/kit.d.ts +4 -0
- package/dist/kit.js +12 -0
- package/dist/node.js +4 -3
- package/package.json +23 -18
- package/src/browser.ts +4 -3
- package/src/cli.ts +15 -0
- package/src/{being → core/being}/being.ts +4 -0
- package/src/{being → core/being}/faculty.ts +5 -2
- package/src/{being → core/being}/index.ts +1 -1
- package/src/{being → core/being}/kind.ts +7 -0
- package/src/{being → core/being}/types.ts +1 -1
- package/src/{browser → core/browser}/index.ts +16 -13
- package/src/{browser → core/browser}/worker.ts +11 -14
- package/src/{cli → core/cli}/command.ts +113 -66
- package/src/{cli → core/cli}/edge.ts +4 -2
- package/src/{cli → core/cli}/harbor.ts +48 -31
- package/src/{contract → core/contract}/index.ts +14 -14
- package/src/core/contract/link.ts +58 -0
- package/src/{crypto → core/crypto}/ed25519.ts +22 -14
- package/src/core/crypto/subtle.ts +13 -0
- package/src/core/crypto/x25519.ts +23 -0
- package/src/core/edge/index.ts +865 -0
- package/src/core/git/http.ts +103 -0
- package/src/core/git/index.ts +10 -0
- package/src/core/git/object.ts +116 -0
- package/src/core/git/pack.ts +147 -0
- package/src/core/git/store.ts +122 -0
- package/src/core/git/zlib.ts +197 -0
- package/src/core/harbor/carrying.ts +124 -0
- package/src/core/harbor/catalogue.ts +386 -0
- package/src/core/harbor/dna.ts +116 -0
- package/src/core/harbor/dock.ts +420 -0
- package/src/core/harbor/harbor.ts +433 -0
- package/src/core/harbor/index.ts +14 -0
- package/src/core/harbor/memory.ts +31 -0
- package/src/{harbor → core/harbor}/package.ts +15 -15
- package/src/core/harbor/probe.ts +39 -0
- package/src/{harbor → core/harbor}/registry.ts +28 -11
- package/src/core/harbor/root-line.ts +19 -0
- package/src/{harbor → core/harbor}/terrain.ts +14 -7
- package/src/{http → core/http}/index.ts +5 -8
- package/src/{line → core/line}/answer.ts +3 -2
- package/src/{line → core/line}/frame.ts +0 -5
- package/src/core/line/ground.ts +18 -0
- package/src/core/line/index.ts +8 -0
- package/src/{line → core/line}/web.ts +1 -105
- package/src/core/node/index.ts +139 -0
- package/src/core/pointer/bodies.ts +122 -0
- package/src/core/pointer/index.ts +4 -0
- package/src/{pointer → core/pointer}/world.ts +45 -21
- package/src/{proof → core/proof}/contracts.ts +18 -13
- package/src/{proof → core/proof}/index.ts +3 -3
- package/src/core/proof/law.ts +742 -0
- package/src/{stand → core/stand}/stand.ts +2 -2
- package/src/{tcp → core/tcp}/index.ts +17 -74
- package/src/core/ward/house.ts +524 -0
- package/src/core/ward/index.ts +7 -0
- package/src/{ward → core/ward}/partition.ts +5 -1
- package/src/{ward → core/ward}/stance.ts +5 -2
- package/src/core/ward/ward.ts +166 -0
- package/src/core.ts +55 -0
- package/src/defaults/dock/index.ts +12 -0
- package/src/defaults/index.ts +10 -0
- package/src/defaults/memory/index.ts +50 -0
- package/src/defaults/tcp/index.ts +89 -0
- package/src/defaults/ward/index.ts +12 -0
- package/src/defaults/web/index.ts +97 -0
- package/src/edge.ts +4 -3
- package/src/index.ts +13 -50
- package/src/kit.ts +15 -0
- package/src/node.ts +4 -3
- package/dist/cli/harbor.d.ts +0 -16
- package/dist/cli/main.js +0 -14
- package/dist/crypto/subtle.d.ts +0 -10
- package/dist/crypto/subtle.js +0 -29
- package/dist/crypto/x25519.js +0 -21
- package/dist/edge/index.d.ts +0 -81
- package/dist/edge/index.js +0 -400
- package/dist/harbor/carrying.d.ts +0 -17
- package/dist/harbor/carrying.js +0 -38
- package/dist/harbor/catalogue.d.ts +0 -28
- package/dist/harbor/catalogue.js +0 -109
- package/dist/harbor/dock.js +0 -236
- package/dist/harbor/harbor.d.ts +0 -45
- package/dist/harbor/harbor.js +0 -347
- package/dist/harbor/index.d.ts +0 -11
- package/dist/harbor/probe.d.ts +0 -18
- package/dist/harbor/probe.js +0 -15
- package/dist/harbor/registry.d.ts +0 -10
- package/dist/harbor/relay.d.ts +0 -15
- package/dist/harbor/relay.js +0 -406
- package/dist/harbor/root-line.d.ts +0 -9
- package/dist/harbor/root-line.js +0 -38
- package/dist/harbor/store.d.ts +0 -13
- package/dist/harbor/store.js +0 -53
- package/dist/http/index.d.ts +0 -4
- package/dist/line/ground.js +0 -9
- package/dist/line/index.d.ts +0 -5
- package/dist/line/index.js +0 -9
- package/dist/line/push.d.ts +0 -7
- package/dist/line/push.js +0 -92
- package/dist/line/web.d.ts +0 -30
- package/dist/node/index.js +0 -236
- package/dist/pointer/bodies.js +0 -80
- package/dist/pointer/index.d.ts +0 -2
- package/dist/proof/index.d.ts +0 -3
- package/dist/proof/law.d.ts +0 -90
- package/dist/proof/law.js +0 -591
- package/dist/tcp/frame.d.ts +0 -25
- package/dist/tcp/frame.js +0 -64
- package/dist/ward/index.d.ts +0 -6
- package/dist/ward/index.js +0 -8
- package/dist/ward/pilot.d.ts +0 -8
- package/dist/ward/pilot.js +0 -50
- package/dist/ward/ward-being.js +0 -82
- package/dist/ward/ward.js +0 -290
- package/src/cli/main.ts +0 -13
- package/src/crypto/subtle.ts +0 -33
- package/src/crypto/x25519.ts +0 -21
- package/src/edge/index.ts +0 -490
- package/src/harbor/carrying.ts +0 -56
- package/src/harbor/catalogue.ts +0 -134
- package/src/harbor/dock.ts +0 -265
- package/src/harbor/harbor.ts +0 -381
- package/src/harbor/index.ts +0 -14
- package/src/harbor/probe.ts +0 -34
- package/src/harbor/relay.ts +0 -418
- package/src/harbor/root-line.ts +0 -39
- package/src/harbor/store.ts +0 -69
- package/src/line/ground.ts +0 -19
- package/src/line/index.ts +0 -9
- package/src/line/push.ts +0 -112
- package/src/node/index.ts +0 -241
- package/src/pointer/bodies.ts +0 -82
- package/src/pointer/index.ts +0 -4
- package/src/proof/law.ts +0 -591
- package/src/ward/index.ts +0 -8
- package/src/ward/pilot.ts +0 -50
- package/src/ward/ward-being.ts +0 -103
- package/src/ward/ward.ts +0 -328
- /package/dist/{cli/main.d.ts → cli.d.ts} +0 -0
- /package/dist/{being → core/being}/being.d.ts +0 -0
- /package/dist/{being → core/being}/digest.d.ts +0 -0
- /package/dist/{being → core/being}/digest.js +0 -0
- /package/dist/{being → core/being}/faculty.d.ts +0 -0
- /package/dist/{being → core/being}/types.d.ts +0 -0
- /package/dist/{being → core/being}/words.d.ts +0 -0
- /package/dist/{being → core/being}/words.js +0 -0
- /package/dist/{cli → core/cli}/edge.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/aes.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/aes.js +0 -0
- /package/dist/{crypto → core/crypto}/bytes.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/bytes.js +0 -0
- /package/dist/{crypto → core/crypto}/ed25519.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/hash.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/hash.js +0 -0
- /package/dist/{crypto → core/crypto}/index.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/index.js +0 -0
- /package/dist/{crypto → core/crypto}/json.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/json.js +0 -0
- /package/dist/{crypto → core/crypto}/mlkem.d.ts +0 -0
- /package/dist/{crypto → core/crypto}/mlkem.js +0 -0
- /package/dist/{crypto → core/crypto}/x25519.d.ts +0 -0
- /package/dist/{folder → core/folder}/index.d.ts +0 -0
- /package/dist/{folder → core/folder}/index.js +0 -0
- /package/dist/{http → core/http}/websocket.d.ts +0 -0
- /package/dist/{http → core/http}/websocket.js +0 -0
- /package/dist/{line → core/line}/answer.js +0 -0
- /package/dist/{line → core/line}/ground.d.ts +0 -0
- /package/dist/{proof → core/proof}/expect.d.ts +0 -0
- /package/dist/{proof → core/proof}/expect.js +0 -0
- /package/dist/{quo → core/quo}/address.d.ts +0 -0
- /package/dist/{quo → core/quo}/address.js +0 -0
- /package/dist/{quo → core/quo}/door.d.ts +0 -0
- /package/dist/{quo → core/quo}/door.js +0 -0
- /package/dist/{quo → core/quo}/index.d.ts +0 -0
- /package/dist/{quo → core/quo}/index.js +0 -0
- /package/dist/{quo → core/quo}/invitation.d.ts +0 -0
- /package/dist/{quo → core/quo}/invitation.js +0 -0
- /package/dist/{quo → core/quo}/keys.d.ts +0 -0
- /package/dist/{quo → core/quo}/keys.js +0 -0
- /package/dist/{quo → core/quo}/payload.d.ts +0 -0
- /package/dist/{quo → core/quo}/payload.js +0 -0
- /package/dist/{quo → core/quo}/relations.d.ts +0 -0
- /package/dist/{quo → core/quo}/relations.js +0 -0
- /package/dist/{quo → core/quo}/reply.d.ts +0 -0
- /package/dist/{quo → core/quo}/reply.js +0 -0
- /package/dist/{quo → core/quo}/seal.d.ts +0 -0
- /package/dist/{quo → core/quo}/seal.js +0 -0
- /package/dist/{quo → core/quo}/standing.d.ts +0 -0
- /package/dist/{quo → core/quo}/standing.js +0 -0
- /package/dist/{ward → core/ward}/allowance.d.ts +0 -0
- /package/dist/{ward → core/ward}/allowance.js +0 -0
- /package/dist/{ward → core/ward}/cells.d.ts +0 -0
- /package/dist/{ward → core/ward}/cells.js +0 -0
- /package/dist/{ward → core/ward}/partition.js +0 -0
- /package/src/{being → core/being}/digest.ts +0 -0
- /package/src/{being → core/being}/words.ts +0 -0
- /package/src/{crypto → core/crypto}/aes.ts +0 -0
- /package/src/{crypto → core/crypto}/bytes.ts +0 -0
- /package/src/{crypto → core/crypto}/hash.ts +0 -0
- /package/src/{crypto → core/crypto}/index.ts +0 -0
- /package/src/{crypto → core/crypto}/json.ts +0 -0
- /package/src/{crypto → core/crypto}/mlkem.ts +0 -0
- /package/src/{folder → core/folder}/index.ts +0 -0
- /package/src/{http → core/http}/websocket.ts +0 -0
- /package/src/{proof → core/proof}/expect.ts +0 -0
- /package/src/{quo → core/quo}/address.ts +0 -0
- /package/src/{quo → core/quo}/door.ts +0 -0
- /package/src/{quo → core/quo}/index.ts +0 -0
- /package/src/{quo → core/quo}/invitation.ts +0 -0
- /package/src/{quo → core/quo}/keys.ts +0 -0
- /package/src/{quo → core/quo}/payload.ts +0 -0
- /package/src/{quo → core/quo}/relations.ts +0 -0
- /package/src/{quo → core/quo}/reply.ts +0 -0
- /package/src/{quo → core/quo}/seal.ts +0 -0
- /package/src/{quo → core/quo}/standing.ts +0 -0
- /package/src/{stand → core/stand}/main.ts +0 -0
- /package/src/{ward → core/ward}/allowance.ts +0 -0
- /package/src/{ward → core/ward}/cells.ts +0 -0
|
@@ -0,0 +1,438 @@
|
|
|
1
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
2
|
+
// The harbor: the onion, unpacked from a terrain alone, in three levels.
|
|
3
|
+
// Each level stands the next and leaves it alone.
|
|
4
|
+
//
|
|
5
|
+
// L1, the boot, the harbor's own, the core alone
|
|
6
|
+
// the seed and the package the harbor's one secret, from custody,
|
|
7
|
+
// opens its sealed memory, the vault
|
|
8
|
+
// the box ward unpacked as every ward is, under the
|
|
9
|
+
// harbor's seed, no being standing yet
|
|
10
|
+
// the catalogue the core's registry, stood from the core
|
|
11
|
+
// on empty memory and from her row after;
|
|
12
|
+
// every module the commit `live` names is
|
|
13
|
+
// run through the terrain's loader
|
|
14
|
+
// the registries every box faculty the catalogue resolves
|
|
15
|
+
// to a registry, where her row names the
|
|
16
|
+
// catalogue as hers
|
|
17
|
+
// the dock the box ward's ward, of the class her row
|
|
18
|
+
// names through its registry, the default
|
|
19
|
+
// dock where it does not stand; the door is
|
|
20
|
+
// hers from here, and `open` returns
|
|
21
|
+
// L2, the dock's her `stand` ask: every other faculty, the
|
|
22
|
+
// routes, and every hosted ward, each ward
|
|
23
|
+
// standing on the class, the registry and
|
|
24
|
+
// the memory the dock keeps for it
|
|
25
|
+
// L3, each ward's beings born from her rows for the asks that
|
|
26
|
+
// reach them, and dropped after; nothing
|
|
27
|
+
// stands them
|
|
28
|
+
//
|
|
29
|
+
// L1 is one call and no ask can make it. After it the harbor takes asks
|
|
30
|
+
// alone. Whoever holds a harbor has five things of it and no other:
|
|
31
|
+
//
|
|
32
|
+
// Harbor.open(terrain?) the boot
|
|
33
|
+
// ask(request) the root line, a ward asked as its root
|
|
34
|
+
// arrive(pk, box) a Quo box at one of its doors
|
|
35
|
+
// holds(pk) whether one of its doors is that ward's
|
|
36
|
+
// close() every carrier asleep, and the ground let go
|
|
37
|
+
//
|
|
38
|
+
// What stands inside it, the wards, the dock, the catalogue and the
|
|
39
|
+
// carriers, is reached by an ask and never by a hand. The box ward's
|
|
40
|
+
// stance carries the harbor's `ground`, the one thing the dock, the
|
|
41
|
+
// catalogue and every faculty of the box are handed.
|
|
42
|
+
//
|
|
43
|
+
// The harbor fails only where the seed or the box ward's own place cannot
|
|
44
|
+
// be read, or the catalogue does not stand. A module, a registry, a
|
|
45
|
+
// faculty, a route, a hosted ward or a being that cannot stand fails
|
|
46
|
+
// alone, and the census names it.
|
|
47
|
+
//
|
|
48
|
+
// Genesis and wake are one path: on empty memory the box ward holds no
|
|
49
|
+
// catalogue, and the harbor writes her from the core; the root's asks
|
|
50
|
+
// write the rest, and nothing enters unasked.
|
|
51
|
+
import { isSilence, isWord, told } from '../being/index.js';
|
|
52
|
+
import { hex, isHex, unhex } from '../crypto/index.js';
|
|
53
|
+
import { unspecified, WardKey } from '../quo/index.js';
|
|
54
|
+
import { DOCK, House } from '../ward/index.js';
|
|
55
|
+
import { Catalogue, CATALOGUE } from './catalogue.js';
|
|
56
|
+
import { CarrierFaculty, UNDIALED } from './carrying.js';
|
|
57
|
+
import { BOX, Dock, hostable } from './dock.js';
|
|
58
|
+
import { Dna } from './dna.js';
|
|
59
|
+
import { Package } from './package.js';
|
|
60
|
+
import { MemoryFaculty } from './memory.js';
|
|
61
|
+
import { registers, RegistryFaculty } from './registry.js';
|
|
62
|
+
import { probeGround } from './probe.js';
|
|
63
|
+
import { readRootRequest } from './root-line.js';
|
|
64
|
+
import { Terrain } from './terrain.js';
|
|
65
|
+
// The box ward's ward is a dock, the terrain's default at genesis and
|
|
66
|
+
// while her row's kind does not resolve.
|
|
67
|
+
const boxWard = ({ dock }) => ({ genesis: dock.kind, contract: 'dock', fits: (C) => Dock.fulfils(C), fallback: dock });
|
|
68
|
+
// A hosted ward's ward is a ward and no dock, of the kind `host` named or
|
|
69
|
+
// the terrain's default at genesis.
|
|
70
|
+
const hostedWard = ({ ward }, kind = ward.kind) => ({ genesis: kind, contract: 'hosted ward', fits: hostable });
|
|
71
|
+
export class Harbor {
|
|
72
|
+
#terrain;
|
|
73
|
+
#package;
|
|
74
|
+
#wards = new Map();
|
|
75
|
+
#failed = { wards: {}, routes: {} };
|
|
76
|
+
#ground;
|
|
77
|
+
// Every ward speaks through the harbor: a pk of one of its doors goes to
|
|
78
|
+
// that door, any other along its route or to the terrain's carrier.
|
|
79
|
+
#carrier = { carry: (pk, bytes) => this.#carry(pk, bytes) };
|
|
80
|
+
// Every class a row names, through the registry faculty of the box the
|
|
81
|
+
// row names, or the catalogue.
|
|
82
|
+
#classes = { classOf: (kind, registry) => this.#classOf(kind, registry) };
|
|
83
|
+
constructor(terrain, pack) {
|
|
84
|
+
const { dock, ward, classes } = terrain.defaults;
|
|
85
|
+
if (!Dock.fulfils(dock))
|
|
86
|
+
throw new Error('the default dock is no dock');
|
|
87
|
+
if (!hostable(ward))
|
|
88
|
+
throw new Error('the default ward is no hosted ward');
|
|
89
|
+
this.#terrain = terrain;
|
|
90
|
+
this.#package = pack;
|
|
91
|
+
const dna = new Dna(terrain.memory, pack);
|
|
92
|
+
// The kit's classes the catalogue resolves: her own, the core's alone,
|
|
93
|
+
// then the defaults the terrain hands in.
|
|
94
|
+
const kit = [Catalogue, dock, ward, ...classes];
|
|
95
|
+
this.#ground = {
|
|
96
|
+
terrain,
|
|
97
|
+
dna,
|
|
98
|
+
kit,
|
|
99
|
+
foreground: terrain.foreground,
|
|
100
|
+
arrive: (pk, bytes) => this.arrive(pk, bytes),
|
|
101
|
+
host: (name, invitation, seed, memory, kind, registry) => this.#host(name, invitation, seed, memory, kind, registry),
|
|
102
|
+
stand: (hosted) => this.#stand(hosted),
|
|
103
|
+
move: (name, seed, from, to) => this.#move(name, seed, from, to),
|
|
104
|
+
release: async (name, memory) => this.#keeper(memory).forget(await this.#package.place(name)),
|
|
105
|
+
route: (pk, at) => this.#route(pk, at),
|
|
106
|
+
reached: (pk, at) => {
|
|
107
|
+
if (!this.#dialable(at))
|
|
108
|
+
this.#failed.routes[pk] = 'no carrier dials it';
|
|
109
|
+
},
|
|
110
|
+
keep: () => this.#box.partition.kept(),
|
|
111
|
+
failures: () => this.#failures(),
|
|
112
|
+
sweep: () => this.#sweep(),
|
|
113
|
+
awaken: async (key) => {
|
|
114
|
+
const being = this.#box.being(key);
|
|
115
|
+
if (being instanceof CarrierFaculty)
|
|
116
|
+
await being.awake();
|
|
117
|
+
},
|
|
118
|
+
rouse: async (key) => {
|
|
119
|
+
if (terrain.wakes)
|
|
120
|
+
await this.#ground.awaken(key);
|
|
121
|
+
},
|
|
122
|
+
lull: async (key) => {
|
|
123
|
+
const being = this.#box.being(key);
|
|
124
|
+
if (being instanceof CarrierFaculty)
|
|
125
|
+
await being.sleep();
|
|
126
|
+
},
|
|
127
|
+
listening: () => this.#carriers.flatMap((carrier) => carrier.listening()),
|
|
128
|
+
heard: async () => {
|
|
129
|
+
await Promise.all(this.#carriers.map((carrier) => carrier.heard()));
|
|
130
|
+
},
|
|
131
|
+
ran: () => {
|
|
132
|
+
for (const house of this.#wards.values())
|
|
133
|
+
house.renew();
|
|
134
|
+
return Promise.resolve();
|
|
135
|
+
},
|
|
136
|
+
stands: (kinds) => [...this.#wards.values()].some((house) => Object.values(house.partition.beings).some((row) => kinds.includes(row.class))),
|
|
137
|
+
kept: () => [...new Set([...this.#wards.values()].flatMap((house) => Object.values(house.partition.beings).map((row) => row.class)))],
|
|
138
|
+
};
|
|
139
|
+
}
|
|
140
|
+
// A harbor on the terrain handed in, or, with none, on the ground the
|
|
141
|
+
// probe finds here. A ground another run holds refuses, and what the
|
|
142
|
+
// ground serves beside the harbor stands once it is whole.
|
|
143
|
+
static async open(from = {}) {
|
|
144
|
+
const terrain = from instanceof Terrain ? from : probeGround(from).terrain;
|
|
145
|
+
await terrain.claim();
|
|
146
|
+
let harbor;
|
|
147
|
+
try {
|
|
148
|
+
harbor = await Harbor.#boot(terrain);
|
|
149
|
+
}
|
|
150
|
+
catch (e) {
|
|
151
|
+
await terrain.release();
|
|
152
|
+
throw e;
|
|
153
|
+
}
|
|
154
|
+
try {
|
|
155
|
+
await terrain.stand(harbor);
|
|
156
|
+
}
|
|
157
|
+
catch (e) {
|
|
158
|
+
await harbor.close();
|
|
159
|
+
throw e;
|
|
160
|
+
}
|
|
161
|
+
return harbor;
|
|
162
|
+
}
|
|
163
|
+
// L1, the one call no ask makes, ending with the door handed to the dock.
|
|
164
|
+
// What stands beyond it stands because someone asked `stand`.
|
|
165
|
+
static async #boot(terrain) {
|
|
166
|
+
const seed = await terrain.custody.seed();
|
|
167
|
+
const harbor = new Harbor(terrain, await Package.open(terrain.memory, terrain.entropy, seed));
|
|
168
|
+
const box = await harbor.#unpack(BOX, seed, { ward: boxWard(terrain.defaults), carries: { ground: harbor.#ground }, classes: harbor.#classes, stands: true });
|
|
169
|
+
if (box.partition.being(CATALOGUE))
|
|
170
|
+
box.stand(CATALOGUE);
|
|
171
|
+
else if ((await box.make(CATALOGUE, Catalogue.kind)) !== 'booted' || !(await box.partition.kept()))
|
|
172
|
+
throw new Error('the catalogue did not stand');
|
|
173
|
+
const catalogue = box.being(CATALOGUE);
|
|
174
|
+
if (!(catalogue instanceof Catalogue))
|
|
175
|
+
throw new Error('the catalogue did not stand');
|
|
176
|
+
await catalogue.wake();
|
|
177
|
+
for (const [key, row] of Object.entries(box.partition.beings)) {
|
|
178
|
+
if (row.registry === undefined && registers(catalogue.classOf(row.class)))
|
|
179
|
+
box.stand(key);
|
|
180
|
+
}
|
|
181
|
+
await box.standWard();
|
|
182
|
+
return harbor;
|
|
183
|
+
}
|
|
184
|
+
// The root line: one request, `{ ward?, method?, args? }`, asked of the
|
|
185
|
+
// box ward or the hosted ward named as its root, and one plain JSON
|
|
186
|
+
// answer, whatever front carried it.
|
|
187
|
+
//
|
|
188
|
+
// { answer } what the ward said
|
|
189
|
+
// { silence: true } she said nothing
|
|
190
|
+
// { word } a kit word: unreached, late, ...
|
|
191
|
+
// { error } the request was none, or names no ward that
|
|
192
|
+
// stands, with the reason one did not
|
|
193
|
+
async ask(value) {
|
|
194
|
+
const request = readRootRequest(value);
|
|
195
|
+
if (request === null)
|
|
196
|
+
return { error: 'not a root request' };
|
|
197
|
+
const ward = request.ward === undefined ? this.#box : this.#wards.get(request.ward);
|
|
198
|
+
if (ward === undefined) {
|
|
199
|
+
const failed = this.#failures().wards[request.ward];
|
|
200
|
+
return failed === undefined ? { error: 'no such ward' } : { error: 'the ward did not stand', reason: failed };
|
|
201
|
+
}
|
|
202
|
+
const out = await ward.root(request.method, request.args);
|
|
203
|
+
if (isSilence(out))
|
|
204
|
+
return { silence: true };
|
|
205
|
+
if (isWord(out))
|
|
206
|
+
return { word: told(out) };
|
|
207
|
+
return { answer: out };
|
|
208
|
+
}
|
|
209
|
+
// Bytes for one of this harbor's doors, or for a ward a relay of this
|
|
210
|
+
// harbor answers for, or nothing.
|
|
211
|
+
async arrive(pk, bytes) {
|
|
212
|
+
const ward = this.#door(pk);
|
|
213
|
+
if (ward)
|
|
214
|
+
return (await ward.door.arrive(bytes)).bytes;
|
|
215
|
+
return (await this.#relaying(pk)?.relay(pk, bytes)) ?? null;
|
|
216
|
+
}
|
|
217
|
+
// Whether one of this harbor's doors is that ward's.
|
|
218
|
+
holds(pk) {
|
|
219
|
+
return this.#door(pk) !== undefined;
|
|
220
|
+
}
|
|
221
|
+
// Every carrier asleep, the last opened first: nothing listens and no
|
|
222
|
+
// line stays open.
|
|
223
|
+
async close() {
|
|
224
|
+
for (const carrier of this.#carriers.reverse())
|
|
225
|
+
await carrier.sleep();
|
|
226
|
+
await this.#terrain.release();
|
|
227
|
+
}
|
|
228
|
+
get #box() {
|
|
229
|
+
return this.#wards.get(BOX);
|
|
230
|
+
}
|
|
231
|
+
get #dock() {
|
|
232
|
+
return this.#box.ward;
|
|
233
|
+
}
|
|
234
|
+
// A kind, through the registry faculty of the box named, or the
|
|
235
|
+
// catalogue. The catalogue's own kind is the core's, and resolves before
|
|
236
|
+
// any registry stands.
|
|
237
|
+
#classOf(kind, registry = CATALOGUE) {
|
|
238
|
+
if (kind === Catalogue.kind)
|
|
239
|
+
return Catalogue;
|
|
240
|
+
const found = this.#wards.get(BOX)?.being(registry);
|
|
241
|
+
return found instanceof RegistryFaculty ? found.classOf(kind) : undefined;
|
|
242
|
+
}
|
|
243
|
+
// The classes of a hosted ward, every one through the registry the dock
|
|
244
|
+
// keeps for it.
|
|
245
|
+
#through(registry) {
|
|
246
|
+
return { classOf: (kind) => this.#classOf(kind, registry) };
|
|
247
|
+
}
|
|
248
|
+
// A hosted ward standing, as the dock's cells name it.
|
|
249
|
+
async #stand(hosted) {
|
|
250
|
+
const fresh = !this.#wards.has(hosted.ward);
|
|
251
|
+
try {
|
|
252
|
+
if (fresh)
|
|
253
|
+
await this.#unpack(hosted.ward, unhex(hosted.seed), { ward: hostedWard(this.#terrain.defaults), classes: this.#through(hosted.registry) }, this.#keeper(hosted.memory));
|
|
254
|
+
await this.#wards.get(hosted.ward).standWard();
|
|
255
|
+
delete this.#failed.wards[hosted.ward];
|
|
256
|
+
return fresh;
|
|
257
|
+
}
|
|
258
|
+
catch (e) {
|
|
259
|
+
this.#wards.delete(hosted.ward);
|
|
260
|
+
this.#failed.wards[hosted.ward] = e instanceof Error ? e.message : String(e);
|
|
261
|
+
return false;
|
|
262
|
+
}
|
|
263
|
+
}
|
|
264
|
+
// Every place of the root memory and of each memory faculty that the
|
|
265
|
+
// dock does not name there, gone. A crash inside `host` or `move` leaves
|
|
266
|
+
// such a place, sealed under a seed nothing kept or kept elsewhere, and
|
|
267
|
+
// nothing else writes one. A place a memory faculty keeps in the root
|
|
268
|
+
// memory is the memory faculty's.
|
|
269
|
+
async #sweep() {
|
|
270
|
+
const named = async (memory) => {
|
|
271
|
+
const wards = this.#dock.hosted.filter((h) => h.memory === memory).map((h) => h.ward);
|
|
272
|
+
return new Set(await Promise.all((memory === undefined ? [BOX, ...wards] : wards).map((name) => this.#package.place(name))));
|
|
273
|
+
};
|
|
274
|
+
const memories = this.#memories();
|
|
275
|
+
const swept = [];
|
|
276
|
+
const root = await named(undefined);
|
|
277
|
+
for (const place of await this.#terrain.memory.places()) {
|
|
278
|
+
if (root.has(place) || Dna.occupies(place) || memories.some(([, s]) => s.occupies(place)))
|
|
279
|
+
continue;
|
|
280
|
+
await this.#terrain.memory.forget(place);
|
|
281
|
+
swept.push(place);
|
|
282
|
+
}
|
|
283
|
+
for (const [key, memory] of memories) {
|
|
284
|
+
const mine = await named(key);
|
|
285
|
+
for (const place of await memory.places()) {
|
|
286
|
+
if (mine.has(place))
|
|
287
|
+
continue;
|
|
288
|
+
await memory.forget(place);
|
|
289
|
+
swept.push(place);
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
return swept;
|
|
293
|
+
}
|
|
294
|
+
// A standing ward, carried whole to another keeper. The ward leaves the
|
|
295
|
+
// harbor's doors while it moves, so no arrival lands on the keeper it
|
|
296
|
+
// leaves.
|
|
297
|
+
async #move(name, seed, from, to) {
|
|
298
|
+
const ward = this.#wards.get(name);
|
|
299
|
+
if (!ward)
|
|
300
|
+
return 'the ward does not stand';
|
|
301
|
+
const source = this.#keeper(from);
|
|
302
|
+
const target = this.#keeper(to);
|
|
303
|
+
this.#wards.delete(name);
|
|
304
|
+
try {
|
|
305
|
+
if (!(await ward.partition.kept()))
|
|
306
|
+
throw new Error('the ward was not kept');
|
|
307
|
+
const place = await this.#package.place(name);
|
|
308
|
+
const entries = new Map(await source.read(place));
|
|
309
|
+
for (const entry of (await target.read(place)).keys())
|
|
310
|
+
if (!entries.has(entry))
|
|
311
|
+
entries.set(entry, null);
|
|
312
|
+
await target.write(place, entries);
|
|
313
|
+
const registry = this.#dock.hosted.find((h) => h.ward === name)?.registry;
|
|
314
|
+
const moved = await this.#unpack(name, unhex(seed), { ward: hostedWard(this.#terrain.defaults), classes: this.#through(registry) }, target);
|
|
315
|
+
await moved.standWard();
|
|
316
|
+
return null;
|
|
317
|
+
}
|
|
318
|
+
catch (e) {
|
|
319
|
+
this.#wards.set(name, ward);
|
|
320
|
+
return e instanceof Error ? e.message : String(e);
|
|
321
|
+
}
|
|
322
|
+
}
|
|
323
|
+
// The root memory, or the memory faculty standing under the key named.
|
|
324
|
+
#keeper(memory) {
|
|
325
|
+
if (memory === undefined)
|
|
326
|
+
return this.#terrain.memory;
|
|
327
|
+
const being = this.#box.being(memory);
|
|
328
|
+
if (being instanceof MemoryFaculty)
|
|
329
|
+
return being;
|
|
330
|
+
throw new Error(`the memory faculty ${memory} does not stand`);
|
|
331
|
+
}
|
|
332
|
+
#memories() {
|
|
333
|
+
return Object.keys(this.#box.partition.beings).flatMap((key) => {
|
|
334
|
+
const being = this.#box.being(key);
|
|
335
|
+
return being instanceof MemoryFaculty ? [[key, being]] : [];
|
|
336
|
+
});
|
|
337
|
+
}
|
|
338
|
+
// What did not stand when the harbor opened, each alone, and why the box
|
|
339
|
+
// ward stands the default dock where her row names another.
|
|
340
|
+
#failures() {
|
|
341
|
+
const fault = this.#box.fault;
|
|
342
|
+
return { wards: { ...this.#failed.wards, ...(fault === null ? {} : { [BOX]: fault }) }, routes: { ...this.#failed.routes } };
|
|
343
|
+
}
|
|
344
|
+
// This harbor's own doors and relays first, then a route's addresses in
|
|
345
|
+
// order, each to the carrier that dials it, and with no route the
|
|
346
|
+
// terrain's carrier.
|
|
347
|
+
async #carry(pk, bytes) {
|
|
348
|
+
if (this.holds(pk) || this.#relaying(pk))
|
|
349
|
+
return this.arrive(pk, bytes);
|
|
350
|
+
const at = this.#dock.routes[pk];
|
|
351
|
+
if (at === undefined)
|
|
352
|
+
return this.#terrain.carrier.carry(pk, bytes);
|
|
353
|
+
for (const address of at) {
|
|
354
|
+
const carrier = this.#carriers.find((c) => c.accepts(address));
|
|
355
|
+
const out = carrier ? await carrier.dial(address, pk, bytes) : UNDIALED;
|
|
356
|
+
if (out !== UNDIALED)
|
|
357
|
+
return out;
|
|
358
|
+
}
|
|
359
|
+
return null;
|
|
360
|
+
}
|
|
361
|
+
// A ward the dock hosts stands now, under the seed named or a drawn one,
|
|
362
|
+
// and the seed it stands under comes back. A ward whose key another ward
|
|
363
|
+
// of this harbor already has does not stand.
|
|
364
|
+
async #host(name, invitation, seed, memory, kind, registry) {
|
|
365
|
+
if (this.#wards.has(name))
|
|
366
|
+
return null;
|
|
367
|
+
const bytes = seed === undefined ? this.#terrain.entropy.draw(32) : isHex(seed, 32) ? unhex(seed) : null;
|
|
368
|
+
if (bytes === null || this.holds((await WardKey.from(bytes)).pk))
|
|
369
|
+
return null;
|
|
370
|
+
let house;
|
|
371
|
+
try {
|
|
372
|
+
house = await this.#unpack(name, bytes, { dock: invitation, ward: hostedWard(this.#terrain.defaults, kind), classes: this.#through(registry) }, this.#keeper(memory));
|
|
373
|
+
await house.standWard();
|
|
374
|
+
}
|
|
375
|
+
catch {
|
|
376
|
+
this.#wards.delete(name);
|
|
377
|
+
return null;
|
|
378
|
+
}
|
|
379
|
+
if (!house.ward.stance.standings.get(DOCK)) {
|
|
380
|
+
this.#wards.delete(name);
|
|
381
|
+
return null;
|
|
382
|
+
}
|
|
383
|
+
return hex(bytes);
|
|
384
|
+
}
|
|
385
|
+
// A route is taken where a carrier of this harbor dials one of its
|
|
386
|
+
// addresses; forgetting one always is.
|
|
387
|
+
#route(pk, at) {
|
|
388
|
+
const taken = isHex(pk, 64) && (at === null || this.#dialable(at));
|
|
389
|
+
if (taken)
|
|
390
|
+
delete this.#failed.routes[pk];
|
|
391
|
+
return taken;
|
|
392
|
+
}
|
|
393
|
+
// The carrier faculties standing in the box ward.
|
|
394
|
+
get #carriers() {
|
|
395
|
+
return Object.keys(this.#box.partition.beings)
|
|
396
|
+
.map((key) => this.#box.being(key))
|
|
397
|
+
.filter((being) => being instanceof CarrierFaculty);
|
|
398
|
+
}
|
|
399
|
+
#relaying(pk) {
|
|
400
|
+
return this.#carriers.find((carrier) => carrier.relays(pk));
|
|
401
|
+
}
|
|
402
|
+
#dialable(at) {
|
|
403
|
+
return at.some((address) => this.#carriers.some((carrier) => carrier.accepts(address)));
|
|
404
|
+
}
|
|
405
|
+
async #unpack(name, seed, own, keeper) {
|
|
406
|
+
const { entropy, clock } = this.#terrain;
|
|
407
|
+
const ward = await House.unpack({
|
|
408
|
+
seed,
|
|
409
|
+
memory: await this.#package.rows(name, keeper),
|
|
410
|
+
entropy,
|
|
411
|
+
clock,
|
|
412
|
+
carrier: this.#carrier,
|
|
413
|
+
routes: this.#routes,
|
|
414
|
+
...own,
|
|
415
|
+
});
|
|
416
|
+
this.#wards.set(name, ward);
|
|
417
|
+
return ward;
|
|
418
|
+
}
|
|
419
|
+
// Every ward is reached where the harbor is: where the root's `reach`
|
|
420
|
+
// says, and where it said nothing, where its carriers listen, save the
|
|
421
|
+
// unspecified host. What a ward learns from an invitation's `at` is the
|
|
422
|
+
// dock's to keep. A ward of this harbor needs no route.
|
|
423
|
+
#routes = {
|
|
424
|
+
reach: () => {
|
|
425
|
+
if (!this.#wards.has(BOX))
|
|
426
|
+
return [];
|
|
427
|
+
const set = this.#dock.addresses;
|
|
428
|
+
return set.length > 0 ? set : this.#carriers.flatMap((carrier) => carrier.listening()).filter((address) => !unspecified(address));
|
|
429
|
+
},
|
|
430
|
+
learn: (ward, at) => (this.holds(ward) ? Promise.resolve() : this.#dock.learn(ward, at)),
|
|
431
|
+
};
|
|
432
|
+
#door(pk) {
|
|
433
|
+
for (const ward of this.#wards.values())
|
|
434
|
+
if (ward.pk === pk)
|
|
435
|
+
return ward;
|
|
436
|
+
return undefined;
|
|
437
|
+
}
|
|
438
|
+
}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export { Catalogue, CATALOGUE, type Cataloguing } from './catalogue.ts';
|
|
2
|
+
export { Dna } from './dna.ts';
|
|
3
|
+
export { BOX, Dock, type DockStance, type Failures, type Hosted, type Hosting } from './dock.ts';
|
|
4
|
+
export { CarrierFaculty, carrierIn, groundOf, UNDIALED, type Arrivals, type Dialed, type Ground, type Sockets, type TcpListening, type WebListen, type WebListener, type WebServe } from './carrying.ts';
|
|
5
|
+
export { Harbor } from './harbor.ts';
|
|
6
|
+
export { carryPlaces, copyPackage, landPlaces, Package, readCarried, type Carried } from './package.ts';
|
|
7
|
+
export { readRootRequest, type RootRequest } from './root-line.ts';
|
|
8
|
+
export { addGround, grounds, probeGround, type GroundProbe, type KnownGround, type Probing } from './probe.ts';
|
|
9
|
+
export { registers, Registry, REGISTRY, RegistryFaculty } from './registry.ts';
|
|
10
|
+
export { MEMORY, MemoryFaculty } from './memory.ts';
|
|
11
|
+
export { Terrain, type Defaults } from './terrain.ts';
|
|
@@ -2,13 +2,13 @@
|
|
|
2
2
|
// The onion: a terrain, the package, the dock, the catalogue and its
|
|
3
3
|
// registry, and the harbor.
|
|
4
4
|
export { Catalogue, CATALOGUE } from './catalogue.js';
|
|
5
|
+
export { Dna } from './dna.js';
|
|
5
6
|
export { BOX, Dock } from './dock.js';
|
|
6
|
-
export { CarrierFaculty, UNDIALED } from './carrying.js';
|
|
7
|
+
export { CarrierFaculty, carrierIn, groundOf, UNDIALED } from './carrying.js';
|
|
7
8
|
export { Harbor } from './harbor.js';
|
|
8
9
|
export { carryPlaces, copyPackage, landPlaces, Package, readCarried } from './package.js';
|
|
9
|
-
export { readRootRequest
|
|
10
|
+
export { readRootRequest } from './root-line.js';
|
|
10
11
|
export { addGround, grounds, probeGround } from './probe.js';
|
|
11
|
-
export { Registry } from './registry.js';
|
|
12
|
-
export {
|
|
13
|
-
export { GROUND_STORE, groundStore, Store, STORE } from './store.js';
|
|
12
|
+
export { registers, Registry, REGISTRY, RegistryFaculty } from './registry.js';
|
|
13
|
+
export { MEMORY, MemoryFaculty } from './memory.js';
|
|
14
14
|
export { Terrain } from './terrain.js';
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { Faculty } from '../being/index.ts';
|
|
2
|
+
export declare const MEMORY = "org.nervur.memory";
|
|
3
|
+
export declare abstract class MemoryFaculty extends Faculty {
|
|
4
|
+
static readonly kind: string;
|
|
5
|
+
abstract read(place: string): Promise<Map<string, Uint8Array>>;
|
|
6
|
+
abstract write(place: string, entries: ReadonlyMap<string, Uint8Array | null>): Promise<void>;
|
|
7
|
+
abstract places(): Promise<string[]>;
|
|
8
|
+
abstract forget(place: string): Promise<void>;
|
|
9
|
+
occupies(_place: string): boolean;
|
|
10
|
+
}
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
// SPDX-License-Identifier: Apache-2.0
|
|
2
|
+
// The memory faculty: a faculty that keeps a hosted ward's place, where the
|
|
3
|
+
// root memory does not. It makes the same promise the Memory body makes,
|
|
4
|
+
// lent once the dock stands: sealed entries in places, each keep whole or
|
|
5
|
+
// not at all. The box ward never moves off the root memory, since the
|
|
6
|
+
// memory faculty itself stands from the box ward's cells.
|
|
7
|
+
//
|
|
8
|
+
// A ward is the unit a memory faculty holds: its head, its ward and every
|
|
9
|
+
// being of it are one place and one keep, so an answer's cells and the
|
|
10
|
+
// door's keys move together, whichever memory faculty keeps them. A memory
|
|
11
|
+
// faculty of a disk, a cloud, a database or a ledger is a class fulfilling
|
|
12
|
+
// `org.nervur.memory`.
|
|
13
|
+
import { Faculty, ships } from '../being/index.js';
|
|
14
|
+
export const MEMORY = 'org.nervur.memory';
|
|
15
|
+
export class MemoryFaculty extends Faculty {
|
|
16
|
+
static kind = MEMORY;
|
|
17
|
+
static {
|
|
18
|
+
ships(this);
|
|
19
|
+
}
|
|
20
|
+
// Whether a place of the root memory is this memory faculty's own, so the root's
|
|
21
|
+
// sweep leaves it.
|
|
22
|
+
occupies(_place) {
|
|
23
|
+
return false;
|
|
24
|
+
}
|
|
25
|
+
}
|
|
@@ -3,7 +3,6 @@ export declare const copyPackage: (from: Memory, to: Memory) => Promise<string[]
|
|
|
3
3
|
export type Carried = {
|
|
4
4
|
seed?: string;
|
|
5
5
|
places: Record<string, Record<string, string>>;
|
|
6
|
-
modules?: Record<string, string>;
|
|
7
6
|
};
|
|
8
7
|
export declare const readCarried: (value: unknown) => Carried | null;
|
|
9
8
|
export declare const carryPlaces: (memory: Memory) => Promise<Carried['places']>;
|
|
@@ -30,12 +30,9 @@ export const copyPackage = async (from, to) => {
|
|
|
30
30
|
export const readCarried = (value) => {
|
|
31
31
|
if (typeof value !== 'object' || value === null)
|
|
32
32
|
return null;
|
|
33
|
-
const { seed, places
|
|
33
|
+
const { seed, places } = value;
|
|
34
34
|
if (seed !== undefined && !isHex(seed, 32))
|
|
35
35
|
return null;
|
|
36
|
-
const hints = modules === undefined || (typeof modules === 'object' && modules !== null && !Array.isArray(modules) && Object.values(modules).every((m) => typeof m === 'string'));
|
|
37
|
-
if (!hints)
|
|
38
|
-
return null;
|
|
39
36
|
if (typeof places !== 'object' || places === null || Array.isArray(places))
|
|
40
37
|
return null;
|
|
41
38
|
for (const entries of Object.values(places)) {
|
|
@@ -45,7 +42,7 @@ export const readCarried = (value) => {
|
|
|
45
42
|
if (!isHex(bytes))
|
|
46
43
|
return null;
|
|
47
44
|
}
|
|
48
|
-
return { ...(seed === undefined ? {} : { seed }), places: places
|
|
45
|
+
return { ...(seed === undefined ? {} : { seed }), places: places };
|
|
49
46
|
};
|
|
50
47
|
// Every place of a memory, as a carried harbor holds it.
|
|
51
48
|
export const carryPlaces = async (memory) => {
|
|
@@ -77,7 +74,8 @@ class PackageRows {
|
|
|
77
74
|
this.#told.add(row);
|
|
78
75
|
}
|
|
79
76
|
// Every row told since the last keep, sealed and written as one keep, one
|
|
80
|
-
// keep at a time.
|
|
77
|
+
// keep at a time. Where nothing was told, nothing is written, so an ask
|
|
78
|
+
// that only reads keeps even where the keeper refuses every write.
|
|
81
79
|
kept() {
|
|
82
80
|
const rows = [...this.#told];
|
|
83
81
|
this.#told.clear();
|
|
@@ -85,6 +83,8 @@ class PackageRows {
|
|
|
85
83
|
return this.#line;
|
|
86
84
|
}
|
|
87
85
|
async #write(told) {
|
|
86
|
+
if (told.length === 0)
|
|
87
|
+
return true;
|
|
88
88
|
const beings = (this.rows.beings ?? {});
|
|
89
89
|
const entries = new Map();
|
|
90
90
|
for (const row of told) {
|
|
@@ -95,7 +95,7 @@ class PackageRows {
|
|
|
95
95
|
return true;
|
|
96
96
|
}
|
|
97
97
|
}
|
|
98
|
-
class
|
|
98
|
+
class WardPlace {
|
|
99
99
|
#pack;
|
|
100
100
|
#name;
|
|
101
101
|
#seal;
|
|
@@ -151,9 +151,9 @@ export class Package {
|
|
|
151
151
|
return this.derive(['place', name], 16).then(hex);
|
|
152
152
|
}
|
|
153
153
|
// One ward's rows, as its keeper kept them: the root memory unless a
|
|
154
|
-
//
|
|
154
|
+
// memory faculty is named.
|
|
155
155
|
async rows(name, keeper = this.memory) {
|
|
156
|
-
const ward = new
|
|
156
|
+
const ward = new WardPlace(this, name, await this.derive(['seal', name], 32), await this.place(name), keeper);
|
|
157
157
|
const rows = {};
|
|
158
158
|
const beings = {};
|
|
159
159
|
let any = false;
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import type { Bundled } from '../contract/index.ts';
|
|
2
|
+
import type { Defaults, Terrain } from './terrain.ts';
|
|
3
|
+
export type Probing = {
|
|
4
|
+
readonly where?: string;
|
|
5
|
+
readonly given?: unknown;
|
|
6
|
+
readonly bundle?: readonly Bundled[];
|
|
7
|
+
};
|
|
8
|
+
export type GroundProbe = {
|
|
9
|
+
readonly name: string;
|
|
10
|
+
fits(probing: Probing): boolean;
|
|
11
|
+
terrain(probing: Probing, defaults: Defaults): Terrain;
|
|
12
|
+
};
|
|
13
|
+
export type KnownGround = {
|
|
14
|
+
readonly probe: GroundProbe;
|
|
15
|
+
readonly defaults: Defaults;
|
|
16
|
+
};
|
|
17
|
+
export declare const addGround: (probe: GroundProbe, defaults: Defaults) => void;
|
|
18
|
+
export declare const grounds: () => string[];
|
|
19
|
+
export declare const probeGround: (probing: Probing, among?: readonly KnownGround[]) => {
|
|
20
|
+
ground: string;
|
|
21
|
+
terrain: Terrain;
|
|
22
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
const known = [];
|
|
2
|
+
// A ground this process can stand on, known once by its name.
|
|
3
|
+
export const addGround = (probe, defaults) => {
|
|
4
|
+
if (!known.some((k) => k.probe.name === probe.name))
|
|
5
|
+
known.push({ probe, defaults });
|
|
6
|
+
};
|
|
7
|
+
// The grounds known, in the order they are tried.
|
|
8
|
+
export const grounds = () => known.map((k) => k.probe.name).reverse();
|
|
9
|
+
// The terrain of the first ground that fits, and its name.
|
|
10
|
+
export const probeGround = (probing, among = known) => {
|
|
11
|
+
for (const { probe, defaults } of [...among].reverse())
|
|
12
|
+
if (probe.fits(probing))
|
|
13
|
+
return { ground: probe.name, terrain: probe.terrain(probing, defaults) };
|
|
14
|
+
throw new Error('no ground fits here');
|
|
15
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { Faculty, type BeingClass } from '../being/index.ts';
|
|
2
|
+
import type { Module } from '../contract/index.ts';
|
|
3
|
+
export declare const REGISTRY = "org.nervur.registry";
|
|
4
|
+
export declare abstract class RegistryFaculty extends Faculty {
|
|
5
|
+
static readonly kind: string;
|
|
6
|
+
abstract classOf(kind: string): BeingClass | undefined;
|
|
7
|
+
}
|
|
8
|
+
export declare const registers: (C: unknown) => C is typeof RegistryFaculty;
|
|
9
|
+
export declare class Registry {
|
|
10
|
+
#private;
|
|
11
|
+
constructor(kit: readonly BeingClass[], modules: readonly Module[]);
|
|
12
|
+
static refusal(kit: readonly BeingClass[], modules: readonly Module[]): string | null;
|
|
13
|
+
classOf(kind: string): BeingClass | undefined;
|
|
14
|
+
kindsOf(module: string): string[];
|
|
15
|
+
}
|