shield360 1.1.0 → 1.2.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 +330 -3
- package/dist/__tests__/build-info.test.js +8 -1
- package/dist/__tests__/build-info.test.js.map +1 -1
- package/dist/__tests__/code-location.test.js +1 -1
- package/dist/__tests__/masking.test.d.ts +1 -0
- package/dist/__tests__/masking.test.js +66 -0
- package/dist/__tests__/masking.test.js.map +1 -0
- package/dist/__tests__/register.e2e.test.d.ts +1 -0
- package/dist/__tests__/register.e2e.test.js +264 -0
- package/dist/__tests__/register.e2e.test.js.map +1 -0
- package/dist/__tests__/register.test.js +60 -0
- package/dist/__tests__/register.test.js.map +1 -1
- package/dist/agents/__tests__/agents.test.d.ts +1 -0
- package/dist/agents/__tests__/agents.test.js +529 -0
- package/dist/agents/__tests__/agents.test.js.map +1 -0
- package/dist/agents/index.d.ts +15 -0
- package/dist/agents/index.js +25 -0
- package/dist/agents/index.js.map +1 -0
- package/dist/agents/passport.d.ts +92 -0
- package/dist/agents/passport.js +301 -0
- package/dist/agents/passport.js.map +1 -0
- package/dist/agents/policy.d.ts +24 -0
- package/dist/agents/policy.js +93 -0
- package/dist/agents/policy.js.map +1 -0
- package/dist/agents/replay.d.ts +20 -0
- package/dist/agents/replay.js +47 -0
- package/dist/agents/replay.js.map +1 -0
- package/dist/agents/report.d.ts +30 -0
- package/dist/agents/report.js +93 -0
- package/dist/agents/report.js.map +1 -0
- package/dist/agents/types.d.ts +148 -0
- package/dist/agents/types.js +37 -0
- package/dist/agents/types.js.map +1 -0
- package/dist/agents/verifier.d.ts +33 -0
- package/dist/agents/verifier.js +276 -0
- package/dist/agents/verifier.js.map +1 -0
- package/dist/ai-security/__tests__/bench.test.d.ts +1 -0
- package/dist/ai-security/__tests__/bench.test.js +50 -0
- package/dist/ai-security/__tests__/bench.test.js.map +1 -0
- package/dist/ai-security/__tests__/checks.test.d.ts +1 -0
- package/dist/ai-security/__tests__/checks.test.js +248 -0
- package/dist/ai-security/__tests__/checks.test.js.map +1 -0
- package/dist/ai-security/__tests__/config.test.d.ts +1 -0
- package/dist/ai-security/__tests__/config.test.js +164 -0
- package/dist/ai-security/__tests__/config.test.js.map +1 -0
- package/dist/ai-security/__tests__/detection.test.d.ts +1 -0
- package/dist/ai-security/__tests__/detection.test.js +114 -0
- package/dist/ai-security/__tests__/detection.test.js.map +1 -0
- package/dist/ai-security/__tests__/fixtures.d.ts +8 -0
- package/dist/ai-security/__tests__/fixtures.js +30 -0
- package/dist/ai-security/__tests__/fixtures.js.map +1 -0
- package/dist/ai-security/__tests__/hooks.test.d.ts +1 -0
- package/dist/ai-security/__tests__/hooks.test.js +174 -0
- package/dist/ai-security/__tests__/hooks.test.js.map +1 -0
- package/dist/ai-security/__tests__/stream.test.d.ts +1 -0
- package/dist/ai-security/__tests__/stream.test.js +85 -0
- package/dist/ai-security/__tests__/stream.test.js.map +1 -0
- package/dist/ai-security/config.d.ts +94 -0
- package/dist/ai-security/config.js +241 -0
- package/dist/ai-security/config.js.map +1 -0
- package/dist/ai-security/context.d.ts +45 -0
- package/dist/ai-security/context.js +108 -0
- package/dist/ai-security/context.js.map +1 -0
- package/dist/ai-security/custom-kinds.d.ts +23 -0
- package/dist/ai-security/custom-kinds.js +97 -0
- package/dist/ai-security/custom-kinds.js.map +1 -0
- package/dist/ai-security/events.d.ts +77 -0
- package/dist/ai-security/events.js +153 -0
- package/dist/ai-security/events.js.map +1 -0
- package/dist/ai-security/hooks.d.ts +48 -0
- package/dist/ai-security/hooks.js +461 -0
- package/dist/ai-security/hooks.js.map +1 -0
- package/dist/ai-security/index.d.ts +209 -0
- package/dist/ai-security/index.js +587 -0
- package/dist/ai-security/index.js.map +1 -0
- package/dist/ai-security/injection-rules.json +1024 -0
- package/dist/ai-security/injection.d.ts +46 -0
- package/dist/ai-security/injection.js +635 -0
- package/dist/ai-security/injection.js.map +1 -0
- package/dist/ai-security/jailbreak.d.ts +38 -0
- package/dist/ai-security/jailbreak.js +73 -0
- package/dist/ai-security/jailbreak.js.map +1 -0
- package/dist/ai-security/limits.d.ts +84 -0
- package/dist/ai-security/limits.js +195 -0
- package/dist/ai-security/limits.js.map +1 -0
- package/dist/ai-security/mcp.d.ts +82 -0
- package/dist/ai-security/mcp.js +150 -0
- package/dist/ai-security/mcp.js.map +1 -0
- package/dist/ai-security/output.d.ts +107 -0
- package/dist/ai-security/output.js +390 -0
- package/dist/ai-security/output.js.map +1 -0
- package/dist/ai-security/policy.d.ts +125 -0
- package/dist/ai-security/policy.js +196 -0
- package/dist/ai-security/policy.js.map +1 -0
- package/dist/ai-security/rag.d.ts +70 -0
- package/dist/ai-security/rag.js +174 -0
- package/dist/ai-security/rag.js.map +1 -0
- package/dist/ai-security/tool-rules.json +203 -0
- package/dist/ai-security/tools.d.ts +46 -0
- package/dist/ai-security/tools.js +62 -0
- package/dist/ai-security/tools.js.map +1 -0
- package/dist/budgets/__tests__/budgets.test.d.ts +1 -0
- package/dist/budgets/__tests__/budgets.test.js +134 -0
- package/dist/budgets/__tests__/budgets.test.js.map +1 -0
- package/dist/budgets/auto.d.ts +25 -0
- package/dist/budgets/auto.js +63 -0
- package/dist/budgets/auto.js.map +1 -0
- package/dist/budgets/index.d.ts +110 -0
- package/dist/budgets/index.js +239 -0
- package/dist/budgets/index.js.map +1 -0
- package/dist/customer/__tests__/customer.test.d.ts +1 -0
- package/dist/customer/__tests__/customer.test.js +155 -0
- package/dist/customer/__tests__/customer.test.js.map +1 -0
- package/dist/customer/index.d.ts +48 -0
- package/dist/customer/index.js +132 -0
- package/dist/customer/index.js.map +1 -0
- package/dist/feedback/__tests__/feedback.test.d.ts +1 -0
- package/dist/feedback/__tests__/feedback.test.js +80 -0
- package/dist/feedback/__tests__/feedback.test.js.map +1 -0
- package/dist/feedback/index.d.ts +48 -0
- package/dist/feedback/index.js +97 -0
- package/dist/feedback/index.js.map +1 -0
- package/dist/flags/__tests__/flags.test.d.ts +1 -0
- package/dist/flags/__tests__/flags.test.js +301 -0
- package/dist/flags/__tests__/flags.test.js.map +1 -0
- package/dist/flags/client.d.ts +131 -0
- package/dist/flags/client.js +301 -0
- package/dist/flags/client.js.map +1 -0
- package/dist/flags/engine.d.ts +200 -0
- package/dist/flags/engine.js +677 -0
- package/dist/flags/engine.js.map +1 -0
- package/dist/flags/index.d.ts +4 -0
- package/dist/flags/index.js +16 -0
- package/dist/flags/index.js.map +1 -0
- package/dist/guard/__tests__/findings.test.js +1 -1
- package/dist/guard/__tests__/report.test.js +67 -0
- package/dist/guard/__tests__/report.test.js.map +1 -1
- package/dist/guard/heartbeat.d.ts +34 -0
- package/dist/guard/heartbeat.js +83 -0
- package/dist/guard/heartbeat.js.map +1 -0
- package/dist/guard/integration.d.ts +9 -0
- package/dist/guard/integration.js +4 -2
- package/dist/guard/integration.js.map +1 -1
- package/dist/guard/report.d.ts +24 -1
- package/dist/guard/report.js +67 -18
- package/dist/guard/report.js.map +1 -1
- package/dist/index.d.ts +88 -0
- package/dist/index.js +193 -2
- package/dist/index.js.map +1 -1
- package/dist/instrumentation/__tests__/langchain-wrapper.test.js +1 -1
- package/dist/instrumentation/__tests__/langchain-wrapper.test.js.map +1 -1
- package/dist/instrumentation/anthropic/wrapper.js +4 -0
- package/dist/instrumentation/anthropic/wrapper.js.map +1 -1
- package/dist/instrumentation/openai/wrapper.js +6 -0
- package/dist/instrumentation/openai/wrapper.js.map +1 -1
- package/dist/masking.d.ts +42 -0
- package/dist/masking.js +197 -0
- package/dist/masking.js.map +1 -0
- package/dist/otel/__tests__/app-logs-safety.test.d.ts +1 -0
- package/dist/otel/__tests__/app-logs-safety.test.js +129 -0
- package/dist/otel/__tests__/app-logs-safety.test.js.map +1 -0
- package/dist/otel/__tests__/app-logs.test.d.ts +1 -0
- package/dist/otel/__tests__/app-logs.test.js +269 -0
- package/dist/otel/__tests__/app-logs.test.js.map +1 -0
- package/dist/otel/__tests__/log-auto.test.d.ts +1 -0
- package/dist/otel/__tests__/log-auto.test.js +125 -0
- package/dist/otel/__tests__/log-auto.test.js.map +1 -0
- package/dist/otel/__tests__/log-bridges.test.d.ts +1 -0
- package/dist/otel/__tests__/log-bridges.test.js +170 -0
- package/dist/otel/__tests__/log-bridges.test.js.map +1 -0
- package/dist/otel/__tests__/system-metrics.test.d.ts +1 -0
- package/dist/otel/__tests__/system-metrics.test.js +79 -0
- package/dist/otel/__tests__/system-metrics.test.js.map +1 -0
- package/dist/otel/app-logs.d.ts +80 -0
- package/dist/otel/app-logs.js +195 -0
- package/dist/otel/app-logs.js.map +1 -0
- package/dist/otel/build-info.d.ts +2 -1
- package/dist/otel/build-info.js +3 -2
- package/dist/otel/build-info.js.map +1 -1
- package/dist/otel/events.d.ts +1 -0
- package/dist/otel/events.js +21 -12
- package/dist/otel/events.js.map +1 -1
- package/dist/otel/log-auto.d.ts +44 -0
- package/dist/otel/log-auto.js +200 -0
- package/dist/otel/log-auto.js.map +1 -0
- package/dist/otel/log-bridges.d.ts +54 -0
- package/dist/otel/log-bridges.js +307 -0
- package/dist/otel/log-bridges.js.map +1 -0
- package/dist/otel/system-metrics.d.ts +39 -0
- package/dist/otel/system-metrics.js +166 -0
- package/dist/otel/system-metrics.js.map +1 -0
- package/dist/otel/tracing.js +5 -1
- package/dist/otel/tracing.js.map +1 -1
- package/dist/protect/__tests__/protect.test.js +4 -0
- package/dist/protect/__tests__/protect.test.js.map +1 -1
- package/dist/protect/index.js +9 -4
- package/dist/protect/index.js.map +1 -1
- package/dist/rasp/__tests__/auto-http.test.d.ts +1 -0
- package/dist/rasp/__tests__/auto-http.test.js +136 -0
- package/dist/rasp/__tests__/auto-http.test.js.map +1 -0
- package/dist/rasp/__tests__/baseline.test.d.ts +1 -0
- package/dist/rasp/__tests__/baseline.test.js +86 -0
- package/dist/rasp/__tests__/baseline.test.js.map +1 -0
- package/dist/rasp/__tests__/benign-corpus.test.d.ts +1 -0
- package/dist/rasp/__tests__/benign-corpus.test.js +68 -0
- package/dist/rasp/__tests__/benign-corpus.test.js.map +1 -0
- package/dist/rasp/__tests__/capture-context.test.d.ts +1 -0
- package/dist/rasp/__tests__/capture-context.test.js +135 -0
- package/dist/rasp/__tests__/capture-context.test.js.map +1 -0
- package/dist/rasp/__tests__/code-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/code-hook.test.js +218 -0
- package/dist/rasp/__tests__/code-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/config-client.test.d.ts +1 -0
- package/dist/rasp/__tests__/config-client.test.js +283 -0
- package/dist/rasp/__tests__/config-client.test.js.map +1 -0
- package/dist/rasp/__tests__/corpus.d.ts +13 -0
- package/dist/rasp/__tests__/corpus.js +111 -0
- package/dist/rasp/__tests__/corpus.js.map +1 -0
- package/dist/rasp/__tests__/custom-rules.test.d.ts +1 -0
- package/dist/rasp/__tests__/custom-rules.test.js +276 -0
- package/dist/rasp/__tests__/custom-rules.test.js.map +1 -0
- package/dist/rasp/__tests__/db-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/db-hook.test.js +438 -0
- package/dist/rasp/__tests__/db-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/deception.test.d.ts +1 -0
- package/dist/rasp/__tests__/deception.test.js +567 -0
- package/dist/rasp/__tests__/deception.test.js.map +1 -0
- package/dist/rasp/__tests__/detect.test.d.ts +1 -0
- package/dist/rasp/__tests__/detect.test.js +276 -0
- package/dist/rasp/__tests__/detect.test.js.map +1 -0
- package/dist/rasp/__tests__/esm-exports.test.d.ts +1 -0
- package/dist/rasp/__tests__/esm-exports.test.js +20 -0
- package/dist/rasp/__tests__/esm-exports.test.js.map +1 -0
- package/dist/rasp/__tests__/fs-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/fs-hook.test.js +241 -0
- package/dist/rasp/__tests__/fs-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/hook-contracts.test.d.ts +1 -0
- package/dist/rasp/__tests__/hook-contracts.test.js +201 -0
- package/dist/rasp/__tests__/hook-contracts.test.js.map +1 -0
- package/dist/rasp/__tests__/hook-kit.d.ts +42 -0
- package/dist/rasp/__tests__/hook-kit.js +139 -0
- package/dist/rasp/__tests__/hook-kit.js.map +1 -0
- package/dist/rasp/__tests__/http-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/http-hook.test.js +250 -0
- package/dist/rasp/__tests__/http-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/iast.test.d.ts +1 -0
- package/dist/rasp/__tests__/iast.test.js +361 -0
- package/dist/rasp/__tests__/iast.test.js.map +1 -0
- package/dist/rasp/__tests__/include-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/include-hook.test.js +122 -0
- package/dist/rasp/__tests__/include-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/middleware.test.d.ts +1 -0
- package/dist/rasp/__tests__/middleware.test.js +302 -0
- package/dist/rasp/__tests__/middleware.test.js.map +1 -0
- package/dist/rasp/__tests__/process-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/process-hook.test.js +238 -0
- package/dist/rasp/__tests__/process-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/reporter.test.d.ts +1 -0
- package/dist/rasp/__tests__/reporter.test.js +114 -0
- package/dist/rasp/__tests__/reporter.test.js.map +1 -0
- package/dist/rasp/__tests__/route.test.d.ts +1 -0
- package/dist/rasp/__tests__/route.test.js +46 -0
- package/dist/rasp/__tests__/route.test.js.map +1 -0
- package/dist/rasp/__tests__/rule-expr.test.d.ts +1 -0
- package/dist/rasp/__tests__/rule-expr.test.js +151 -0
- package/dist/rasp/__tests__/rule-expr.test.js.map +1 -0
- package/dist/rasp/__tests__/rule-phases.test.d.ts +1 -0
- package/dist/rasp/__tests__/rule-phases.test.js +271 -0
- package/dist/rasp/__tests__/rule-phases.test.js.map +1 -0
- package/dist/rasp/__tests__/sinks-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/sinks-hook.test.js +177 -0
- package/dist/rasp/__tests__/sinks-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/targets.test.d.ts +1 -0
- package/dist/rasp/__tests__/targets.test.js +82 -0
- package/dist/rasp/__tests__/targets.test.js.map +1 -0
- package/dist/rasp/__tests__/template-hook.test.d.ts +1 -0
- package/dist/rasp/__tests__/template-hook.test.js +254 -0
- package/dist/rasp/__tests__/template-hook.test.js.map +1 -0
- package/dist/rasp/__tests__/upload.test.d.ts +1 -0
- package/dist/rasp/__tests__/upload.test.js +81 -0
- package/dist/rasp/__tests__/upload.test.js.map +1 -0
- package/dist/rasp/__tests__/vpatch-engine.test.d.ts +1 -0
- package/dist/rasp/__tests__/vpatch-engine.test.js +177 -0
- package/dist/rasp/__tests__/vpatch-engine.test.js.map +1 -0
- package/dist/rasp/auto-http.d.ts +6 -0
- package/dist/rasp/auto-http.js +194 -0
- package/dist/rasp/auto-http.js.map +1 -0
- package/dist/rasp/baseline.d.ts +35 -0
- package/dist/rasp/baseline.js +91 -0
- package/dist/rasp/baseline.js.map +1 -0
- package/dist/rasp/capture.d.ts +76 -0
- package/dist/rasp/capture.js +304 -0
- package/dist/rasp/capture.js.map +1 -0
- package/dist/rasp/config-client.d.ts +122 -0
- package/dist/rasp/config-client.js +337 -0
- package/dist/rasp/config-client.js.map +1 -0
- package/dist/rasp/context.d.ts +65 -0
- package/dist/rasp/context.js +68 -0
- package/dist/rasp/context.js.map +1 -0
- package/dist/rasp/custom-rules.d.ts +68 -0
- package/dist/rasp/custom-rules.js +222 -0
- package/dist/rasp/custom-rules.js.map +1 -0
- package/dist/rasp/data/default-rules.json +199 -0
- package/dist/rasp/data/default-sinks.json +4 -0
- package/dist/rasp/data/dnslog-domains.json +11 -0
- package/dist/rasp/deception.d.ts +70 -0
- package/dist/rasp/deception.js +220 -0
- package/dist/rasp/deception.js.map +1 -0
- package/dist/rasp/detect.d.ts +68 -0
- package/dist/rasp/detect.js +671 -0
- package/dist/rasp/detect.js.map +1 -0
- package/dist/rasp/engine.d.ts +107 -0
- package/dist/rasp/engine.js +330 -0
- package/dist/rasp/engine.js.map +1 -0
- package/dist/rasp/hooks/code.d.ts +20 -0
- package/dist/rasp/hooks/code.js +334 -0
- package/dist/rasp/hooks/code.js.map +1 -0
- package/dist/rasp/hooks/db.d.ts +48 -0
- package/dist/rasp/hooks/db.js +322 -0
- package/dist/rasp/hooks/db.js.map +1 -0
- package/dist/rasp/hooks/esm.d.ts +7 -0
- package/dist/rasp/hooks/esm.js +18 -0
- package/dist/rasp/hooks/esm.js.map +1 -0
- package/dist/rasp/hooks/fs.d.ts +3 -0
- package/dist/rasp/hooks/fs.js +206 -0
- package/dist/rasp/hooks/fs.js.map +1 -0
- package/dist/rasp/hooks/http.d.ts +4 -0
- package/dist/rasp/hooks/http.js +213 -0
- package/dist/rasp/hooks/http.js.map +1 -0
- package/dist/rasp/hooks/include.d.ts +9 -0
- package/dist/rasp/hooks/include.js +79 -0
- package/dist/rasp/hooks/include.js.map +1 -0
- package/dist/rasp/hooks/marks.d.ts +2 -0
- package/dist/rasp/hooks/marks.js +16 -0
- package/dist/rasp/hooks/marks.js.map +1 -0
- package/dist/rasp/hooks/process.d.ts +22 -0
- package/dist/rasp/hooks/process.js +191 -0
- package/dist/rasp/hooks/process.js.map +1 -0
- package/dist/rasp/hooks/sinks.d.ts +54 -0
- package/dist/rasp/hooks/sinks.js +329 -0
- package/dist/rasp/hooks/sinks.js.map +1 -0
- package/dist/rasp/hooks/template.d.ts +21 -0
- package/dist/rasp/hooks/template.js +152 -0
- package/dist/rasp/hooks/template.js.map +1 -0
- package/dist/rasp/iast-rules.d.ts +82 -0
- package/dist/rasp/iast-rules.js +240 -0
- package/dist/rasp/iast-rules.js.map +1 -0
- package/dist/rasp/iast-scope.d.ts +29 -0
- package/dist/rasp/iast-scope.js +54 -0
- package/dist/rasp/iast-scope.js.map +1 -0
- package/dist/rasp/iast.d.ts +81 -0
- package/dist/rasp/iast.js +272 -0
- package/dist/rasp/iast.js.map +1 -0
- package/dist/rasp/index.d.ts +52 -0
- package/dist/rasp/index.js +280 -0
- package/dist/rasp/index.js.map +1 -0
- package/dist/rasp/lexers.d.ts +32 -0
- package/dist/rasp/lexers.js +444 -0
- package/dist/rasp/lexers.js.map +1 -0
- package/dist/rasp/middleware.d.ts +155 -0
- package/dist/rasp/middleware.js +568 -0
- package/dist/rasp/middleware.js.map +1 -0
- package/dist/rasp/model-output.d.ts +14 -0
- package/dist/rasp/model-output.js +107 -0
- package/dist/rasp/model-output.js.map +1 -0
- package/dist/rasp/normalize.d.ts +23 -0
- package/dist/rasp/normalize.js +140 -0
- package/dist/rasp/normalize.js.map +1 -0
- package/dist/rasp/reporter.d.ts +60 -0
- package/dist/rasp/reporter.js +230 -0
- package/dist/rasp/reporter.js.map +1 -0
- package/dist/rasp/rule-expr.d.ts +236 -0
- package/dist/rasp/rule-expr.js +1253 -0
- package/dist/rasp/rule-expr.js.map +1 -0
- package/dist/rasp/template.d.ts +53 -0
- package/dist/rasp/template.js +336 -0
- package/dist/rasp/template.js.map +1 -0
- package/dist/rasp/types.d.ts +110 -0
- package/dist/rasp/types.js +51 -0
- package/dist/rasp/types.js.map +1 -0
- package/dist/rasp/vpatch.d.ts +55 -0
- package/dist/rasp/vpatch.js +120 -0
- package/dist/rasp/vpatch.js.map +1 -0
- package/dist/register.js +52 -11
- package/dist/register.js.map +1 -1
- package/dist/semantic-convention.d.ts +2 -0
- package/dist/semantic-convention.js +5 -0
- package/dist/semantic-convention.js.map +1 -1
- package/dist/types.d.ts +75 -1
- package/dist/zero-code.d.ts +8 -0
- package/dist/zero-code.js +38 -0
- package/dist/zero-code.js.map +1 -0
- package/package.json +18 -2
|
@@ -0,0 +1,304 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.VP_SINK = exports.INPUT_HEADERS = void 0;
|
|
4
|
+
exports.uploadNames = uploadNames;
|
|
5
|
+
exports.lowerHeaders = lowerHeaders;
|
|
6
|
+
exports.captureRequest = captureRequest;
|
|
7
|
+
exports.bodyAbsent = bodyAbsent;
|
|
8
|
+
exports.captureNoBody = captureNoBody;
|
|
9
|
+
exports.captureBody = captureBody;
|
|
10
|
+
exports.runVirtualPatches = runVirtualPatches;
|
|
11
|
+
exports.runRequestRules = runRequestRules;
|
|
12
|
+
exports.captureLater = captureLater;
|
|
13
|
+
/**
|
|
14
|
+
* Request capture shared by every framework middleware: turns a request into
|
|
15
|
+
* the context's inputs (README "Sources of untrusted input") and runs the
|
|
16
|
+
* virtual patches. Inputs stay in memory, in the request's context only.
|
|
17
|
+
*/
|
|
18
|
+
const context_1 = require("./context");
|
|
19
|
+
const detect_1 = require("./detect");
|
|
20
|
+
const custom_rules_1 = require("./custom-rules");
|
|
21
|
+
const engine_1 = require("./engine");
|
|
22
|
+
const normalize_1 = require("./normalize");
|
|
23
|
+
const types_1 = require("./types");
|
|
24
|
+
const vpatch_1 = require("./vpatch");
|
|
25
|
+
/** Headers the contract treats as input (OpenRASP's headerInjection). */
|
|
26
|
+
exports.INPUT_HEADERS = ['user-agent', 'referer', 'x-forwarded-for'];
|
|
27
|
+
exports.VP_SINK = 'server.request';
|
|
28
|
+
const MAX_UPLOAD_SCAN = 1024 * 1024;
|
|
29
|
+
const MAX_UPLOADS = 32;
|
|
30
|
+
const PART_FILENAME = /content-disposition:[^\r\n]*?\bname="([^"\r\n]*)"[^\r\n]*?\bfilename="([^"\r\n]*)"/gi;
|
|
31
|
+
/** The names of uploaded files: from raw multipart part headers, or a parser's file objects. */
|
|
32
|
+
function uploadNames(b, raw) {
|
|
33
|
+
const out = [];
|
|
34
|
+
const ct = (b.contentType || '').toLowerCase();
|
|
35
|
+
if (raw && ct.includes('multipart/form-data')) {
|
|
36
|
+
for (const m of raw.slice(0, MAX_UPLOAD_SCAN).matchAll(PART_FILENAME)) {
|
|
37
|
+
if (out.length >= MAX_UPLOADS)
|
|
38
|
+
break;
|
|
39
|
+
if (m[2])
|
|
40
|
+
out.push({ field: m[1] || 'file', name: m[2] });
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
const visit = (f, field) => {
|
|
44
|
+
if (out.length >= MAX_UPLOADS || !f || typeof f !== 'object')
|
|
45
|
+
return;
|
|
46
|
+
const o = f;
|
|
47
|
+
const name = [o.originalname, o.originalFilename, o.filename, o.name].find((v) => typeof v === 'string' && v);
|
|
48
|
+
if (typeof name === 'string')
|
|
49
|
+
out.push({ field: typeof o.fieldname === 'string' ? o.fieldname : field, name });
|
|
50
|
+
};
|
|
51
|
+
const files = b.files;
|
|
52
|
+
if (Array.isArray(files))
|
|
53
|
+
files.forEach((f) => visit(f, 'file'));
|
|
54
|
+
else if (files && typeof files === 'object') {
|
|
55
|
+
const one = files;
|
|
56
|
+
if (typeof one.originalname === 'string' || typeof one.fieldname === 'string')
|
|
57
|
+
visit(files, 'file');
|
|
58
|
+
else
|
|
59
|
+
for (const [field, v] of Object.entries(one))
|
|
60
|
+
(Array.isArray(v) ? v : [v]).forEach((f) => visit(f, field));
|
|
61
|
+
}
|
|
62
|
+
return out;
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Runs fn with ctx as the current context. Capture runs before the entry
|
|
66
|
+
* point enters the request's context, and the checks it makes (virtual
|
|
67
|
+
* patches, request rules, uploads) report findings that custom finding rules
|
|
68
|
+
* judge with the current request's fields.
|
|
69
|
+
*/
|
|
70
|
+
function inContext(ctx, fn) {
|
|
71
|
+
return (0, context_1.currentContext)() === ctx ? fn() : context_1.storage.run(ctx, fn);
|
|
72
|
+
}
|
|
73
|
+
/** Records uploaded file names as request input and checks each (file_write.upload). Throws the block error when blocking. */
|
|
74
|
+
function captureUploads(ctx, b, raw) {
|
|
75
|
+
for (const { field, name } of uploadNames(b, raw)) {
|
|
76
|
+
const key = `body.${field}.filename`;
|
|
77
|
+
(0, normalize_1.addInput)(ctx.inputs, name, key);
|
|
78
|
+
inContext(ctx, () => (0, engine_1.check)('request.upload', () => (0, detect_1.detectUpload)({ value: name, key, source: 'request' })));
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
const header = (h, name) => {
|
|
82
|
+
const v = h[name];
|
|
83
|
+
return v === undefined ? '' : Array.isArray(v) ? v.join(', ') : String(v);
|
|
84
|
+
};
|
|
85
|
+
function splitUrl(url) {
|
|
86
|
+
const q = url.indexOf('?');
|
|
87
|
+
const hash = url.indexOf('#');
|
|
88
|
+
const end = hash >= 0 ? hash : url.length;
|
|
89
|
+
return q >= 0 && q < end ? { path: url.slice(0, q), query: url.slice(q + 1, end) } : { path: url.slice(0, end), query: '' };
|
|
90
|
+
}
|
|
91
|
+
/** Lower-cases header names (Node already does; other sources may not). */
|
|
92
|
+
function lowerHeaders(h) {
|
|
93
|
+
const out = {};
|
|
94
|
+
if (!h || typeof h !== 'object')
|
|
95
|
+
return out;
|
|
96
|
+
for (const [k, v] of Object.entries(h)) {
|
|
97
|
+
if (typeof v === 'string' || Array.isArray(v))
|
|
98
|
+
out[k.toLowerCase()] = v;
|
|
99
|
+
else if (v != null)
|
|
100
|
+
out[k.toLowerCase()] = String(v);
|
|
101
|
+
}
|
|
102
|
+
return out;
|
|
103
|
+
}
|
|
104
|
+
/** Builds the request's context: query, params, cookies, the input headers. */
|
|
105
|
+
function captureRequest(shape) {
|
|
106
|
+
const { path, query } = splitUrl(shape.url || '/');
|
|
107
|
+
const ctx = (0, context_1.newContext)({ inRequest: true, method: shape.method, path, route: shape.route, framework: shape.framework });
|
|
108
|
+
if (typeof shape.ip === 'string' && shape.ip)
|
|
109
|
+
ctx.ip = shape.ip;
|
|
110
|
+
const inputs = ctx.inputs;
|
|
111
|
+
if (shape.query && typeof shape.query === 'object') {
|
|
112
|
+
(0, normalize_1.flatten)(inputs, shape.query, 'query');
|
|
113
|
+
ctx.trees.push(shape.query);
|
|
114
|
+
}
|
|
115
|
+
else if (query) {
|
|
116
|
+
const tree = {};
|
|
117
|
+
for (const [k, v] of new URLSearchParams(query)) {
|
|
118
|
+
(0, normalize_1.addInput)(inputs, v, `query.${k}`);
|
|
119
|
+
const prev = tree[k];
|
|
120
|
+
tree[k] = prev === undefined ? v : Array.isArray(prev) ? [...prev, v] : [prev, v];
|
|
121
|
+
}
|
|
122
|
+
ctx.trees.push(tree);
|
|
123
|
+
}
|
|
124
|
+
if (shape.params && typeof shape.params === 'object')
|
|
125
|
+
(0, normalize_1.flatten)(inputs, shape.params, 'params');
|
|
126
|
+
const cookie = header(shape.headers, 'cookie');
|
|
127
|
+
for (const [name, value] of (0, normalize_1.parseCookies)(cookie))
|
|
128
|
+
(0, normalize_1.addInput)(inputs, value, `cookie.${name}`);
|
|
129
|
+
for (const h of exports.INPUT_HEADERS) {
|
|
130
|
+
const v = header(shape.headers, h);
|
|
131
|
+
if (v)
|
|
132
|
+
(0, normalize_1.addInput)(inputs, v, `header.${h}`);
|
|
133
|
+
}
|
|
134
|
+
// SHIELD: inside the zero-code capture's context, the phases it already judged are not judged again,
|
|
135
|
+
// and its custom-rule state carries over, so a rule matches at most once per request.
|
|
136
|
+
const auto = (0, context_1.currentContext)()?.auto ? (0, context_1.currentContext)() : undefined;
|
|
137
|
+
ctx.vp = {
|
|
138
|
+
req: { method: shape.method, path, query, headers: shape.headers, cookie, body: '' },
|
|
139
|
+
bodyKnown: false,
|
|
140
|
+
ranHead: Boolean(auto?.vp?.ranHead),
|
|
141
|
+
ranBody: Boolean(auto?.vp?.ranBody),
|
|
142
|
+
};
|
|
143
|
+
if (auto?.rules)
|
|
144
|
+
ctx.rules = auto.rules;
|
|
145
|
+
return ctx;
|
|
146
|
+
}
|
|
147
|
+
/**
|
|
148
|
+
* Whether the request has no body, by its headers: neither `Transfer-Encoding`
|
|
149
|
+
* nor a non-zero `Content-Length` (HTTP/1.x; body parsers use the same test).
|
|
150
|
+
* Over HTTP/2 a body needs no length, so only `Content-Length: 0` says so.
|
|
151
|
+
*/
|
|
152
|
+
function bodyAbsent(h, httpVersionMajor) {
|
|
153
|
+
if (h['transfer-encoding'] !== undefined)
|
|
154
|
+
return false;
|
|
155
|
+
const len = header(h, 'content-length').trim();
|
|
156
|
+
if (len === '0')
|
|
157
|
+
return true;
|
|
158
|
+
return len === '' && !(typeof httpVersionMajor === 'number' && httpVersionMajor >= 2);
|
|
159
|
+
}
|
|
160
|
+
/** Records that the request has no body: the body is known and empty, so the body phase runs. */
|
|
161
|
+
function captureNoBody(ctx) {
|
|
162
|
+
if (ctx.vp)
|
|
163
|
+
ctx.vp.bodyKnown = true;
|
|
164
|
+
}
|
|
165
|
+
function isFormType(ct) {
|
|
166
|
+
return ct.includes('application/x-www-form-urlencoded');
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Adds the body to the context: string leaves of a parsed body (`body.a.b`),
|
|
170
|
+
* form fields, or the raw text when it is text, unparsed and at most 8 KiB.
|
|
171
|
+
* Also gives the virtual patches the body text.
|
|
172
|
+
*/
|
|
173
|
+
function captureBody(ctx, b) {
|
|
174
|
+
const body = b.body;
|
|
175
|
+
if (body === undefined || body === null)
|
|
176
|
+
return;
|
|
177
|
+
// Inputs added from here on are body inputs: head rules never see them.
|
|
178
|
+
ctx.headInputs ?? (ctx.headInputs = ctx.inputs.length);
|
|
179
|
+
const ct = (b.contentType || '').toLowerCase();
|
|
180
|
+
let raw = '';
|
|
181
|
+
if (typeof body === 'string' || Buffer.isBuffer(body) || body instanceof Uint8Array) {
|
|
182
|
+
raw = typeof body === 'string' ? body : Buffer.from(body).toString('utf8');
|
|
183
|
+
let parsed;
|
|
184
|
+
if (ct.includes('json')) {
|
|
185
|
+
try {
|
|
186
|
+
parsed = JSON.parse(raw);
|
|
187
|
+
}
|
|
188
|
+
catch {
|
|
189
|
+
parsed = undefined;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
else if (isFormType(ct)) {
|
|
193
|
+
const tree = {};
|
|
194
|
+
for (const [k, v] of new URLSearchParams(raw.slice(0, 1024 * 1024)))
|
|
195
|
+
tree[k] = v;
|
|
196
|
+
parsed = tree;
|
|
197
|
+
}
|
|
198
|
+
if (parsed !== undefined && parsed !== null && typeof parsed === 'object') {
|
|
199
|
+
(0, normalize_1.flatten)(ctx.inputs, parsed, 'body');
|
|
200
|
+
ctx.trees.push(parsed);
|
|
201
|
+
}
|
|
202
|
+
else if (raw.length <= normalize_1.MAX_RAW_BODY) {
|
|
203
|
+
(0, normalize_1.addInput)(ctx.inputs, raw, 'body');
|
|
204
|
+
}
|
|
205
|
+
}
|
|
206
|
+
else if (typeof body === 'object') {
|
|
207
|
+
(0, normalize_1.flatten)(ctx.inputs, body, 'body');
|
|
208
|
+
ctx.trees.push(body);
|
|
209
|
+
try {
|
|
210
|
+
raw = JSON.stringify(body) ?? '';
|
|
211
|
+
}
|
|
212
|
+
catch {
|
|
213
|
+
raw = '';
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
if (ctx.vp) {
|
|
217
|
+
ctx.vp.req.body = raw.length > vpatch_1.MAX_VP_TEXT ? raw.slice(0, vpatch_1.MAX_VP_TEXT) : raw;
|
|
218
|
+
ctx.vp.bodyKnown = true;
|
|
219
|
+
}
|
|
220
|
+
captureUploads(ctx, b, raw);
|
|
221
|
+
}
|
|
222
|
+
/**
|
|
223
|
+
* Runs the virtual patches the request can be judged by so far: rules that
|
|
224
|
+
* do not read the body at once, rules that do once the body is known. Each
|
|
225
|
+
* rule set runs once. Throws the block error when a blocking rule matches;
|
|
226
|
+
* any other failure lets the request through.
|
|
227
|
+
*/
|
|
228
|
+
function runVirtualPatches(ctx) {
|
|
229
|
+
inContext(ctx, () => runPhases(ctx));
|
|
230
|
+
}
|
|
231
|
+
function runPhases(ctx) {
|
|
232
|
+
const vp = ctx.vp;
|
|
233
|
+
if (!vp)
|
|
234
|
+
return;
|
|
235
|
+
const phases = [];
|
|
236
|
+
if (!vp.ranHead) {
|
|
237
|
+
vp.ranHead = true;
|
|
238
|
+
phases.push('head');
|
|
239
|
+
}
|
|
240
|
+
if (vp.bodyKnown && !vp.ranBody) {
|
|
241
|
+
vp.ranBody = true;
|
|
242
|
+
phases.push('body');
|
|
243
|
+
}
|
|
244
|
+
for (const phase of phases) {
|
|
245
|
+
let finding = null;
|
|
246
|
+
try {
|
|
247
|
+
finding = (0, vpatch_1.matchVirtualPatches)(vp.req, (0, engine_1.virtualPatches)(), phase);
|
|
248
|
+
}
|
|
249
|
+
catch {
|
|
250
|
+
finding = null;
|
|
251
|
+
}
|
|
252
|
+
// A monitored match is reported and the next phase still runs; a blocked one throws.
|
|
253
|
+
if (finding)
|
|
254
|
+
(0, engine_1.handleFinding)(finding, exports.VP_SINK, { framework: ctx.framework, route: ctx.route, method: ctx.method, path: ctx.path });
|
|
255
|
+
runRequestRules(ctx, phase);
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
/**
|
|
259
|
+
* Custom request rules (README "Custom rules"): each match is reported in
|
|
260
|
+
* order; the first that blocks throws the block error. Any other failure
|
|
261
|
+
* lets the request through.
|
|
262
|
+
*/
|
|
263
|
+
function runRequestRules(ctx, phase) {
|
|
264
|
+
let matches;
|
|
265
|
+
try {
|
|
266
|
+
const rules = (0, engine_1.customRules)();
|
|
267
|
+
// Mode off skips custom rules: nothing is evaluated.
|
|
268
|
+
if (!rules.length || (0, engine_1.modeFor)('custom_rule') === 'off')
|
|
269
|
+
return;
|
|
270
|
+
const inputs = phase === 'head' && ctx.headInputs !== undefined ? ctx.inputs.slice(0, ctx.headInputs) : ctx.inputs;
|
|
271
|
+
matches = (0, custom_rules_1.matchRequestRules)(rules, ctx, phase, (0, custom_rules_1.requestSubject)(ctx, (0, engine_1.applicationName)(), inputs));
|
|
272
|
+
}
|
|
273
|
+
catch {
|
|
274
|
+
return;
|
|
275
|
+
}
|
|
276
|
+
const extra = { framework: ctx.framework, route: ctx.route, method: ctx.method, path: ctx.path };
|
|
277
|
+
for (const m of matches)
|
|
278
|
+
(0, engine_1.handleFinding)((0, custom_rules_1.customFinding)(m.rule, m.input), exports.VP_SINK, extra);
|
|
279
|
+
}
|
|
280
|
+
/**
|
|
281
|
+
* Sets up late body capture: when a sink first reads the inputs, a body a
|
|
282
|
+
* parser set after the middleware ran is captured and judged.
|
|
283
|
+
*/
|
|
284
|
+
function captureLater(ctx, read) {
|
|
285
|
+
if (ctx.vp?.bodyKnown)
|
|
286
|
+
return;
|
|
287
|
+
ctx.late = () => {
|
|
288
|
+
try {
|
|
289
|
+
const b = read();
|
|
290
|
+
if (!b || b.body === undefined || b.body === null)
|
|
291
|
+
return false;
|
|
292
|
+
captureBody(ctx, b);
|
|
293
|
+
}
|
|
294
|
+
catch (e) {
|
|
295
|
+
// An upload check that blocks stops the call; any other failure lets it through.
|
|
296
|
+
if (e instanceof types_1.RaspBlockedError)
|
|
297
|
+
throw e;
|
|
298
|
+
return true;
|
|
299
|
+
}
|
|
300
|
+
runVirtualPatches(ctx);
|
|
301
|
+
return true;
|
|
302
|
+
};
|
|
303
|
+
}
|
|
304
|
+
//# sourceMappingURL=capture.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"capture.js","sourceRoot":"","sources":["../../src/rasp/capture.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,122 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Signed RASP config client (README "The signed config").
|
|
3
|
+
*
|
|
4
|
+
* `GET /api/rasp/config?app=` returns `{ config: <compact JWS>, keys }`. The
|
|
5
|
+
* JWS is trusted only when it verifies against a key the app pinned
|
|
6
|
+
* (`configPublicKey` / `SHIELD360_CONFIG_PUBLIC_KEY`: a JWK, a JWKS for
|
|
7
|
+
* rotation, or the bare base64url Ed25519 `x`). The `keys` in the response
|
|
8
|
+
* are never trusted on their own: they came over the same channel as the
|
|
9
|
+
* config. Only with trust on first use (development: `allowUnpinnedConfig`
|
|
10
|
+
* or `SHIELD360_CONFIG_TOFU=dev`, never in production) is the first `kid`
|
|
11
|
+
* seen pinned; a config signed by another kid after that is rejected. A
|
|
12
|
+
* pinned key that does not verify never falls back to trust on first use.
|
|
13
|
+
*
|
|
14
|
+
* ETag polling every 60 s ± 10 s, 5 minutes after a failure; the last
|
|
15
|
+
* verified config is kept in memory and in a cache file that is re-verified
|
|
16
|
+
* when loaded. Never throws and never blocks start-up.
|
|
17
|
+
*/
|
|
18
|
+
import { KeyObject } from 'crypto';
|
|
19
|
+
import type { AttackType, ConfigPublicKey, RaspAllow, RaspMode } from './types';
|
|
20
|
+
import type { VirtualPatch } from './vpatch';
|
|
21
|
+
export declare const JWS_TYPE = "shield360-rasp+jws";
|
|
22
|
+
export declare const SKEW_S = 60;
|
|
23
|
+
export declare const POLL_MS = 60000;
|
|
24
|
+
export declare const JITTER_MS = 10000;
|
|
25
|
+
export declare const BACKOFF_MS: number;
|
|
26
|
+
export type RaspClaims = {
|
|
27
|
+
v: number;
|
|
28
|
+
app: string;
|
|
29
|
+
iat?: number;
|
|
30
|
+
exp: number;
|
|
31
|
+
version: string;
|
|
32
|
+
killSwitch?: boolean;
|
|
33
|
+
snippets?: boolean;
|
|
34
|
+
reportTargets?: boolean;
|
|
35
|
+
mode?: RaspMode;
|
|
36
|
+
attacks?: Partial<Record<AttackType, RaspMode>>;
|
|
37
|
+
allow?: Partial<RaspAllow>;
|
|
38
|
+
rules?: VirtualPatch[] | null;
|
|
39
|
+
sinks?: unknown[] | null;
|
|
40
|
+
/** Custom rules (README "Custom rules"); null = none. */
|
|
41
|
+
customRules?: unknown[] | null;
|
|
42
|
+
/** Decoy paths as sent (README "Deception"; deception.ts reads them); absent or null = off. */
|
|
43
|
+
deception?: unknown;
|
|
44
|
+
/** Passive IAST switch and sampling rate (README "Passive IAST"). */
|
|
45
|
+
iast?: 'on' | 'off';
|
|
46
|
+
iastSampleRate?: number;
|
|
47
|
+
};
|
|
48
|
+
export type PinnedKey = {
|
|
49
|
+
kid?: string;
|
|
50
|
+
x: string;
|
|
51
|
+
key: KeyObject;
|
|
52
|
+
};
|
|
53
|
+
/**
|
|
54
|
+
* Parses a pinned key: a JWK, a JWKS, or the bare base64url Ed25519 `x`
|
|
55
|
+
* (objects or JSON text). Unusable entries are left out; [] when none is usable.
|
|
56
|
+
*/
|
|
57
|
+
export declare function parsePublicKeys(input: ConfigPublicKey | undefined | null): PinnedKey[];
|
|
58
|
+
export type VerifyResult = {
|
|
59
|
+
ok: true;
|
|
60
|
+
claims: RaspClaims;
|
|
61
|
+
kid?: string;
|
|
62
|
+
} | {
|
|
63
|
+
ok: false;
|
|
64
|
+
reason: string;
|
|
65
|
+
};
|
|
66
|
+
/** The `kid` in a JWS header, or undefined. */
|
|
67
|
+
export declare function jwsKid(token: string): string | undefined;
|
|
68
|
+
/**
|
|
69
|
+
* Verifies a compact JWS against the given keys only: `alg` EdDSA, `typ`
|
|
70
|
+
* shield360-rasp+jws, an Ed25519 signature by the pinned key whose kid
|
|
71
|
+
* matches the header (any pinned key when the header names none listed), `v` 1, `app` equal to ours, `exp` in the future
|
|
72
|
+
* (60 s skew).
|
|
73
|
+
*/
|
|
74
|
+
export declare function verifyConfigJws(token: unknown, keys: PinnedKey[], app: string, nowS?: number): VerifyResult;
|
|
75
|
+
export type PollResult = 'updated' | 'unchanged' | 'rejected' | 'failed';
|
|
76
|
+
export type ConfigClientOptions = {
|
|
77
|
+
url: string;
|
|
78
|
+
apiKey: string;
|
|
79
|
+
app: string;
|
|
80
|
+
/** Pinned keys (parsePublicKeys). */
|
|
81
|
+
pinned: PinnedKey[];
|
|
82
|
+
/** Development only (the caller already refused it in production): pin the first kid the server sends. */
|
|
83
|
+
allowUnpinned?: boolean;
|
|
84
|
+
cacheDir: string;
|
|
85
|
+
/** A verified config, or undefined when the one in force expired. */
|
|
86
|
+
onConfig: (claims: RaspClaims | undefined) => void;
|
|
87
|
+
/** Why a config was refused (once per reason). */
|
|
88
|
+
onWarning?: (reason: string) => void;
|
|
89
|
+
fetchImpl?: typeof fetch;
|
|
90
|
+
now?: () => number;
|
|
91
|
+
random?: () => number;
|
|
92
|
+
};
|
|
93
|
+
export declare class RaspConfigClient {
|
|
94
|
+
private readonly o;
|
|
95
|
+
private etag?;
|
|
96
|
+
private timer?;
|
|
97
|
+
private readonly base;
|
|
98
|
+
/** Keys pinned on first use (allowUnpinned only). */
|
|
99
|
+
private tofu;
|
|
100
|
+
private readonly warned;
|
|
101
|
+
current?: RaspClaims;
|
|
102
|
+
stopped: boolean;
|
|
103
|
+
constructor(o: ConfigClientOptions);
|
|
104
|
+
/** The keys a config must verify against right now. */
|
|
105
|
+
private trusted;
|
|
106
|
+
private nowMs;
|
|
107
|
+
cacheFile(): string;
|
|
108
|
+
private warn;
|
|
109
|
+
private apply;
|
|
110
|
+
/** Loads the cached config and re-verifies it. Pinned keys are never read from the cache. */
|
|
111
|
+
loadCache(): boolean;
|
|
112
|
+
private saveCache;
|
|
113
|
+
/** Drops the config in force once it has expired (the platform could not be reached for its whole lifetime). */
|
|
114
|
+
private expire;
|
|
115
|
+
/** One poll. Never throws. */
|
|
116
|
+
poll(): Promise<PollResult>;
|
|
117
|
+
private fetchOnce;
|
|
118
|
+
/** The delay before the next poll after a result. */
|
|
119
|
+
nextDelay(r: PollResult): number;
|
|
120
|
+
start(): void;
|
|
121
|
+
stop(): void;
|
|
122
|
+
}
|