@winkjs/composer 0.0.2 → 0.4.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/LICENSE +1 -1
- package/README.md +42 -103
- package/package.json +53 -29
- package/src/composer.js +75 -0
- package/src/core/batch/aoo-encoder.js +148 -0
- package/src/core/batch/index.js +12 -0
- package/src/core/batch/sliding-window.js +91 -0
- package/src/core/codec/index.js +137 -0
- package/src/core/emitter-manager/mqtt/constants.js +102 -0
- package/src/core/emitter-manager/mqtt/emitter.js +780 -0
- package/src/core/emitter-manager/mqtt/index.js +190 -0
- package/src/core/emitter-manager/mqtt/mqtt-store.js +538 -0
- package/src/core/emitter-manager/terminal/assert-columns.js +98 -0
- package/src/core/emitter-manager/terminal/formatters.js +160 -0
- package/src/core/emitter-manager/terminal/index.js +341 -0
- package/src/core/env-vars.js +245 -0
- package/src/core/mqtt-protocol.js +47 -0
- package/src/core/partition-manager/index.js +7 -0
- package/src/core/partition-manager/init.js +44 -0
- package/src/core/partition-manager/introspect.js +15 -0
- package/src/core/partition-manager/publish-to.js +6 -0
- package/src/core/partition-manager/recompute.js +5 -0
- package/src/core/partition-manager/reset.js +5 -0
- package/src/core/partition-manager/update.js +264 -0
- package/src/core/partition-manager/validate-flow.js +157 -0
- package/src/core/semantics/digest.js +128 -0
- package/src/core/semantics/index.js +83 -0
- package/src/core/semantics/loader.js +571 -0
- package/src/core/semantics/schemas/asset-class-schema.js +218 -0
- package/src/core/semantics/schemas/column-schema.js +651 -0
- package/src/core/semantics/schemas/enum-schema.js +153 -0
- package/src/core/semantics/schemas/index.js +51 -0
- package/src/core/semantics/warnings.js +141 -0
- package/src/core/shutdown-manager/index.js +289 -0
- package/src/core/source-manager/csv/index.js +171 -0
- package/src/core/source-manager/csv/start.js +456 -0
- package/src/core/source-manager/mqtt/client.js +406 -0
- package/src/core/source-manager/mqtt/constants.js +147 -0
- package/src/core/source-manager/mqtt/dedup.js +244 -0
- package/src/core/source-manager/mqtt/index.js +260 -0
- package/src/core/source-manager/mqtt/status.js +546 -0
- package/src/core/source-manager/test-harness/comparator.js +226 -0
- package/src/core/source-manager/test-harness/field-generator.js +85 -0
- package/src/core/source-manager/test-harness/fuzz.js +87 -0
- package/src/core/source-manager/test-harness/index.js +115 -0
- package/src/core/source-manager/test-harness/prng.js +57 -0
- package/src/core/source-manager/test-harness/start.js +232 -0
- package/src/core/source-manager/test-harness/validate.js +213 -0
- package/src/core/storage-manager/questdb/assert-columns.js +120 -0
- package/src/core/storage-manager/questdb/ensure-tables.js +187 -0
- package/src/core/storage-manager/questdb/index.js +1251 -0
- package/src/core/storage-manager/questdb/persist-plan.js +488 -0
- package/src/core/storage-manager/questdb/writers.js +142 -0
- package/src/core/test-utils/sealed-record.js +80 -0
- package/src/core/test-utils/soak-signature.js +149 -0
- package/src/core/test-utils/tcp-proxy.js +106 -0
- package/src/core/tunable/helpers.js +254 -0
- package/src/core/tunable/index.js +87 -0
- package/src/core/utils/console-formatter/index.js +207 -0
- package/src/core/utils/create-smart-store-as/index.js +98 -0
- package/src/core/utils/create-smart-store-as/sanitize-field.js +46 -0
- package/src/core/utils/create-smart-store-as/smart-truncate.js +93 -0
- package/src/core/utils/flow/index.js +5 -0
- package/src/core/utils/flow/make-collision-checker.js +23 -0
- package/src/core/utils/flow/to-kebab.js +20 -0
- package/src/core/utils/half-life/index.js +111 -0
- package/src/core/utils/node/disable.js +11 -0
- package/src/core/utils/node/enable.js +11 -0
- package/src/core/utils/node/execute-triggers.js +40 -0
- package/src/core/utils/node/index.js +10 -0
- package/src/core/utils/node/pause.js +11 -0
- package/src/core/utils/node/populate-predicate-inputs.js +14 -0
- package/src/core/utils/node/publish-nan.js +19 -0
- package/src/core/utils/node/reset-predicate-inputs.js +11 -0
- package/src/core/utils/node/unpause.js +11 -0
- package/src/core/utils/node/validate-spec.js +22 -0
- package/src/core/utils/options/resolve-field-keyed.js +115 -0
- package/src/core/utils/quantize/index.js +75 -0
- package/src/core/utils/stats/formulas.js +67 -0
- package/src/core/utils/stats/index.js +3 -0
- package/src/core/utils/validate/composer-validators.js +141 -0
- package/src/core/utils/validate/helpers.js +206 -0
- package/src/core/utils/validate/index.js +12 -0
- package/src/core/utils/validate/type-validators.js +538 -0
- package/src/core/utils/validate/validate.js +107 -0
- package/src/core/utils/validate/validators.js +177 -0
- package/src/core/wiring/assert-handle.js +57 -0
- package/src/core/wiring/assert-module.js +63 -0
- package/src/core/wiring/index.js +5 -0
- package/src/core/wiring/node-type-to-module.js +17 -0
- package/src/core/wiring/wire-emitters.js +256 -0
- package/src/core/wiring/wire-linear-graph.js +25 -0
- package/src/core/wiring/wire-node.js +157 -0
- package/src/core/wiring/wire-semantics.js +173 -0
- package/src/core/wiring/wire-storages.js +344 -0
- package/src/flow/check-output-collisions.js +93 -0
- package/src/flow/consts.js +9 -0
- package/src/flow/deep-clone-spec.js +64 -0
- package/src/flow/driver.js +171 -0
- package/src/flow/expand-single-input-array.js +76 -0
- package/src/flow/expand-template-spec.js +93 -0
- package/src/flow/flow-api-schemas.js +300 -0
- package/src/flow/flow.js +658 -0
- package/src/flow/for-each.js +225 -0
- package/src/flow/get-signature-pattern.js +31 -0
- package/src/flow/get-target-array.js +46 -0
- package/src/flow/inspect.js +67 -0
- package/src/flow/load-node-module.js +81 -0
- package/src/flow/make-node-method.js +112 -0
- package/src/flow/resolve-pick-by-field.js +77 -0
- package/src/flow/resolve-tunables.js +76 -0
- package/src/flow/run.js +392 -0
- package/src/flow/serialize.js +161 -0
- package/src/flow/signatures-schema.js +222 -0
- package/src/flow/spec-builder.js +65 -0
- package/src/flow/validate-triggers.js +250 -0
- package/src/flow/validate.js +261 -0
- package/src/nodes/accumulate/index.js +21 -0
- package/src/nodes/accumulate/init.js +48 -0
- package/src/nodes/accumulate/introspect.js +123 -0
- package/src/nodes/accumulate/publish-to.js +34 -0
- package/src/nodes/accumulate/recompute.js +27 -0
- package/src/nodes/accumulate/reset.js +25 -0
- package/src/nodes/accumulate/update.js +42 -0
- package/src/nodes/appraise/calibrate.js +64 -0
- package/src/nodes/appraise/decision.js +66 -0
- package/src/nodes/appraise/deviation.js +140 -0
- package/src/nodes/appraise/index.js +23 -0
- package/src/nodes/appraise/init.js +165 -0
- package/src/nodes/appraise/integrate.js +45 -0
- package/src/nodes/appraise/introspect.js +352 -0
- package/src/nodes/appraise/publish-to.js +93 -0
- package/src/nodes/appraise/receptor.js +69 -0
- package/src/nodes/appraise/recompute.js +79 -0
- package/src/nodes/appraise/reset.js +53 -0
- package/src/nodes/appraise/update.js +130 -0
- package/src/nodes/archive/csv/index.js +6 -0
- package/src/nodes/archive/csv/init.js +36 -0
- package/src/nodes/archive/csv/load.js +70 -0
- package/src/nodes/archive/csv/reset.js +14 -0
- package/src/nodes/archive/csv/simple-parser.js +216 -0
- package/src/nodes/archive/csv/test.js +173 -0
- package/src/nodes/archive/csv/update.js +63 -0
- package/src/nodes/butterworth-filter/index.js +18 -0
- package/src/nodes/butterworth-filter/init.js +184 -0
- package/src/nodes/butterworth-filter/introspect.js +228 -0
- package/src/nodes/butterworth-filter/publish-to.js +21 -0
- package/src/nodes/butterworth-filter/recompute.js +13 -0
- package/src/nodes/butterworth-filter/reset.js +30 -0
- package/src/nodes/butterworth-filter/update.js +38 -0
- package/src/nodes/categorize/index.js +19 -0
- package/src/nodes/categorize/init.js +58 -0
- package/src/nodes/categorize/introspect.js +177 -0
- package/src/nodes/categorize/publish-to.js +29 -0
- package/src/nodes/categorize/recompute.js +14 -0
- package/src/nodes/categorize/reset.js +16 -0
- package/src/nodes/categorize/update.js +53 -0
- package/src/nodes/controller/index.js +9 -0
- package/src/nodes/controller/init.js +55 -0
- package/src/nodes/controller/introspect.js +91 -0
- package/src/nodes/controller/publish-to.js +8 -0
- package/src/nodes/controller/recompute.js +9 -0
- package/src/nodes/controller/reset.js +17 -0
- package/src/nodes/controller/update.js +63 -0
- package/src/nodes/diff/index.js +19 -0
- package/src/nodes/diff/init.js +37 -0
- package/src/nodes/diff/introspect.js +132 -0
- package/src/nodes/diff/publish-to.js +21 -0
- package/src/nodes/diff/recompute.js +12 -0
- package/src/nodes/diff/reset.js +12 -0
- package/src/nodes/diff/update.js +37 -0
- package/src/nodes/digest-moments/formulas.js +12 -0
- package/src/nodes/digest-moments/index.js +14 -0
- package/src/nodes/digest-moments/init.js +67 -0
- package/src/nodes/digest-moments/introspect.js +154 -0
- package/src/nodes/digest-moments/publish-to.js +34 -0
- package/src/nodes/digest-moments/recompute.js +14 -0
- package/src/nodes/digest-moments/reset.js +14 -0
- package/src/nodes/digest-moments/update.js +120 -0
- package/src/nodes/dwell-time-tracker/index.js +14 -0
- package/src/nodes/dwell-time-tracker/init.js +59 -0
- package/src/nodes/dwell-time-tracker/introspect.js +137 -0
- package/src/nodes/dwell-time-tracker/publish-to.js +22 -0
- package/src/nodes/dwell-time-tracker/recompute.js +8 -0
- package/src/nodes/dwell-time-tracker/reset.js +23 -0
- package/src/nodes/dwell-time-tracker/update.js +103 -0
- package/src/nodes/emit-if/helpers.js +94 -0
- package/src/nodes/emit-if/index.js +16 -0
- package/src/nodes/emit-if/init.js +67 -0
- package/src/nodes/emit-if/introspect.js +102 -0
- package/src/nodes/emit-if/publish-to.js +13 -0
- package/src/nodes/emit-if/recompute.js +12 -0
- package/src/nodes/emit-if/reset.js +27 -0
- package/src/nodes/emit-if/update.js +93 -0
- package/src/nodes/es-correlation/index.js +19 -0
- package/src/nodes/es-correlation/init.js +73 -0
- package/src/nodes/es-correlation/introspect.js +176 -0
- package/src/nodes/es-correlation/publish-to.js +32 -0
- package/src/nodes/es-correlation/recompute.js +56 -0
- package/src/nodes/es-correlation/reset.js +27 -0
- package/src/nodes/es-correlation/update.js +110 -0
- package/src/nodes/es-mean/index.js +20 -0
- package/src/nodes/es-mean/init.js +58 -0
- package/src/nodes/es-mean/introspect.js +129 -0
- package/src/nodes/es-mean/publish-to.js +19 -0
- package/src/nodes/es-mean/recompute.js +16 -0
- package/src/nodes/es-mean/reset.js +24 -0
- package/src/nodes/es-mean/update.js +69 -0
- package/src/nodes/es-pairwise-correlation/index.js +19 -0
- package/src/nodes/es-pairwise-correlation/init.js +98 -0
- package/src/nodes/es-pairwise-correlation/introspect.js +187 -0
- package/src/nodes/es-pairwise-correlation/publish-to.js +31 -0
- package/src/nodes/es-pairwise-correlation/recompute.js +69 -0
- package/src/nodes/es-pairwise-correlation/reset.js +29 -0
- package/src/nodes/es-pairwise-correlation/update.js +89 -0
- package/src/nodes/es-stats/index.js +21 -0
- package/src/nodes/es-stats/init.js +105 -0
- package/src/nodes/es-stats/introspect.js +157 -0
- package/src/nodes/es-stats/publish-to.js +42 -0
- package/src/nodes/es-stats/recompute.js +74 -0
- package/src/nodes/es-stats/reset.js +49 -0
- package/src/nodes/es-stats/update-envelope.js +44 -0
- package/src/nodes/es-stats/update-welford.js +64 -0
- package/src/nodes/es-stats/update.js +59 -0
- package/src/nodes/index.js +83 -0
- package/src/nodes/invert-flag/index.js +20 -0
- package/src/nodes/invert-flag/init.js +36 -0
- package/src/nodes/invert-flag/introspect.js +115 -0
- package/src/nodes/invert-flag/publish-to.js +23 -0
- package/src/nodes/invert-flag/recompute.js +12 -0
- package/src/nodes/invert-flag/reset.js +12 -0
- package/src/nodes/invert-flag/update.js +32 -0
- package/src/nodes/kalman1d/index.js +20 -0
- package/src/nodes/kalman1d/init.js +103 -0
- package/src/nodes/kalman1d/introspect.js +250 -0
- package/src/nodes/kalman1d/publish-to.js +34 -0
- package/src/nodes/kalman1d/recompute.js +23 -0
- package/src/nodes/kalman1d/reset.js +29 -0
- package/src/nodes/kalman1d/update.js +144 -0
- package/src/nodes/kernel/index.js +18 -0
- package/src/nodes/kernel/init.js +66 -0
- package/src/nodes/kernel/introspect.js +163 -0
- package/src/nodes/kernel/presets.js +74 -0
- package/src/nodes/kernel/publish-to.js +25 -0
- package/src/nodes/kernel/recompute.js +14 -0
- package/src/nodes/kernel/reset.js +20 -0
- package/src/nodes/kernel/update.js +69 -0
- package/src/nodes/lag/index.js +21 -0
- package/src/nodes/lag/init.js +87 -0
- package/src/nodes/lag/introspect.js +202 -0
- package/src/nodes/lag/publish-to.js +64 -0
- package/src/nodes/lag/recompute.js +33 -0
- package/src/nodes/lag/reset.js +49 -0
- package/src/nodes/lag/update.js +133 -0
- package/src/nodes/median3/index.js +19 -0
- package/src/nodes/median3/init.js +40 -0
- package/src/nodes/median3/introspect.js +116 -0
- package/src/nodes/median3/publish-to.js +21 -0
- package/src/nodes/median3/recompute.js +12 -0
- package/src/nodes/median3/reset.js +15 -0
- package/src/nodes/median3/update.js +58 -0
- package/src/nodes/moments-digest/copy-from.js +12 -0
- package/src/nodes/moments-digest/flush.js +17 -0
- package/src/nodes/moments-digest/index.js +132 -0
- package/src/nodes/moments-digest/init.js +84 -0
- package/src/nodes/moments-digest/introspect.js +122 -0
- package/src/nodes/moments-digest/prelude.js +28 -0
- package/src/nodes/moments-digest/publish-to.js +31 -0
- package/src/nodes/moments-digest/recompute.js +9 -0
- package/src/nodes/moments-digest/reset.js +20 -0
- package/src/nodes/moments-digest/update.js +182 -0
- package/src/nodes/node-names.js +67 -0
- package/src/nodes/page-hinkley/index.js +20 -0
- package/src/nodes/page-hinkley/init.js +66 -0
- package/src/nodes/page-hinkley/introspect.js +193 -0
- package/src/nodes/page-hinkley/publish-to.js +28 -0
- package/src/nodes/page-hinkley/recompute.js +14 -0
- package/src/nodes/page-hinkley/reset.js +23 -0
- package/src/nodes/page-hinkley/update.js +105 -0
- package/src/nodes/pass-if/index.js +21 -0
- package/src/nodes/pass-if/init.js +37 -0
- package/src/nodes/pass-if/introspect.js +93 -0
- package/src/nodes/pass-if/publish-to.js +15 -0
- package/src/nodes/pass-if/recompute.js +15 -0
- package/src/nodes/pass-if/reset.js +18 -0
- package/src/nodes/pass-if/update.js +37 -0
- package/src/nodes/persist-if/helpers.js +111 -0
- package/src/nodes/persist-if/index.js +9 -0
- package/src/nodes/persist-if/init.js +98 -0
- package/src/nodes/persist-if/introspect.js +106 -0
- package/src/nodes/persist-if/publish-to.js +21 -0
- package/src/nodes/persist-if/recompute.js +20 -0
- package/src/nodes/persist-if/reset.js +35 -0
- package/src/nodes/persist-if/update.js +112 -0
- package/src/nodes/persistence-check/index.js +14 -0
- package/src/nodes/persistence-check/init.js +38 -0
- package/src/nodes/persistence-check/introspect.js +144 -0
- package/src/nodes/persistence-check/publish-to.js +11 -0
- package/src/nodes/persistence-check/recompute.js +7 -0
- package/src/nodes/persistence-check/reset.js +12 -0
- package/src/nodes/persistence-check/update.js +57 -0
- package/src/nodes/process-index/index.js +15 -0
- package/src/nodes/process-index/init.js +48 -0
- package/src/nodes/process-index/introspect.js +182 -0
- package/src/nodes/process-index/publish-to.js +29 -0
- package/src/nodes/process-index/recompute.js +8 -0
- package/src/nodes/process-index/reset.js +8 -0
- package/src/nodes/process-index/update.js +75 -0
- package/src/nodes/ratio/index.js +14 -0
- package/src/nodes/ratio/init.js +37 -0
- package/src/nodes/ratio/introspect.js +155 -0
- package/src/nodes/ratio/publish-to.js +15 -0
- package/src/nodes/ratio/recompute.js +7 -0
- package/src/nodes/ratio/reset.js +7 -0
- package/src/nodes/ratio/update.js +47 -0
- package/src/nodes/sanitize/index.js +82 -0
- package/src/nodes/sanitize/init.js +82 -0
- package/src/nodes/sanitize/introspect.js +194 -0
- package/src/nodes/sanitize/publish-to.js +15 -0
- package/src/nodes/sanitize/recompute.js +8 -0
- package/src/nodes/sanitize/reset.js +14 -0
- package/src/nodes/sanitize/update.js +102 -0
- package/src/nodes/spike-guard/index.js +14 -0
- package/src/nodes/spike-guard/init.js +47 -0
- package/src/nodes/spike-guard/introspect.js +130 -0
- package/src/nodes/spike-guard/publish-to.js +35 -0
- package/src/nodes/spike-guard/recompute.js +14 -0
- package/src/nodes/spike-guard/reset.js +19 -0
- package/src/nodes/spike-guard/update.js +89 -0
- package/src/nodes/sse-emitter/index.js +7 -0
- package/src/nodes/sse-emitter/init.js +105 -0
- package/src/nodes/sse-emitter/introspect.js +134 -0
- package/src/nodes/sse-emitter/publish-to.js +6 -0
- package/src/nodes/sse-emitter/recompute.js +16 -0
- package/src/nodes/sse-emitter/reset.js +19 -0
- package/src/nodes/sse-emitter/update.js +69 -0
- package/src/nodes/sse-emitter/utils/broadcast-heartbeat.js +36 -0
- package/src/nodes/sse-emitter/utils/build-message.js +31 -0
- package/src/nodes/sse-emitter/utils/connection-manager.js +45 -0
- package/src/nodes/sse-emitter/utils/endpoint-initializer.js +20 -0
- package/src/nodes/sse-emitter/utils/health-monitor.js +38 -0
- package/src/nodes/sse-emitter/utils/qos-handler.js +41 -0
- package/src/nodes/state-change-detector/helpers.js +35 -0
- package/src/nodes/state-change-detector/index.js +12 -0
- package/src/nodes/state-change-detector/init.js +56 -0
- package/src/nodes/state-change-detector/introspect.js +146 -0
- package/src/nodes/state-change-detector/publish-to.js +20 -0
- package/src/nodes/state-change-detector/recompute.js +6 -0
- package/src/nodes/state-change-detector/reset.js +20 -0
- package/src/nodes/state-change-detector/update.js +97 -0
- package/src/nodes/sw-stats/index.js +14 -0
- package/src/nodes/sw-stats/init.js +51 -0
- package/src/nodes/sw-stats/introspect.js +131 -0
- package/src/nodes/sw-stats/publish-to.js +45 -0
- package/src/nodes/sw-stats/recompute.js +33 -0
- package/src/nodes/sw-stats/reset.js +15 -0
- package/src/nodes/sw-stats/update.js +39 -0
- package/src/nodes/swing-watch/index.js +17 -0
- package/src/nodes/swing-watch/init.js +144 -0
- package/src/nodes/swing-watch/introspect.js +188 -0
- package/src/nodes/swing-watch/publish-to.js +53 -0
- package/src/nodes/swing-watch/recompute.js +22 -0
- package/src/nodes/swing-watch/reset.js +55 -0
- package/src/nodes/swing-watch/update.js +767 -0
- package/src/nodes/tally/index.js +15 -0
- package/src/nodes/tally/init.js +32 -0
- package/src/nodes/tally/introspect.js +116 -0
- package/src/nodes/tally/publish-to.js +28 -0
- package/src/nodes/tally/recompute.js +10 -0
- package/src/nodes/tally/reset.js +10 -0
- package/src/nodes/tally/update.js +44 -0
- package/src/nodes/threshold/index.js +14 -0
- package/src/nodes/threshold/init.js +121 -0
- package/src/nodes/threshold/introspect.js +192 -0
- package/src/nodes/threshold/publish-to.js +11 -0
- package/src/nodes/threshold/recompute.js +8 -0
- package/src/nodes/threshold/reset.js +14 -0
- package/src/nodes/threshold/update.js +54 -0
- package/src/nodes/transform/helpers.js +39 -0
- package/src/nodes/transform/index.js +15 -0
- package/src/nodes/transform/init.js +35 -0
- package/src/nodes/transform/introspect.js +118 -0
- package/src/nodes/transform/publish-to.js +23 -0
- package/src/nodes/transform/recompute.js +12 -0
- package/src/nodes/transform/reset.js +11 -0
- package/src/nodes/transform/update.js +32 -0
- package/src/nodes/trend/compute-confidence.js +112 -0
- package/src/nodes/trend/index.js +14 -0
- package/src/nodes/trend/init.js +81 -0
- package/src/nodes/trend/introspect.js +151 -0
- package/src/nodes/trend/publish-to.js +22 -0
- package/src/nodes/trend/recompute.js +15 -0
- package/src/nodes/trend/reset.js +26 -0
- package/src/nodes/trend/update.js +93 -0
- package/src/nodes/tw-stats/copy-from.js +16 -0
- package/src/nodes/tw-stats/flush.js +12 -0
- package/src/nodes/tw-stats/index.js +41 -0
- package/src/nodes/tw-stats/init.js +92 -0
- package/src/nodes/tw-stats/introspect.js +171 -0
- package/src/nodes/tw-stats/publish-to.js +108 -0
- package/src/nodes/tw-stats/recompute.js +9 -0
- package/src/nodes/tw-stats/reset.js +16 -0
- package/src/nodes/tw-stats/update.js +113 -0
- package/src/nodes/unbalance/index.js +15 -0
- package/src/nodes/unbalance/init.js +59 -0
- package/src/nodes/unbalance/introspect.js +167 -0
- package/src/nodes/unbalance/publish-to.js +52 -0
- package/src/nodes/unbalance/recompute.js +11 -0
- package/src/nodes/unbalance/reset.js +10 -0
- package/src/nodes/unbalance/update.js +83 -0
- package/src/nodes/vector-distance/index.js +14 -0
- package/src/nodes/vector-distance/init.js +54 -0
- package/src/nodes/vector-distance/introspect.js +149 -0
- package/src/nodes/vector-distance/publish-to.js +35 -0
- package/src/nodes/vector-distance/recompute.js +11 -0
- package/src/nodes/vector-distance/reset.js +20 -0
- package/src/nodes/vector-distance/update.js +139 -0
- package/src/nodes/winnow/index.js +12 -0
- package/src/nodes/winnow/init.js +82 -0
- package/src/nodes/winnow/introspect.js +253 -0
- package/src/nodes/winnow/publish-to.js +51 -0
- package/src/nodes/winnow/recompute.js +14 -0
- package/src/nodes/winnow/reset.js +34 -0
- package/src/nodes/winnow/update.js +203 -0
- package/src/tools/training/features.js +227 -0
- package/src/tools/training/index.js +21 -0
- package/src/tools/training/logistic.js +238 -0
- package/src/tools/training/metrics.js +126 -0
- package/src/tools/training/scale.js +239 -0
- package/src/tools/training/validate.js +103 -0
- package/src/windowing/count-sliding/create.js +16 -0
- package/src/windowing/count-sliding/get-reverse-chronological-index.js +19 -0
- package/src/windowing/count-sliding/index.js +6 -0
- package/src/windowing/count-sliding/is-not-full.js +5 -0
- package/src/windowing/count-sliding/push.js +15 -0
- package/src/windowing/count-sliding/reset.js +11 -0
- package/src/windowing/count-sliding/size.js +5 -0
- package/src/windowing/time-sliding/create.js +25 -0
- package/src/windowing/time-sliding/push.js +42 -0
- package/CODE_OF_CONDUCT.md +0 -46
- package/CONTRIBUTING.md +0 -132
- package/docs/.nojekyll +0 -0
- package/docs/CONTRIBUTING.md +0 -134
- package/docs/README.md +0 -132
- package/docs/_coverpage.md +0 -26
- package/docs/_media/bg.png +0 -0
- package/docs/_media/wink-logo.png +0 -0
- package/docs/_navbar.md +0 -14
- package/docs/_sidebar.md +0 -2
- package/docs/index.html +0 -44
- package/eslint.config.js +0 -283
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
// nodes/appraise/decision.js
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @fileoverview L2 decision neuron for the SNN appraise architecture.
|
|
5
|
+
*
|
|
6
|
+
* A single non-spiking neuron that accumulates weighted spike input from
|
|
7
|
+
* all L1 receptor neurons. Signed weights enable excitatory (+) and
|
|
8
|
+
* inhibitory (-) synapses — failure evidence drives conviction up,
|
|
9
|
+
* recovery evidence drives it down.
|
|
10
|
+
*
|
|
11
|
+
* Pipeline: synaptic current -> leaky membrane -> MM readout.
|
|
12
|
+
* I2 = sum( wi * si ) / sum( |wi| ) normalised synaptic current
|
|
13
|
+
* V2 = max( 0, V2 * decay + I2 ) unbounded leaky accumulation, floored at 0
|
|
14
|
+
* conviction = V2 / ( V2 + Theta ) MM readout bounds to [0, 1)
|
|
15
|
+
*
|
|
16
|
+
* All functions are pure, stateless, and zero-alloc.
|
|
17
|
+
*
|
|
18
|
+
* @see Dayan, P. & Abbott, L.F. (2001). Theoretical Neuroscience. MIT Press.
|
|
19
|
+
*/
|
|
20
|
+
|
|
21
|
+
/**
|
|
22
|
+
* Computes normalised synaptic current from L1 graded spikes.
|
|
23
|
+
* Signed weights allow excitatory (positive) and inhibitory (negative) inputs.
|
|
24
|
+
*
|
|
25
|
+
* @param {Float64Array} spikes - Per-source graded spike values
|
|
26
|
+
* @param {Float64Array} weights - Signed weights (+ excitatory, - inhibitory)
|
|
27
|
+
* @param {number} totalAbsWeight - Pre-computed sum( |wi| )
|
|
28
|
+
* @param {number} n - Source count
|
|
29
|
+
* @returns {number} Normalised synaptic current I2
|
|
30
|
+
*/
|
|
31
|
+
const computeSynapticCurrent = function ( spikes, weights, totalAbsWeight, n ) {
|
|
32
|
+
let sum = 0;
|
|
33
|
+
for ( let i = 0; i < n; i += 1 ) {
|
|
34
|
+
sum += weights[ i ] * spikes[ i ];
|
|
35
|
+
}
|
|
36
|
+
return sum / totalAbsWeight;
|
|
37
|
+
}; // computeSynapticCurrent()
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* Updates the L2 membrane potential with leaky accumulation.
|
|
41
|
+
* Floors at zero — negative conviction is not meaningful.
|
|
42
|
+
*
|
|
43
|
+
* @param {number} membrane - Current V2
|
|
44
|
+
* @param {number} current - Synaptic current I2
|
|
45
|
+
* @param {number} decayFactor - exp( -dt / tau2 )
|
|
46
|
+
* @returns {number} Updated V2, always >= 0
|
|
47
|
+
*/
|
|
48
|
+
const updateMembrane = function ( membrane, current, decayFactor ) {
|
|
49
|
+
const v = ( membrane * decayFactor ) + current;
|
|
50
|
+
return v > 0 ? v : 0;
|
|
51
|
+
}; // updateMembrane()
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Michaelis-Menten readout — bounds unbounded membrane to [0, 1).
|
|
55
|
+
* Guards against theta <= 0 (returns 0 to prevent division by zero).
|
|
56
|
+
*
|
|
57
|
+
* @param {number} membrane - V2, always >= 0
|
|
58
|
+
* @param {number} theta - Half-saturation constant (must be > 0)
|
|
59
|
+
* @returns {number} Conviction from [0, 1)
|
|
60
|
+
*/
|
|
61
|
+
const readout = function ( membrane, theta ) {
|
|
62
|
+
if ( theta <= 0 ) return 0;
|
|
63
|
+
return membrane / ( membrane + theta );
|
|
64
|
+
}; // readout()
|
|
65
|
+
|
|
66
|
+
export { computeSynapticCurrent, updateMembrane, readout };
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
// nodes/appraise/deviation.js
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @fileoverview Pure deviation functions for the SNN appraise node.
|
|
5
|
+
*
|
|
6
|
+
* Each deviation type converts a raw detection signal into a non-negative
|
|
7
|
+
* "badness" value. All five functions are module-level singletons shared
|
|
8
|
+
* across every partition instance — no per-instance closures.
|
|
9
|
+
*
|
|
10
|
+
* The monomorphic dispatch function `computeDeviation` uses a switch on
|
|
11
|
+
* dense integer type indices (0–4), enabling V8 to generate a jump table
|
|
12
|
+
* and inline the entire dispatch into the caller's loop.
|
|
13
|
+
*
|
|
14
|
+
* Parameter encoding for typed arrays:
|
|
15
|
+
* identity, absolute — p1 and p2 unused (0 from Float64Array default)
|
|
16
|
+
* highExceedance — p1 = baseline
|
|
17
|
+
* lowExceedance — p1 = baseline
|
|
18
|
+
* bandExceedance — p1 = lower, p2 = upper
|
|
19
|
+
*/
|
|
20
|
+
|
|
21
|
+
// ── Type Constants (dense integers for switch jump table) ───────────────────
|
|
22
|
+
|
|
23
|
+
const IDENTITY = 0;
|
|
24
|
+
const ABSOLUTE = 1;
|
|
25
|
+
const HIGH_EXCEEDANCE = 2;
|
|
26
|
+
const LOW_EXCEEDANCE = 3;
|
|
27
|
+
const BAND_EXCEEDANCE = 4;
|
|
28
|
+
|
|
29
|
+
// ── Deviation Type Set (consumed by introspect.js for validation) ───────────
|
|
30
|
+
|
|
31
|
+
const DEVIATION_TYPES = new Set( [
|
|
32
|
+
'identity',
|
|
33
|
+
'absolute',
|
|
34
|
+
'highExceedance',
|
|
35
|
+
'lowExceedance',
|
|
36
|
+
'bandExceedance'
|
|
37
|
+
] );
|
|
38
|
+
|
|
39
|
+
// ── String-to-Index Lookup (used at init time only) ─────────────────────────
|
|
40
|
+
|
|
41
|
+
const DEVIATION_TYPE_INDEX = Object.create( null );
|
|
42
|
+
DEVIATION_TYPE_INDEX.identity = IDENTITY;
|
|
43
|
+
DEVIATION_TYPE_INDEX.absolute = ABSOLUTE;
|
|
44
|
+
DEVIATION_TYPE_INDEX.highExceedance = HIGH_EXCEEDANCE;
|
|
45
|
+
DEVIATION_TYPE_INDEX.lowExceedance = LOW_EXCEEDANCE;
|
|
46
|
+
DEVIATION_TYPE_INDEX.bandExceedance = BAND_EXCEEDANCE;
|
|
47
|
+
|
|
48
|
+
// ── Pure Deviation Functions (module-level, shared across all instances) ────
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Identity — raw is already non-negative badness. Clamps negative to 0.
|
|
52
|
+
*
|
|
53
|
+
* @param {number} raw - Raw signal value
|
|
54
|
+
* @returns {number} Non-negative deviation
|
|
55
|
+
*/
|
|
56
|
+
const identity = ( raw ) => ( raw > 0 ? raw : 0 );
|
|
57
|
+
|
|
58
|
+
/**
|
|
59
|
+
* Absolute — both directions are bad.
|
|
60
|
+
*
|
|
61
|
+
* @param {number} raw - Raw signal value
|
|
62
|
+
* @returns {number} Non-negative deviation
|
|
63
|
+
*/
|
|
64
|
+
const absolute = ( raw ) => Math.abs( raw );
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* High exceedance — only exceeding a baseline is bad.
|
|
68
|
+
*
|
|
69
|
+
* @param {number} raw - Raw signal value
|
|
70
|
+
* @param {number} baseline - Reference value (p1)
|
|
71
|
+
* @returns {number} Non-negative deviation
|
|
72
|
+
*/
|
|
73
|
+
const highExceedance = function ( raw, baseline ) {
|
|
74
|
+
const d = raw - baseline;
|
|
75
|
+
return d > 0 ? d : 0;
|
|
76
|
+
}; // highExceedance()
|
|
77
|
+
|
|
78
|
+
/**
|
|
79
|
+
* Low exceedance — only dropping below a baseline is bad.
|
|
80
|
+
*
|
|
81
|
+
* @param {number} raw - Raw signal value
|
|
82
|
+
* @param {number} baseline - Reference value (p1)
|
|
83
|
+
* @returns {number} Non-negative deviation
|
|
84
|
+
*/
|
|
85
|
+
const lowExceedance = function ( raw, baseline ) {
|
|
86
|
+
const d = baseline - raw;
|
|
87
|
+
return d > 0 ? d : 0;
|
|
88
|
+
}; // lowExceedance()
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* Band exceedance — normal is a range; either direction is bad.
|
|
92
|
+
*
|
|
93
|
+
* @param {number} raw - Raw signal value
|
|
94
|
+
* @param {number} lower - Lower bound of normal range (p1)
|
|
95
|
+
* @param {number} upper - Upper bound of normal range (p2)
|
|
96
|
+
* @returns {number} Non-negative deviation
|
|
97
|
+
*/
|
|
98
|
+
const bandExceedance = function ( raw, lower, upper ) {
|
|
99
|
+
const above = raw - upper;
|
|
100
|
+
const below = lower - raw;
|
|
101
|
+
return ( above > 0 ? above : 0 ) + ( below > 0 ? below : 0 );
|
|
102
|
+
}; // bandExceedance()
|
|
103
|
+
|
|
104
|
+
// ── Monomorphic Dispatch ────────────────────────────────────────────────────
|
|
105
|
+
|
|
106
|
+
/**
|
|
107
|
+
* Computes deviation via switch dispatch on integer type index.
|
|
108
|
+
* V8 compiles dense-integer switch as a jump table; the single call site
|
|
109
|
+
* is monomorphic, so the entire function (including named function calls)
|
|
110
|
+
* is inlined into the caller's loop body.
|
|
111
|
+
*
|
|
112
|
+
* @param {number} type - Deviation type index (0–4, from Uint8Array)
|
|
113
|
+
* @param {number} raw - Raw signal value
|
|
114
|
+
* @param {number} p1 - Parameter 1 (baseline or band.lower, 0 if unused)
|
|
115
|
+
* @param {number} p2 - Parameter 2 (band.upper, 0 if unused)
|
|
116
|
+
* @returns {number} Non-negative deviation
|
|
117
|
+
*/
|
|
118
|
+
const computeDeviation = function ( type, raw, p1, p2 ) {
|
|
119
|
+
switch ( type ) {
|
|
120
|
+
case IDENTITY:
|
|
121
|
+
return identity( raw );
|
|
122
|
+
case ABSOLUTE:
|
|
123
|
+
return absolute( raw );
|
|
124
|
+
case HIGH_EXCEEDANCE:
|
|
125
|
+
return highExceedance( raw, p1 );
|
|
126
|
+
case LOW_EXCEEDANCE:
|
|
127
|
+
return lowExceedance( raw, p1 );
|
|
128
|
+
case BAND_EXCEEDANCE:
|
|
129
|
+
return bandExceedance( raw, p1, p2 );
|
|
130
|
+
default:
|
|
131
|
+
return 0;
|
|
132
|
+
}
|
|
133
|
+
}; // computeDeviation()
|
|
134
|
+
|
|
135
|
+
export {
|
|
136
|
+
computeDeviation,
|
|
137
|
+
identity, absolute, highExceedance, lowExceedance, bandExceedance,
|
|
138
|
+
DEVIATION_TYPES, DEVIATION_TYPE_INDEX,
|
|
139
|
+
IDENTITY, ABSOLUTE, HIGH_EXCEEDANCE, LOW_EXCEEDANCE, BAND_EXCEEDANCE
|
|
140
|
+
};
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
// nodes/appraise/index.js
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @fileoverview Appraise node module exports.
|
|
5
|
+
*
|
|
6
|
+
* Two-layer SNN that accumulates evidence from multiple detection signals
|
|
7
|
+
* into a stable conviction score. L1 receptor neurons (LIF + BLI + Rate)
|
|
8
|
+
* feed an L2 decision neuron with signed weights (excitatory/inhibitory)
|
|
9
|
+
* and MM readout. Burn-in calibration derives Theta from warmup baseline.
|
|
10
|
+
*
|
|
11
|
+
* @see ADR-004
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
export { default as init } from './init.js';
|
|
15
|
+
export { default as update } from './update.js';
|
|
16
|
+
export { default as reset } from './reset.js';
|
|
17
|
+
export { default as recompute } from './recompute.js';
|
|
18
|
+
export { default as publishTo } from './publish-to.js';
|
|
19
|
+
export { default as disable } from '../../core/utils/node/disable.js';
|
|
20
|
+
export { default as enable } from '../../core/utils/node/enable.js';
|
|
21
|
+
export { default as pause } from '../../core/utils/node/pause.js';
|
|
22
|
+
export { default as unpause } from '../../core/utils/node/unpause.js';
|
|
23
|
+
export * from './introspect.js';
|
|
@@ -0,0 +1,165 @@
|
|
|
1
|
+
// nodes/appraise/init.js
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @fileoverview Initializes the two-layer SNN appraise node state.
|
|
5
|
+
*
|
|
6
|
+
* Validates the spec, resolves deviation type indices and parameters into
|
|
7
|
+
* typed arrays, pre-allocates all typed arrays for L1 receptor neurons
|
|
8
|
+
* (membranes, spikes, fired, charges, rates) and L2 decision neuron
|
|
9
|
+
* (membrane, tau, theta). Computes signed weight infrastructure
|
|
10
|
+
* (absWeights, totalAbsWeight) and calibration parameters
|
|
11
|
+
* (warmupSamples, cTarget). All allocation happens here —
|
|
12
|
+
* the hot path is zero-alloc.
|
|
13
|
+
*
|
|
14
|
+
* @see ADR-004
|
|
15
|
+
*/
|
|
16
|
+
|
|
17
|
+
import { validateSpec } from '../../core/utils/node/index.js';
|
|
18
|
+
import * as introspect from './introspect.js';
|
|
19
|
+
import { DEVIATION_TYPE_INDEX } from './deviation.js';
|
|
20
|
+
import { computeWarmupSamples, deriveCTarget } from './calibrate.js';
|
|
21
|
+
|
|
22
|
+
/**
|
|
23
|
+
* Initializes the appraise node state from a validated spec.
|
|
24
|
+
*
|
|
25
|
+
* @param {Object} spec - Node specification
|
|
26
|
+
* @param {string} spec.name - Unique node identifier
|
|
27
|
+
* @param {Object} spec.from - Input field specification
|
|
28
|
+
* @param {string[]} spec.from.x - Source field names (ordered)
|
|
29
|
+
* @param {Object} spec.sources - Per-source config keyed by field name (signed weights)
|
|
30
|
+
* @param {number} spec.halfLife - L1 decay half-life (same units as timestamps)
|
|
31
|
+
* @param {number} [spec.l2HalfLife] - L2 decay half-life (defaults to max L1 tau * ln2)
|
|
32
|
+
* @param {number} [spec.messageRate=1] - Messages per timestamp unit (for warmup calc)
|
|
33
|
+
* @param {Object} spec.thresholds - Classification thresholds
|
|
34
|
+
* @param {Object} spec.stats - Output statistics configuration
|
|
35
|
+
* @returns {Object} Initialized state object
|
|
36
|
+
*/
|
|
37
|
+
const init = function ( spec ) {
|
|
38
|
+
validateSpec( spec, introspect );
|
|
39
|
+
|
|
40
|
+
const state = Object.create( null );
|
|
41
|
+
const fields = spec.from.x;
|
|
42
|
+
const configs = spec.sources;
|
|
43
|
+
const n = fields.length;
|
|
44
|
+
|
|
45
|
+
// ── Standard Flags ──────────────────────────────────────────────────────
|
|
46
|
+
state.inputValidationFailed = false;
|
|
47
|
+
state.disable = false;
|
|
48
|
+
state.pause = false;
|
|
49
|
+
|
|
50
|
+
// ── Configuration from Spec ─────────────────────────────────────────────
|
|
51
|
+
state.stats = spec.stats;
|
|
52
|
+
state.sourceCount = n;
|
|
53
|
+
|
|
54
|
+
// ── Deviation Type Dispatch (module-level pure functions, no closures) ───
|
|
55
|
+
state.deviationTypes = new Uint8Array( n );
|
|
56
|
+
state.deviationP1 = new Float64Array( n );
|
|
57
|
+
state.deviationP2 = new Float64Array( n );
|
|
58
|
+
state.sourceFields = new Array( n );
|
|
59
|
+
|
|
60
|
+
// ── Pre-build Per-Source Field Names (zero string ops in hot path) ────
|
|
61
|
+
const chargePrefix = spec.stats.charge ? spec.stats.charge.storeAs : null;
|
|
62
|
+
const ratePrefix = spec.stats.rate ? spec.stats.rate.storeAs : null;
|
|
63
|
+
state.chargeFields = chargePrefix ? new Array( n ) : null;
|
|
64
|
+
state.rateFields = ratePrefix ? new Array( n ) : null;
|
|
65
|
+
|
|
66
|
+
for ( let i = 0; i < n; i += 1 ) {
|
|
67
|
+
const fieldName = fields[ i ];
|
|
68
|
+
const cfg = configs[ fieldName ];
|
|
69
|
+
state.sourceFields[ i ] = fieldName;
|
|
70
|
+
state.deviationTypes[ i ] = DEVIATION_TYPE_INDEX[ cfg.deviation ];
|
|
71
|
+
|
|
72
|
+
if ( cfg.deviation === 'highExceedance' || cfg.deviation === 'lowExceedance' ) {
|
|
73
|
+
state.deviationP1[ i ] = cfg.baseline;
|
|
74
|
+
} else if ( cfg.deviation === 'bandExceedance' ) {
|
|
75
|
+
state.deviationP1[ i ] = cfg.band.lower;
|
|
76
|
+
state.deviationP2[ i ] = cfg.band.upper;
|
|
77
|
+
}
|
|
78
|
+
// identity, absolute: p1=0, p2=0 (Float64Array default)
|
|
79
|
+
|
|
80
|
+
if ( chargePrefix ) state.chargeFields[ i ] = chargePrefix + '_' + fieldName;
|
|
81
|
+
if ( ratePrefix ) state.rateFields[ i ] = ratePrefix + '_' + fieldName;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
// ── Per-Source Config (pre-compiled) ─────────────────────────────────────
|
|
85
|
+
state.thetas = new Float64Array( n );
|
|
86
|
+
state.weights = new Float64Array( n );
|
|
87
|
+
state.absWeights = new Float64Array( n );
|
|
88
|
+
|
|
89
|
+
let totalAbsWeight = 0;
|
|
90
|
+
for ( let i = 0; i < n; i += 1 ) {
|
|
91
|
+
const cfg = configs[ fields[ i ] ];
|
|
92
|
+
state.thetas[ i ] = cfg.theta;
|
|
93
|
+
state.weights[ i ] = cfg.weight;
|
|
94
|
+
state.absWeights[ i ] = Math.abs( cfg.weight );
|
|
95
|
+
totalAbsWeight += state.absWeights[ i ];
|
|
96
|
+
}
|
|
97
|
+
state.totalAbsWeight = totalAbsWeight;
|
|
98
|
+
|
|
99
|
+
// ── Pre-compute Per-Source Decay Constants ───────────────────────────────
|
|
100
|
+
const globalTau = spec.halfLife / Math.LN2;
|
|
101
|
+
state.taus = new Float64Array( n );
|
|
102
|
+
|
|
103
|
+
let uniform = true;
|
|
104
|
+
let maxTau = 0;
|
|
105
|
+
for ( let i = 0; i < n; i += 1 ) {
|
|
106
|
+
const hl = configs[ fields[ i ] ].halfLife;
|
|
107
|
+
state.taus[ i ] = ( hl === undefined ) ? globalTau : ( hl / Math.LN2 );
|
|
108
|
+
if ( state.taus[ i ] !== globalTau ) uniform = false;
|
|
109
|
+
if ( state.taus[ i ] > maxTau ) maxTau = state.taus[ i ];
|
|
110
|
+
}
|
|
111
|
+
state.uniformDecay = uniform;
|
|
112
|
+
|
|
113
|
+
// Pre-allocate for non-uniform path (zero-alloc hot path)
|
|
114
|
+
state.decayFactors = new Float64Array( n );
|
|
115
|
+
|
|
116
|
+
// ── L1 LIF State ────────────────────────────────────────────────────────
|
|
117
|
+
state.membranes = new Float64Array( n );
|
|
118
|
+
state.spikes = new Float64Array( n );
|
|
119
|
+
state.fired = new Uint8Array( n );
|
|
120
|
+
|
|
121
|
+
// ── L1 BLI State (intensity explanation) ────────────────────────────────
|
|
122
|
+
state.charges = new Float64Array( n );
|
|
123
|
+
|
|
124
|
+
// ── L1 Rate State (persistence explanation) ─────────────────────────────
|
|
125
|
+
state.rates = new Float64Array( n );
|
|
126
|
+
|
|
127
|
+
// ── L2 Decision Neuron ──────────────────────────────────────────────────
|
|
128
|
+
const l2Tau = spec.l2HalfLife ?
|
|
129
|
+
( spec.l2HalfLife / Math.LN2 ) :
|
|
130
|
+
maxTau;
|
|
131
|
+
state.l2Tau = l2Tau;
|
|
132
|
+
state.l2Membrane = 0;
|
|
133
|
+
state.l2Theta = 1.0; // placeholder until calibrated
|
|
134
|
+
|
|
135
|
+
// ── Calibration ─────────────────────────────────────────────────────────
|
|
136
|
+
const messageRate = spec.messageRate || 1.0;
|
|
137
|
+
state.calibrating = true;
|
|
138
|
+
state.warmupSamples = computeWarmupSamples( l2Tau, messageRate );
|
|
139
|
+
state.messageCount = 0;
|
|
140
|
+
state.cTarget = deriveCTarget( spec.thresholds.monitor.at );
|
|
141
|
+
|
|
142
|
+
// ── Threshold Configuration ─────────────────────────────────────────────
|
|
143
|
+
// Sorted ascending for classification loop
|
|
144
|
+
state.thresholdLevels = [
|
|
145
|
+
{ at: spec.thresholds.monitor.at, name: 'Monitor', action: spec.thresholds.monitor.action },
|
|
146
|
+
{ at: spec.thresholds.degraded.at, name: 'Degraded', action: spec.thresholds.degraded.action },
|
|
147
|
+
{ at: spec.thresholds.critical.at, name: 'Critical', action: spec.thresholds.critical.action }
|
|
148
|
+
];
|
|
149
|
+
|
|
150
|
+
// ── Timing State ────────────────────────────────────────────────────────
|
|
151
|
+
state.lastTimestamp = 0;
|
|
152
|
+
state.hasReceivedMessage = false;
|
|
153
|
+
|
|
154
|
+
// ── Combined Score & Classification ─────────────────────────────────────
|
|
155
|
+
state.combined = 0;
|
|
156
|
+
state.stateName = 'Normal';
|
|
157
|
+
|
|
158
|
+
// ── Constants ───────────────────────────────────────────────────────────
|
|
159
|
+
state.VTH = 1.0;
|
|
160
|
+
state.nodeType = introspect.getNodeType();
|
|
161
|
+
|
|
162
|
+
return state;
|
|
163
|
+
}; // init()
|
|
164
|
+
|
|
165
|
+
export default init;
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
// nodes/appraise/integrate.js
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
* @fileoverview Pure functions for MM normalization and leaky integration.
|
|
5
|
+
*
|
|
6
|
+
* Both functions are stateless, zero-alloc, and used in the hot-path loop.
|
|
7
|
+
*
|
|
8
|
+
* MM normalization — Michaelis-Menten saturation:
|
|
9
|
+
* n = d / ( d + θ )
|
|
10
|
+
* Properties: bounded [0, 1), output = 0.5 when d = θ.
|
|
11
|
+
*
|
|
12
|
+
* Integration — two-step: decay first, inject into post-decay headroom:
|
|
13
|
+
* charge = decayed + n × ( 1 - decayed )
|
|
14
|
+
* This guarantees charge ∈ [0, 1] — the ceiling is provably unreachable
|
|
15
|
+
* from below because injection fills only a fraction of the headroom.
|
|
16
|
+
*
|
|
17
|
+
* @see Michaelis, L. & Menten, M.L. (1913). Die Kinetik der Invertinwirkung.
|
|
18
|
+
*/
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* Michaelis-Menten saturation. Maps non-negative deviation to [0, 1).
|
|
22
|
+
*
|
|
23
|
+
* @param {number} deviation - Non-negative deviation (from deviation closure)
|
|
24
|
+
* @param {number} theta - Half-saturation constant (output = 0.5 when d = θ)
|
|
25
|
+
* @returns {number} Normalised signal ∈ [0, 1)
|
|
26
|
+
*/
|
|
27
|
+
const normalise = function ( deviation, theta ) {
|
|
28
|
+
return deviation / ( deviation + theta );
|
|
29
|
+
}; // normalise()
|
|
30
|
+
|
|
31
|
+
/**
|
|
32
|
+
* Bounded leaky integration. Decays existing charge, then injects
|
|
33
|
+
* normalised signal into the post-decay headroom.
|
|
34
|
+
*
|
|
35
|
+
* @param {number} charge - Current charge ∈ [0, 1]
|
|
36
|
+
* @param {number} normalised - MM-normalised signal ∈ [0, 1)
|
|
37
|
+
* @param {number} decayFactor - exp( -Δt / τ ), ∈ [0, 1]
|
|
38
|
+
* @returns {number} Updated charge ∈ [0, 1]
|
|
39
|
+
*/
|
|
40
|
+
const integrate = function ( charge, normalised, decayFactor ) {
|
|
41
|
+
const decayed = charge * decayFactor;
|
|
42
|
+
return decayed + ( normalised * ( 1 - decayed ) );
|
|
43
|
+
}; // integrate()
|
|
44
|
+
|
|
45
|
+
export { normalise, integrate };
|