@blamejs/blamejs-shop 0.4.31 → 0.4.32
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/CHANGELOG.md +2 -0
- package/lib/asset-manifest.json +1 -1
- package/lib/vendor/MANIFEST.json +392 -278
- package/lib/vendor/blamejs/.github/workflows/ci.yml +34 -3
- package/lib/vendor/blamejs/.github/workflows/npm-publish.yml +21 -4
- package/lib/vendor/blamejs/.gitignore +6 -0
- package/lib/vendor/blamejs/CHANGELOG.md +26 -0
- package/lib/vendor/blamejs/MIGRATING.md +43 -0
- package/lib/vendor/blamejs/README.md +8 -6
- package/lib/vendor/blamejs/SECURITY.md +19 -3
- package/lib/vendor/blamejs/api-snapshot.json +2190 -664
- package/lib/vendor/blamejs/docker/caddy/localstack.Caddyfile +19 -0
- package/lib/vendor/blamejs/docker/init/generate-certs.sh +1 -1
- package/lib/vendor/blamejs/docker/otel/config.yaml +42 -0
- package/lib/vendor/blamejs/docker/otel/export/.gitkeep +0 -0
- package/lib/vendor/blamejs/docker/postgres/initdb/10-replication.sh +15 -0
- package/lib/vendor/blamejs/docker/postgres/replica-entrypoint.sh +38 -0
- package/lib/vendor/blamejs/docker/toxiproxy/toxiproxy.json +14 -0
- package/lib/vendor/blamejs/docker-compose.test.yml +209 -0
- package/lib/vendor/blamejs/examples/wiki/lib/page-generator.js +132 -0
- package/lib/vendor/blamejs/examples/wiki/lib/source-comment-block-validator.js +221 -61
- package/lib/vendor/blamejs/examples/wiki/lib/source-doc-parser.js +144 -9
- package/lib/vendor/blamejs/examples/wiki/test/e2e.js +99 -0
- package/lib/vendor/blamejs/fuzz/guard-sql.fuzz.js +36 -0
- package/lib/vendor/blamejs/index.js +4 -0
- package/lib/vendor/blamejs/lib/agent-envelope-mac.js +104 -0
- package/lib/vendor/blamejs/lib/agent-event-bus.js +105 -4
- package/lib/vendor/blamejs/lib/agent-posture-chain.js +8 -42
- package/lib/vendor/blamejs/lib/ai-content-detect.js +9 -10
- package/lib/vendor/blamejs/lib/api-key.js +158 -77
- package/lib/vendor/blamejs/lib/atomic-file.js +62 -4
- package/lib/vendor/blamejs/lib/audit-chain.js +47 -11
- package/lib/vendor/blamejs/lib/audit-sign.js +77 -2
- package/lib/vendor/blamejs/lib/audit-tools.js +79 -51
- package/lib/vendor/blamejs/lib/audit.js +259 -123
- package/lib/vendor/blamejs/lib/auth/oauth.js +53 -9
- package/lib/vendor/blamejs/lib/auth/openid-federation.js +108 -47
- package/lib/vendor/blamejs/lib/auth/saml.js +6 -8
- package/lib/vendor/blamejs/lib/auth/sd-jwt-vc.js +31 -5
- package/lib/vendor/blamejs/lib/backup/index.js +45 -10
- package/lib/vendor/blamejs/lib/break-glass.js +355 -147
- package/lib/vendor/blamejs/lib/cache.js +174 -105
- package/lib/vendor/blamejs/lib/chain-writer.js +38 -16
- package/lib/vendor/blamejs/lib/cli.js +19 -14
- package/lib/vendor/blamejs/lib/cluster-provider-db.js +130 -104
- package/lib/vendor/blamejs/lib/cluster-storage.js +119 -22
- package/lib/vendor/blamejs/lib/cluster.js +119 -71
- package/lib/vendor/blamejs/lib/codepoint-class.js +23 -0
- package/lib/vendor/blamejs/lib/compliance.js +206 -4
- package/lib/vendor/blamejs/lib/consent.js +82 -29
- package/lib/vendor/blamejs/lib/constants.js +27 -11
- package/lib/vendor/blamejs/lib/crypto-field.js +916 -156
- package/lib/vendor/blamejs/lib/db-declare-row-policy.js +35 -22
- package/lib/vendor/blamejs/lib/db-file-lifecycle.js +3 -2
- package/lib/vendor/blamejs/lib/db-query.js +882 -260
- package/lib/vendor/blamejs/lib/db-schema.js +228 -44
- package/lib/vendor/blamejs/lib/db.js +249 -99
- package/lib/vendor/blamejs/lib/dsr.js +385 -55
- package/lib/vendor/blamejs/lib/error-page.js +14 -1
- package/lib/vendor/blamejs/lib/external-db-migrate.js +239 -137
- package/lib/vendor/blamejs/lib/external-db.js +549 -34
- package/lib/vendor/blamejs/lib/file-upload.js +52 -7
- package/lib/vendor/blamejs/lib/framework-error.js +20 -1
- package/lib/vendor/blamejs/lib/framework-files.js +73 -0
- package/lib/vendor/blamejs/lib/framework-schema.js +695 -394
- package/lib/vendor/blamejs/lib/gate-contract.js +659 -1
- package/lib/vendor/blamejs/lib/guard-agent-registry.js +26 -44
- package/lib/vendor/blamejs/lib/guard-all.js +1 -0
- package/lib/vendor/blamejs/lib/guard-auth.js +42 -112
- package/lib/vendor/blamejs/lib/guard-cidr.js +33 -154
- package/lib/vendor/blamejs/lib/guard-csv.js +46 -113
- package/lib/vendor/blamejs/lib/guard-domain.js +34 -157
- package/lib/vendor/blamejs/lib/guard-dsn.js +27 -43
- package/lib/vendor/blamejs/lib/guard-email.js +47 -69
- package/lib/vendor/blamejs/lib/guard-envelope.js +19 -32
- package/lib/vendor/blamejs/lib/guard-event-bus-payload.js +24 -42
- package/lib/vendor/blamejs/lib/guard-event-bus-topic.js +25 -43
- package/lib/vendor/blamejs/lib/guard-filename.js +42 -106
- package/lib/vendor/blamejs/lib/guard-graphql.js +42 -123
- package/lib/vendor/blamejs/lib/guard-html.js +53 -108
- package/lib/vendor/blamejs/lib/guard-idempotency-key.js +24 -42
- package/lib/vendor/blamejs/lib/guard-image.js +46 -103
- package/lib/vendor/blamejs/lib/guard-imap-command.js +18 -32
- package/lib/vendor/blamejs/lib/guard-jmap.js +16 -30
- package/lib/vendor/blamejs/lib/guard-json.js +38 -108
- package/lib/vendor/blamejs/lib/guard-jsonpath.js +38 -171
- package/lib/vendor/blamejs/lib/guard-jwt.js +49 -179
- package/lib/vendor/blamejs/lib/guard-list-id.js +25 -41
- package/lib/vendor/blamejs/lib/guard-list-unsubscribe.js +27 -43
- package/lib/vendor/blamejs/lib/guard-mail-compose.js +24 -42
- package/lib/vendor/blamejs/lib/guard-mail-move.js +26 -44
- package/lib/vendor/blamejs/lib/guard-mail-query.js +28 -46
- package/lib/vendor/blamejs/lib/guard-mail-reply.js +24 -42
- package/lib/vendor/blamejs/lib/guard-mail-sieve.js +24 -42
- package/lib/vendor/blamejs/lib/guard-managesieve-command.js +17 -31
- package/lib/vendor/blamejs/lib/guard-markdown.js +37 -104
- package/lib/vendor/blamejs/lib/guard-message-id.js +26 -45
- package/lib/vendor/blamejs/lib/guard-mime.js +39 -151
- package/lib/vendor/blamejs/lib/guard-oauth.js +54 -135
- package/lib/vendor/blamejs/lib/guard-pdf.js +45 -101
- package/lib/vendor/blamejs/lib/guard-pop3-command.js +21 -31
- package/lib/vendor/blamejs/lib/guard-posture-chain.js +24 -42
- package/lib/vendor/blamejs/lib/guard-regex.js +33 -107
- package/lib/vendor/blamejs/lib/guard-saga-config.js +24 -42
- package/lib/vendor/blamejs/lib/guard-shell.js +42 -172
- package/lib/vendor/blamejs/lib/guard-smtp-command.js +48 -54
- package/lib/vendor/blamejs/lib/guard-snapshot-envelope.js +24 -42
- package/lib/vendor/blamejs/lib/guard-sql.js +1491 -0
- package/lib/vendor/blamejs/lib/guard-stream-args.js +24 -43
- package/lib/vendor/blamejs/lib/guard-svg.js +47 -65
- package/lib/vendor/blamejs/lib/guard-template.js +35 -172
- package/lib/vendor/blamejs/lib/guard-tenant-id.js +26 -45
- package/lib/vendor/blamejs/lib/guard-time.js +32 -154
- package/lib/vendor/blamejs/lib/guard-trace-context.js +25 -44
- package/lib/vendor/blamejs/lib/guard-uuid.js +32 -153
- package/lib/vendor/blamejs/lib/guard-xml.js +38 -113
- package/lib/vendor/blamejs/lib/guard-yaml.js +51 -163
- package/lib/vendor/blamejs/lib/http-client.js +37 -9
- package/lib/vendor/blamejs/lib/inbox.js +120 -107
- package/lib/vendor/blamejs/lib/legal-hold.js +121 -50
- package/lib/vendor/blamejs/lib/log-stream-cloudwatch.js +47 -31
- package/lib/vendor/blamejs/lib/log-stream-otlp.js +32 -18
- package/lib/vendor/blamejs/lib/mail-auth.js +236 -0
- package/lib/vendor/blamejs/lib/mail-crypto-smime.js +2 -6
- package/lib/vendor/blamejs/lib/mail-dkim.js +1 -0
- package/lib/vendor/blamejs/lib/mail-greylist.js +2 -6
- package/lib/vendor/blamejs/lib/mail-helo.js +2 -6
- package/lib/vendor/blamejs/lib/mail-journal.js +85 -64
- package/lib/vendor/blamejs/lib/mail-rbl.js +2 -6
- package/lib/vendor/blamejs/lib/mail-scan.js +2 -6
- package/lib/vendor/blamejs/lib/mail-server-jmap.js +117 -12
- package/lib/vendor/blamejs/lib/mail-server-mx.js +276 -7
- package/lib/vendor/blamejs/lib/mail-spam-score.js +2 -6
- package/lib/vendor/blamejs/lib/mail-store.js +293 -154
- package/lib/vendor/blamejs/lib/mail.js +8 -4
- package/lib/vendor/blamejs/lib/middleware/body-parser.js +71 -25
- package/lib/vendor/blamejs/lib/middleware/csrf-protect.js +19 -8
- package/lib/vendor/blamejs/lib/middleware/dpop.js +10 -1
- package/lib/vendor/blamejs/lib/middleware/fetch-metadata.js +17 -7
- package/lib/vendor/blamejs/lib/middleware/idempotency-key.js +75 -51
- package/lib/vendor/blamejs/lib/middleware/rate-limit.js +102 -32
- package/lib/vendor/blamejs/lib/middleware/security-headers.js +21 -5
- package/lib/vendor/blamejs/lib/migrations.js +108 -66
- package/lib/vendor/blamejs/lib/network-heartbeat.js +7 -0
- package/lib/vendor/blamejs/lib/network-proxy.js +24 -1
- package/lib/vendor/blamejs/lib/nonce-store.js +31 -9
- package/lib/vendor/blamejs/lib/object-store/azure-blob-bucket-ops.js +9 -4
- package/lib/vendor/blamejs/lib/object-store/azure-blob.js +57 -3
- package/lib/vendor/blamejs/lib/object-store/gcs.js +4 -1
- package/lib/vendor/blamejs/lib/object-store/sigv4-bucket-ops.js +5 -2
- package/lib/vendor/blamejs/lib/object-store/sigv4.js +38 -6
- package/lib/vendor/blamejs/lib/observability-otlp-exporter.js +9 -1
- package/lib/vendor/blamejs/lib/observability.js +124 -0
- package/lib/vendor/blamejs/lib/otel-export.js +12 -3
- package/lib/vendor/blamejs/lib/outbox.js +184 -83
- package/lib/vendor/blamejs/lib/parsers/safe-xml.js +47 -7
- package/lib/vendor/blamejs/lib/pqc-agent.js +44 -0
- package/lib/vendor/blamejs/lib/pubsub-cluster.js +42 -20
- package/lib/vendor/blamejs/lib/queue-local.js +225 -140
- package/lib/vendor/blamejs/lib/queue-redis.js +9 -1
- package/lib/vendor/blamejs/lib/queue-sqs.js +6 -0
- package/lib/vendor/blamejs/lib/queue.js +7 -0
- package/lib/vendor/blamejs/lib/redact.js +68 -11
- package/lib/vendor/blamejs/lib/redis-client.js +160 -31
- package/lib/vendor/blamejs/lib/request-helpers.js +7 -0
- package/lib/vendor/blamejs/lib/retention.js +101 -40
- package/lib/vendor/blamejs/lib/router.js +212 -5
- package/lib/vendor/blamejs/lib/safe-dns.js +29 -45
- package/lib/vendor/blamejs/lib/safe-ical.js +18 -33
- package/lib/vendor/blamejs/lib/safe-icap.js +27 -43
- package/lib/vendor/blamejs/lib/safe-sieve.js +21 -40
- package/lib/vendor/blamejs/lib/safe-sql.js +212 -3
- package/lib/vendor/blamejs/lib/safe-url.js +170 -3
- package/lib/vendor/blamejs/lib/safe-vcard.js +18 -33
- package/lib/vendor/blamejs/lib/scheduler.js +35 -12
- package/lib/vendor/blamejs/lib/seeders.js +122 -74
- package/lib/vendor/blamejs/lib/session-stores.js +42 -14
- package/lib/vendor/blamejs/lib/session.js +175 -77
- package/lib/vendor/blamejs/lib/sql.js +3842 -0
- package/lib/vendor/blamejs/lib/sse.js +26 -0
- package/lib/vendor/blamejs/lib/ssrf-guard.js +151 -4
- package/lib/vendor/blamejs/lib/static.js +177 -34
- package/lib/vendor/blamejs/lib/subject.js +96 -49
- package/lib/vendor/blamejs/lib/vault/index.js +3 -2
- package/lib/vendor/blamejs/lib/vault/passphrase-ops.js +3 -2
- package/lib/vendor/blamejs/lib/vault/rotate.js +168 -108
- package/lib/vendor/blamejs/lib/vault-aad.js +6 -0
- package/lib/vendor/blamejs/lib/vendor-data.js +2 -0
- package/lib/vendor/blamejs/lib/websocket.js +35 -5
- package/lib/vendor/blamejs/lib/worker-pool.js +11 -0
- package/lib/vendor/blamejs/package.json +2 -2
- package/lib/vendor/blamejs/release-notes/v0.14.x.json +1503 -0
- package/lib/vendor/blamejs/release-notes/v0.15.0.json +77 -0
- package/lib/vendor/blamejs/release-notes/v0.15.1.json +22 -0
- package/lib/vendor/blamejs/release-notes/v0.15.2.json +22 -0
- package/lib/vendor/blamejs/release-notes/v0.15.3.json +39 -0
- package/lib/vendor/blamejs/release-notes/v0.15.4.json +39 -0
- package/lib/vendor/blamejs/release-notes/v0.15.5.json +22 -0
- package/lib/vendor/blamejs/release-notes/v0.15.6.json +59 -0
- package/lib/vendor/blamejs/scripts/check-services.js +21 -0
- package/lib/vendor/blamejs/scripts/gen-migrating.js +51 -0
- package/lib/vendor/blamejs/scripts/release.js +398 -38
- package/lib/vendor/blamejs/test/00-primitives.js +117 -0
- package/lib/vendor/blamejs/test/10-state.js +140 -14
- package/lib/vendor/blamejs/test/20-db.js +65 -2
- package/lib/vendor/blamejs/test/helpers/db.js +9 -0
- package/lib/vendor/blamejs/test/helpers/drivers.js +27 -15
- package/lib/vendor/blamejs/test/helpers/services.js +21 -0
- package/lib/vendor/blamejs/test/integration/audit-actor-binding-pg.test.js +246 -0
- package/lib/vendor/blamejs/test/integration/audit-chain-external-db.test.js +517 -0
- package/lib/vendor/blamejs/test/integration/audit-stack-mysql.test.js +639 -0
- package/lib/vendor/blamejs/test/integration/audit-stack-postgres.test.js +832 -0
- package/lib/vendor/blamejs/test/integration/backup-restore-objectstore.test.js +453 -0
- package/lib/vendor/blamejs/test/integration/data-layer-cluster-mysql.test.js +649 -0
- package/lib/vendor/blamejs/test/integration/data-layer-cluster-pg.test.js +770 -0
- package/lib/vendor/blamejs/test/integration/data-layer-mysql-privacy.test.js +630 -0
- package/lib/vendor/blamejs/test/integration/data-layer-mysql.test.js +610 -0
- package/lib/vendor/blamejs/test/integration/data-layer-pg.test.js +577 -0
- package/lib/vendor/blamejs/test/integration/data-layer-postgres.test.js +771 -0
- package/lib/vendor/blamejs/test/integration/db-layer-mysql.test.js +549 -0
- package/lib/vendor/blamejs/test/integration/db-layer-postgres.test.js +598 -0
- package/lib/vendor/blamejs/test/integration/distributed-scheduler-fencing-pg.test.js +602 -0
- package/lib/vendor/blamejs/test/integration/external-db-postgres.test.js +576 -0
- package/lib/vendor/blamejs/test/integration/framework-schema-mysql.test.js +353 -0
- package/lib/vendor/blamejs/test/integration/log-stream-cloudwatch.test.js +224 -0
- package/lib/vendor/blamejs/test/integration/mail-crypto-smime.test.js +142 -17
- package/lib/vendor/blamejs/test/integration/network-heartbeat.test.js +25 -10
- package/lib/vendor/blamejs/test/integration/object-store-azure.test.js +101 -0
- package/lib/vendor/blamejs/test/integration/object-store-gcs.test.js +239 -0
- package/lib/vendor/blamejs/test/integration/object-store-sigv4.test.js +35 -16
- package/lib/vendor/blamejs/test/integration/object-store-worm-lock.test.js +291 -0
- package/lib/vendor/blamejs/test/integration/pubsub.test.js +14 -0
- package/lib/vendor/blamejs/test/integration/queue-sqs.test.js +322 -0
- package/lib/vendor/blamejs/test/integration/redis-reconnect-toxiproxy.test.js +300 -0
- package/lib/vendor/blamejs/test/integration/sql-fts5-catalog-sqlite.test.js +154 -0
- package/lib/vendor/blamejs/test/integration/tls-classical-downgrade-audit.test.js +71 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/agent-event-bus.test.js +175 -12
- package/lib/vendor/blamejs/test/layer-0-primitives/atomic-file-exclusive-temp.test.js +216 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/audit-checkpoint-false-rollback.test.js +203 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/audit-query-self-log.test.js +126 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/audit-safeemit-redacts-secrets.test.js +196 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/audit-signing-key-rotation.test.js +197 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/audit-verifybundle-tamper.test.js +209 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/azure-blob-key-encoding.test.js +121 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/backup-residency-posture.test.js +168 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/backup-scheduletest-drill.test.js +318 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/break-glass.test.js +233 -7
- package/lib/vendor/blamejs/test/layer-0-primitives/codebase-patterns.test.js +1120 -14
- package/lib/vendor/blamejs/test/layer-0-primitives/compliance.test.js +229 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-field-derived-hash.test.js +24 -7
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-field-dual-read-migrate.test.js +165 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-field-per-row-key.test.js +350 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-field-unseal-rate-cap.test.js +27 -9
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-field-upgrade-dialect.test.js +76 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/crypto-interop-oracles.test.js +392 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/csrf-protect.test.js +159 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/db-column-gate.test.js +180 -1
- package/lib/vendor/blamejs/test/layer-0-primitives/db-query-cross-schema.test.js +5 -2
- package/lib/vendor/blamejs/test/layer-0-primitives/db-query-sealed-field-in.test.js +101 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/db-raw-residency-gate.test.js +128 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/db-schema-drift.test.js +38 -5
- package/lib/vendor/blamejs/test/layer-0-primitives/db-schema-reconcile-emittable.test.js +127 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/db-stream-and-payload-shape.test.js +267 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/db-worm.test.js +150 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/defineguard-default-gate-posture-caps.test.js +30 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/dpop-middleware-replaystore-required.test.js +46 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/dsr.test.js +218 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/erase-posture-vacuum.test.js +210 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/external-db-hardening.test.js +4 -1
- package/lib/vendor/blamejs/test/layer-0-primitives/external-db-migrate.test.js +48 -2
- package/lib/vendor/blamejs/test/layer-0-primitives/federation-vc-suite.test.js +237 -5
- package/lib/vendor/blamejs/test/layer-0-primitives/fetch-metadata.test.js +20 -9
- package/lib/vendor/blamejs/test/layer-0-primitives/file-upload-content-safety-skip-audit.test.js +193 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/guard-csv.test.js +90 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/http-client-stream.test.js +85 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/idempotency-key.test.js +10 -6
- package/lib/vendor/blamejs/test/layer-0-primitives/inbox.test.js +15 -4
- package/lib/vendor/blamejs/test/layer-0-primitives/legal-hold.test.js +146 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/mail-auth.test.js +189 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/mail-journal.test.js +3 -1
- package/lib/vendor/blamejs/test/layer-0-primitives/mail-server-jmap.test.js +123 -4
- package/lib/vendor/blamejs/test/layer-0-primitives/mail-server-mx.test.js +207 -2
- package/lib/vendor/blamejs/test/layer-0-primitives/mail-store.test.js +74 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/oauth-callback.test.js +43 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/otel-export.test.js +133 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/otlp-attr-redaction.test.js +101 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/outbox-inflight-reaper.test.js +136 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/parsers-standalone.test.js +83 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/passkey-real-vectors.test.js +429 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/pqc-agent-curve.test.js +21 -11
- package/lib/vendor/blamejs/test/layer-0-primitives/queue-byo-db.test.js +40 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/redact-dlp.test.js +83 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/redis-client.test.js +113 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/retention-dryrun-no-vacuum.test.js +99 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/router-use-path-scope.test.js +255 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/safe-url-canonicalize.test.js +309 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/safe-xml.test.js +143 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/saml-subjectconfirmation-notonorafter.test.js +287 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/sd-jwt-vc-ecdsa-p1363.test.js +79 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/sd-jwt-vc.test.js +50 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/security-headers.test.js +31 -4
- package/lib/vendor/blamejs/test/layer-0-primitives/session-extensions.test.js +45 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/sigv4-bucket-ops.test.js +49 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/sql.test.js +595 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/sse-backpressure.test.js +91 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/ssrf-guard.test.js +69 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/static.test.js +194 -2
- package/lib/vendor/blamejs/test/layer-0-primitives/websocket-extension-header.test.js +88 -0
- package/lib/vendor/blamejs/test/layer-0-primitives/worker-pool-recycle-race.test.js +66 -0
- package/lib/vendor/blamejs/test/layer-1-state/api-key.test.js +84 -0
- package/lib/vendor/blamejs/test/layer-5-integration/external-db-residency.test.js +638 -0
- package/lib/vendor/blamejs/test/layer-5-integration/guard-host-integration.test.js +21 -0
- package/lib/vendor/blamejs/test/smoke.js +79 -21
- package/package.json +1 -1
- package/lib/vendor/blamejs/release-notes/v0.14.0.json +0 -43
- package/lib/vendor/blamejs/release-notes/v0.14.1.json +0 -60
- package/lib/vendor/blamejs/release-notes/v0.14.10.json +0 -54
- package/lib/vendor/blamejs/release-notes/v0.14.11.json +0 -72
- package/lib/vendor/blamejs/release-notes/v0.14.12.json +0 -95
- package/lib/vendor/blamejs/release-notes/v0.14.13.json +0 -52
- package/lib/vendor/blamejs/release-notes/v0.14.14.json +0 -31
- package/lib/vendor/blamejs/release-notes/v0.14.16.json +0 -45
- package/lib/vendor/blamejs/release-notes/v0.14.17.json +0 -57
- package/lib/vendor/blamejs/release-notes/v0.14.18.json +0 -127
- package/lib/vendor/blamejs/release-notes/v0.14.19.json +0 -61
- package/lib/vendor/blamejs/release-notes/v0.14.2.json +0 -18
- package/lib/vendor/blamejs/release-notes/v0.14.20.json +0 -73
- package/lib/vendor/blamejs/release-notes/v0.14.21.json +0 -98
- package/lib/vendor/blamejs/release-notes/v0.14.22.json +0 -91
- package/lib/vendor/blamejs/release-notes/v0.14.3.json +0 -18
- package/lib/vendor/blamejs/release-notes/v0.14.4.json +0 -18
- package/lib/vendor/blamejs/release-notes/v0.14.5.json +0 -18
- package/lib/vendor/blamejs/release-notes/v0.14.6.json +0 -60
- package/lib/vendor/blamejs/release-notes/v0.14.7.json +0 -77
- package/lib/vendor/blamejs/release-notes/v0.14.8.json +0 -27
- package/lib/vendor/blamejs/release-notes/v0.14.9.json +0 -40
|
@@ -89,8 +89,13 @@ function _firstSegment(primTag) {
|
|
|
89
89
|
// Probe the universe of primitive signatures available for @related
|
|
90
90
|
// cross-reference. Sources: every @primitive block under lib/, plus
|
|
91
91
|
// every primitive heading in seeded page bodies (which includes
|
|
92
|
-
// hand-authored AND generated pages once the seeder ran)
|
|
93
|
-
|
|
92
|
+
// hand-authored AND generated pages once the seeder ran), plus the
|
|
93
|
+
// factory-synthesized ABI methods (compliancePosture / buildProfile /
|
|
94
|
+
// loadRulePack / gate) every defineGuard / defineParser guard exposes —
|
|
95
|
+
// these have no in-source @primitive block (the doc lives once in
|
|
96
|
+
// gate-contract.js's @abiTemplate blocks) but the page generator renders
|
|
97
|
+
// them per guard, so a real guard block's @related to them must resolve.
|
|
98
|
+
function _knownPrimitiveSet(docs, seederIndex, parser) {
|
|
94
99
|
var set = {};
|
|
95
100
|
Object.keys(docs).forEach(function (file) {
|
|
96
101
|
docs[file].primitives.forEach(function (p) {
|
|
@@ -98,6 +103,22 @@ function _knownPrimitiveSet(docs, seederIndex) {
|
|
|
98
103
|
if (sig) set[_bare(sig)] = true;
|
|
99
104
|
});
|
|
100
105
|
});
|
|
106
|
+
// Register the per-guard ABI method sigs the factory synthesizes.
|
|
107
|
+
if (parser && typeof parser.factoryTemplates === "function") {
|
|
108
|
+
var templates = parser.factoryTemplates(docs);
|
|
109
|
+
Object.keys(docs).forEach(function (file) {
|
|
110
|
+
var rec = docs[file];
|
|
111
|
+
if (!rec.factory) return;
|
|
112
|
+
var ns = rec.module && rec.module.tags
|
|
113
|
+
? _moduleNs(rec.module.tags.module)
|
|
114
|
+
: null;
|
|
115
|
+
if (!ns) return;
|
|
116
|
+
(templates[rec.factory.kind] || []).forEach(function (tpl) {
|
|
117
|
+
var method = tpl.tags && tpl.tags.method;
|
|
118
|
+
if (method) set[ns + "." + method] = true;
|
|
119
|
+
});
|
|
120
|
+
});
|
|
121
|
+
}
|
|
101
122
|
if (seederIndex) {
|
|
102
123
|
try {
|
|
103
124
|
var pages = require(seederIndex);
|
|
@@ -131,73 +152,113 @@ function _knownPrimitiveSet(docs, seederIndex) {
|
|
|
131
152
|
function _extractExportKeys(source) {
|
|
132
153
|
var keys = {};
|
|
133
154
|
|
|
134
|
-
// Shape
|
|
155
|
+
// Shape A: per-property module.exports.foo = ...
|
|
135
156
|
var perPropRe = /\bmodule\.exports\.([a-zA-Z_$][a-zA-Z0-9_$]*)\s*=/g;
|
|
136
157
|
var pm;
|
|
137
158
|
while ((pm = perPropRe.exec(source)) !== null) keys[pm[1]] = true;
|
|
138
159
|
|
|
139
|
-
// Shape
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
160
|
+
// Shape B: object literal `module.exports = {`. Shape C: factory call
|
|
161
|
+
// `module.exports = [ns.]defineGuard({` / `defineParser({` — the guard
|
|
162
|
+
// family's consolidated wiring assembles the frozen exports object inside
|
|
163
|
+
// gateContract.defineGuard/defineParser, so there is no object literal to
|
|
164
|
+
// scan. Both forms open an object whose keys we collect identically; the
|
|
165
|
+
// factory form additionally yields the per-guard FUNCTION exports it wires
|
|
166
|
+
// in (the spec's `validate` / `sanitize` / `gate` / `entry` references and
|
|
167
|
+
// any functions passed through `extra: { ... }`). The factory-generated
|
|
168
|
+
// wiring (buildProfile / compliancePosture / loadRulePack / gate default)
|
|
169
|
+
// has no in-source `function NAME`, so the arity filter in the missing-block
|
|
170
|
+
// pass skips it — but a per-guard function the author forgot to document is
|
|
171
|
+
// still caught, so the doc gate survives the factory refactor.
|
|
172
|
+
var litMatch = source.match(/module\.exports\s*=\s*\{/);
|
|
173
|
+
var factoryMatch = source.match(/module\.exports\s*=\s*(?:[a-zA-Z_$][a-zA-Z0-9_$]*\.)?define(?:Guard|Parser)\s*\(\s*\{/);
|
|
174
|
+
var openIdx = -1;
|
|
175
|
+
var factoryMode = false;
|
|
176
|
+
if (litMatch) {
|
|
177
|
+
openIdx = litMatch.index + litMatch[0].length - 1;
|
|
178
|
+
} else if (factoryMatch) {
|
|
179
|
+
openIdx = factoryMatch.index + factoryMatch[0].lastIndexOf("{");
|
|
180
|
+
factoryMode = true;
|
|
181
|
+
}
|
|
182
|
+
if (openIdx >= 0) {
|
|
183
|
+
_collectObjectKeys(source, openIdx, factoryMode).forEach(function (k) { keys[k] = true; });
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
return Object.keys(keys).filter(function (k) { return !/^_/.test(k); });
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
// Bracket-count the object literal whose opening `{` is at openIdx and return
|
|
190
|
+
// its top-level property names. In factoryMode it also returns bare-identifier
|
|
191
|
+
// property VALUES (e.g. `entry: validate` -> `validate`, the exported function
|
|
192
|
+
// the spec references) and the keys/values of a nested `extra: { ... }` map.
|
|
193
|
+
// The missing-block pass arity-filters the result, so non-function names
|
|
194
|
+
// (NAME / PROFILES / error classes) are harmless.
|
|
195
|
+
function _collectObjectKeys(source, openIdx, factoryMode) {
|
|
196
|
+
var i = openIdx + 1;
|
|
197
|
+
var depth = 1;
|
|
198
|
+
var inStr = null; // null | '"' | "'" | '`'
|
|
199
|
+
var inSlash = false; // line comment
|
|
200
|
+
var inBlock = false; // block comment
|
|
201
|
+
var prev = "";
|
|
202
|
+
while (i < source.length && depth > 0) {
|
|
203
|
+
var c = source[i];
|
|
204
|
+
if (inSlash) {
|
|
205
|
+
if (c === "\n") inSlash = false;
|
|
206
|
+
} else if (inBlock) {
|
|
207
|
+
if (prev === "*" && c === "/") inBlock = false;
|
|
208
|
+
} else if (inStr) {
|
|
209
|
+
if (c === "\\") { i += 2; prev = source[i - 1]; continue; }
|
|
210
|
+
if (c === inStr) inStr = null;
|
|
211
|
+
} else if (c === "/" && source[i + 1] === "/") {
|
|
212
|
+
inSlash = true;
|
|
213
|
+
} else if (c === "/" && source[i + 1] === "*") {
|
|
214
|
+
inBlock = true;
|
|
215
|
+
} else if (c === '"' || c === "'" || c === "`") {
|
|
216
|
+
inStr = c;
|
|
217
|
+
} else if (c === "{") {
|
|
218
|
+
depth++;
|
|
219
|
+
} else if (c === "}") {
|
|
220
|
+
depth--;
|
|
171
221
|
}
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
190
|
-
|
|
222
|
+
prev = c;
|
|
223
|
+
i++;
|
|
224
|
+
}
|
|
225
|
+
var found = [];
|
|
226
|
+
if (depth !== 0) return found;
|
|
227
|
+
var body = source.slice(openIdx + 1, i - 1);
|
|
228
|
+
// Match `name:` or `name,` at the start of an object-property position,
|
|
229
|
+
// after stripping nested object/array/call interiors via a depth scan.
|
|
230
|
+
var depth2 = 0;
|
|
231
|
+
var line = "";
|
|
232
|
+
var lines = [];
|
|
233
|
+
for (var j = 0; j < body.length; j++) {
|
|
234
|
+
var ch = body[j];
|
|
235
|
+
if (ch === "{" || ch === "(" || ch === "[") depth2++;
|
|
236
|
+
else if (ch === "}" || ch === ")" || ch === "]") depth2--;
|
|
237
|
+
if (depth2 === 0) {
|
|
238
|
+
line += ch;
|
|
239
|
+
if (ch === "," || ch === "\n") {
|
|
240
|
+
lines.push(line); line = "";
|
|
191
241
|
}
|
|
192
|
-
|
|
193
|
-
|
|
194
|
-
|
|
195
|
-
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
if (line) lines.push(line);
|
|
245
|
+
lines.forEach(function (l) {
|
|
246
|
+
var lm = l.match(/^\s*([a-zA-Z_$][a-zA-Z0-9_$]*)\s*[:,]/);
|
|
247
|
+
if (lm) found.push(lm[1]);
|
|
248
|
+
if (factoryMode) {
|
|
249
|
+
var vm = l.match(/:\s*([a-zA-Z_$][a-zA-Z0-9_$]*)\s*,?\s*$/);
|
|
250
|
+
if (vm) found.push(vm[1]);
|
|
251
|
+
}
|
|
252
|
+
});
|
|
253
|
+
if (factoryMode) {
|
|
254
|
+
var em = body.match(/(^|[\s,{])extra\s*:\s*\{/);
|
|
255
|
+
if (em) {
|
|
256
|
+
_collectObjectKeys(body, em.index + em[0].lastIndexOf("{"), true).forEach(function (k) {
|
|
257
|
+
found.push(k);
|
|
196
258
|
});
|
|
197
259
|
}
|
|
198
260
|
}
|
|
199
|
-
|
|
200
|
-
return Object.keys(keys).filter(function (k) { return !/^_/.test(k); });
|
|
261
|
+
return found;
|
|
201
262
|
}
|
|
202
263
|
|
|
203
264
|
// Count parameters in a signature like `b.X.Y(a, b, opts?)`. The `?`
|
|
@@ -276,7 +337,7 @@ function validate(config) {
|
|
|
276
337
|
|
|
277
338
|
var findings = [];
|
|
278
339
|
var docs = parser.parseTree(libDir);
|
|
279
|
-
var known = _knownPrimitiveSet(docs, seederIndex);
|
|
340
|
+
var known = _knownPrimitiveSet(docs, seederIndex, parser);
|
|
280
341
|
|
|
281
342
|
var declaredNs = {};
|
|
282
343
|
curationPages.forEach(function (page) {
|
|
@@ -578,9 +639,108 @@ function validate(config) {
|
|
|
578
639
|
}
|
|
579
640
|
});
|
|
580
641
|
|
|
642
|
+
// ---- Pass: @abiTemplate structural checks ----
|
|
643
|
+
// ABI doc templates are single-sourced placeholder blocks (b.{NS}.<method>
|
|
644
|
+
// with {NS}/{ERR} substituted per guard at page-gen time). They are NOT
|
|
645
|
+
// resolvable primitives, so the per-primitive pass skips them (the parser
|
|
646
|
+
// routes them to rec.abiTemplates, not rec.primitives). Validate their
|
|
647
|
+
// template shape instead: a known factory kind, a @method, a placeholder
|
|
648
|
+
// @signature, valid @status, real prose, and at least one @example. The
|
|
649
|
+
// placeholder sig + placeholder @example bodies are intentional, so the
|
|
650
|
+
// resolvable-primitive / JS-parse passes do not apply.
|
|
651
|
+
Object.keys(docs).forEach(function (file) {
|
|
652
|
+
var rec = docs[file];
|
|
653
|
+
if (!rec.abiTemplates || rec.abiTemplates.length === 0) return;
|
|
654
|
+
var rel = path.relative(libDir, file);
|
|
655
|
+
var seen = {};
|
|
656
|
+
rec.abiTemplates.forEach(function (t) {
|
|
657
|
+
var tags = t.tags || {};
|
|
658
|
+
var kind = tags.abiTemplate;
|
|
659
|
+
var label = "@abiTemplate " + (kind || "?") + (tags.method ? " " + tags.method : "");
|
|
660
|
+
if (kind !== "defineGuard" && kind !== "defineParser") {
|
|
661
|
+
findings.push({
|
|
662
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
663
|
+
msg: "@abiTemplate value must be `defineGuard` or `defineParser` (got `" + kind + "`)",
|
|
664
|
+
});
|
|
665
|
+
}
|
|
666
|
+
if (!tags.method) {
|
|
667
|
+
findings.push({
|
|
668
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
669
|
+
msg: "@abiTemplate block lacks @method — name the factory-generated ABI method it documents",
|
|
670
|
+
});
|
|
671
|
+
} else {
|
|
672
|
+
var dupeKey = kind + "::" + tags.method;
|
|
673
|
+
if (seen[dupeKey]) {
|
|
674
|
+
findings.push({
|
|
675
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
676
|
+
msg: "duplicate @abiTemplate for " + dupeKey + " — one template per (factory, method)",
|
|
677
|
+
});
|
|
678
|
+
}
|
|
679
|
+
seen[dupeKey] = true;
|
|
680
|
+
}
|
|
681
|
+
if (!tags.signature) {
|
|
682
|
+
findings.push({
|
|
683
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
684
|
+
msg: "@abiTemplate block lacks @signature",
|
|
685
|
+
});
|
|
686
|
+
} else if (tags.signature.indexOf("{NS}") === -1) {
|
|
687
|
+
findings.push({
|
|
688
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
689
|
+
msg: "@abiTemplate @signature must carry the `{NS}` placeholder (got `" + tags.signature + "`)",
|
|
690
|
+
});
|
|
691
|
+
} else if (tags.method && _bareTemplateMethod(tags.signature) !== tags.method) {
|
|
692
|
+
findings.push({
|
|
693
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
694
|
+
msg: "@abiTemplate @signature method `" + _bareTemplateMethod(tags.signature) + "` does not match @method `" + tags.method + "`",
|
|
695
|
+
});
|
|
696
|
+
}
|
|
697
|
+
if (tags.status && !KNOWN_STATUSES[tags.status]) {
|
|
698
|
+
findings.push({
|
|
699
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
700
|
+
msg: "@abiTemplate @status must be one of " + Object.keys(KNOWN_STATUSES).join(" / ") + " (got `" + tags.status + "`)",
|
|
701
|
+
});
|
|
702
|
+
}
|
|
703
|
+
if (tags.compliance) {
|
|
704
|
+
String(tags.compliance).split(",").map(function (s) { return s.trim(); }).filter(Boolean).forEach(function (p2) {
|
|
705
|
+
if (!KNOWN_POSTURES[p2]) {
|
|
706
|
+
findings.push({
|
|
707
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
708
|
+
msg: "@abiTemplate @compliance value `" + p2 + "` not in posture catalog",
|
|
709
|
+
});
|
|
710
|
+
}
|
|
711
|
+
});
|
|
712
|
+
}
|
|
713
|
+
if (!t.prose || t.prose.replace(/\s/g, "").length < 12) {
|
|
714
|
+
findings.push({
|
|
715
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
716
|
+
msg: "@abiTemplate prose body is empty or too short (<12 non-whitespace chars)",
|
|
717
|
+
});
|
|
718
|
+
}
|
|
719
|
+
if (t.proseAfterMultiLine) {
|
|
720
|
+
findings.push({
|
|
721
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
722
|
+
msg: "prose appears AFTER a multi-line tag (@opts/@example) — move prose ABOVE the multi-line tags",
|
|
723
|
+
});
|
|
724
|
+
}
|
|
725
|
+
if (!Array.isArray(tags.examples) || tags.examples.length === 0) {
|
|
726
|
+
findings.push({
|
|
727
|
+
kind: "abi-template", file: rel, primitive: label,
|
|
728
|
+
msg: "@abiTemplate block lacks @example",
|
|
729
|
+
});
|
|
730
|
+
}
|
|
731
|
+
});
|
|
732
|
+
});
|
|
733
|
+
|
|
581
734
|
return findings;
|
|
582
735
|
}
|
|
583
736
|
|
|
737
|
+
// Extract the bare method name from a placeholder template signature like
|
|
738
|
+
// `b.{NS}.compliancePosture(name)` → `compliancePosture`.
|
|
739
|
+
function _bareTemplateMethod(sig) {
|
|
740
|
+
var m = String(sig).replace(/\([^)]*\)/g, "").match(/\.([a-zA-Z_$][a-zA-Z0-9_$]*)\s*$/);
|
|
741
|
+
return m ? m[1] : null;
|
|
742
|
+
}
|
|
743
|
+
|
|
584
744
|
module.exports = {
|
|
585
745
|
validate: validate,
|
|
586
746
|
KNOWN_STATUSES: KNOWN_STATUSES,
|
|
@@ -58,6 +58,13 @@ var SINGLE_LINE_TAGS = {
|
|
|
58
58
|
primitive: true,
|
|
59
59
|
module: true,
|
|
60
60
|
concept: true,
|
|
61
|
+
// @abiTemplate <factoryKind> — single-sourced ABI doc text for a
|
|
62
|
+
// factory-generated guard method (defineGuard / defineParser). Routed
|
|
63
|
+
// to a separate template bucket, NOT the primitive list, so it renders
|
|
64
|
+
// per guard instead of as a gateContract primitive. @method names the
|
|
65
|
+
// ABI method the template documents.
|
|
66
|
+
abiTemplate: true,
|
|
67
|
+
method: true,
|
|
61
68
|
title: true,
|
|
62
69
|
nav: true,
|
|
63
70
|
order: true,
|
|
@@ -202,6 +209,10 @@ function parseBlock(raw) {
|
|
|
202
209
|
if (tags.primitive) kindFlags.push("primitive");
|
|
203
210
|
if (tags.module) kindFlags.push("module");
|
|
204
211
|
if (tags.concept) kindFlags.push("concept");
|
|
212
|
+
// @abiTemplate blocks are a distinct kind — single-sourced ABI doc
|
|
213
|
+
// text routed to the per-factory template bucket, never the primitive
|
|
214
|
+
// list. They carry no @primitive tag, so they don't trip mixedKind.
|
|
215
|
+
if (tags.abiTemplate) kindFlags.push("abiTemplate");
|
|
205
216
|
var kind = kindFlags[0] || null;
|
|
206
217
|
var mixedKind = kindFlags.length > 1 ? kindFlags : null;
|
|
207
218
|
|
|
@@ -235,17 +246,111 @@ function extractBlocks(source) {
|
|
|
235
246
|
return blocks;
|
|
236
247
|
}
|
|
237
248
|
|
|
249
|
+
// Detect a guard-family factory call at module scope:
|
|
250
|
+
// module.exports = [ns.]defineGuard({ ...
|
|
251
|
+
// module.exports = [ns.]defineParser({ ...
|
|
252
|
+
// Returns { kind, errorClass } or null. The errorClass is read from the
|
|
253
|
+
// spec's `errorClass: Ident` (the guard supplies a pre-built class) and
|
|
254
|
+
// falls back to a `Guard<Name>Error` stem derived from `errorName:` or
|
|
255
|
+
// `name:` — matching the factory's own default-class minting — so the
|
|
256
|
+
// rendered ABI template's `{ERR}` placeholder resolves even when the
|
|
257
|
+
// guard lets the factory mint the class.
|
|
258
|
+
function _detectFactory(source) {
|
|
259
|
+
var m = source.match(/module\.exports\s*=\s*(?:[a-zA-Z_$][a-zA-Z0-9_$]*\.)?define(Guard|Parser)\s*\(\s*\{/);
|
|
260
|
+
if (!m) return null;
|
|
261
|
+
var kind = "define" + m[1];
|
|
262
|
+
// Scan the spec object literal (bracket-counted) for errorClass /
|
|
263
|
+
// errorName / name / errCodePrefix.
|
|
264
|
+
var openIdx = m.index + m[0].lastIndexOf("{");
|
|
265
|
+
var spec = _sliceObjectLiteral(source, openIdx);
|
|
266
|
+
var errorClass = null;
|
|
267
|
+
var name = null;
|
|
268
|
+
var errCodePrefix = null;
|
|
269
|
+
if (spec) {
|
|
270
|
+
var nameMatch = spec.match(/(^|[\s,{])name\s*:\s*["']([^"']+)["']/);
|
|
271
|
+
if (nameMatch) name = nameMatch[2];
|
|
272
|
+
var ecpMatch = spec.match(/(^|[\s,{])errCodePrefix\s*:\s*["']([^"']+)["']/);
|
|
273
|
+
if (ecpMatch) errCodePrefix = ecpMatch[2];
|
|
274
|
+
|
|
275
|
+
var ecMatch = spec.match(/(^|[\s,{])errorClass\s*:\s*([a-zA-Z_$][a-zA-Z0-9_$]*)/);
|
|
276
|
+
if (ecMatch) {
|
|
277
|
+
errorClass = ecMatch[2];
|
|
278
|
+
} else {
|
|
279
|
+
var enMatch = spec.match(/(^|[\s,{])errorName\s*:\s*["']([^"']+)["']/);
|
|
280
|
+
if (enMatch) {
|
|
281
|
+
errorClass = enMatch[2];
|
|
282
|
+
} else if (name) {
|
|
283
|
+
errorClass = _defaultErrorClassName(name);
|
|
284
|
+
}
|
|
285
|
+
}
|
|
286
|
+
}
|
|
287
|
+
// Error-code prefix mirrors the factory: errCodePrefix || name. This is
|
|
288
|
+
// the stem used in thrown codes ("csv.bad-posture"), which differs from
|
|
289
|
+
// the namespace ("guardCsv") — the ABI templates carry both placeholders.
|
|
290
|
+
return {
|
|
291
|
+
kind: kind,
|
|
292
|
+
errorClass: errorClass,
|
|
293
|
+
codePrefix: errCodePrefix || name,
|
|
294
|
+
};
|
|
295
|
+
}
|
|
296
|
+
|
|
297
|
+
// Mirror gate-contract.js's default-class stem: Guard + PascalCase(name) +
|
|
298
|
+
// Error (name's leading char upper-cased, rest verbatim — matches
|
|
299
|
+
// `"Guard" + name.charAt(0).toUpperCase() + name.slice(1) + "Error"`).
|
|
300
|
+
function _defaultErrorClassName(name) {
|
|
301
|
+
if (!name) return null;
|
|
302
|
+
return "Guard" + name.charAt(0).toUpperCase() + name.slice(1) + "Error";
|
|
303
|
+
}
|
|
304
|
+
|
|
305
|
+
// Return the substring of `source` spanning the object literal whose
|
|
306
|
+
// opening brace is at `openIdx` (inclusive of both braces), string- and
|
|
307
|
+
// comment-aware so braces inside strings / comments don't miscount.
|
|
308
|
+
function _sliceObjectLiteral(source, openIdx) {
|
|
309
|
+
var i = openIdx + 1;
|
|
310
|
+
var depth = 1;
|
|
311
|
+
var inStr = null;
|
|
312
|
+
var inSlash = false;
|
|
313
|
+
var inBlock = false;
|
|
314
|
+
var prev = "";
|
|
315
|
+
while (i < source.length && depth > 0) {
|
|
316
|
+
var c = source[i];
|
|
317
|
+
if (inSlash) {
|
|
318
|
+
if (c === "\n") inSlash = false;
|
|
319
|
+
} else if (inBlock) {
|
|
320
|
+
if (prev === "*" && c === "/") inBlock = false;
|
|
321
|
+
} else if (inStr) {
|
|
322
|
+
if (c === "\\") { i += 2; prev = source[i - 1]; continue; }
|
|
323
|
+
if (c === inStr) inStr = null;
|
|
324
|
+
} else if (c === "/" && source[i + 1] === "/") {
|
|
325
|
+
inSlash = true;
|
|
326
|
+
} else if (c === "/" && source[i + 1] === "*") {
|
|
327
|
+
inBlock = true;
|
|
328
|
+
} else if (c === '"' || c === "'" || c === "`") {
|
|
329
|
+
inStr = c;
|
|
330
|
+
} else if (c === "{") {
|
|
331
|
+
depth++;
|
|
332
|
+
} else if (c === "}") {
|
|
333
|
+
depth--;
|
|
334
|
+
}
|
|
335
|
+
prev = c;
|
|
336
|
+
i++;
|
|
337
|
+
}
|
|
338
|
+
if (depth !== 0) return null;
|
|
339
|
+
return source.slice(openIdx, i);
|
|
340
|
+
}
|
|
341
|
+
|
|
238
342
|
function parseFile(source, sourcePath) {
|
|
239
343
|
var blocks = extractBlocks(source);
|
|
240
344
|
var module_ = null;
|
|
241
345
|
var primitives = [];
|
|
242
346
|
var concepts = [];
|
|
347
|
+
var abiTemplates = [];
|
|
243
348
|
for (var i = 0; i < blocks.length; i++) {
|
|
244
349
|
var parsed = parseBlock(blocks[i].raw);
|
|
245
350
|
if (!parsed.kind) continue;
|
|
246
351
|
if (parsed.kind === "module") {
|
|
247
352
|
if (module_) {
|
|
248
|
-
|
|
353
|
+
|
|
249
354
|
console.warn("[source-doc-parser] duplicate @module block in", sourcePath); // allow:console-direct — wiki seeder helper, runs at boot before b.log is wired
|
|
250
355
|
}
|
|
251
356
|
module_ = parsed;
|
|
@@ -253,13 +358,22 @@ function parseFile(source, sourcePath) {
|
|
|
253
358
|
primitives.push(parsed);
|
|
254
359
|
} else if (parsed.kind === "concept") {
|
|
255
360
|
concepts.push(parsed);
|
|
361
|
+
} else if (parsed.kind === "abiTemplate") {
|
|
362
|
+
abiTemplates.push(parsed);
|
|
256
363
|
}
|
|
257
364
|
}
|
|
258
365
|
return {
|
|
259
|
-
sourcePath:
|
|
260
|
-
module:
|
|
261
|
-
primitives:
|
|
262
|
-
concepts:
|
|
366
|
+
sourcePath: sourcePath,
|
|
367
|
+
module: module_,
|
|
368
|
+
primitives: primitives,
|
|
369
|
+
concepts: concepts,
|
|
370
|
+
// ABI doc templates declared in this file (only gate-contract.js
|
|
371
|
+
// carries them today). parseTree aggregates them across the tree.
|
|
372
|
+
abiTemplates: abiTemplates,
|
|
373
|
+
// Guard-family factory detection — populated when this file's
|
|
374
|
+
// module.exports is a defineGuard / defineParser call. Drives the
|
|
375
|
+
// page generator's per-guard ABI-method synthesis.
|
|
376
|
+
factory: _detectFactory(source),
|
|
263
377
|
};
|
|
264
378
|
}
|
|
265
379
|
|
|
@@ -310,9 +424,30 @@ function parseTree(rootDir) {
|
|
|
310
424
|
return byPath;
|
|
311
425
|
}
|
|
312
426
|
|
|
427
|
+
// Aggregate every @abiTemplate block across a parsed tree into a map
|
|
428
|
+
// keyed by factory kind ("defineGuard" / "defineParser"). Each value is
|
|
429
|
+
// an array of template records ({ kind:"abiTemplate", tags, prose }).
|
|
430
|
+
// Both the page generator (to synthesize per-guard ABI sections) and the
|
|
431
|
+
// comment-block validator (to register the templated method sigs as
|
|
432
|
+
// resolvable @related targets) read from this single derivation.
|
|
433
|
+
function factoryTemplates(byPath) {
|
|
434
|
+
var byKind = { defineGuard: [], defineParser: [] };
|
|
435
|
+
Object.keys(byPath).forEach(function (file) {
|
|
436
|
+
var tpls = byPath[file].abiTemplates || [];
|
|
437
|
+
tpls.forEach(function (t) {
|
|
438
|
+
var kind = t.tags && t.tags.abiTemplate;
|
|
439
|
+
if (!kind) return;
|
|
440
|
+
if (!byKind[kind]) byKind[kind] = [];
|
|
441
|
+
byKind[kind].push(t);
|
|
442
|
+
});
|
|
443
|
+
});
|
|
444
|
+
return byKind;
|
|
445
|
+
}
|
|
446
|
+
|
|
313
447
|
module.exports = {
|
|
314
|
-
parseBlock:
|
|
315
|
-
parseFile:
|
|
316
|
-
parseTree:
|
|
317
|
-
extractBlocks:
|
|
448
|
+
parseBlock: parseBlock,
|
|
449
|
+
parseFile: parseFile,
|
|
450
|
+
parseTree: parseTree,
|
|
451
|
+
extractBlocks: extractBlocks,
|
|
452
|
+
factoryTemplates: factoryTemplates,
|
|
318
453
|
};
|
|
@@ -628,6 +628,105 @@ async function run() {
|
|
|
628
628
|
navFailures.forEach(function (f) { console.error(" nav-cov: " + f); });
|
|
629
629
|
}
|
|
630
630
|
|
|
631
|
+
// ---- Guard ABI completeness gate ----
|
|
632
|
+
// For every guard built on the gateContract.defineGuard / defineParser
|
|
633
|
+
// FACTORY, assert that EVERY non-constant runtime export (a function
|
|
634
|
+
// that isn't the guard's error class) renders as a section on that
|
|
635
|
+
// guard's wiki page. The factory single-sources its generated ABI docs
|
|
636
|
+
// (compliancePosture / buildProfile / loadRulePack / gate) in
|
|
637
|
+
// gate-contract.js's @abiTemplate blocks; the page generator
|
|
638
|
+
// instantiates them per guard. This gate makes it impossible for that
|
|
639
|
+
// de-duplication to silently DROP a method — a method that stops
|
|
640
|
+
// rendering (template not instantiated, dedup mis-firing, a removed
|
|
641
|
+
// floating block with no template behind it) fails here, on the live
|
|
642
|
+
// page, not just in the parser.
|
|
643
|
+
//
|
|
644
|
+
// Scope: only factory-built guards. Guards still hand-wiring the export
|
|
645
|
+
// surface (not yet migrated to the factory) are out of scope for this
|
|
646
|
+
// mechanism — their pages render whatever doc blocks they carry today,
|
|
647
|
+
// and they enter this gate the moment they adopt the factory. Runtime
|
|
648
|
+
// exports are the ground truth: walk b.<guard>.* the same way the
|
|
649
|
+
// api-snapshot does. Constants (NAME / KIND / PROFILES / DEFAULTS /
|
|
650
|
+
// COMPLIANCE_POSTURES / MIME_TYPES / EXTENSIONS / INTEGRATION_FIXTURES /
|
|
651
|
+
// verb tables) are non-functions and excluded; the per-guard error
|
|
652
|
+
// class is the one function whose prototype is an Error subclass and is
|
|
653
|
+
// excluded too (it documents under the error-catalog harvester).
|
|
654
|
+
var bCore = require("@blamejs/core");
|
|
655
|
+
var abiParser = require("../lib/source-doc-parser");
|
|
656
|
+
var autoSiteEntries = require("../lib/auto-site-entries");
|
|
657
|
+
var abiLibDir = path.join(__dirname, "..", "..", "..", "lib");
|
|
658
|
+
var abiDocs = abiParser.parseTree(abiLibDir);
|
|
659
|
+
// Namespaces whose owning file is a defineGuard / defineParser call —
|
|
660
|
+
// walked directly (not via b.guardAll.allGuards(), which only
|
|
661
|
+
// aggregates the gate-bearing content/filename/identifier guards and
|
|
662
|
+
// omits the defineParser line-protocol guards).
|
|
663
|
+
var factoryNsList = [];
|
|
664
|
+
Object.keys(abiDocs).forEach(function (file) {
|
|
665
|
+
var rec = abiDocs[file];
|
|
666
|
+
if (rec.factory && rec.module && rec.module.tags && rec.module.tags.module) {
|
|
667
|
+
factoryNsList.push(rec.module.tags.module.replace(/^\s*b\./, ""));
|
|
668
|
+
}
|
|
669
|
+
});
|
|
670
|
+
var abiEntries = autoSiteEntries.deriveFromLib(abiLibDir);
|
|
671
|
+
var nsToSlug = {};
|
|
672
|
+
abiEntries.forEach(function (e) {
|
|
673
|
+
(e.namespaces || []).forEach(function (ns) { nsToSlug[ns] = e.slug; });
|
|
674
|
+
});
|
|
675
|
+
var pageCache = {};
|
|
676
|
+
var abiFailures = [];
|
|
677
|
+
var abiMethodsChecked = 0;
|
|
678
|
+
var abiGuardsChecked = 0;
|
|
679
|
+
for (var agi = 0; agi < factoryNsList.length; agi++) {
|
|
680
|
+
var nsKey = factoryNsList[agi];
|
|
681
|
+
var guardObj = bCore[nsKey];
|
|
682
|
+
if (!guardObj || typeof guardObj !== "object") { abiFailures.push(nsKey + " has no b.<ns> runtime binding"); continue; }
|
|
683
|
+
var slug = nsToSlug[nsKey];
|
|
684
|
+
if (!slug) { abiFailures.push(nsKey + " has no derived wiki page slug"); continue; }
|
|
685
|
+
abiGuardsChecked++;
|
|
686
|
+
// Required methods: every PUBLIC function export that isn't the error
|
|
687
|
+
// class. Underscore-prefixed names are private by convention (the wiki
|
|
688
|
+
// renderer + comment-block validator filter them too) — they carry no
|
|
689
|
+
// @primitive block and render no section, so they are not required here.
|
|
690
|
+
var required = Object.keys(guardObj).filter(function (k) {
|
|
691
|
+
var v = guardObj[k];
|
|
692
|
+
if (typeof v !== "function") return false; // skip constants
|
|
693
|
+
if (v.prototype instanceof Error) return false; // skip the error class
|
|
694
|
+
if (k.charAt(0) === "_") return false; // skip private (underscore) exports
|
|
695
|
+
return true;
|
|
696
|
+
});
|
|
697
|
+
// Fetch the page once per slug.
|
|
698
|
+
if (!pageCache[slug]) {
|
|
699
|
+
var gp = await _request({
|
|
700
|
+
method: "GET", host: "127.0.0.1", port: info.port, path: "/" + slug,
|
|
701
|
+
headers: BROWSER_HEADERS,
|
|
702
|
+
});
|
|
703
|
+
pageCache[slug] = gp.statusCode === 200 ? gp.body : null;
|
|
704
|
+
if (pageCache[slug] === null) { abiFailures.push("/" + slug + " -> " + gp.statusCode); }
|
|
705
|
+
}
|
|
706
|
+
var pageBody = pageCache[slug];
|
|
707
|
+
if (!pageBody) continue;
|
|
708
|
+
for (var rqi = 0; rqi < required.length; rqi++) {
|
|
709
|
+
var method = required[rqi];
|
|
710
|
+
abiMethodsChecked++;
|
|
711
|
+
// A rendered section is `<h2|h3 id="...">b.<ns>.<method>(...) ...`.
|
|
712
|
+
// Match the signature heading text — the method name immediately
|
|
713
|
+
// after `b.<ns>.` and followed by `(` or whitespace / `<`.
|
|
714
|
+
var sig = "b." + nsKey + "." + method;
|
|
715
|
+
var headingRe = new RegExp(
|
|
716
|
+
"<h[23][^>]*>\\s*" + sig.replace(/[.*+?^${}()|[\]\\]/g, "\\$&") + "\\s*(?:\\(|<|\\s)"); // allow:dynamic-regex — nsKey/method come from runtime export keys (identifier chars); the full metacharacter escape (incl. backslash) keeps the constructed RegExp injection-safe regardless
|
|
717
|
+
if (!headingRe.test(pageBody)) {
|
|
718
|
+
abiFailures.push(sig + " — not rendered as a section on /" + slug);
|
|
719
|
+
}
|
|
720
|
+
}
|
|
721
|
+
}
|
|
722
|
+
assert("guard-abi-completeness: every factory-guard runtime method (" + abiMethodsChecked +
|
|
723
|
+
" across " + abiGuardsChecked + " factory guards) renders a wiki section (" +
|
|
724
|
+
abiFailures.length + " missing)",
|
|
725
|
+
abiMethodsChecked > 0 && abiFailures.length === 0);
|
|
726
|
+
if (abiFailures.length > 0) {
|
|
727
|
+
abiFailures.forEach(function (f) { console.error(" guard-abi: " + f); });
|
|
728
|
+
}
|
|
729
|
+
|
|
631
730
|
// ---- env-var snapshot gate ----
|
|
632
731
|
// Catches drift between the wiki's source `process.env.X` reads,
|
|
633
732
|
// the framework's `safeEnv.readVar("X")` reads (in lib/), and the
|