@livon/runtime 0.27.0-rc.3 → 0.27.0-rc.5
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/LICENCE.md +21 -0
- package/README.md +153 -5
- package/dist/index.cjs +60 -1
- package/dist/index.js +12 -1
- package/dist/mini/index.cjs +1 -0
- package/dist/mini/index.d.ts +8 -0
- package/dist/mini/index.js +1 -0
- package/dist/mini/runtime.cjs +1 -0
- package/dist/mini/runtime.d.ts +13 -0
- package/dist/mini/runtime.js +1 -0
- package/dist/mini/types.cjs +1 -0
- package/dist/mini/types.d.ts +143 -0
- package/dist/mini/types.js +0 -0
- package/dist/runtime.cjs +429 -1
- package/dist/runtime.js +385 -1
- package/dist/types.cjs +29 -1
- package/dist/types.js +4 -0
- package/package.json +11 -4
package/LICENCE.md
ADDED
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 LIVON contributors
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
CHANGED
|
@@ -1,8 +1,156 @@
|
|
|
1
1
|
# @livon/runtime
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
- https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime
|
|
3
|
+
## Install
|
|
5
4
|
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
5
|
+
```sh
|
|
6
|
+
pnpm add @livon/runtime
|
|
7
|
+
```
|
|
8
|
+
|
|
9
|
+
## Purpose
|
|
10
|
+
|
|
11
|
+
[@livon/runtime](https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime) is the event pipeline core. It composes modules and executes hook chains for:
|
|
12
|
+
|
|
13
|
+
- `onReceive`
|
|
14
|
+
- `onSend`
|
|
15
|
+
- `onError`
|
|
16
|
+
|
|
17
|
+
## Basic usage
|
|
18
|
+
|
|
19
|
+
```ts
|
|
20
|
+
import {runtime} from '@livon/runtime';
|
|
21
|
+
|
|
22
|
+
runtime(moduleA, moduleB);
|
|
23
|
+
```
|
|
24
|
+
|
|
25
|
+
## Parameters
|
|
26
|
+
|
|
27
|
+
`runtime(...modules)`:
|
|
28
|
+
|
|
29
|
+
- `modules` (`RuntimeModule[]`): ordered module list to register and execute.
|
|
30
|
+
|
|
31
|
+
`RuntimeModule`:
|
|
32
|
+
|
|
33
|
+
- `name` (`string`): module identifier for debugging and traceability.
|
|
34
|
+
- `register` (`(registry) => void`): setup callback where hooks are registered.
|
|
35
|
+
|
|
36
|
+
## Execution order (important)
|
|
37
|
+
|
|
38
|
+
Runtime module order defines execution order.
|
|
39
|
+
|
|
40
|
+
```ts
|
|
41
|
+
runtime(moduleA, moduleB, moduleC);
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Hook chains run from left to right:
|
|
45
|
+
|
|
46
|
+
1. `moduleA`
|
|
47
|
+
2. `moduleB`
|
|
48
|
+
3. `moduleC`
|
|
49
|
+
|
|
50
|
+
This applies to `onReceive`, `onSend`, and `onError` registration order.
|
|
51
|
+
|
|
52
|
+
## Writing a runtime module
|
|
53
|
+
|
|
54
|
+
```ts
|
|
55
|
+
import type {RuntimeModule} from '@livon/runtime';
|
|
56
|
+
|
|
57
|
+
const traceModule: RuntimeModule = {
|
|
58
|
+
name: 'trace',
|
|
59
|
+
register: ({onReceive, onSend, onError}) => {
|
|
60
|
+
onReceive(async (envelope, ctx, next) => {
|
|
61
|
+
return next();
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
onSend(async (envelope, ctx, next) => {
|
|
65
|
+
return next();
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
onError((error, envelope, ctx) => {
|
|
69
|
+
// error handling
|
|
70
|
+
});
|
|
71
|
+
},
|
|
72
|
+
};
|
|
73
|
+
```
|
|
74
|
+
|
|
75
|
+
### Hook callback parameters
|
|
76
|
+
|
|
77
|
+
`onReceive((envelope, ctx, next) => ...)` and `onSend((envelope, ctx, next) => ...)`:
|
|
78
|
+
|
|
79
|
+
- `envelope` (`EventEnvelope`): current event envelope flowing through the chain.
|
|
80
|
+
- `ctx` (`RuntimeContext`): emit APIs, room-scoped context, and shared runtime state.
|
|
81
|
+
- `next` (`(update?) => Promise<EventEnvelope>`): continue chain and optionally merge envelope updates.
|
|
82
|
+
|
|
83
|
+
`onError((error, envelope, ctx) => ...)`:
|
|
84
|
+
|
|
85
|
+
- `error` (`unknown`): thrown/normalized error from runtime chain.
|
|
86
|
+
- `envelope` (`EventEnvelope`): failed envelope snapshot.
|
|
87
|
+
- `ctx` (`RuntimeContext`): same runtime context for recovery/reporting logic.
|
|
88
|
+
|
|
89
|
+
## Runtime context model
|
|
90
|
+
|
|
91
|
+
`RuntimeContext` (`ctx` in hooks) is runtime control surface.
|
|
92
|
+
It is separate from `envelope.context` (event data flowing through the pipeline).
|
|
93
|
+
|
|
94
|
+
```mermaid
|
|
95
|
+
flowchart TD
|
|
96
|
+
Runtime["runtime(...)"] --> Ctx["RuntimeContext"]
|
|
97
|
+
Ctx --> EmitReceive["emitReceive(input)"]
|
|
98
|
+
Ctx --> EmitSend["emitSend(input)"]
|
|
99
|
+
Ctx --> EmitError["emitError(input)"]
|
|
100
|
+
Ctx --> EmitEvent["emitEvent(input)"]
|
|
101
|
+
Ctx --> Room["room(name) -> RuntimeContext"]
|
|
102
|
+
Ctx --> State["state.get/set shared map"]
|
|
103
|
+
EmitReceive --> Envelope["EventEnvelope"]
|
|
104
|
+
EmitSend --> Envelope
|
|
105
|
+
EmitError --> Envelope
|
|
106
|
+
EmitEvent --> Envelope
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
```mermaid
|
|
110
|
+
sequenceDiagram
|
|
111
|
+
participant M1 as moduleA
|
|
112
|
+
participant R as runtime
|
|
113
|
+
participant M2 as moduleB
|
|
114
|
+
|
|
115
|
+
M1->>R: next({ context: { traceId: "t-1" } })
|
|
116
|
+
R->>R: mergeContext(base, update)
|
|
117
|
+
R->>M2: onReceive(... envelope.context includes traceId)
|
|
118
|
+
M2->>R: throw { message, context: { phase: "auth" } }
|
|
119
|
+
R->>R: buildFailedEnvelope + mergeContext(error.context)
|
|
120
|
+
```
|
|
121
|
+
|
|
122
|
+
Rules:
|
|
123
|
+
|
|
124
|
+
- `ctx.room(name)` creates a room-scoped context that injects `metadata.room`.
|
|
125
|
+
- `ctx.state` is shared across room scopes for one runtime instance.
|
|
126
|
+
- `envelope.context` is immutable hook input; use `next(update)` to merge context changes.
|
|
127
|
+
|
|
128
|
+
## Emit APIs in runtime context
|
|
129
|
+
|
|
130
|
+
Inside hooks/modules you can emit:
|
|
131
|
+
|
|
132
|
+
- `ctx.emitReceive(...)`
|
|
133
|
+
- `ctx.emitSend(...)`
|
|
134
|
+
- `ctx.emitError(...)`
|
|
135
|
+
- `ctx.emitEvent(...)` (alias to send path)
|
|
136
|
+
|
|
137
|
+
You can also scope to rooms via `ctx.room(roomId)`.
|
|
138
|
+
|
|
139
|
+
### Emit input parameters
|
|
140
|
+
|
|
141
|
+
`emitReceive`, `emitSend`, `emitError`, `emitEvent` all accept one `EmitInput`:
|
|
142
|
+
|
|
143
|
+
- `event` (`string`, required): event name.
|
|
144
|
+
- `payload` (`Uint8Array`, required unless `error` is provided): transport payload.
|
|
145
|
+
- `error` (`EventError`, required unless `payload` is provided): error payload.
|
|
146
|
+
- `id` (`string`, optional): envelope id override.
|
|
147
|
+
- `status` (`'sending' | 'receiving' | 'failed'`, optional): explicit status override.
|
|
148
|
+
- `metadata` (`Record<string, unknown>`, optional): routing/correlation metadata.
|
|
149
|
+
- `context` (`RuntimeEventContext`, optional): module context object merged across pipeline.
|
|
150
|
+
|
|
151
|
+
## Related pages
|
|
152
|
+
|
|
153
|
+
- [Validated by Default](https://live-input-vector-output-node.github.io/livon-ts/docs/core/validated-by-default)
|
|
154
|
+
- [@livon/schema](https://live-input-vector-output-node.github.io/livon-ts/docs/packages/schema)
|
|
155
|
+
- [Runtime Design](https://live-input-vector-output-node.github.io/livon-ts/docs/technical/runtime-design)
|
|
156
|
+
- [Event Flow](https://live-input-vector-output-node.github.io/livon-ts/docs/technical/event-flow)
|
package/dist/index.cjs
CHANGED
|
@@ -1 +1,60 @@
|
|
|
1
|
-
"use strict";
|
|
1
|
+
"use strict";
|
|
2
|
+
const __rslib_import_meta_url__ = /*#__PURE__*/ (function () {
|
|
3
|
+
return typeof document === 'undefined'
|
|
4
|
+
? new (require('url'.replace('', '')).URL)('file:' + __filename).href
|
|
5
|
+
: (document.currentScript && document.currentScript.src) ||
|
|
6
|
+
new URL('main.js', document.baseURI).href;
|
|
7
|
+
})();
|
|
8
|
+
;
|
|
9
|
+
// The require scope
|
|
10
|
+
var __webpack_require__ = {};
|
|
11
|
+
|
|
12
|
+
// webpack/runtime/define_property_getters
|
|
13
|
+
(() => {
|
|
14
|
+
__webpack_require__.d = (exports, definition) => {
|
|
15
|
+
for(var key in definition) {
|
|
16
|
+
if(__webpack_require__.o(definition, key) && !__webpack_require__.o(exports, key)) {
|
|
17
|
+
Object.defineProperty(exports, key, { enumerable: true, get: definition[key] });
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
};
|
|
21
|
+
})();
|
|
22
|
+
// webpack/runtime/has_own_property
|
|
23
|
+
(() => {
|
|
24
|
+
__webpack_require__.o = (obj, prop) => (Object.prototype.hasOwnProperty.call(obj, prop))
|
|
25
|
+
})();
|
|
26
|
+
// webpack/runtime/make_namespace_object
|
|
27
|
+
(() => {
|
|
28
|
+
// define __esModule on exports
|
|
29
|
+
__webpack_require__.r = (exports) => {
|
|
30
|
+
if(typeof Symbol !== 'undefined' && Symbol.toStringTag) {
|
|
31
|
+
Object.defineProperty(exports, Symbol.toStringTag, { value: 'Module' });
|
|
32
|
+
}
|
|
33
|
+
Object.defineProperty(exports, '__esModule', { value: true });
|
|
34
|
+
};
|
|
35
|
+
})();
|
|
36
|
+
var __webpack_exports__ = {};
|
|
37
|
+
// ESM COMPAT FLAG
|
|
38
|
+
__webpack_require__.r(__webpack_exports__);
|
|
39
|
+
|
|
40
|
+
// EXPORTS
|
|
41
|
+
__webpack_require__.d(__webpack_exports__, {
|
|
42
|
+
runtime: () => (/* reexport */ external_runtime_cjs_namespaceObject.runtime)
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
;// CONCATENATED MODULE: external "./runtime.cjs"
|
|
46
|
+
const external_runtime_cjs_namespaceObject = require("./runtime.cjs");
|
|
47
|
+
;// CONCATENATED MODULE: ./src/index.ts
|
|
48
|
+
/**
|
|
49
|
+
* Public package entrypoint for `@livon/runtime`.
|
|
50
|
+
*
|
|
51
|
+
* @see https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime
|
|
52
|
+
*/
|
|
53
|
+
|
|
54
|
+
exports.runtime = __webpack_exports__.runtime;
|
|
55
|
+
for(var __rspack_i in __webpack_exports__) {
|
|
56
|
+
if(["runtime"].indexOf(__rspack_i) === -1) {
|
|
57
|
+
exports[__rspack_i] = __webpack_exports__[__rspack_i];
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
Object.defineProperty(exports, '__esModule', { value: true });
|
package/dist/index.js
CHANGED
|
@@ -1 +1,12 @@
|
|
|
1
|
-
import{runtime
|
|
1
|
+
import { runtime } from "./runtime.js";
|
|
2
|
+
|
|
3
|
+
;// CONCATENATED MODULE: external "./runtime.js"
|
|
4
|
+
|
|
5
|
+
;// CONCATENATED MODULE: ./src/index.ts
|
|
6
|
+
/**
|
|
7
|
+
* Public package entrypoint for `@livon/runtime`.
|
|
8
|
+
*
|
|
9
|
+
* @see https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime
|
|
10
|
+
*/
|
|
11
|
+
|
|
12
|
+
export { runtime };
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const __rslib_import_meta_url__="u"<typeof document?new(require("url".replace("",""))).URL("file:"+__filename).href:document.currentScript&&document.currentScript.src||new URL("main.js",document.baseURI).href;var __webpack_require__={};__webpack_require__.d=(e,_)=>{for(var r in _)__webpack_require__.o(_,r)&&!__webpack_require__.o(e,r)&&Object.defineProperty(e,r,{enumerable:!0,get:_[r]})},__webpack_require__.o=(e,_)=>Object.prototype.hasOwnProperty.call(e,_),__webpack_require__.r=e=>{"u">typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var __webpack_exports__={};__webpack_require__.r(__webpack_exports__),__webpack_require__.d(__webpack_exports__,{runtime:()=>external_runtime_cjs_namespaceObject.runtime});const external_runtime_cjs_namespaceObject=require("./runtime.cjs");for(var __rspack_i in exports.runtime=__webpack_exports__.runtime,__webpack_exports__)-1===["runtime"].indexOf(__rspack_i)&&(exports[__rspack_i]=__webpack_exports__[__rspack_i]);Object.defineProperty(exports,"__esModule",{value:!0});
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Public package entrypoint for `@livon/runtime`.
|
|
3
|
+
*
|
|
4
|
+
* @see https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime
|
|
5
|
+
*/
|
|
6
|
+
export { runtime } from './runtime.js';
|
|
7
|
+
export type { RuntimeEventContext, EventStatus, EventError, EventEnvelopeBase, EventEnvelopePayload, EventEnvelopeError, EventEnvelope, EventAck, EmitInputBase, EmitInputPayload, EmitInputError, EmitInput, EmitEvent, EmitReceive, EmitSend, EmitError, RoomSelector, StateGet, StateSet, RuntimeState, RuntimeContext, RuntimeHook, RuntimeModule, RuntimeOnError, RuntimeInput, RuntimeModuleRegister, RuntimeHookRegister, RuntimeOnErrorRegister, RuntimeHookSubscription, RuntimeUnsubscribe, RuntimeRegistry, RuntimeStart, PartialEventEnvelopeBase, PartialEventEnvelopePayload, PartialEventEnvelopeError, PartialEventEnvelopeEmpty, PartialEventEnvelope, } from './types.js';
|
|
8
|
+
export type { RuntimeStart as RuntimeFactory } from './types.js';
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
import{runtime as r}from"./runtime.js";export{r as runtime};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const __rslib_import_meta_url__="u"<typeof document?new(require("url".replace("",""))).URL("file:"+__filename).href:document.currentScript&&document.currentScript.src||new URL("main.js",document.baseURI).href;var __webpack_require__={};__webpack_require__.d=(e,r)=>{for(var t in r)__webpack_require__.o(r,t)&&!__webpack_require__.o(e,t)&&Object.defineProperty(e,t,{enumerable:!0,get:r[t]})},__webpack_require__.o=(e,r)=>Object.prototype.hasOwnProperty.call(e,r),__webpack_require__.r=e=>{"u">typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var __webpack_exports__={};__webpack_require__.r(__webpack_exports__),__webpack_require__.d(__webpack_exports__,{runtime:()=>runtime});const createHookStore=()=>({onReceive:[],onSend:[],onError:[]}),createState=()=>{let e=new Map;return{get:r=>e.get(r),set:(r,t)=>{e.set(r,t)}}},mergeMetadata=(e,r)=>{if(e||r)return{...e??{},...r??{}}};let fallbackEventIdCounter=0;const createEventId=()=>{let e=globalThis.crypto;return e?.randomUUID?e.randomUUID():(fallbackEventIdCounter+=1,`evt_${Date.now().toString(36)}_${fallbackEventIdCounter.toString(36)}`)},isContextRecord=e=>"object"==typeof e&&null!==e&&!Array.isArray(e),contextRecordFrom=e=>{if(e&&isContextRecord(e))return e},errorFromUnknown=e=>{if(e instanceof Error){let r=isContextRecord(e.context)?e.context:void 0;return{message:e.message,...e.name?{name:e.name}:{},...e.stack?{stack:e.stack}:{},...r?{context:r}:{}}}if("string"==typeof e)return{message:e};if("object"==typeof e&&null!==e){let r="string"==typeof e.message?e.message:"Unknown error",t="string"==typeof e.name?e.name:void 0,o="string"==typeof e.stack?e.stack:void 0,n=isContextRecord(e.context)?e.context:void 0;return{message:r,...t?{name:t}:{},...o?{stack:o}:{},...n?{context:n}:{}}}return{message:"Unknown error"}},registerHook=e=>r=>(e.push(r),{unsub:()=>{let t=e.indexOf(r);t>=0&&e.splice(t,1)}}),registerErrorHook=e=>r=>(e.push(r),{unsub:()=>{let t=e.indexOf(r);t>=0&&e.splice(t,1)}}),runtime=(e,...r)=>{let t=("modules"in e?e:{modules:[e,...r]}).modules,o=createState(),n=createHookStore(),a=registerHook(n.onReceive),i=registerHook(n.onSend),s=registerErrorHook(n.onError),c=({runtimeError:e,eventEnvelope:r,runtimeContext:t})=>{n.onError.forEach(o=>{try{o(e,r,t)}catch{}})},_=(e,r)=>{let t=contextRecordFrom(e),o=contextRecordFrom(r);if(t||o)return{...t??{},...o??{}}},u=({emitInput:e,fallbackStatus:r,roomName:t})=>{let{id:o,event:n,status:a,metadata:i,context:s,payload:c,error:_}=e,u=mergeMetadata(t?{room:t}:void 0,i),l=o??createEventId();if(void 0===c&&void 0===_)throw Error("Emit input must contain payload or error.");let d={id:l,event:n,status:a??r,metadata:u,context:s};return void 0!==c&&void 0!==_?{...d,payload:c,error:_}:void 0!==c?{...d,payload:c}:{...d,error:_}},l=({runtimeError:e,eventEnvelope:r})=>{let t=errorFromUnknown(e),o=_(r.context,t.context);return{...r,error:t,context:o}},d=e=>{let r,t=e.hookChain[e.hookIndex];if(!t)return Promise.resolve(e.eventEnvelope);let o=!1,n=t(e.eventEnvelope,e.runtimeContext,t=>(o=!0,r=d({hookChain:e.hookChain,hookIndex:e.hookIndex+1,eventEnvelope:((e,r)=>{if(!r)return e;let t=r.id??e.id,o=r.event??e.event,n=r.status??e.status,a=mergeMetadata(e.metadata,r.metadata),i=_(e.context,r.context),s=r.payload??e.payload,c=r.error??e.error;if(void 0===s&&void 0===c)throw Error("Event envelope must contain payload or error.");let u={...e,id:t,event:o,status:n,metadata:a,context:i};return void 0!==s&&void 0!==c?{...u,payload:s,error:c}:void 0!==s?{...u,payload:s}:{...u,error:c}})(e.eventEnvelope,t),runtimeContext:e.runtimeContext})));return void 0===n&&o?r??Promise.resolve(e.eventEnvelope):Promise.resolve(n).then(t=>t??r??e.eventEnvelope)},m=({runtimeContext:e,roomName:r})=>async t=>{let o=u({emitInput:t,fallbackStatus:"sending",roomName:r});try{return await d({hookChain:n.onSend,hookIndex:0,eventEnvelope:o,runtimeContext:e}),{ok:!0}}catch(t){let r=l({runtimeError:t,eventEnvelope:o});return c({runtimeError:t,eventEnvelope:r,runtimeContext:e}),{ok:!1,error:r.error.message}}},p=e=>{let r={},t={runtimeContext:r,roomName:e};return r.emitReceive=(({runtimeContext:e,roomName:r})=>async t=>{let o=u({emitInput:t,fallbackStatus:"receiving",roomName:r});try{return await d({hookChain:n.onReceive,hookIndex:0,eventEnvelope:o,runtimeContext:e}),{ok:!0}}catch(t){let r=l({runtimeError:t,eventEnvelope:o});return c({runtimeError:t,eventEnvelope:r,runtimeContext:e}),{ok:!1,error:r.error.message}}})(t),r.emitSend=m(t),r.emitError=(({runtimeContext:e,roomName:r})=>async t=>{let o=u({emitInput:t,fallbackStatus:"sending",roomName:r}),n=o.error??{message:"Unknown error"},a={...o,error:n};return c({runtimeError:n,eventEnvelope:a,runtimeContext:e}),{ok:!0}})(t),r.emitEvent=async e=>m(t)(e),r.room=e=>p(e),r.state=o,r},v=p(),k={emitReceive:v.emitReceive,emitSend:v.emitSend,emitError:v.emitError,onReceive:a,onSend:i,onError:s,state:o};t.forEach(e=>{e.register(k)})};for(var __rspack_i in exports.runtime=__webpack_exports__.runtime,__webpack_exports__)-1===["runtime"].indexOf(__rspack_i)&&(exports[__rspack_i]=__webpack_exports__[__rspack_i]);Object.defineProperty(exports,"__esModule",{value:!0});
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import type { RuntimeStart } from './types.js';
|
|
2
|
+
/**
|
|
3
|
+
* runtime is part of the public LIVON API.
|
|
4
|
+
*
|
|
5
|
+
* @remarks
|
|
6
|
+
* Parameter and return types are defined in the TypeScript signature.
|
|
7
|
+
*
|
|
8
|
+
* @see https://live-input-vector-output-node.github.io/livon-ts/docs/packages/runtime
|
|
9
|
+
*
|
|
10
|
+
* @example
|
|
11
|
+
* const result = runtime(undefined as never);
|
|
12
|
+
*/
|
|
13
|
+
export declare const runtime: RuntimeStart;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
let e=(e,t)=>{if(e||t)return{...e??{},...t??{}}},t=0,r=e=>"object"==typeof e&&null!==e&&!Array.isArray(e),o=e=>{if(e&&r(e))return e},n=e=>t=>(e.push(t),{unsub:()=>{let r=e.indexOf(t);r>=0&&e.splice(r,1)}}),i=(i,...a)=>{let s,l,v=("modules"in i?i:{modules:[i,...a]}).modules,m=(s=new Map,{get:e=>s.get(e),set:(e,t)=>{s.set(e,t)}}),u=[],d=[],c=[],p=n(u),E=n(d),h=(l=c,e=>(l.push(e),{unsub:()=>{let t=l.indexOf(e);t>=0&&l.splice(t,1)}})),k=({runtimeError:e,eventEnvelope:t,runtimeContext:r})=>{c.forEach(o=>{try{o(e,t,r)}catch{}})},f=(e,t)=>{let r=o(e),n=o(t);if(r||n)return{...r??{},...n??{}}},x=({emitInput:r,fallbackStatus:o,roomName:n})=>{let i,{id:a,event:s,status:l,metadata:v,context:m,payload:u,error:d}=r,c=e(n?{room:n}:void 0,v),p=a??(i=globalThis.crypto,i?.randomUUID?i.randomUUID():(t+=1,`evt_${Date.now().toString(36)}_${t.toString(36)}`));if(void 0===u&&void 0===d)throw Error("Emit input must contain payload or error.");let E={id:p,event:s,status:l??o,metadata:c,context:m};return void 0!==u&&void 0!==d?{...E,payload:u,error:d}:void 0!==u?{...E,payload:u}:{...E,error:d}},g=({runtimeError:e,eventEnvelope:t})=>{let o=(e=>{if(e instanceof Error){let t=r(e.context)?e.context:void 0;return{message:e.message,...e.name?{name:e.name}:{},...e.stack?{stack:e.stack}:{},...t?{context:t}:{}}}if("string"==typeof e)return{message:e};if("object"==typeof e&&null!==e){let t="string"==typeof e.message?e.message:"Unknown error",o="string"==typeof e.name?e.name:void 0,n="string"==typeof e.stack?e.stack:void 0,i=r(e.context)?e.context:void 0;return{message:t,...o?{name:o}:{},...n?{stack:n}:{},...i?{context:i}:{}}}return{message:"Unknown error"}})(e),n=f(t.context,o.context);return{...t,error:o,context:n}},y=t=>{let r,o=t.hookChain[t.hookIndex];if(!o)return Promise.resolve(t.eventEnvelope);let n=!1,i=o(t.eventEnvelope,t.runtimeContext,o=>(n=!0,r=y({hookChain:t.hookChain,hookIndex:t.hookIndex+1,eventEnvelope:((t,r)=>{if(!r)return t;let o=r.id??t.id,n=r.event??t.event,i=r.status??t.status,a=e(t.metadata,r.metadata),s=f(t.context,r.context),l=r.payload??t.payload,v=r.error??t.error;if(void 0===l&&void 0===v)throw Error("Event envelope must contain payload or error.");let m={...t,id:o,event:n,status:i,metadata:a,context:s};return void 0!==l&&void 0!==v?{...m,payload:l,error:v}:void 0!==l?{...m,payload:l}:{...m,error:v}})(t.eventEnvelope,o),runtimeContext:t.runtimeContext})));return void 0===i&&n?r??Promise.resolve(t.eventEnvelope):Promise.resolve(i).then(e=>e??r??t.eventEnvelope)},C=({runtimeContext:e,roomName:t})=>async r=>{let o=x({emitInput:r,fallbackStatus:"sending",roomName:t});try{return await y({hookChain:d,hookIndex:0,eventEnvelope:o,runtimeContext:e}),{ok:!0}}catch(r){let t=g({runtimeError:r,eventEnvelope:o});return k({runtimeError:r,eventEnvelope:t,runtimeContext:e}),{ok:!1,error:t.error.message}}},w=e=>{let t={},r={runtimeContext:t,roomName:e};return t.emitReceive=(({runtimeContext:e,roomName:t})=>async r=>{let o=x({emitInput:r,fallbackStatus:"receiving",roomName:t});try{return await y({hookChain:u,hookIndex:0,eventEnvelope:o,runtimeContext:e}),{ok:!0}}catch(r){let t=g({runtimeError:r,eventEnvelope:o});return k({runtimeError:r,eventEnvelope:t,runtimeContext:e}),{ok:!1,error:t.error.message}}})(r),t.emitSend=C(r),t.emitError=(({runtimeContext:e,roomName:t})=>async r=>{let o=x({emitInput:r,fallbackStatus:"sending",roomName:t}),n=o.error??{message:"Unknown error"},i={...o,error:n};return k({runtimeError:n,eventEnvelope:i,runtimeContext:e}),{ok:!0}})(r),t.emitEvent=async e=>C(r)(e),t.room=e=>w(e),t.state=m,t},b=w(),S={emitReceive:b.emitReceive,emitSend:b.emitSend,emitError:b.emitError,onReceive:p,onSend:E,onError:h,state:m};v.forEach(e=>{e.register(S)})};export{i as runtime};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
"use strict";const __rslib_import_meta_url__="u"<typeof document?new(require("url".replace("",""))).URL("file:"+__filename).href:document.currentScript&&document.currentScript.src||new URL("main.js",document.baseURI).href;var __webpack_require__={};__webpack_require__.r=e=>{"u">typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})};var __webpack_exports__={};for(var __rspack_i in __webpack_require__.r(__webpack_exports__),__webpack_exports__)exports[__rspack_i]=__webpack_exports__[__rspack_i];Object.defineProperty(exports,"__esModule",{value:!0});
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
export interface RuntimeEventContext {
|
|
2
|
+
}
|
|
3
|
+
export type EventStatus = 'sending' | 'receiving' | 'failed';
|
|
4
|
+
export interface EventError {
|
|
5
|
+
message: string;
|
|
6
|
+
name?: string;
|
|
7
|
+
stack?: string;
|
|
8
|
+
context?: Readonly<RuntimeEventContext>;
|
|
9
|
+
}
|
|
10
|
+
export interface EventEnvelopeBase {
|
|
11
|
+
id: string;
|
|
12
|
+
event: string;
|
|
13
|
+
status: EventStatus;
|
|
14
|
+
metadata?: Readonly<Record<string, unknown>>;
|
|
15
|
+
context?: RuntimeEventContext;
|
|
16
|
+
}
|
|
17
|
+
export interface EventEnvelopePayload extends EventEnvelopeBase {
|
|
18
|
+
payload: Uint8Array;
|
|
19
|
+
error?: EventError;
|
|
20
|
+
}
|
|
21
|
+
export interface EventEnvelopeError extends EventEnvelopeBase {
|
|
22
|
+
error: EventError;
|
|
23
|
+
payload?: Uint8Array;
|
|
24
|
+
}
|
|
25
|
+
export type EventEnvelope = EventEnvelopePayload | EventEnvelopeError;
|
|
26
|
+
export interface EmitInputBase {
|
|
27
|
+
id?: string;
|
|
28
|
+
event: string;
|
|
29
|
+
status?: EventStatus;
|
|
30
|
+
metadata?: Readonly<Record<string, unknown>>;
|
|
31
|
+
context?: RuntimeEventContext;
|
|
32
|
+
}
|
|
33
|
+
export interface EmitInputPayload extends EmitInputBase {
|
|
34
|
+
payload: Uint8Array;
|
|
35
|
+
error?: EventError;
|
|
36
|
+
}
|
|
37
|
+
export interface EmitInputError extends EmitInputBase {
|
|
38
|
+
error: EventError;
|
|
39
|
+
payload?: Uint8Array;
|
|
40
|
+
}
|
|
41
|
+
export type EmitInput = EmitInputPayload | EmitInputError;
|
|
42
|
+
export interface EventAck {
|
|
43
|
+
ok: boolean;
|
|
44
|
+
error?: string;
|
|
45
|
+
metadata?: Readonly<Record<string, unknown>>;
|
|
46
|
+
}
|
|
47
|
+
export interface EmitEvent {
|
|
48
|
+
(input: EmitInput): Promise<EventAck>;
|
|
49
|
+
}
|
|
50
|
+
export interface EmitReceive {
|
|
51
|
+
(input: EmitInput): Promise<EventAck>;
|
|
52
|
+
}
|
|
53
|
+
export interface EmitSend {
|
|
54
|
+
(input: EmitInput): Promise<EventAck>;
|
|
55
|
+
}
|
|
56
|
+
export interface EmitError {
|
|
57
|
+
(input: EmitInput): Promise<EventAck>;
|
|
58
|
+
}
|
|
59
|
+
export interface RoomSelector {
|
|
60
|
+
(name: string): RuntimeContext;
|
|
61
|
+
}
|
|
62
|
+
export interface StateGet {
|
|
63
|
+
<T = unknown>(key: string): T | undefined;
|
|
64
|
+
}
|
|
65
|
+
export interface StateSet {
|
|
66
|
+
<T = unknown>(key: string, value: T): void;
|
|
67
|
+
}
|
|
68
|
+
export interface RuntimeState {
|
|
69
|
+
get: StateGet;
|
|
70
|
+
set: StateSet;
|
|
71
|
+
}
|
|
72
|
+
export interface RuntimeContext {
|
|
73
|
+
emitEvent: EmitEvent;
|
|
74
|
+
emitReceive: EmitReceive;
|
|
75
|
+
emitSend: EmitSend;
|
|
76
|
+
emitError: EmitError;
|
|
77
|
+
room: RoomSelector;
|
|
78
|
+
state: RuntimeState;
|
|
79
|
+
}
|
|
80
|
+
export interface RuntimeNext {
|
|
81
|
+
(update?: PartialEventEnvelope): Promise<EventEnvelope>;
|
|
82
|
+
}
|
|
83
|
+
export interface RuntimeHook {
|
|
84
|
+
(envelope: EventEnvelope, ctx: RuntimeContext, next: RuntimeNext): Promise<EventEnvelope> | EventEnvelope;
|
|
85
|
+
}
|
|
86
|
+
export interface RuntimeModule {
|
|
87
|
+
name: string;
|
|
88
|
+
register: RuntimeModuleRegister;
|
|
89
|
+
}
|
|
90
|
+
export interface RuntimeOnError {
|
|
91
|
+
(error: unknown, envelope: EventEnvelope, ctx: RuntimeContext): void;
|
|
92
|
+
}
|
|
93
|
+
export interface RuntimeHookSubscription {
|
|
94
|
+
unsub: RuntimeUnsubscribe;
|
|
95
|
+
}
|
|
96
|
+
export interface RuntimeUnsubscribe {
|
|
97
|
+
(): void;
|
|
98
|
+
}
|
|
99
|
+
export interface RuntimeInput {
|
|
100
|
+
modules: readonly RuntimeModule[];
|
|
101
|
+
}
|
|
102
|
+
export interface RuntimeModuleRegister {
|
|
103
|
+
(registry: RuntimeRegistry): void;
|
|
104
|
+
}
|
|
105
|
+
export interface RuntimeHookRegister {
|
|
106
|
+
(hook: RuntimeHook): RuntimeHookSubscription;
|
|
107
|
+
}
|
|
108
|
+
export interface RuntimeOnErrorRegister {
|
|
109
|
+
(hook: RuntimeOnError): RuntimeHookSubscription;
|
|
110
|
+
}
|
|
111
|
+
export interface RuntimeRegistry {
|
|
112
|
+
emitReceive: EmitReceive;
|
|
113
|
+
emitSend: EmitSend;
|
|
114
|
+
emitError: EmitError;
|
|
115
|
+
onReceive: RuntimeHookRegister;
|
|
116
|
+
onSend: RuntimeHookRegister;
|
|
117
|
+
onError: RuntimeOnErrorRegister;
|
|
118
|
+
state: RuntimeState;
|
|
119
|
+
}
|
|
120
|
+
export interface PartialEventEnvelopeBase {
|
|
121
|
+
id?: string;
|
|
122
|
+
event?: string;
|
|
123
|
+
status?: EventStatus;
|
|
124
|
+
metadata?: Readonly<Record<string, unknown>>;
|
|
125
|
+
context?: RuntimeEventContext;
|
|
126
|
+
}
|
|
127
|
+
export interface PartialEventEnvelopePayload extends PartialEventEnvelopeBase {
|
|
128
|
+
payload?: Uint8Array;
|
|
129
|
+
error?: EventError;
|
|
130
|
+
}
|
|
131
|
+
export interface PartialEventEnvelopeError extends PartialEventEnvelopeBase {
|
|
132
|
+
error?: EventError;
|
|
133
|
+
payload?: Uint8Array;
|
|
134
|
+
}
|
|
135
|
+
export interface PartialEventEnvelopeEmpty extends PartialEventEnvelopeBase {
|
|
136
|
+
payload?: undefined;
|
|
137
|
+
error?: undefined;
|
|
138
|
+
}
|
|
139
|
+
export type PartialEventEnvelope = PartialEventEnvelopePayload | PartialEventEnvelopeError | PartialEventEnvelopeEmpty;
|
|
140
|
+
export interface RuntimeStart {
|
|
141
|
+
(...modules: RuntimeModule[]): void;
|
|
142
|
+
(input: RuntimeInput): void;
|
|
143
|
+
}
|
|
File without changes
|