@fougere/core 0.6.0-alpha.0 → 0.7.0-alpha.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 +1 -1
- package/dist/boot/Emissions.d.ts +13 -90
- package/dist/boot/Emissions.d.ts.map +1 -1
- package/dist/boot/Emissions.js +21 -118
- package/dist/boot/Emissions.js.map +1 -1
- package/dist/boot/ambient-port.d.ts +3 -24
- package/dist/boot/ambient-port.d.ts.map +1 -1
- package/dist/boot/ambient.als.d.ts.map +1 -1
- package/dist/boot/ambient.als.js +7 -12
- package/dist/boot/ambient.als.js.map +1 -1
- package/dist/boot/ambient.queue.d.ts +2 -5
- package/dist/boot/ambient.queue.d.ts.map +1 -1
- package/dist/boot/ambient.queue.js.map +1 -1
- package/dist/boot/apply.d.ts +1 -13
- package/dist/boot/apply.d.ts.map +1 -1
- package/dist/boot/apply.js +3 -15
- package/dist/boot/apply.js.map +1 -1
- package/dist/boot/auth.d.ts +2 -12
- package/dist/boot/auth.d.ts.map +1 -1
- package/dist/boot/boot.d.ts +3 -16
- package/dist/boot/boot.d.ts.map +1 -1
- package/dist/boot/boot.js +3 -10
- package/dist/boot/boot.js.map +1 -1
- package/dist/boot/bootstrap.d.ts.map +1 -1
- package/dist/boot/bootstrap.js +61 -127
- package/dist/boot/bootstrap.js.map +1 -1
- package/dist/boot/card.d.ts +1 -17
- package/dist/boot/card.d.ts.map +1 -1
- package/dist/boot/card.js +3 -32
- package/dist/boot/card.js.map +1 -1
- package/dist/boot/frame.d.ts +8 -32
- package/dist/boot/frame.d.ts.map +1 -1
- package/dist/boot/frame.js +20 -54
- package/dist/boot/frame.js.map +1 -1
- package/dist/boot/hosted.d.ts +2 -24
- package/dist/boot/hosted.d.ts.map +1 -1
- package/dist/boot/hosted.js +10 -15
- package/dist/boot/hosted.js.map +1 -1
- package/dist/boot/ownership.d.ts +3 -36
- package/dist/boot/ownership.d.ts.map +1 -1
- package/dist/boot/ownership.js +5 -40
- package/dist/boot/ownership.js.map +1 -1
- package/dist/boot/ports.d.ts +1 -14
- package/dist/boot/ports.d.ts.map +1 -1
- package/dist/boot/ports.js +1 -14
- package/dist/boot/ports.js.map +1 -1
- package/dist/boot/remote.d.ts +5 -38
- package/dist/boot/remote.d.ts.map +1 -1
- package/dist/boot/remote.js +8 -41
- package/dist/boot/remote.js.map +1 -1
- package/dist/boot/runner.d.ts +4 -21
- package/dist/boot/runner.d.ts.map +1 -1
- package/dist/boot/runner.js +4 -17
- package/dist/boot/runner.js.map +1 -1
- package/dist/boot/seed.d.ts +4 -31
- package/dist/boot/seed.d.ts.map +1 -1
- package/dist/boot/seed.js +6 -37
- package/dist/boot/seed.js.map +1 -1
- package/dist/boot/statement-drift.d.ts +2 -21
- package/dist/boot/statement-drift.d.ts.map +1 -1
- package/dist/boot/statement-drift.js +4 -9
- package/dist/boot/statement-drift.js.map +1 -1
- package/dist/boot/together.d.ts +4 -8
- package/dist/boot/together.d.ts.map +1 -1
- package/dist/boot/together.js +15 -50
- package/dist/boot/together.js.map +1 -1
- package/dist/boot/types.d.ts +28 -173
- package/dist/boot/types.d.ts.map +1 -1
- package/dist/builtin/config.d.ts +7 -0
- package/dist/builtin/config.d.ts.map +1 -0
- package/dist/builtin/config.js +15 -0
- package/dist/builtin/config.js.map +1 -0
- package/dist/{builtins → builtin}/logger.d.ts +4 -25
- package/dist/builtin/logger.d.ts.map +1 -0
- package/dist/{builtins → builtin}/logger.js +5 -32
- package/dist/builtin/logger.js.map +1 -0
- package/dist/config-loader.d.ts +9 -67
- package/dist/config-loader.d.ts.map +1 -1
- package/dist/config-loader.js +5 -18
- package/dist/config-loader.js.map +1 -1
- package/dist/contract.d.ts +13 -31
- package/dist/contract.d.ts.map +1 -1
- package/dist/contract.js +10 -26
- package/dist/contract.js.map +1 -1
- package/dist/crypto/encoding.d.ts +2 -15
- package/dist/crypto/encoding.d.ts.map +1 -1
- package/dist/crypto/encoding.js +2 -15
- package/dist/crypto/encoding.js.map +1 -1
- package/dist/crypto/node.d.ts.map +1 -1
- package/dist/crypto/node.js +1 -7
- package/dist/crypto/node.js.map +1 -1
- package/dist/crypto/port.d.ts +2 -18
- package/dist/crypto/port.d.ts.map +1 -1
- package/dist/crypto/port.js +1 -17
- package/dist/crypto/port.js.map +1 -1
- package/dist/crypto/webcrypto.d.ts.map +1 -1
- package/dist/crypto/webcrypto.js +1 -12
- package/dist/crypto/webcrypto.js.map +1 -1
- package/dist/declare.d.ts +6 -36
- package/dist/declare.d.ts.map +1 -1
- package/dist/declare.js +4 -29
- package/dist/declare.js.map +1 -1
- package/dist/define.d.ts +2 -3
- package/dist/define.d.ts.map +1 -1
- package/dist/define.js +2 -3
- package/dist/define.js.map +1 -1
- package/dist/descriptor/Fronds.d.ts +3 -28
- package/dist/descriptor/Fronds.d.ts.map +1 -1
- package/dist/descriptor/Fronds.js +6 -31
- package/dist/descriptor/Fronds.js.map +1 -1
- package/dist/descriptor/frond.d.ts +14 -63
- package/dist/descriptor/frond.d.ts.map +1 -1
- package/dist/dispatch/ArgumentResolver.d.ts +1 -1
- package/dist/dispatch/ArgumentResolver.d.ts.map +1 -1
- package/dist/dispatch/ArgumentResolver.js +5 -5
- package/dist/dispatch/ArgumentResolver.js.map +1 -1
- package/dist/dispatch/DispatchEvent.d.ts +2 -2
- package/dist/dispatch/DispatchEvent.d.ts.map +1 -1
- package/dist/dispatch/DispatchLifecycle.d.ts +1 -7
- package/dist/dispatch/DispatchLifecycle.d.ts.map +1 -1
- package/dist/dispatch/DispatchLifecycle.js +1 -7
- package/dist/dispatch/DispatchLifecycle.js.map +1 -1
- package/dist/dispatch/DispatchPort.d.ts +1 -1
- package/dist/dispatch/DispatchPort.d.ts.map +1 -1
- package/dist/dispatch/Dispatcher.d.ts +1 -1
- package/dist/dispatch/Dispatcher.d.ts.map +1 -1
- package/dist/dispatch/Dispatcher.js +2 -2
- package/dist/dispatch/Dispatcher.js.map +1 -1
- package/dist/{boot → dispatch}/HandlerFacade.d.ts +25 -38
- package/dist/dispatch/HandlerFacade.d.ts.map +1 -0
- package/dist/{boot → dispatch}/HandlerFacade.js +65 -74
- package/dist/dispatch/HandlerFacade.js.map +1 -0
- package/dist/dispatch/LocalRoutePolicy.d.ts +1 -1
- package/dist/dispatch/LocalRoutePolicy.d.ts.map +1 -1
- package/dist/dispatch/LocalRoutePolicy.js +4 -4
- package/dist/dispatch/LocalRoutePolicy.js.map +1 -1
- package/dist/dispatch/OperationRoute.d.ts +2 -2
- package/dist/dispatch/OperationRoute.d.ts.map +1 -1
- package/dist/dispatch/OutputView.d.ts +3 -2
- package/dist/dispatch/OutputView.d.ts.map +1 -1
- package/dist/dispatch/OutputView.js +19 -1
- package/dist/dispatch/OutputView.js.map +1 -1
- package/dist/dispatch/Route.d.ts +2 -2
- package/dist/dispatch/Route.d.ts.map +1 -1
- package/dist/dispatch/RoutePolicy.d.ts +1 -1
- package/dist/dispatch/RoutePolicy.d.ts.map +1 -1
- package/dist/dispatch/RouteRegistry.d.ts +1 -1
- package/dist/dispatch/RouteRegistry.d.ts.map +1 -1
- package/dist/dispatch/RouteRegistry.js +2 -2
- package/dist/dispatch/RouteRegistry.js.map +1 -1
- package/dist/dispatch/RouteResolver.d.ts +2 -4
- package/dist/dispatch/RouteResolver.d.ts.map +1 -1
- package/dist/dispatch/StorageGuard.d.ts +8 -7
- package/dist/dispatch/StorageGuard.d.ts.map +1 -1
- package/dist/dispatch/StorageGuard.js +61 -18
- package/dist/dispatch/StorageGuard.js.map +1 -1
- package/dist/dispatch/presenterArguments.d.ts +7 -0
- package/dist/dispatch/presenterArguments.d.ts.map +1 -0
- package/dist/dispatch/presenterArguments.js +12 -0
- package/dist/dispatch/presenterArguments.js.map +1 -0
- package/dist/dispatch/remoteRoutes.d.ts +7 -0
- package/dist/dispatch/remoteRoutes.d.ts.map +1 -0
- package/dist/dispatch/{RemoteRouteResolver.js → remoteRoutes.js} +6 -10
- package/dist/dispatch/remoteRoutes.js.map +1 -0
- package/dist/dispatch/routeNotFound.d.ts +9 -0
- package/dist/dispatch/routeNotFound.d.ts.map +1 -0
- package/dist/dispatch/routeNotFound.js +21 -0
- package/dist/dispatch/routeNotFound.js.map +1 -0
- package/dist/dispatch/validateInput.d.ts +5 -0
- package/dist/dispatch/validateInput.d.ts.map +1 -0
- package/dist/dispatch/validateInput.js +20 -0
- package/dist/dispatch/validateInput.js.map +1 -0
- package/dist/effective-operation.d.ts +1 -24
- package/dist/effective-operation.d.ts.map +1 -1
- package/dist/effective-operation.js +21 -50
- package/dist/effective-operation.js.map +1 -1
- package/dist/emit.d.ts +4 -42
- package/dist/emit.d.ts.map +1 -1
- package/dist/emit.js +3 -39
- package/dist/emit.js.map +1 -1
- package/dist/entry/facade.d.ts +8 -0
- package/dist/entry/facade.d.ts.map +1 -0
- package/dist/entry/facade.js +28 -0
- package/dist/entry/facade.js.map +1 -0
- package/dist/entry/transport.d.ts +5 -0
- package/dist/entry/transport.d.ts.map +1 -0
- package/dist/entry/transport.js +11 -0
- package/dist/entry/transport.js.map +1 -0
- package/dist/frond-config.d.ts +7 -70
- package/dist/frond-config.d.ts.map +1 -1
- package/dist/frond-config.js +1 -9
- package/dist/frond-config.js.map +1 -1
- package/dist/identity-keys.d.ts +2 -5
- package/dist/identity-keys.d.ts.map +1 -1
- package/dist/identity-keys.js +3 -16
- package/dist/identity-keys.js.map +1 -1
- package/dist/identity.d.ts +4 -30
- package/dist/identity.d.ts.map +1 -1
- package/dist/identity.js +11 -73
- package/dist/identity.js.map +1 -1
- package/dist/imports.d.ts +1 -7
- package/dist/imports.d.ts.map +1 -1
- package/dist/imports.js +1 -7
- package/dist/imports.js.map +1 -1
- package/dist/index.d.ts +17 -24
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +10 -18
- package/dist/index.js.map +1 -1
- package/dist/loader.d.ts +1 -8
- package/dist/loader.d.ts.map +1 -1
- package/dist/loader.js +1 -8
- package/dist/loader.js.map +1 -1
- package/dist/node.d.ts +2 -11
- package/dist/node.d.ts.map +1 -1
- package/dist/node.js +2 -11
- package/dist/node.js.map +1 -1
- package/dist/prefab/collector.d.ts +1 -22
- package/dist/prefab/collector.d.ts.map +1 -1
- package/dist/prefab/collector.js +1 -22
- package/dist/prefab/collector.js.map +1 -1
- package/dist/prefab/crud.d.ts +16 -32
- package/dist/prefab/crud.d.ts.map +1 -1
- package/dist/prefab/crud.js +31 -58
- package/dist/prefab/crud.js.map +1 -1
- package/dist/prefab/mirror.d.ts +2 -24
- package/dist/prefab/mirror.d.ts.map +1 -1
- package/dist/prefab/mirror.js +2 -20
- package/dist/prefab/mirror.js.map +1 -1
- package/dist/prefab/prefab.d.ts +1 -7
- package/dist/prefab/prefab.d.ts.map +1 -1
- package/dist/prefab/prefab.js +1 -7
- package/dist/prefab/prefab.js.map +1 -1
- package/dist/prefab/presenter.d.ts +2 -36
- package/dist/prefab/presenter.d.ts.map +1 -1
- package/dist/prefab/presenter.js +2 -36
- package/dist/prefab/presenter.js.map +1 -1
- package/dist/prefab/repository.d.ts +5 -73
- package/dist/prefab/repository.d.ts.map +1 -1
- package/dist/prefab/repository.js +3 -16
- package/dist/prefab/repository.js.map +1 -1
- package/dist/scan/adapters.d.ts +3 -0
- package/dist/scan/adapters.d.ts.map +1 -0
- package/dist/scan/adapters.js +25 -0
- package/dist/scan/adapters.js.map +1 -0
- package/dist/scan/bundling.d.ts +1 -12
- package/dist/scan/bundling.d.ts.map +1 -1
- package/dist/scan/bundling.js +1 -12
- package/dist/scan/bundling.js.map +1 -1
- package/dist/scan/conventions.d.ts +6 -40
- package/dist/scan/conventions.d.ts.map +1 -1
- package/dist/scan/conventions.js +5 -34
- package/dist/scan/conventions.js.map +1 -1
- package/dist/scan/emit.d.ts +1 -5
- package/dist/scan/emit.d.ts.map +1 -1
- package/dist/scan/emit.js +4 -38
- package/dist/scan/emit.js.map +1 -1
- package/dist/scan/handler-parser.d.ts +4 -26
- package/dist/scan/handler-parser.d.ts.map +1 -1
- package/dist/scan/handler-parser.js +26 -83
- package/dist/scan/handler-parser.js.map +1 -1
- package/dist/scan/result.d.ts +3 -16
- package/dist/scan/result.d.ts.map +1 -1
- package/dist/scan/scanner.d.ts +2 -27
- package/dist/scan/scanner.d.ts.map +1 -1
- package/dist/scan/scanner.js +28 -127
- package/dist/scan/scanner.js.map +1 -1
- package/dist/scan/statement.d.ts.map +1 -1
- package/dist/scan/statement.js +4 -30
- package/dist/scan/statement.js.map +1 -1
- package/dist/source.d.ts +41 -0
- package/dist/source.d.ts.map +1 -0
- package/dist/source.js +10 -0
- package/dist/source.js.map +1 -0
- package/dist/storage.d.ts +13 -210
- package/dist/storage.d.ts.map +1 -1
- package/dist/storage.js +4 -68
- package/dist/storage.js.map +1 -1
- package/dist/store.d.ts +18 -0
- package/dist/store.d.ts.map +1 -0
- package/dist/store.js +146 -0
- package/dist/store.js.map +1 -0
- package/dist/verify.d.ts +5 -38
- package/dist/verify.d.ts.map +1 -1
- package/dist/verify.js +17 -37
- package/dist/verify.js.map +1 -1
- package/dist/wire/CallLog.d.ts +32 -0
- package/dist/wire/CallLog.d.ts.map +1 -0
- package/dist/{contract → wire}/CallLog.js.map +1 -1
- package/dist/wire/Invocation.d.ts +32 -0
- package/dist/wire/Invocation.d.ts.map +1 -0
- package/dist/wire/Invocation.js +66 -0
- package/dist/wire/Invocation.js.map +1 -0
- package/dist/{contract → wire}/RouteAddress.d.ts +5 -0
- package/dist/wire/RouteAddress.d.ts.map +1 -0
- package/dist/{contract → wire}/RouteAddress.js +7 -0
- package/dist/wire/RouteAddress.js.map +1 -0
- package/dist/wire/binding.d.ts +5 -21
- package/dist/wire/binding.d.ts.map +1 -1
- package/dist/wire/binding.js +5 -10
- package/dist/wire/binding.js.map +1 -1
- package/dist/wire/call.d.ts +24 -133
- package/dist/wire/call.d.ts.map +1 -1
- package/dist/wire/call.js +15 -41
- package/dist/wire/call.js.map +1 -1
- package/dist/wire/drift.d.ts +3 -28
- package/dist/wire/drift.d.ts.map +1 -1
- package/dist/wire/drift.js +4 -23
- package/dist/wire/drift.js.map +1 -1
- package/dist/wire/errors.d.ts +4 -24
- package/dist/wire/errors.d.ts.map +1 -1
- package/dist/wire/errors.js +4 -24
- package/dist/wire/errors.js.map +1 -1
- package/dist/wire/http-error.d.ts +2 -13
- package/dist/wire/http-error.d.ts.map +1 -1
- package/dist/wire/http-error.js +5 -19
- package/dist/wire/http-error.js.map +1 -1
- package/dist/wire/loggerMiddleware.d.ts +2 -8
- package/dist/wire/loggerMiddleware.d.ts.map +1 -1
- package/dist/wire/loggerMiddleware.js +1 -7
- package/dist/wire/loggerMiddleware.js.map +1 -1
- package/dist/wire/middleware.d.ts +3 -7
- package/dist/wire/middleware.d.ts.map +1 -1
- package/dist/wire/middleware.js +1 -5
- package/dist/wire/middleware.js.map +1 -1
- package/dist/wire/operation.d.ts +7 -43
- package/dist/wire/operation.d.ts.map +1 -1
- package/dist/wire/operation.js +4 -15
- package/dist/wire/operation.js.map +1 -1
- package/dist/wire/signature.d.ts +4 -25
- package/dist/wire/signature.d.ts.map +1 -1
- package/package.json +3 -3
- package/src/boot/Emissions.ts +21 -118
- package/src/boot/ambient-port.ts +3 -24
- package/src/boot/ambient.als.ts +7 -12
- package/src/boot/ambient.queue.ts +2 -5
- package/src/boot/apply.ts +3 -15
- package/src/boot/auth.ts +2 -12
- package/src/boot/boot.ts +5 -20
- package/src/boot/bootstrap.ts +69 -136
- package/src/boot/card.ts +4 -33
- package/src/boot/frame.ts +28 -62
- package/src/boot/hosted.ts +12 -34
- package/src/boot/ownership.ts +5 -39
- package/src/boot/ports.ts +1 -14
- package/src/boot/remote.ts +11 -58
- package/src/boot/runner.ts +5 -22
- package/src/boot/seed.ts +6 -37
- package/src/boot/statement-drift.ts +5 -24
- package/src/boot/together.ts +18 -51
- package/src/boot/types.ts +28 -173
- package/src/{builtins → builtin}/config.ts +1 -7
- package/src/{builtins → builtin}/logger.ts +6 -39
- package/src/config-loader.ts +12 -71
- package/src/contract.ts +15 -39
- package/src/crypto/encoding.ts +2 -15
- package/src/crypto/node.ts +1 -7
- package/src/crypto/port.ts +2 -18
- package/src/crypto/webcrypto.ts +1 -12
- package/src/declare.ts +8 -39
- package/src/define.ts +2 -3
- package/src/descriptor/Fronds.ts +6 -31
- package/src/descriptor/frond.ts +14 -63
- package/src/dispatch/ArgumentResolver.ts +6 -6
- package/src/dispatch/DispatchEvent.ts +2 -2
- package/src/dispatch/DispatchLifecycle.ts +1 -7
- package/src/dispatch/DispatchPort.ts +1 -1
- package/src/dispatch/Dispatcher.ts +3 -3
- package/src/dispatch/HandlerFacade.ts +231 -0
- package/src/dispatch/LocalRoutePolicy.ts +4 -4
- package/src/dispatch/OperationRoute.ts +2 -2
- package/src/dispatch/OutputView.ts +24 -2
- package/src/dispatch/Route.ts +2 -2
- package/src/dispatch/RoutePolicy.ts +1 -1
- package/src/dispatch/RouteRegistry.ts +2 -2
- package/src/dispatch/RouteResolver.ts +2 -4
- package/src/dispatch/StorageGuard.ts +70 -18
- package/src/dispatch/presenterArguments.ts +25 -0
- package/src/dispatch/{RemoteRouteResolver.ts → remoteRoutes.ts} +7 -9
- package/src/dispatch/routeNotFound.ts +33 -0
- package/src/dispatch/validateInput.ts +28 -0
- package/src/effective-operation.ts +21 -50
- package/src/emit.ts +5 -63
- package/src/entry/facade.ts +44 -0
- package/src/entry/transport.ts +16 -0
- package/src/frond-config.ts +7 -70
- package/src/identity-keys.ts +3 -16
- package/src/identity.ts +12 -80
- package/src/imports.ts +2 -31
- package/src/index.ts +17 -24
- package/src/loader.ts +2 -16
- package/src/node.ts +2 -11
- package/src/prefab/collector.ts +1 -22
- package/src/prefab/crud.ts +37 -76
- package/src/prefab/mirror.ts +4 -44
- package/src/prefab/prefab.ts +2 -21
- package/src/prefab/presenter.ts +2 -36
- package/src/prefab/repository.ts +7 -83
- package/src/scan/adapters.ts +32 -0
- package/src/scan/bundling.ts +1 -12
- package/src/scan/conventions.ts +6 -40
- package/src/scan/emit.ts +4 -38
- package/src/scan/handler-parser.ts +27 -96
- package/src/scan/result.ts +3 -16
- package/src/scan/scanner.ts +27 -126
- package/src/scan/statement.ts +4 -30
- package/src/source.ts +44 -0
- package/src/storage.ts +14 -234
- package/src/store.ts +152 -0
- package/src/verify.ts +16 -57
- package/src/wire/CallLog.ts +30 -0
- package/src/{contract → wire}/Invocation.ts +24 -17
- package/src/{contract → wire}/RouteAddress.ts +7 -0
- package/src/wire/binding.ts +9 -25
- package/src/wire/call.ts +30 -133
- package/src/wire/drift.ts +5 -30
- package/src/wire/errors.ts +4 -24
- package/src/wire/http-error.ts +5 -19
- package/src/wire/loggerMiddleware.ts +2 -8
- package/src/wire/middleware.ts +3 -7
- package/src/wire/operation.ts +8 -48
- package/src/wire/signature.ts +4 -25
- package/dist/boot/HandlerFacade.d.ts.map +0 -1
- package/dist/boot/HandlerFacade.js.map +0 -1
- package/dist/builtins/config.d.ts +0 -13
- package/dist/builtins/config.d.ts.map +0 -1
- package/dist/builtins/config.js +0 -21
- package/dist/builtins/config.js.map +0 -1
- package/dist/builtins/logger.d.ts.map +0 -1
- package/dist/builtins/logger.js.map +0 -1
- package/dist/contract/Call.d.ts +0 -10
- package/dist/contract/Call.d.ts.map +0 -1
- package/dist/contract/Call.js +0 -15
- package/dist/contract/Call.js.map +0 -1
- package/dist/contract/CallLog.d.ts +0 -57
- package/dist/contract/CallLog.d.ts.map +0 -1
- package/dist/contract/Invocation.d.ts +0 -27
- package/dist/contract/Invocation.d.ts.map +0 -1
- package/dist/contract/Invocation.js +0 -59
- package/dist/contract/Invocation.js.map +0 -1
- package/dist/contract/RouteAddress.d.ts.map +0 -1
- package/dist/contract/RouteAddress.js.map +0 -1
- package/dist/dispatch/InputValidator.d.ts +0 -7
- package/dist/dispatch/InputValidator.d.ts.map +0 -1
- package/dist/dispatch/InputValidator.js +0 -22
- package/dist/dispatch/InputValidator.js.map +0 -1
- package/dist/dispatch/OperationExecutor.d.ts +0 -25
- package/dist/dispatch/OperationExecutor.d.ts.map +0 -1
- package/dist/dispatch/OperationExecutor.js +0 -32
- package/dist/dispatch/OperationExecutor.js.map +0 -1
- package/dist/dispatch/OutputProjector.d.ts +0 -12
- package/dist/dispatch/OutputProjector.d.ts.map +0 -1
- package/dist/dispatch/OutputProjector.js +0 -30
- package/dist/dispatch/OutputProjector.js.map +0 -1
- package/dist/dispatch/PresenterArgumentResolver.d.ts +0 -12
- package/dist/dispatch/PresenterArgumentResolver.d.ts.map +0 -1
- package/dist/dispatch/PresenterArgumentResolver.js +0 -20
- package/dist/dispatch/PresenterArgumentResolver.js.map +0 -1
- package/dist/dispatch/RemoteRouteResolver.d.ts +0 -13
- package/dist/dispatch/RemoteRouteResolver.d.ts.map +0 -1
- package/dist/dispatch/RemoteRouteResolver.js.map +0 -1
- package/dist/dispatch/RouteNotFoundError.d.ts +0 -10
- package/dist/dispatch/RouteNotFoundError.d.ts.map +0 -1
- package/dist/dispatch/RouteNotFoundError.js +0 -24
- package/dist/dispatch/RouteNotFoundError.js.map +0 -1
- package/dist/entry/DynamicFacade.d.ts +0 -10
- package/dist/entry/DynamicFacade.d.ts.map +0 -1
- package/dist/entry/DynamicFacade.js +0 -27
- package/dist/entry/DynamicFacade.js.map +0 -1
- package/dist/entry/FacadeEntry.d.ts +0 -11
- package/dist/entry/FacadeEntry.d.ts.map +0 -1
- package/dist/entry/FacadeEntry.js +0 -26
- package/dist/entry/FacadeEntry.js.map +0 -1
- package/dist/entry/TransportEntry.d.ts +0 -13
- package/dist/entry/TransportEntry.d.ts.map +0 -1
- package/dist/entry/TransportEntry.js +0 -24
- package/dist/entry/TransportEntry.js.map +0 -1
- package/dist/rows.d.ts +0 -40
- package/dist/rows.d.ts.map +0 -1
- package/dist/rows.js +0 -146
- package/dist/rows.js.map +0 -1
- package/src/boot/HandlerFacade.ts +0 -242
- package/src/contract/Call.ts +0 -18
- package/src/contract/CallLog.ts +0 -55
- package/src/dispatch/InputValidator.ts +0 -28
- package/src/dispatch/OperationExecutor.ts +0 -60
- package/src/dispatch/OutputProjector.ts +0 -32
- package/src/dispatch/PresenterArgumentResolver.ts +0 -25
- package/src/dispatch/RouteNotFoundError.ts +0 -29
- package/src/entry/DynamicFacade.ts +0 -28
- package/src/entry/FacadeEntry.ts +0 -32
- package/src/entry/TransportEntry.ts +0 -30
- package/src/rows.ts +0 -155
- /package/dist/{contract → wire}/CallLog.js +0 -0
package/src/verify.ts
CHANGED
|
@@ -5,24 +5,11 @@ import { storageKeyOf } from './storage.js';
|
|
|
5
5
|
import { presenterKeyOf } from './prefab/presenter.js';
|
|
6
6
|
import { collectorKeyOf } from './prefab/collector.js';
|
|
7
7
|
|
|
8
|
-
/**
|
|
9
|
-
* What a rule found in an app.
|
|
10
|
-
*
|
|
11
|
-
* `message` is the sentence the rule replaces — the prose a human used to have
|
|
12
|
-
* to remember. `Known issues` says "Keep collectors in the consuming frond";
|
|
13
|
-
* this is that sentence, told about a specific handler, by something that runs.
|
|
14
|
-
*/
|
|
8
|
+
/** What a rule found in an app. */
|
|
15
9
|
export interface Violation {
|
|
16
10
|
/** Rule name, stable — 'cross-frond-dependency'. */
|
|
17
11
|
rule: string;
|
|
18
|
-
/**
|
|
19
|
-
* What it costs, decided by the rule that raises it — never by whoever renders it.
|
|
20
|
-
*
|
|
21
|
-
* The two rules here are not the same animal: a cross-frond dependency resolves
|
|
22
|
-
* today and stops resolving the day the other frond answers over the wire, while a
|
|
23
|
-
* collector declared elsewhere is already wrong in one process. A reader holding a
|
|
24
|
-
* table of rule names would be a second opinion on a fact the rule already has.
|
|
25
|
-
*/
|
|
12
|
+
/** What it costs, decided by the rule that raises it — never by whoever renders it. */
|
|
26
13
|
severity: 'blocking' | 'warning';
|
|
27
14
|
/** The frond the subject lives in. */
|
|
28
15
|
frond: string;
|
|
@@ -30,15 +17,7 @@ export interface Violation {
|
|
|
30
17
|
subject: string;
|
|
31
18
|
/** Where to go and look. */
|
|
32
19
|
filePath: string;
|
|
33
|
-
/**
|
|
34
|
-
* What the subject reaches for, and where it actually lives.
|
|
35
|
-
*
|
|
36
|
-
* `frond` above is the CONSUMER; the target used to exist only inside the
|
|
37
|
-
* sentence. A reader that has to parse prose to learn which frond a violation
|
|
38
|
-
* points at is a second opinion on a fact the checker already held — so the
|
|
39
|
-
* boot can ask "does this violation target a frond named in `remotes:`?" by
|
|
40
|
-
* reading a field.
|
|
41
|
-
*/
|
|
20
|
+
/** What the subject reaches for, and where it actually lives. */
|
|
42
21
|
dependsOn: { key: string; frond: string; kind: string };
|
|
43
22
|
/** What breaks, and what the caller gets instead. */
|
|
44
23
|
message: string;
|
|
@@ -48,20 +27,16 @@ export interface Violation {
|
|
|
48
27
|
type Registration = { frond: string; kind: string };
|
|
49
28
|
|
|
50
29
|
/**
|
|
51
|
-
* The container keys a frond registers in its own scope, keyed as a handler's
|
|
52
|
-
*
|
|
53
|
-
*
|
|
54
|
-
* Every key comes from the function that states it, never from a derivation
|
|
55
|
-
* respelled here: a second reader that spells one differently finds nothing and
|
|
56
|
-
* reports nothing wrong, which is the failure mode a checker must not have.
|
|
30
|
+
* The container keys a frond registers in its own scope, keyed as a handler's `deps` spell them —
|
|
31
|
+
* DI resolves by type name, so both sides are PascalCase.
|
|
57
32
|
*/
|
|
58
33
|
function registrationsOf(frond: FrondDescriptor): Map<string, Registration> {
|
|
59
34
|
const out = new Map<string, Registration>();
|
|
60
35
|
const put = (key: string, kind: string) => out.set(key, { frond: frond.name, kind });
|
|
61
36
|
|
|
62
|
-
for (const
|
|
63
|
-
for (const
|
|
64
|
-
for (const
|
|
37
|
+
for (const provider of frond.providers) put(provider.ctor.name, 'provider');
|
|
38
|
+
for (const presenter of frond.presenters) put(presenterKeyOf(presenter.entityName), 'presenter');
|
|
39
|
+
for (const collector of frond.collectors) put(collectorKeyOf(collector.typeName), 'collector');
|
|
65
40
|
for (const e of frond.entities) {
|
|
66
41
|
put(storageKeyOf(e.name), 'storage');
|
|
67
42
|
put(repositoryKeyOf(e.name), 'repository');
|
|
@@ -69,11 +44,7 @@ function registrationsOf(frond: FrondDescriptor): Map<string, Registration> {
|
|
|
69
44
|
return out;
|
|
70
45
|
}
|
|
71
46
|
|
|
72
|
-
/**
|
|
73
|
-
* Everything in a frond that is constructed by DI, so carries `deps`.
|
|
74
|
-
* Handlers, presenters and collectors are all built from a constructor whose
|
|
75
|
-
* argument types the scan read; each one can therefore reach across.
|
|
76
|
-
*/
|
|
47
|
+
/** Everything in a frond that is constructed by DI, so carries `deps`. */
|
|
77
48
|
function injectablesOf(frond: FrondDescriptor) {
|
|
78
49
|
return [
|
|
79
50
|
...frond.handlers.map((h) => ({ name: h.ctor.name, deps: h.deps, filePath: h.filePath })),
|
|
@@ -83,20 +54,8 @@ function injectablesOf(frond: FrondDescriptor) {
|
|
|
83
54
|
}
|
|
84
55
|
|
|
85
56
|
/**
|
|
86
|
-
* Does this app survive being split?
|
|
87
|
-
*
|
|
88
|
-
* A frond runs in-process or in its own process behind JSON-RPC with identical
|
|
89
|
-
* user code — that is the whole claim. What the claim does not say is that
|
|
90
|
-
* *every* app survives the move: a dependency that crosses a frond boundary
|
|
91
|
-
* resolves today because both scopes live in one container, and resolves to
|
|
92
|
-
* nothing the day the other frond answers over the wire.
|
|
93
|
-
*
|
|
94
|
-
* The question only exists where a module boundary is meant to become a process
|
|
95
|
-
* boundary later. Where every inter-module call is already remote there is
|
|
96
|
-
* nothing to check, and where no exit is planned there is nothing to check
|
|
97
|
-
* either. Here it means something, and until now it had no answer.
|
|
98
|
-
*
|
|
99
|
-
* Pure over `app.fronds`: no mount, no process, no file. Call it from a test.
|
|
57
|
+
* Does this app survive being split? A frond runs in-process or in its own process behind JSON-RPC
|
|
58
|
+
* with identical user code — that is the whole claim.
|
|
100
59
|
*/
|
|
101
60
|
export function verify(app: { fronds: readonly FrondDescriptor[] }): Violation[] {
|
|
102
61
|
const index = new Map<string, Registration>();
|
|
@@ -109,7 +68,7 @@ export function verify(app: { fronds: readonly FrondDescriptor[] }): Violation[]
|
|
|
109
68
|
// they need their own index and their own rule.
|
|
110
69
|
const collectorFronds = new Map<string, string>();
|
|
111
70
|
for (const frond of app.fronds) {
|
|
112
|
-
for (const
|
|
71
|
+
for (const collector of frond.collectors) collectorFronds.set(collector.typeName, frond.name);
|
|
113
72
|
}
|
|
114
73
|
|
|
115
74
|
const violations: Violation[] = [];
|
|
@@ -144,8 +103,8 @@ export function verify(app: { fronds: readonly FrondDescriptor[] }): Violation[]
|
|
|
144
103
|
|
|
145
104
|
// Rule 2 — an operation parameter that wanted a collector this frond has not
|
|
146
105
|
// got. The preliminary binding convention can only see this frond's collector
|
|
147
|
-
// set, so it produces
|
|
148
|
-
// before boot: another frond's collector proves the provenance is not
|
|
106
|
+
// set, so it produces input evidence. EffectiveOperation refuses that evidence
|
|
107
|
+
// before boot: another frond's collector proves the provenance is not an input.
|
|
149
108
|
const own = new Set(frond.collectors.map((c) => c.typeName));
|
|
150
109
|
for (const handler of frond.handlers) {
|
|
151
110
|
for (const [opName, op] of handler.operations) {
|
|
@@ -156,7 +115,7 @@ export function verify(app: { fronds: readonly FrondDescriptor[] }): Violation[]
|
|
|
156
115
|
const wanted = lowerFirst(param.type.name);
|
|
157
116
|
if (own.has(wanted)) continue;
|
|
158
117
|
const elsewhere = collectorFronds.get(wanted);
|
|
159
|
-
// No collector anywhere for that type may be an ordinary
|
|
118
|
+
// No collector anywhere for that type may be an ordinary input parameter.
|
|
160
119
|
// Only a collector that exists in the wrong place makes that interpretation
|
|
161
120
|
// provably false.
|
|
162
121
|
if (!elsewhere) continue;
|
|
@@ -170,7 +129,7 @@ export function verify(app: { fronds: readonly FrondDescriptor[] }): Violation[]
|
|
|
170
129
|
message:
|
|
171
130
|
`'${param.name}' is typed ${param.type.name}, and the collector that produces one ` +
|
|
172
131
|
`is declared in frond '${elsewhere}'. A binding plan only sees its own frond's ` +
|
|
173
|
-
`collectors, so the preliminary
|
|
132
|
+
`collectors, so the preliminary input interpretation is invalid. Fougere refuses ` +
|
|
174
133
|
`the operation before it can receive what the caller sent. ` +
|
|
175
134
|
`Move the collector into '${frond.name}'.`,
|
|
176
135
|
});
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import type { RouteKind } from './RouteAddress.js';
|
|
2
|
+
|
|
3
|
+
/** What crosses the door. */
|
|
4
|
+
export interface CallRecord {
|
|
5
|
+
/** Monotonic, and the whole cursor protocol: a reader asks for what is above its own. */
|
|
6
|
+
seq: number;
|
|
7
|
+
frond?: string;
|
|
8
|
+
entity: string;
|
|
9
|
+
operation: string;
|
|
10
|
+
surface?: string;
|
|
11
|
+
/** Known at `resolved`, so absent on a call that never found a route. */
|
|
12
|
+
route?: RouteKind;
|
|
13
|
+
/** The traceparent the invocation carried, when one did. */
|
|
14
|
+
trace?: string;
|
|
15
|
+
/** The peer that established this call, when one did. */
|
|
16
|
+
caller?: string;
|
|
17
|
+
startedAt: number;
|
|
18
|
+
/** Known at `settled`. */
|
|
19
|
+
ms?: number;
|
|
20
|
+
verdict: 'running' | 'ok' | 'failed';
|
|
21
|
+
refusal?: { code?: string; message: string };
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
/** One page of the ring. */
|
|
25
|
+
export interface CallPage {
|
|
26
|
+
calls: CallRecord[];
|
|
27
|
+
cursor: number;
|
|
28
|
+
inFlight: number;
|
|
29
|
+
dropped: number;
|
|
30
|
+
}
|
|
@@ -1,15 +1,16 @@
|
|
|
1
1
|
export interface InvocationContext {
|
|
2
2
|
params: Record<string, unknown>;
|
|
3
3
|
query: Record<string, unknown>;
|
|
4
|
-
|
|
4
|
+
input: unknown;
|
|
5
5
|
state: Record<string, unknown>;
|
|
6
6
|
trace?: string;
|
|
7
7
|
identity?: string;
|
|
8
8
|
caller?: string;
|
|
9
9
|
}
|
|
10
10
|
|
|
11
|
-
export type
|
|
11
|
+
export type PartialInvocation = Partial<InvocationContext>;
|
|
12
12
|
|
|
13
|
+
/** Freezes plain data deeply, and leaves a class instance alone — a `Date` is not a record. */
|
|
13
14
|
function canonicalValue(value: unknown): unknown {
|
|
14
15
|
if (value === null || value === undefined || typeof value !== 'object') return value;
|
|
15
16
|
if (Array.isArray(value)) return Object.freeze(value.map(canonicalValue));
|
|
@@ -19,6 +20,7 @@ function canonicalValue(value: unknown): unknown {
|
|
|
19
20
|
return canonicalRecord(value);
|
|
20
21
|
}
|
|
21
22
|
|
|
23
|
+
/** Drops the keys set to `undefined`, so an input and its JSON round-trip agree. */
|
|
22
24
|
function canonicalRecord(value: unknown): Record<string, unknown> {
|
|
23
25
|
if (!value || typeof value !== 'object' || Array.isArray(value)) return Object.freeze({});
|
|
24
26
|
|
|
@@ -33,33 +35,37 @@ function canonicalRecord(value: unknown): Record<string, unknown> {
|
|
|
33
35
|
export class Invocation implements InvocationContext {
|
|
34
36
|
readonly params: Record<string, unknown>;
|
|
35
37
|
readonly query: Record<string, unknown>;
|
|
36
|
-
readonly
|
|
38
|
+
readonly input: unknown;
|
|
37
39
|
readonly state: Record<string, unknown>;
|
|
38
40
|
readonly trace?: string;
|
|
39
41
|
readonly identity?: string;
|
|
40
42
|
readonly caller?: string;
|
|
41
43
|
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
this.
|
|
45
|
-
this.
|
|
44
|
+
/** Gives every entry and every transport the same seven-member value, frozen. */
|
|
45
|
+
private constructor(context: PartialInvocation) {
|
|
46
|
+
this.params = canonicalRecord(context.params);
|
|
47
|
+
this.query = canonicalRecord(context.query);
|
|
48
|
+
this.input = canonicalValue(context.input);
|
|
46
49
|
// State is host-owned and may still be enriched by existing middlewares. Moving it
|
|
47
50
|
// to immutable lifecycle context is a separate migration.
|
|
48
|
-
this.state =
|
|
49
|
-
if (
|
|
50
|
-
if (
|
|
51
|
-
if (
|
|
51
|
+
this.state = context.state ?? {};
|
|
52
|
+
if (context.trace !== undefined) this.trace = context.trace;
|
|
53
|
+
if (context.identity !== undefined) this.identity = context.identity;
|
|
54
|
+
if (context.caller !== undefined) this.caller = context.caller;
|
|
52
55
|
Object.freeze(this);
|
|
53
56
|
}
|
|
54
57
|
|
|
55
|
-
|
|
56
|
-
|
|
58
|
+
/** Takes a raw object or an invocation, so a caller never has to know which it holds. */
|
|
59
|
+
static from(context?: PartialInvocation): Invocation {
|
|
60
|
+
return context instanceof Invocation ? context : new Invocation(context ?? {});
|
|
57
61
|
}
|
|
58
62
|
|
|
59
|
-
|
|
60
|
-
|
|
63
|
+
/** Replaces the input — how the façade hands on the value it parsed. */
|
|
64
|
+
withInput(input: unknown): Invocation {
|
|
65
|
+
return new Invocation({ ...this, input });
|
|
61
66
|
}
|
|
62
67
|
|
|
68
|
+
/** Replaces the host-owned state, which a middleware enriches before the handler runs. */
|
|
63
69
|
withState(state: Record<string, unknown>): Invocation {
|
|
64
70
|
return new Invocation({ ...this, state });
|
|
65
71
|
}
|
|
@@ -67,6 +73,7 @@ export class Invocation implements InvocationContext {
|
|
|
67
73
|
|
|
68
74
|
export const EMPTY_INVOCATION = Invocation.from();
|
|
69
75
|
|
|
70
|
-
|
|
71
|
-
|
|
76
|
+
/** Names the same gesture as `Invocation.from` for callers that read better this way. */
|
|
77
|
+
export function canonicalInvocation(context?: PartialInvocation): Invocation {
|
|
78
|
+
return Invocation.from(context);
|
|
72
79
|
}
|
|
@@ -7,11 +7,13 @@ export interface RouteAddressInput {
|
|
|
7
7
|
surface?: string;
|
|
8
8
|
}
|
|
9
9
|
|
|
10
|
+
/** Refuses an empty segment, so no address can be built that nothing can serve. */
|
|
10
11
|
function required(value: string, name: string): string {
|
|
11
12
|
if (value.trim().length === 0) throw new TypeError(`Route ${name} cannot be empty`);
|
|
12
13
|
return value;
|
|
13
14
|
}
|
|
14
15
|
|
|
16
|
+
/** Applies the same refusal to a segment that may be absent, but not blank. */
|
|
15
17
|
function optional(value: string | undefined, name: string): string | undefined {
|
|
16
18
|
return value === undefined ? undefined : required(value, name);
|
|
17
19
|
}
|
|
@@ -22,6 +24,7 @@ export class RouteAddress {
|
|
|
22
24
|
readonly operation: string;
|
|
23
25
|
readonly surface?: string;
|
|
24
26
|
|
|
27
|
+
/** Names one callable operation, and freezes it so a registry key cannot drift. */
|
|
25
28
|
constructor(input: RouteAddressInput) {
|
|
26
29
|
this.entity = required(input.entity, 'entity');
|
|
27
30
|
this.operation = required(input.operation, 'operation');
|
|
@@ -29,19 +32,23 @@ export class RouteAddress {
|
|
|
29
32
|
Object.freeze(this);
|
|
30
33
|
}
|
|
31
34
|
|
|
35
|
+
/** Serializes the three segments so a route can be looked up in a `Map`. */
|
|
32
36
|
key(): string {
|
|
33
37
|
return JSON.stringify([this.surface ?? null, this.entity, this.operation]);
|
|
34
38
|
}
|
|
35
39
|
|
|
40
|
+
/** Compares two addresses by their key, so `surface` counts as much as the operation. */
|
|
36
41
|
equals(other: RouteAddress): boolean {
|
|
37
42
|
return this.key() === other.key();
|
|
38
43
|
}
|
|
39
44
|
|
|
45
|
+
/** Writes the address the way a log and an error message name it. */
|
|
40
46
|
toString(): string {
|
|
41
47
|
const audience = this.surface ? `${this.surface}/` : '';
|
|
42
48
|
return `${audience}${this.entity}.${this.operation}`;
|
|
43
49
|
}
|
|
44
50
|
|
|
51
|
+
/** Sends the address over the wire without `surface: undefined` riding along. */
|
|
45
52
|
toJSON(): RouteAddressInput {
|
|
46
53
|
return {
|
|
47
54
|
entity: this.entity,
|
package/src/wire/binding.ts
CHANGED
|
@@ -1,10 +1,6 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Where each parameter of an operation gets its value — decided once at boot from the
|
|
3
|
-
*
|
|
4
|
-
*
|
|
5
|
-
* The branches are ORDERED and each states why it sits where it does; the list used to
|
|
6
|
-
* be repeated here too, and it had already lost `Fact` — the one whose position is
|
|
7
|
-
* load-bearing, since the fall-through would otherwise hand it the caller's body.
|
|
2
|
+
* Where each parameter of an operation gets its value — decided once at boot from the parsed
|
|
3
|
+
* signature, replayed per call by `resolveArgs`.
|
|
8
4
|
*/
|
|
9
5
|
import type { Param } from './signature.js';
|
|
10
6
|
import { lowerFirst } from '@fougere/schema';
|
|
@@ -13,17 +9,10 @@ import { lowerFirst } from '@fougere/schema';
|
|
|
13
9
|
|
|
14
10
|
type ParamSource =
|
|
15
11
|
| { kind: 'collector'; typeName: string }
|
|
16
|
-
/**
|
|
17
|
-
* `Fact<PostPublished>` — something that happened, not something a caller typed.
|
|
18
|
-
*
|
|
19
|
-
* It resolves from the body exactly like `body` does, and that is deliberate: an
|
|
20
|
-
* emission and a direct call ARE the same call, so a subscriber cannot tell them apart
|
|
21
|
-
* and does not need to. The branch exists so the PLAN says what this parameter is —
|
|
22
|
-
* that sentence is what makes the subscriber index readable without reparsing types.
|
|
23
|
-
*/
|
|
12
|
+
/** `Fact<PostPublished>` — something that happened, not something a caller typed. */
|
|
24
13
|
| { kind: 'fact'; factName: string }
|
|
25
14
|
| { kind: 'param'; name: string; coerce?: 'number' | 'boolean' }
|
|
26
|
-
| { kind: '
|
|
15
|
+
| { kind: 'input' }
|
|
27
16
|
| { kind: 'context' }
|
|
28
17
|
/** The whole query bag, for an op whose argument IS the options (list). */
|
|
29
18
|
| { kind: 'query' };
|
|
@@ -48,12 +37,7 @@ function coercionFor(typeName: string): 'number' | 'boolean' | undefined {
|
|
|
48
37
|
|
|
49
38
|
// ── Compute ───────────────────────────────────
|
|
50
39
|
|
|
51
|
-
/**
|
|
52
|
-
* Build a BindingPlan from parsed method params.
|
|
53
|
-
*
|
|
54
|
-
* @param params - Parsed parameter list from AST
|
|
55
|
-
* @param collectorTypeNames - Registration keys of the types a Collector answers for
|
|
56
|
-
*/
|
|
40
|
+
/** Build a BindingPlan from parsed method params. */
|
|
57
41
|
export function computeBindingPlan(
|
|
58
42
|
params: Param[],
|
|
59
43
|
collectorTypeNames: Set<string>,
|
|
@@ -62,11 +46,11 @@ export function computeBindingPlan(
|
|
|
62
46
|
const typeName = param.type.name;
|
|
63
47
|
// `lowerFirst`, never `toLowerCase()`: the collector set is keyed the way the
|
|
64
48
|
// scan spells it, and the two agree on one word only — `AuthorUser` looked up as
|
|
65
|
-
// `authoruser` missed `authorUser` and fell through to branch 4, the request
|
|
49
|
+
// `authoruser` missed `authorUser` and fell through to branch 4, the request input.
|
|
66
50
|
const typeKey = lowerFirst(typeName);
|
|
67
51
|
|
|
68
52
|
// 0. Fact — `Fact<X>` names itself, so nothing has to be known in advance. It comes
|
|
69
|
-
// FIRST because branch 4 would otherwise hand it the caller's
|
|
53
|
+
// FIRST because branch 4 would otherwise hand it the caller's input under the name
|
|
70
54
|
// of something that happened.
|
|
71
55
|
const factOf = param.type.name === 'Fact' ? param.type.generics?.[0]?.name : undefined;
|
|
72
56
|
if (factOf) {
|
|
@@ -108,10 +92,10 @@ export function computeBindingPlan(
|
|
|
108
92
|
};
|
|
109
93
|
}
|
|
110
94
|
|
|
111
|
-
// 4. Everything else —
|
|
95
|
+
// 4. Everything else — input
|
|
112
96
|
return {
|
|
113
97
|
name: param.name,
|
|
114
|
-
source: { kind: '
|
|
98
|
+
source: { kind: 'input' as const },
|
|
115
99
|
optional: param.optional ?? false,
|
|
116
100
|
};
|
|
117
101
|
});
|
package/src/wire/call.ts
CHANGED
|
@@ -1,16 +1,22 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Call contract — a frond call is a value.
|
|
3
|
-
*
|
|
4
|
-
* (frond, entity, op, invocation) → result, or a thrown FougereError.
|
|
5
|
-
* A transport is a function that executes this call elsewhere; the local
|
|
6
|
-
* runner below is the reference realization. Transports move the value,
|
|
7
|
-
* they never reshape it.
|
|
8
|
-
*/
|
|
1
|
+
/** Call contract — a frond call is a value. */
|
|
9
2
|
import { Card, type SchemaDescriptor } from '@fougere/schema';
|
|
10
3
|
import { factsAnnouncedBy } from '../emit.js';
|
|
11
|
-
import type
|
|
4
|
+
import { Invocation, type InvocationContext, type PartialInvocation } from './Invocation.js';
|
|
5
|
+
import type { RouteAddress } from './RouteAddress.js';
|
|
12
6
|
import { FougereError, ErrorCode } from './errors.js';
|
|
13
7
|
|
|
8
|
+
/** One normalized request, frozen: where it goes and what the caller supplied. */
|
|
9
|
+
export class Call {
|
|
10
|
+
readonly address: RouteAddress;
|
|
11
|
+
readonly invocation: Invocation;
|
|
12
|
+
|
|
13
|
+
constructor(address: RouteAddress, invocation?: PartialInvocation) {
|
|
14
|
+
this.address = address;
|
|
15
|
+
this.invocation = Invocation.from(invocation);
|
|
16
|
+
Object.freeze(this);
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
|
|
14
20
|
/** Target of a call — which façade operation, wherever it lives. */
|
|
15
21
|
export interface FrondCall {
|
|
16
22
|
/** Frond name, when the caller knows it. Routing hint only. */
|
|
@@ -25,49 +31,27 @@ export interface FrondCall {
|
|
|
25
31
|
export type Transport = (call: FrondCall, invocation: InvocationContext) => Promise<unknown>;
|
|
26
32
|
|
|
27
33
|
/** Reserved namespace — calls the runner answers itself, never a façade. */
|
|
28
|
-
/**
|
|
29
|
-
* What a receiver accepts before it stops reading a body.
|
|
30
|
-
*
|
|
31
|
-
* Stated once because it was stated FOUR times — `transport/http/policy.ts` said so in its
|
|
32
|
-
* own comment ("spelled in four packages") while three doors kept their own literal, so
|
|
33
|
-
* raising the cap here used to leave three of them refusing at the old one.
|
|
34
|
-
*
|
|
35
|
-
* `@fougere/http` keeps a fourth copy on purpose: it declares no Fougere dependency at all,
|
|
36
|
-
* and giving a leaf port a dependency on the kernel to share a number is the wrong trade.
|
|
37
|
-
*/
|
|
34
|
+
/** What a receiver accepts before it stops reading an input. */
|
|
38
35
|
export const MAX_BODY_BYTES = 1024 * 1024;
|
|
39
36
|
|
|
40
37
|
export const RPC_ENTITY = 'rpc';
|
|
41
38
|
|
|
42
|
-
/**
|
|
43
|
-
* What an `rpc` op answers — the door for what the app says about ITSELF, never about a row.
|
|
44
|
-
*
|
|
45
|
-
* `discover` is core's own, registered like any other (`bootstrap.ts`): a package declares
|
|
46
|
-
* its reading beside it, and an app that installed none serves none.
|
|
47
|
-
*/
|
|
39
|
+
/** What an `rpc` op answers — the door for what the app says about ITSELF, never about a row. */
|
|
48
40
|
export type RpcAnswer = (invocation: InvocationContext, surface?: string) => unknown;
|
|
49
41
|
|
|
50
|
-
/**
|
|
51
|
-
* Everything a caller's envelope covers — the call as the sender meant it.
|
|
52
|
-
*
|
|
53
|
-
* Here and not beside the signing code because it is a CONTRACT: the sender binds it,
|
|
54
|
-
* the receiver re-presents what arrived, and a frond written in another language reads
|
|
55
|
-
* this shape without reading our crypto. `body` is bound by digest (arbitrary, possibly
|
|
56
|
-
* large), the rest by value — which is what keeps a canonical-JSON dependency out.
|
|
57
|
-
*/
|
|
42
|
+
/** Everything a caller's envelope covers — the call as the sender meant it. */
|
|
58
43
|
export interface SignedCall {
|
|
59
44
|
entity: string;
|
|
60
45
|
op: string;
|
|
61
46
|
params?: Record<string, unknown>;
|
|
62
47
|
query?: Record<string, unknown>;
|
|
63
|
-
|
|
48
|
+
input?: unknown;
|
|
64
49
|
state?: Record<string, unknown>;
|
|
65
50
|
}
|
|
66
51
|
|
|
67
52
|
/**
|
|
68
|
-
* One operation, as a stranger meets it — its name, what it is for, what it takes
|
|
69
|
-
*
|
|
70
|
-
* it just never left the process.
|
|
53
|
+
* One operation, as a stranger meets it — its name, what it is for, what it takes and whether it
|
|
54
|
+
* reads or writes.
|
|
71
55
|
*/
|
|
72
56
|
export interface CardOp {
|
|
73
57
|
name: string;
|
|
@@ -79,57 +63,21 @@ export interface CardOp {
|
|
|
79
63
|
output?: SchemaDescriptor;
|
|
80
64
|
/** `query` reads, `command` writes — the same call REST turns into GET vs POST. */
|
|
81
65
|
kind: 'query' | 'command';
|
|
82
|
-
/**
|
|
83
|
-
* How much `output` describes: one row, maybe one, many, a page, or nothing shaped.
|
|
84
|
-
* `output` alone is the shape of a ROW, so a consumer generating a signature from
|
|
85
|
-
* this card would otherwise have to guess — and `list` returning a page rather than
|
|
86
|
-
* an array is exactly the guess it would get wrong.
|
|
87
|
-
*/
|
|
66
|
+
/** How much `output` describes. */
|
|
88
67
|
cardinality?: 'one' | 'maybe' | 'many' | 'page' | 'none';
|
|
89
68
|
}
|
|
90
69
|
|
|
91
|
-
/**
|
|
92
|
-
* What an app hosts — the wire projection of its scanned fronds.
|
|
93
|
-
*
|
|
94
|
-
* Two lists per frond, and they are duals: **what you may call**, and **what you will
|
|
95
|
-
* receive**. A door is entered from outside; a fact leaves on its own.
|
|
96
|
-
*
|
|
97
|
-
* `doors` was called `entities` and the name lied: an entry is an ADDRESS, and the shape
|
|
98
|
-
* behind it is optional (`facadeKeyOf` builds its key from a handler's name, which need not
|
|
99
|
-
* be an entity's). The lie cost something real — `fougere sync` demanded a descriptor on
|
|
100
|
-
* every entry and refused whole cards over a health check.
|
|
101
|
-
*/
|
|
70
|
+
/** What an app hosts — the wire projection of its scanned fronds. */
|
|
102
71
|
export interface IdentityCard {
|
|
103
72
|
fronds: {
|
|
104
73
|
name: string;
|
|
105
74
|
doors: {
|
|
106
75
|
name: string;
|
|
107
76
|
ops: CardOp[];
|
|
108
|
-
/**
|
|
109
|
-
* The shape stored under this name — **absent when nothing is**. A handler may
|
|
110
|
-
* carry no entity (`bootstrap`: *pointing at nothing is legal*), and a door with
|
|
111
|
-
* no rows behind it is ordinary: a health check, a computation, a search across
|
|
112
|
-
* several shapes. A reader that needs the shape must say what it does without one.
|
|
113
|
-
*/
|
|
77
|
+
/** The shape stored under this name — **absent when nothing is**. */
|
|
114
78
|
schema?: SchemaDescriptor;
|
|
115
79
|
}[];
|
|
116
|
-
/**
|
|
117
|
-
* The facts this frond ANNOUNCES — one entry per `Emit<T>` its handlers inject.
|
|
118
|
-
*
|
|
119
|
-
* They carry no operation, which is why they cannot ride in `doors`: the rule there is
|
|
120
|
-
* *hosting means answering*, and an entity with no façade is excluded on purpose (it
|
|
121
|
-
* would publish the auth tables to anyone who asks). A fact is the opposite case —
|
|
122
|
-
* someone WROTE that it leaves, so publishing its shape is honouring a statement, not
|
|
123
|
-
* leaking one.
|
|
124
|
-
*
|
|
125
|
-
* Without this, a fact stopped at the repository boundary: `remotes:` gives the
|
|
126
|
-
* location, colocation gives the contract, and across two repositories there is no
|
|
127
|
-
* colocation. The subscriber had to hand-copy the emitter's declaration.
|
|
128
|
-
*
|
|
129
|
-
* `schema` is absent when the announced type is not a declared entity — legal (nothing
|
|
130
|
-
* requires a fact to be one) and worth saying rather than hiding: the name travels, the
|
|
131
|
-
* shape does not, and a consumer can see exactly that.
|
|
132
|
-
*/
|
|
80
|
+
/** The facts this frond ANNOUNCES — one entry per `Emit<T>` its handlers inject. */
|
|
133
81
|
facts: { name: string; schema?: SchemaDescriptor }[];
|
|
134
82
|
}[];
|
|
135
83
|
}
|
|
@@ -150,17 +98,7 @@ export interface Edge {
|
|
|
150
98
|
errors: number;
|
|
151
99
|
}
|
|
152
100
|
|
|
153
|
-
/**
|
|
154
|
-
* The shape of the system as ONE process discovered it — the answer to `rpc.topology`.
|
|
155
|
-
*
|
|
156
|
-
* Here and not in the package that produces it, for the reason `SignedCall` is here: it
|
|
157
|
-
* crosses a process boundary, so a reader consumes it without depending on the producer.
|
|
158
|
-
* `@fougere/observability` fills it; a panel reads it; neither imports the other.
|
|
159
|
-
*
|
|
160
|
-
* Nothing in it is declared — a frond is `local` because this process scanned it, `remote`
|
|
161
|
-
* because it answered a call nobody here hosts. `remotes:` states an intent, and the two
|
|
162
|
-
* disagree exactly when something is misconfigured.
|
|
163
|
-
*/
|
|
101
|
+
/** The shape of the system as ONE process discovered it — the answer to `rpc.topology`. */
|
|
164
102
|
export interface TopologyReport {
|
|
165
103
|
/** When this process started counting — an edge count is read against it. */
|
|
166
104
|
since: number;
|
|
@@ -170,18 +108,7 @@ export interface TopologyReport {
|
|
|
170
108
|
edges: Edge[];
|
|
171
109
|
}
|
|
172
110
|
|
|
173
|
-
/**
|
|
174
|
-
* The shape a card must have to be walked — `fronds`, and each frond's `doors`.
|
|
175
|
-
*
|
|
176
|
-
* A card crosses a process boundary, so it is judged like anything else that does.
|
|
177
|
-
* The check lives beside the type because two readers walk it: the boot indexes a
|
|
178
|
-
* remote's doors, and `fougere sync` writes classes from them. `TypeError:
|
|
179
|
-
* card.fronds is not iterable` was what a malformed card produced at the boot,
|
|
180
|
-
* naming neither the remote nor the address.
|
|
181
|
-
*
|
|
182
|
-
* The descriptor behind a door is NOT checked here — `Card.toSchema` refuses it, and
|
|
183
|
-
* only where one is consumed.
|
|
184
|
-
*/
|
|
111
|
+
/** The shape a card must have to be walked — `fronds`, and each frond's `doors`. */
|
|
185
112
|
export function assertIdentityCard(value: unknown, source: string): IdentityCard {
|
|
186
113
|
const card = value as IdentityCard | undefined;
|
|
187
114
|
const fronds = Array.isArray(card?.fronds) ? card.fronds : undefined;
|
|
@@ -205,49 +132,19 @@ function cardRefusal(source: string, what: string): FougereError {
|
|
|
205
132
|
|
|
206
133
|
/** A façade as the runtime holds it: op names to functions, nothing typed about them. */
|
|
207
134
|
|
|
208
|
-
/**
|
|
209
|
-
* The door built in front of a handler — the framework's second port, after `Storage`.
|
|
210
|
-
*
|
|
211
|
-
* `Facade<PostHandler>` is what a neighbouring frond injects. It names what ARRIVES
|
|
212
|
-
* rather than what is written: never the handler (nobody injects it, and its methods take
|
|
213
|
-
* positional arguments), but the door, whose every op takes the invocation and whose
|
|
214
|
-
* implementation is the local façade or a doublure. A signature therefore says nothing
|
|
215
|
-
* about where the other frond runs, which is the whole point.
|
|
216
|
-
*
|
|
217
|
-
* `keyof T` is the right set by construction, not by approximation: the scan skips
|
|
218
|
-
* `private` and `protected` (`handler-parser.ts`) because "TypeScript already has the
|
|
219
|
-
* word for it", so a handler's public methods ARE its operations — and `keyof` excludes
|
|
220
|
-
* the rest for the same reason.
|
|
221
|
-
*/
|
|
135
|
+
/** The door built in front of a handler — the framework's second port, after `Storage`. */
|
|
222
136
|
export type Facade<T> = {
|
|
223
137
|
[K in keyof T]: T[K] extends (...args: never[]) => infer R
|
|
224
138
|
? (invocation?: InvocationContext) => R
|
|
225
139
|
: never;
|
|
226
140
|
};
|
|
227
141
|
|
|
228
|
-
/**
|
|
229
|
-
* The container key of a façade — THE one place that spells the format.
|
|
230
|
-
*
|
|
231
|
-
* A surface is a named audience, and it is a key: `handlers/public/PostHandler.ts`
|
|
232
|
-
* registers `public:postHandler` next to the default `postHandler`. The default
|
|
233
|
-
* surface is the empty key, so callers that know nothing about surfaces keep
|
|
234
|
-
* designating exactly what they designated before.
|
|
235
|
-
*
|
|
236
|
-
* Nobody outside this package builds this string: adapters ask `app.facadeFor()`,
|
|
237
|
-
* which is why an adapter can stay structurally typed and core-free.
|
|
238
|
-
*/
|
|
142
|
+
/** The container key of a façade — THE one place that spells the format. */
|
|
239
143
|
export function facadeKeyOf(entityName: string, surface?: string): string {
|
|
240
144
|
return surface ? `${surface}:${entityName}Handler` : `${entityName}Handler`;
|
|
241
145
|
}
|
|
242
146
|
|
|
243
|
-
/**
|
|
244
|
-
* Where the contracts behind a façade live — the dual of `facadeKeyOf`.
|
|
245
|
-
*
|
|
246
|
-
* The façade answers calls; it does not say what it answers. That sentence used
|
|
247
|
-
* to be true only inside `buildFacade`, so anything asking the app what it hosts
|
|
248
|
-
* got bare names. A door and its terms are registered together, under the same
|
|
249
|
-
* audience.
|
|
250
|
-
*/
|
|
147
|
+
/** Where the contracts behind a façade live — the dual of `facadeKeyOf`. */
|
|
251
148
|
export function contractsKeyOf(entityName: string, surface?: string): string {
|
|
252
149
|
return `${facadeKeyOf(entityName, surface)}:contracts`;
|
|
253
150
|
}
|