@mistriwork/engine 0.0.0-stage → 1.0.0-rc.10
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 +21 -0
- package/README.md +17 -2
- package/dist/adapters/adapter.d.ts +693 -0
- package/dist/adapters/adapter.js +444 -0
- package/dist/adapters/cache/cacheStore.d.ts +75 -0
- package/dist/adapters/cache/cacheStore.js +160 -0
- package/dist/adapters/cache/resp.d.ts +52 -0
- package/dist/adapters/cache/resp.js +237 -0
- package/dist/adapters/commands/canonicalJson.d.ts +19 -0
- package/dist/adapters/commands/canonicalJson.js +154 -0
- package/dist/adapters/connect.d.ts +29 -0
- package/dist/adapters/connect.js +40 -0
- package/dist/adapters/connectionBudget.d.ts +101 -0
- package/dist/adapters/connectionBudget.js +128 -0
- package/dist/adapters/dbLatency.d.ts +35 -0
- package/dist/adapters/dbLatency.js +79 -0
- package/dist/adapters/epochCache.d.ts +50 -0
- package/dist/adapters/epochCache.js +85 -0
- package/dist/adapters/http/egress.d.ts +48 -0
- package/dist/adapters/http/egress.js +175 -0
- package/dist/adapters/http/httpAdapter.d.ts +71 -0
- package/dist/adapters/http/httpAdapter.js +512 -0
- package/dist/adapters/http/httpDescription.d.ts +32 -0
- package/dist/adapters/http/httpDescription.js +246 -0
- package/dist/adapters/http/openapi.d.ts +98 -0
- package/dist/adapters/http/openapi.js +487 -0
- package/dist/adapters/layoutRefusal.d.ts +24 -0
- package/dist/adapters/layoutRefusal.js +35 -0
- package/dist/adapters/net/networkPolicy.d.ts +44 -0
- package/dist/adapters/net/networkPolicy.js +123 -0
- package/dist/adapters/net/untrustedDatabase.d.ts +18 -0
- package/dist/adapters/net/untrustedDatabase.js +120 -0
- package/dist/adapters/poolAdmission.d.ts +43 -0
- package/dist/adapters/poolAdmission.js +184 -0
- package/dist/adapters/poolMetrics.d.ts +121 -0
- package/dist/adapters/poolMetrics.js +185 -0
- package/dist/adapters/postgres.d.ts +436 -0
- package/dist/adapters/postgres.js +1890 -0
- package/dist/adapters/postgresCatalog.d.ts +96 -0
- package/dist/adapters/postgresCatalog.js +387 -0
- package/dist/adapters/postgresCatalogDigest.d.ts +30 -0
- package/dist/adapters/postgresCatalogDigest.js +87 -0
- package/dist/adapters/postgresCatalogRows.d.ts +62 -0
- package/dist/adapters/postgresCatalogRows.js +37 -0
- package/dist/adapters/postgresDates.d.ts +1 -0
- package/dist/adapters/postgresDates.js +39 -0
- package/dist/adapters/postgresMaintenance.d.ts +33 -0
- package/dist/adapters/postgresMaintenance.js +179 -0
- package/dist/adapters/postgresPool.d.ts +255 -0
- package/dist/adapters/postgresPool.js +838 -0
- package/dist/adapters/postgresPooler.d.ts +28 -0
- package/dist/adapters/postgresPooler.js +267 -0
- package/dist/adapters/postgresReadCatalog.d.ts +31 -0
- package/dist/adapters/postgresReadCatalog.js +226 -0
- package/dist/adapters/postgresReadSnapshot.d.ts +46 -0
- package/dist/adapters/postgresReadSnapshot.js +133 -0
- package/dist/adapters/postgresSchemaEpoch.d.ts +24 -0
- package/dist/adapters/postgresSchemaEpoch.js +149 -0
- package/dist/adapters/postgresTransactionHandle.d.ts +173 -0
- package/dist/adapters/postgresTransactionHandle.js +524 -0
- package/dist/adapters/postgresValues.d.ts +30 -0
- package/dist/adapters/postgresValues.js +75 -0
- package/dist/adapters/replicas.d.ts +70 -0
- package/dist/adapters/replicas.js +208 -0
- package/dist/adapters/reservedSql.d.ts +38 -0
- package/dist/adapters/reservedSql.js +264 -0
- package/dist/adapters/rolePrivileges.d.ts +17 -0
- package/dist/adapters/rolePrivileges.js +22 -0
- package/dist/adapters/scoped/keyRows.d.ts +65 -0
- package/dist/adapters/scoped/keyRows.js +173 -0
- package/dist/adapters/scoped/postgresScopeCatalog.d.ts +16 -0
- package/dist/adapters/scoped/postgresScopeCatalog.js +117 -0
- package/dist/adapters/scoped/scopedCommandOperations.d.ts +5 -0
- package/dist/adapters/scoped/scopedCommandOperations.js +48 -0
- package/dist/adapters/scoped/scopedReads.d.ts +20 -0
- package/dist/adapters/scoped/scopedReads.js +174 -0
- package/dist/adapters/scoped/scopedTransaction.d.ts +89 -0
- package/dist/adapters/scoped/scopedTransaction.js +303 -0
- package/dist/adapters/scoped/sqliteScopeCatalog.d.ts +16 -0
- package/dist/adapters/scoped/sqliteScopeCatalog.js +241 -0
- package/dist/adapters/scoped/updateGuard.d.ts +3 -0
- package/dist/adapters/scoped/updateGuard.js +40 -0
- package/dist/adapters/serverSettings.d.ts +45 -0
- package/dist/adapters/serverSettings.js +46 -0
- package/dist/adapters/sqlite.d.ts +262 -0
- package/dist/adapters/sqlite.js +1434 -0
- package/dist/adapters/sqliteCostlyReads.d.ts +33 -0
- package/dist/adapters/sqliteCostlyReads.js +49 -0
- package/dist/adapters/sqliteDecimals.d.ts +22 -0
- package/dist/adapters/sqliteDecimals.js +57 -0
- package/dist/adapters/sqliteHandles.d.ts +43 -0
- package/dist/adapters/sqliteHandles.js +143 -0
- package/dist/adapters/sqliteStatementProcess.d.ts +29 -0
- package/dist/adapters/sqliteStatementProcess.js +131 -0
- package/dist/adapters/statementControl.d.ts +34 -0
- package/dist/adapters/statementControl.js +90 -0
- package/dist/adapters/storeHost.d.ts +130 -0
- package/dist/adapters/storeHost.js +13 -0
- package/dist/adapters/telemetry/drivers.d.ts +21 -0
- package/dist/adapters/telemetry/drivers.js +321 -0
- package/dist/adapters/telemetry/metrics.d.ts +63 -0
- package/dist/adapters/telemetry/metrics.js +122 -0
- package/dist/adapters/telemetry/otlp.d.ts +12 -0
- package/dist/adapters/telemetry/otlp.js +320 -0
- package/dist/adapters/telemetry/otlpEncode.d.ts +48 -0
- package/dist/adapters/telemetry/otlpEncode.js +366 -0
- package/dist/adapters/telemetry/otlpEnv.d.ts +1 -0
- package/dist/adapters/telemetry/otlpEnv.js +12 -0
- package/dist/adapters/telemetry/serverTiming.d.ts +83 -0
- package/dist/adapters/telemetry/serverTiming.js +503 -0
- package/dist/adapters/telemetry/start.d.ts +10 -0
- package/dist/adapters/telemetry/start.js +25 -0
- package/dist/adapters/telemetry/statement.d.ts +16 -0
- package/dist/adapters/telemetry/statement.js +134 -0
- package/dist/adapters/telemetry/trace.d.ts +127 -0
- package/dist/adapters/telemetry/trace.js +295 -0
- package/dist/adapters/writeAhead.d.ts +27 -0
- package/dist/adapters/writeAhead.js +46 -0
- package/dist/adapters/writeAttribution.d.ts +18 -0
- package/dist/adapters/writeAttribution.js +23 -0
- package/dist/adapters/writeCapture.d.ts +73 -0
- package/dist/adapters/writeCapture.js +20 -0
- package/dist/adapters/writeLanes.d.ts +94 -0
- package/dist/adapters/writeLanes.js +232 -0
- package/dist/engine.d.ts +15 -0
- package/dist/engine.js +13 -0
- package/dist/server/auth/credentials.d.ts +61 -0
- package/dist/server/auth/credentials.js +260 -0
- package/dist/server/cacheService.d.ts +50 -0
- package/dist/server/cacheService.js +110 -0
- package/dist/server/cli/args.d.ts +176 -0
- package/dist/server/cli/args.js +342 -0
- package/dist/server/cli/bin.d.ts +5 -0
- package/dist/server/cli/bin.js +66 -0
- package/dist/server/cli/browser.d.ts +15 -0
- package/dist/server/cli/browser.js +37 -0
- package/dist/server/cli/config.d.ts +50 -0
- package/dist/server/cli/config.js +206 -0
- package/dist/server/cli/startup.d.ts +36 -0
- package/dist/server/cli/startup.js +128 -0
- package/dist/server/cli/startupOptions.d.ts +63 -0
- package/dist/server/cli/startupOptions.js +143 -0
- package/dist/server/cli/subcommand.d.ts +28 -0
- package/dist/server/cli/subcommand.js +32 -0
- package/dist/server/cli/usage.d.ts +13 -0
- package/dist/server/cli/usage.js +31 -0
- package/dist/server/clientHttp.d.ts +184 -0
- package/dist/server/clientHttp.js +700 -0
- package/dist/server/clientSurface.d.ts +128 -0
- package/dist/server/clientSurface.js +182 -0
- package/dist/server/columnGrants.d.ts +103 -0
- package/dist/server/columnGrants.js +730 -0
- package/dist/server/compileCache.d.ts +1 -0
- package/dist/server/compileCache.js +30 -0
- package/dist/server/config/locations.d.ts +1 -0
- package/dist/server/config/locations.js +15 -0
- package/dist/server/configPaths.d.ts +7 -0
- package/dist/server/configPaths.js +34 -0
- package/dist/server/configSections.d.ts +64 -0
- package/dist/server/configSections.js +72 -0
- package/dist/server/connectionRedaction.d.ts +30 -0
- package/dist/server/connectionRedaction.js +77 -0
- package/dist/server/connections.d.ts +353 -0
- package/dist/server/connections.js +978 -0
- package/dist/server/constraints.d.ts +82 -0
- package/dist/server/constraints.js +169 -0
- package/dist/server/demo.d.ts +9 -0
- package/dist/server/demo.js +554 -0
- package/dist/server/devclient.d.ts +108 -0
- package/dist/server/devclient.js +361 -0
- package/dist/server/evidence.d.ts +55 -0
- package/dist/server/evidence.js +323 -0
- package/dist/server/hiddenColumns.d.ts +32 -0
- package/dist/server/hiddenColumns.js +238 -0
- package/dist/server/http/baselineHeaders.d.ts +24 -0
- package/dist/server/http/baselineHeaders.js +12 -0
- package/dist/server/http/captured.d.ts +35 -0
- package/dist/server/http/captured.js +73 -0
- package/dist/server/http/clock.d.ts +1 -0
- package/dist/server/http/clock.js +14 -0
- package/dist/server/http/connectionSource.d.ts +4 -0
- package/dist/server/http/connectionSource.js +48 -0
- package/dist/server/http/context.d.ts +189 -0
- package/dist/server/http/context.js +11 -0
- package/dist/server/http/crawlerText.d.ts +15 -0
- package/dist/server/http/crawlerText.js +32 -0
- package/dist/server/http/dataRoutes.d.ts +88 -0
- package/dist/server/http/dataRoutes.js +137 -0
- package/dist/server/http/door.d.ts +57 -0
- package/dist/server/http/door.js +39 -0
- package/dist/server/http/exportRoute.d.ts +15 -0
- package/dist/server/http/exportRoute.js +320 -0
- package/dist/server/http/firstPaint.d.ts +108 -0
- package/dist/server/http/firstPaint.js +262 -0
- package/dist/server/http/httpOperationRoutes.d.ts +11 -0
- package/dist/server/http/httpOperationRoutes.js +50 -0
- package/dist/server/http/pageReads.d.ts +20 -0
- package/dist/server/http/pageReads.js +205 -0
- package/dist/server/http/pageRoutes.d.ts +39 -0
- package/dist/server/http/pageRoutes.js +291 -0
- package/dist/server/http/probes.d.ts +22 -0
- package/dist/server/http/probes.js +27 -0
- package/dist/server/http/rateLimit.d.ts +131 -0
- package/dist/server/http/rateLimit.js +351 -0
- package/dist/server/http/readRoutes.d.ts +9 -0
- package/dist/server/http/readRoutes.js +131 -0
- package/dist/server/http/readRouting.d.ts +20 -0
- package/dist/server/http/readRouting.js +80 -0
- package/dist/server/http/recordCompose.d.ts +67 -0
- package/dist/server/http/recordCompose.js +167 -0
- package/dist/server/http/recordWrites.d.ts +89 -0
- package/dist/server/http/recordWrites.js +298 -0
- package/dist/server/http/refusalReport.d.ts +38 -0
- package/dist/server/http/refusalReport.js +63 -0
- package/dist/server/http/reply.d.ts +130 -0
- package/dist/server/http/reply.js +394 -0
- package/dist/server/http/requestOrigin.d.ts +11 -0
- package/dist/server/http/requestOrigin.js +8 -0
- package/dist/server/http/router.d.ts +45 -0
- package/dist/server/http/router.js +22 -0
- package/dist/server/http/serverCore.d.ts +68 -0
- package/dist/server/http/serverCore.js +177 -0
- package/dist/server/http/traceRequest.d.ts +30 -0
- package/dist/server/http/traceRequest.js +224 -0
- package/dist/server/http/trust.d.ts +261 -0
- package/dist/server/http/trust.js +472 -0
- package/dist/server/http/writeRefusal.d.ts +33 -0
- package/dist/server/http/writeRefusal.js +24 -0
- package/dist/server/httpConnection.d.ts +49 -0
- package/dist/server/httpConnection.js +170 -0
- package/dist/server/impact.d.ts +55 -0
- package/dist/server/impact.js +47 -0
- package/dist/server/journal.d.ts +134 -0
- package/dist/server/journal.js +398 -0
- package/dist/server/keysetReadHttp.d.ts +52 -0
- package/dist/server/keysetReadHttp.js +85 -0
- package/dist/server/layouts.d.ts +49 -0
- package/dist/server/layouts.js +192 -0
- package/dist/server/migrate/cli.d.ts +55 -0
- package/dist/server/migrate/cli.js +517 -0
- package/dist/server/migrate/database.d.ts +37 -0
- package/dist/server/migrate/database.js +247 -0
- package/dist/server/migrate/desired.d.ts +76 -0
- package/dist/server/migrate/desired.js +292 -0
- package/dist/server/migrate/files.d.ts +34 -0
- package/dist/server/migrate/files.js +141 -0
- package/dist/server/migrate/flyway.d.ts +7 -0
- package/dist/server/migrate/flyway.js +69 -0
- package/dist/server/migrate/history.d.ts +70 -0
- package/dist/server/migrate/history.js +211 -0
- package/dist/server/migrate/runner.d.ts +100 -0
- package/dist/server/migrate/runner.js +409 -0
- package/dist/server/migrate/snapshot.d.ts +30 -0
- package/dist/server/migrate/snapshot.js +239 -0
- package/dist/server/migrate/target.d.ts +33 -0
- package/dist/server/migrate/target.js +82 -0
- package/dist/server/openapiDraft.d.ts +25 -0
- package/dist/server/openapiDraft.js +171 -0
- package/dist/server/operations/diagnostics.d.ts +101 -0
- package/dist/server/operations/diagnostics.js +284 -0
- package/dist/server/operations/requestMetrics.d.ts +33 -0
- package/dist/server/operations/requestMetrics.js +94 -0
- package/dist/server/packageVersion.d.ts +1 -0
- package/dist/server/packageVersion.js +11 -0
- package/dist/server/poolConfig.d.ts +34 -0
- package/dist/server/poolConfig.js +114 -0
- package/dist/server/product.d.ts +20 -0
- package/dist/server/product.js +12 -0
- package/dist/server/recordHistoryOperations.d.ts +39 -0
- package/dist/server/recordHistoryOperations.js +43 -0
- package/dist/server/recordWriteOperations.d.ts +111 -0
- package/dist/server/recordWriteOperations.js +329 -0
- package/dist/server/resourceReadHttp.d.ts +81 -0
- package/dist/server/resourceReadHttp.js +606 -0
- package/dist/server/resourceReadOperations.d.ts +147 -0
- package/dist/server/resourceReadOperations.js +452 -0
- package/dist/server/scaffoldMachine.d.ts +54 -0
- package/dist/server/scaffoldMachine.js +184 -0
- package/dist/server/seed/cli.d.ts +20 -0
- package/dist/server/seed/cli.js +164 -0
- package/dist/server/seed/lexicon.d.ts +26 -0
- package/dist/server/seed/lexicon.js +585 -0
- package/dist/server/seed/seed.d.ts +70 -0
- package/dist/server/seed/seed.js +779 -0
- package/dist/server/seed/words.d.ts +21 -0
- package/dist/server/seed/words.js +164 -0
- package/dist/server/serverRequests.d.ts +6 -0
- package/dist/server/serverRequests.js +33 -0
- package/dist/server/serverTimeouts.d.ts +33 -0
- package/dist/server/serverTimeouts.js +32 -0
- package/dist/server/shapeonly.d.ts +32 -0
- package/dist/server/shapeonly.js +110 -0
- package/dist/server/startupWarnings.d.ts +32 -0
- package/dist/server/startupWarnings.js +92 -0
- package/dist/shared/addressParams.d.ts +28 -0
- package/dist/shared/addressParams.js +47 -0
- package/dist/shared/appCards.d.ts +123 -0
- package/dist/shared/appCards.js +385 -0
- package/dist/shared/appComponents.d.ts +177 -0
- package/dist/shared/appComponents.js +422 -0
- package/dist/shared/appDocuments.d.ts +43 -0
- package/dist/shared/appDocuments.js +131 -0
- package/dist/shared/appEmbeds.d.ts +21 -0
- package/dist/shared/appEmbeds.js +24 -0
- package/dist/shared/appIcons.d.ts +28 -0
- package/dist/shared/appIcons.js +223 -0
- package/dist/shared/appLinks.d.ts +17 -0
- package/dist/shared/appLinks.js +124 -0
- package/dist/shared/appListColumns.d.ts +3 -0
- package/dist/shared/appListColumns.js +66 -0
- package/dist/shared/appLocale.d.ts +36 -0
- package/dist/shared/appLocale.js +86 -0
- package/dist/shared/appMessages.d.ts +44 -0
- package/dist/shared/appMessages.js +78 -0
- package/dist/shared/appNoun.d.ts +21 -0
- package/dist/shared/appNoun.js +32 -0
- package/dist/shared/autoBucket.d.ts +98 -0
- package/dist/shared/autoBucket.js +305 -0
- package/dist/shared/autoValues.d.ts +25 -0
- package/dist/shared/autoValues.js +25 -0
- package/dist/shared/breakdown.d.ts +228 -0
- package/dist/shared/breakdown.js +557 -0
- package/dist/shared/breakdowntext.d.ts +41 -0
- package/dist/shared/breakdowntext.js +400 -0
- package/dist/shared/builtInThemes.d.ts +2 -0
- package/dist/shared/builtInThemes.js +771 -0
- package/dist/shared/chartSeparation.d.ts +11 -0
- package/dist/shared/chartSeparation.js +58 -0
- package/dist/shared/clauses.d.ts +22 -0
- package/dist/shared/clauses.js +97 -0
- package/dist/shared/columnCaption.d.ts +16 -0
- package/dist/shared/columnCaption.js +90 -0
- package/dist/shared/commandFieldPath.d.ts +2 -0
- package/dist/shared/commandFieldPath.js +7 -0
- package/dist/shared/commandWire.d.ts +26 -0
- package/dist/shared/commandWire.js +41 -0
- package/dist/shared/computed.d.ts +161 -0
- package/dist/shared/computed.js +378 -0
- package/dist/shared/computedParse.d.ts +13 -0
- package/dist/shared/computedParse.js +278 -0
- package/dist/shared/computedValue.d.ts +47 -0
- package/dist/shared/computedValue.js +191 -0
- package/dist/shared/connection.d.ts +30 -0
- package/dist/shared/connection.js +1 -0
- package/dist/shared/csv.d.ts +20 -0
- package/dist/shared/csv.js +63 -0
- package/dist/shared/dashLayout.d.ts +30 -0
- package/dist/shared/dashLayout.js +132 -0
- package/dist/shared/dashboardAsks.d.ts +93 -0
- package/dist/shared/dashboardAsks.js +129 -0
- package/dist/shared/dashboardTrend.d.ts +20 -0
- package/dist/shared/dashboardTrend.js +50 -0
- package/dist/shared/declaredReferences.d.ts +50 -0
- package/dist/shared/declaredReferences.js +202 -0
- package/dist/shared/definedFields.d.ts +63 -0
- package/dist/shared/definedFields.js +103 -0
- package/dist/shared/definedValues.d.ts +63 -0
- package/dist/shared/definedValues.js +184 -0
- package/dist/shared/displayDefaults.d.ts +135 -0
- package/dist/shared/displayDefaults.js +529 -0
- package/dist/shared/dueDate.d.ts +6 -0
- package/dist/shared/dueDate.js +6 -0
- package/dist/shared/duration.d.ts +4 -0
- package/dist/shared/duration.js +23 -0
- package/dist/shared/fileBounds.d.ts +9 -0
- package/dist/shared/fileBounds.js +9 -0
- package/dist/shared/filter.d.ts +217 -0
- package/dist/shared/filter.js +305 -0
- package/dist/shared/firstPaint.d.ts +24 -0
- package/dist/shared/firstPaint.js +33 -0
- package/dist/shared/form.d.ts +21 -0
- package/dist/shared/form.js +25 -0
- package/dist/shared/formValues.d.ts +104 -0
- package/dist/shared/formValues.js +352 -0
- package/dist/shared/funnel.d.ts +45 -0
- package/dist/shared/funnel.js +108 -0
- package/dist/shared/httpOperations.d.ts +48 -0
- package/dist/shared/httpOperations.js +9 -0
- package/dist/shared/iconGlyphs.d.ts +4 -0
- package/dist/shared/iconGlyphs.js +151 -0
- package/dist/shared/iconWeights.d.ts +3 -0
- package/dist/shared/iconWeights.js +162 -0
- package/dist/shared/imageWidths.d.ts +32 -0
- package/dist/shared/imageWidths.js +38 -0
- package/dist/shared/keysetPage.d.ts +64 -0
- package/dist/shared/keysetPage.js +161 -0
- package/dist/shared/like.d.ts +20 -0
- package/dist/shared/like.js +29 -0
- package/dist/shared/listEmpty.d.ts +12 -0
- package/dist/shared/listEmpty.js +36 -0
- package/dist/shared/listFilters.d.ts +28 -0
- package/dist/shared/listFilters.js +84 -0
- package/dist/shared/listPresentations.d.ts +199 -0
- package/dist/shared/listPresentations.js +7 -0
- package/dist/shared/listQuestion.d.ts +52 -0
- package/dist/shared/listQuestion.js +137 -0
- package/dist/shared/lookPalettes.d.ts +62 -0
- package/dist/shared/lookPalettes.js +306 -0
- package/dist/shared/maskQuoted.d.ts +24 -0
- package/dist/shared/maskQuoted.js +48 -0
- package/dist/shared/mentionLabel.d.ts +19 -0
- package/dist/shared/mentionLabel.js +38 -0
- package/dist/shared/mentionLookup.d.ts +17 -0
- package/dist/shared/mentionLookup.js +64 -0
- package/dist/shared/menuCounts.d.ts +16 -0
- package/dist/shared/menuCounts.js +74 -0
- package/dist/shared/model.d.ts +79 -0
- package/dist/shared/model.js +153 -0
- package/dist/shared/money.d.ts +44 -0
- package/dist/shared/money.js +81 -0
- package/dist/shared/moneyEntry.d.ts +7 -0
- package/dist/shared/moneyEntry.js +27 -0
- package/dist/shared/mount.d.ts +118 -0
- package/dist/shared/mount.js +248 -0
- package/dist/shared/niceTicks.d.ts +26 -0
- package/dist/shared/niceTicks.js +50 -0
- package/dist/shared/order.d.ts +59 -0
- package/dist/shared/order.js +133 -0
- package/dist/shared/page.d.ts +135 -0
- package/dist/shared/page.js +1187 -0
- package/dist/shared/pageAnatomy.d.ts +99 -0
- package/dist/shared/pageAnatomy.js +370 -0
- package/dist/shared/pageConfig.d.ts +25 -0
- package/dist/shared/pageConfig.js +1308 -0
- package/dist/shared/pageEmptyActions.d.ts +12 -0
- package/dist/shared/pageEmptyActions.js +20 -0
- package/dist/shared/pageLayouts.d.ts +72 -0
- package/dist/shared/pageLayouts.js +205 -0
- package/dist/shared/pageModel.d.ts +785 -0
- package/dist/shared/pageModel.js +121 -0
- package/dist/shared/pagePaths.d.ts +180 -0
- package/dist/shared/pagePaths.js +869 -0
- package/dist/shared/pagePlans.d.ts +52 -0
- package/dist/shared/pagePlans.js +108 -0
- package/dist/shared/pageRoutes.d.ts +9 -0
- package/dist/shared/pageRoutes.js +9 -0
- package/dist/shared/query.d.ts +166 -0
- package/dist/shared/query.js +1302 -0
- package/dist/shared/queryDates.d.ts +12 -0
- package/dist/shared/queryDates.js +101 -0
- package/dist/shared/queryOperands.d.ts +99 -0
- package/dist/shared/queryOperands.js +131 -0
- package/dist/shared/reads.d.ts +103 -0
- package/dist/shared/reads.js +154 -0
- package/dist/shared/recordLabel.d.ts +51 -0
- package/dist/shared/recordLabel.js +123 -0
- package/dist/shared/recordReadKeys.d.ts +30 -0
- package/dist/shared/recordReadKeys.js +51 -0
- package/dist/shared/recordReads.d.ts +268 -0
- package/dist/shared/recordReads.js +368 -0
- package/dist/shared/recordview.d.ts +198 -0
- package/dist/shared/recordview.js +356 -0
- package/dist/shared/referenceModel.d.ts +58 -0
- package/dist/shared/referenceModel.js +194 -0
- package/dist/shared/refusal.d.ts +64 -0
- package/dist/shared/refusal.js +144 -0
- package/dist/shared/relatedCreate.d.ts +30 -0
- package/dist/shared/relatedCreate.js +162 -0
- package/dist/shared/resourceHttp.d.ts +464 -0
- package/dist/shared/resourceHttp.js +1 -0
- package/dist/shared/richText.d.ts +85 -0
- package/dist/shared/richText.js +305 -0
- package/dist/shared/rollups.d.ts +143 -0
- package/dist/shared/rollups.js +64 -0
- package/dist/shared/rowScope.d.ts +72 -0
- package/dist/shared/rowScope.js +376 -0
- package/dist/shared/runtimeTables.d.ts +44 -0
- package/dist/shared/runtimeTables.js +79 -0
- package/dist/shared/schema.d.ts +523 -0
- package/dist/shared/schema.js +627 -0
- package/dist/shared/schematext.d.ts +38 -0
- package/dist/shared/schematext.js +101 -0
- package/dist/shared/scopeCatalog.d.ts +29 -0
- package/dist/shared/scopeCatalog.js +468 -0
- package/dist/shared/servedApp.d.ts +681 -0
- package/dist/shared/servedApp.js +45 -0
- package/dist/shared/sessionLease.d.ts +34 -0
- package/dist/shared/sessionLease.js +3 -0
- package/dist/shared/shape.d.ts +55 -0
- package/dist/shared/shape.js +168 -0
- package/dist/shared/slug.d.ts +1 -0
- package/dist/shared/slug.js +12 -0
- package/dist/shared/sortText.d.ts +14 -0
- package/dist/shared/sortText.js +26 -0
- package/dist/shared/sqlRelation.d.ts +4 -0
- package/dist/shared/sqlRelation.js +8 -0
- package/dist/shared/sqlsaved.d.ts +44 -0
- package/dist/shared/sqlsaved.js +63 -0
- package/dist/shared/stitchedPaths.d.ts +27 -0
- package/dist/shared/stitchedPaths.js +38 -0
- package/dist/shared/structuredFilter.d.ts +22 -0
- package/dist/shared/structuredFilter.js +1 -0
- package/dist/shared/subtitlePath.d.ts +20 -0
- package/dist/shared/subtitlePath.js +24 -0
- package/dist/shared/suggest.d.ts +18 -0
- package/dist/shared/suggest.js +59 -0
- package/dist/shared/tableSizing.d.ts +4 -0
- package/dist/shared/tableSizing.js +9 -0
- package/dist/shared/tagLists.d.ts +57 -0
- package/dist/shared/tagLists.js +34 -0
- package/dist/shared/textRules.d.ts +54 -0
- package/dist/shared/textRules.js +133 -0
- package/dist/shared/theme.d.ts +94 -0
- package/dist/shared/theme.js +800 -0
- package/dist/shared/themeColor.d.ts +34 -0
- package/dist/shared/themeColor.js +109 -0
- package/dist/shared/themeFaces.d.ts +30 -0
- package/dist/shared/themeFaces.js +42 -0
- package/dist/shared/themeInk.d.ts +20 -0
- package/dist/shared/themeInk.js +52 -0
- package/dist/shared/themeLooks.d.ts +9 -0
- package/dist/shared/themeLooks.js +572 -0
- package/dist/shared/themeParts.d.ts +26 -0
- package/dist/shared/themeParts.js +71 -0
- package/dist/shared/themePartsCheck.d.ts +21 -0
- package/dist/shared/themePartsCheck.js +91 -0
- package/dist/shared/themePresets.d.ts +85 -0
- package/dist/shared/themePresets.js +139 -0
- package/dist/shared/themeRecipeWords.d.ts +156 -0
- package/dist/shared/themeRecipeWords.js +156 -0
- package/dist/shared/themeRecipes.d.ts +213 -0
- package/dist/shared/themeRecipes.js +234 -0
- package/dist/shared/themeResolve.d.ts +55 -0
- package/dist/shared/themeResolve.js +52 -0
- package/dist/shared/themeTokens.d.ts +107 -0
- package/dist/shared/themeTokens.js +116 -0
- package/dist/shared/themeType.d.ts +38 -0
- package/dist/shared/themeType.js +205 -0
- package/dist/shared/unitWord.d.ts +4 -0
- package/dist/shared/unitWord.js +37 -0
- package/dist/shared/view.d.ts +195 -0
- package/dist/shared/view.js +987 -0
- package/dist/shared/viewLabels.d.ts +47 -0
- package/dist/shared/viewLabels.js +459 -0
- package/dist/shared/viewPaths.d.ts +248 -0
- package/dist/shared/viewPaths.js +294 -0
- package/dist/shared/viewtext.d.ts +57 -0
- package/dist/shared/viewtext.js +282 -0
- package/dist/shared/vocabulary.d.ts +71 -0
- package/dist/shared/vocabulary.js +249 -0
- package/dist/shared/weekStart.d.ts +7 -0
- package/dist/shared/weekStart.js +36 -0
- package/mark.svg +1 -0
- package/package.json +261 -4
- package/schema/model.d.ts +298 -0
- package/schema/theme.d.ts +587 -0
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* A view's paths as the planner writes them, including the one kind of path
|
|
3
|
+
* that is not a column: a record's templated name, `$label` (recordLabel.ts),
|
|
4
|
+
* whose words and columns become one text expression on each engine. Split
|
|
5
|
+
* from view.ts, which plans the joins these qualify against.
|
|
6
|
+
*/
|
|
7
|
+
import type { AnyRows, Condition, SqlStyle } from './filter.js';
|
|
8
|
+
import { type DatabaseSchema } from './schema.js';
|
|
9
|
+
import type { JoinPlan } from './view.js';
|
|
10
|
+
import { type ResolvedPath, type ViewDef } from './viewPaths.js';
|
|
11
|
+
import type { ScopedRelations } from './rowScope.js';
|
|
12
|
+
/**
|
|
13
|
+
* A view's paths, resolved and written against one join plan.
|
|
14
|
+
*
|
|
15
|
+
* Resolution and alias creation are one step, because a join only exists
|
|
16
|
+
* once some path needs it. Recording the key alongside keeps `clauses` from
|
|
17
|
+
* having to re-resolve anything.
|
|
18
|
+
*
|
|
19
|
+
* A `$label` path is a record's templated name (recordLabel.ts): its words
|
|
20
|
+
* are string literals and its columns are paths from the same prefix, each
|
|
21
|
+
* qualified here like any other, so a label through a reference joins what
|
|
22
|
+
* it needs and a reader's pruned catalog refuses a column it may not read.
|
|
23
|
+
* The template comes from the view's `labels`, which the server fills; the
|
|
24
|
+
* literal text is held to characters every engine reads alike inside quotes.
|
|
25
|
+
*/
|
|
26
|
+
export declare function viewPaths(schema: DatabaseSchema, view: ViewDef, plan: JoinPlan, style: SqlStyle, relations?: ScopedRelations): {
|
|
27
|
+
resolve: (path: string) => ResolvedPath;
|
|
28
|
+
qualify: (path: string, condition?: Condition) => string;
|
|
29
|
+
membership: (path: string, holes: readonly string[]) => string;
|
|
30
|
+
exists: (rows: AnyRows) => string;
|
|
31
|
+
};
|
|
32
|
+
/**
|
|
33
|
+
* The view with the record-label templates its `$label` paths need, read from
|
|
34
|
+
* a catalog that serves them (an App's, `TableMeta.labelTemplate`) — and with
|
|
35
|
+
* any it arrived with dropped, so a template is always the catalog's and
|
|
36
|
+
* never a request's words written into a statement.
|
|
37
|
+
*/
|
|
38
|
+
export declare function withViewLabels(schema: DatabaseSchema, view: ViewDef): ViewDef;
|
|
39
|
+
/**
|
|
40
|
+
* The view with the rollups and the computed columns its paths name
|
|
41
|
+
* (rollups.ts, computed.ts), read from a catalog that serves them — an App's,
|
|
42
|
+
* `TableMeta.rollups` and `TableMeta.computed` — and with any it arrived with
|
|
43
|
+
* dropped: like a label template, each is always the catalog's, never a
|
|
44
|
+
* request's words about which rows to sum or what to write into the statement.
|
|
45
|
+
* A computed column's own reads come with it, a rollup among them too.
|
|
46
|
+
*/
|
|
47
|
+
export declare function withViewComputed(schema: DatabaseSchema, view: ViewDef): ViewDef;
|
|
@@ -0,0 +1,459 @@
|
|
|
1
|
+
import { findTable } from './schema.js';
|
|
2
|
+
import { PathError, backrefsTo, labelColumnMeta, resolvePath, tableAtPrefix, tryResolvePath, } from './viewPaths.js';
|
|
3
|
+
import { LABEL_SEGMENT, labelPrefix, parseLabelTemplate } from './recordLabel.js';
|
|
4
|
+
import { MASK } from './model.js';
|
|
5
|
+
import { rollupColumnMeta } from './rollups.js';
|
|
6
|
+
import { compileComputed, computedColumnMeta } from './computed.js';
|
|
7
|
+
import { aggregateInput, columnKind, isFlagColumn } from './schema.js';
|
|
8
|
+
import { TAGS_COLUMN, tagsColumnMeta } from './tagLists.js';
|
|
9
|
+
/** The comparisons a JSON key answers as a number when it is given one (SqlStyle.jsonKey). */
|
|
10
|
+
const RANGES = new Set(['<', '<=', '>', '>=']);
|
|
11
|
+
/**
|
|
12
|
+
* A view's paths, resolved and written against one join plan.
|
|
13
|
+
*
|
|
14
|
+
* Resolution and alias creation are one step, because a join only exists
|
|
15
|
+
* once some path needs it. Recording the key alongside keeps `clauses` from
|
|
16
|
+
* having to re-resolve anything.
|
|
17
|
+
*
|
|
18
|
+
* A `$label` path is a record's templated name (recordLabel.ts): its words
|
|
19
|
+
* are string literals and its columns are paths from the same prefix, each
|
|
20
|
+
* qualified here like any other, so a label through a reference joins what
|
|
21
|
+
* it needs and a reader's pruned catalog refuses a column it may not read.
|
|
22
|
+
* The template comes from the view's `labels`, which the server fills; the
|
|
23
|
+
* literal text is held to characters every engine reads alike inside quotes.
|
|
24
|
+
*/
|
|
25
|
+
export function viewPaths(schema, view, plan, style, relations) {
|
|
26
|
+
const plain = (path) => {
|
|
27
|
+
const resolved = resolvePath(schema, view.base, path);
|
|
28
|
+
let prefix = '';
|
|
29
|
+
for (let i = 0; i < resolved.hops.length; i++) {
|
|
30
|
+
prefix = prefix ? `${prefix}.${resolved.hopNames[i]}` : resolved.hopNames[i];
|
|
31
|
+
plan.record(prefix, resolved.hops[i]);
|
|
32
|
+
}
|
|
33
|
+
return plan.qualify(resolved);
|
|
34
|
+
};
|
|
35
|
+
const template = (path, prefix) => {
|
|
36
|
+
const table = tableAtPrefix(schema, view.base, prefix);
|
|
37
|
+
const text = view.labels?.[prefix];
|
|
38
|
+
if (!table || !text) {
|
|
39
|
+
throw new PathError(`"${path}" names a record label${table ? ` that ${table.name} does not have here` : ', and its reference goes nowhere'}.`, path, LABEL_SEGMENT, prefix ? prefix.split('.').length : 0);
|
|
40
|
+
}
|
|
41
|
+
const parsed = parseLabelTemplate(text);
|
|
42
|
+
if ('problem' in parsed)
|
|
43
|
+
throw new PathError(`"${path}": ${parsed.problem}`, path, LABEL_SEGMENT, 0);
|
|
44
|
+
return { table, parts: parsed.parts };
|
|
45
|
+
};
|
|
46
|
+
const at = (prefix, field) => (prefix ? `${prefix}.${field}` : field);
|
|
47
|
+
/* A rollup a path names: the view's own (a server fills it from the App's
|
|
48
|
+
catalog, rollups.ts), or — where the catalog compiling this is the App's
|
|
49
|
+
— the catalog's, so a check that compiles an App's page against its
|
|
50
|
+
catalog reads the same subquery the read will. */
|
|
51
|
+
const computedAt = (path) => {
|
|
52
|
+
if (view.computed && Object.hasOwn(view.computed, path))
|
|
53
|
+
return view.computed[path];
|
|
54
|
+
const found = tryResolvePath(schema, view.base, path).resolved;
|
|
55
|
+
return found?.rollup ? { ...found.rollup, on: found.rollupAt ?? path.split('.').slice(0, -1).join('.') } : undefined;
|
|
56
|
+
};
|
|
57
|
+
/* The hops to a prefix, walked through one of the table's own columns —
|
|
58
|
+
the same resolver as every path, so a prefix that is not a chain of
|
|
59
|
+
references fails here as it would anywhere. */
|
|
60
|
+
const prefixHops = (prefix) => {
|
|
61
|
+
const table = tableAtPrefix(schema, view.base, prefix);
|
|
62
|
+
if (!table?.columns.length)
|
|
63
|
+
throw new PathError(`"${prefix}" is not a chain of references from ${view.base}.`, prefix, prefix, 0);
|
|
64
|
+
const { hops, hopNames } = prefix ? resolvePath(schema, view.base, at(prefix, table.columns[0].name)) : { hops: [], hopNames: [] };
|
|
65
|
+
return { table, hops, hopNames };
|
|
66
|
+
};
|
|
67
|
+
/* The correlated subquery a rollup is: its child rows, through the
|
|
68
|
+
statement's own relations (a scope's CTE, and a CTE for the rollup's own
|
|
69
|
+
filter), keyed on the reference to the record at its prefix. */
|
|
70
|
+
const rollup = (path, computed) => {
|
|
71
|
+
const { table } = prefixHops(computed.on);
|
|
72
|
+
if (computed.on)
|
|
73
|
+
plain(at(computed.on, table.columns[0].name));
|
|
74
|
+
return subquery(path, computed, table, plan.aliasOfPrefix(computed.on));
|
|
75
|
+
};
|
|
76
|
+
/* One rollup's subquery, keyed on the parent row's alias. A rollup of a
|
|
77
|
+
rollup (`of`) aggregates the inner one's subquery, keyed on this one's
|
|
78
|
+
child alias: every level reads through its own relation, so a row policy
|
|
79
|
+
on the grandchild narrows the number as one on the child does. */
|
|
80
|
+
const subquery = (path, computed, table, parentAlias) => {
|
|
81
|
+
const match = backrefsTo(schema, table.id).find((b) => `${b.child}.${b.fk.from.columns.join('+')}` === computed.via);
|
|
82
|
+
const child = match && findTable(schema, match.child);
|
|
83
|
+
if (!match || !child) {
|
|
84
|
+
throw new PathError(`"${path}" sums rows through "${computed.via}", which does not point at ${table.name} here.`, path, path.split('.').pop(), 0);
|
|
85
|
+
}
|
|
86
|
+
/* A computed column it reads is held to the columns under it: this catalog serves the rollup only where it reads them all. */
|
|
87
|
+
const narrowing = Object.values(computed.computed ?? {}).flatMap((expression) => expression.reads);
|
|
88
|
+
const unread = narrowing.find((read) => !child.columns.some((c) => c.name === read)) ??
|
|
89
|
+
(computed.expression
|
|
90
|
+
? computed.expression.reads.find((read) => !child.columns.some((c) => c.name === read))
|
|
91
|
+
: computed.fn !== 'count' && !computed.of && !child.columns.some((c) => c.name === computed.column)
|
|
92
|
+
? computed.column
|
|
93
|
+
: computed.by !== undefined && !child.columns.some((c) => c.name === computed.by)
|
|
94
|
+
? computed.by
|
|
95
|
+
: undefined);
|
|
96
|
+
if (unread !== undefined) {
|
|
97
|
+
throw new PathError(`"${path}" reads "${unread}", which is not a column on ${child.name} here.`, path, path.split('.').pop(), 0);
|
|
98
|
+
}
|
|
99
|
+
if (computed.filter && !relations)
|
|
100
|
+
throw new Error(`"${path}" narrows its rows and needs the statement's relations.`);
|
|
101
|
+
/* The rows a level reads: the child's relation, narrowed by the level's query where it has one. */
|
|
102
|
+
const sourceOf = (level, of) => {
|
|
103
|
+
const kindOf = (column) => columnRead(of.columns.find((c) => c.name === column));
|
|
104
|
+
return level.filter
|
|
105
|
+
? relations.filtered(of.id, level.filter, level.computed &&
|
|
106
|
+
Object.fromEntries(Object.entries(level.computed).map(([name, expression]) => [
|
|
107
|
+
name,
|
|
108
|
+
(own) => compileComputed(expression, style, own, kindOf),
|
|
109
|
+
])))
|
|
110
|
+
: relations
|
|
111
|
+
? relations.table(of.id)
|
|
112
|
+
: plan.relationOf(of.id);
|
|
113
|
+
};
|
|
114
|
+
const source = sourceOf(computed, child);
|
|
115
|
+
const childAlias = plan.subAlias(child.name);
|
|
116
|
+
const on = match.fk.to.columns
|
|
117
|
+
.map((toCol, i) => `${style.quote(childAlias)}.${style.quote(match.fk.from.columns[i] ?? match.fk.from.columns[0])} = ` +
|
|
118
|
+
`${style.quote(parentAlias)}.${style.quote(toCol)}`)
|
|
119
|
+
.join(' AND ');
|
|
120
|
+
/* COUNT(*), and a sum over no rows left NULL, for the reasons a view's
|
|
121
|
+
aggregates give (view.ts): a record with no lines has no total. */
|
|
122
|
+
/* A count through two references is the sum of its middle rows' counts,
|
|
123
|
+
and a record with no middle rows still has none: 0, never NULL. */
|
|
124
|
+
const own = (column) => `${style.quote(childAlias)}.${style.quote(column)}`;
|
|
125
|
+
/* The newest row's column, as it was written: the greatest `by`, its key breaking a tie, so two rows made in the
|
|
126
|
+
same second still give one answer. LIMIT 1 in a scalar subquery reads the same on all three engines. */
|
|
127
|
+
if (computed.fn === 'latest') {
|
|
128
|
+
/* Through two references the rows are the grandchild's, each joined to the middle record it hangs from: the
|
|
129
|
+
newest of them all, under both levels' relations, so a row policy on either narrows it. */
|
|
130
|
+
const level = computed.of ?? computed;
|
|
131
|
+
let rows = `${source} ${style.quote(childAlias)}`;
|
|
132
|
+
let newest = child;
|
|
133
|
+
let read = own;
|
|
134
|
+
if (computed.of) {
|
|
135
|
+
const inner = backrefsTo(schema, child.id).find((b) => `${b.child}.${b.fk.from.columns.join('+')}` === computed.of.via);
|
|
136
|
+
const grand = inner && findTable(schema, inner.child);
|
|
137
|
+
const reads = [computed.of.column, computed.of.by];
|
|
138
|
+
const missing = !inner || !grand ? computed.of.via : reads.find((name) => !grand.columns.some((c) => c.name === name));
|
|
139
|
+
if (missing !== undefined || !inner || !grand)
|
|
140
|
+
throw new PathError(`"${path}" reads "${missing}", which is not on its rows here.`, path, path.split('.').pop(), 0);
|
|
141
|
+
const grandAlias = plan.subAlias(grand.name);
|
|
142
|
+
read = (column) => `${style.quote(grandAlias)}.${style.quote(column)}`;
|
|
143
|
+
const joined = inner.fk.to.columns
|
|
144
|
+
.map((toCol, i) => `${read(inner.fk.from.columns[i] ?? inner.fk.from.columns[0])} = ${own(toCol)}`)
|
|
145
|
+
.join(' AND ');
|
|
146
|
+
rows = `${sourceOf(computed.of, grand)} ${style.quote(grandAlias)} JOIN ${rows} ON ${joined}`;
|
|
147
|
+
newest = grand;
|
|
148
|
+
}
|
|
149
|
+
const order = [level.by, ...newest.columns.filter((c) => c.primaryKey && c.name !== level.by).map((c) => c.name)];
|
|
150
|
+
/* A row with no `by` yet is not the newest: PostgreSQL sorts nulls first when descending, the others last. */
|
|
151
|
+
const unset = newest.columns.find((c) => c.name === level.by)?.nullable ? [`${read(level.by)} IS NULL ASC`] : [];
|
|
152
|
+
const newestKey = `(SELECT ${read(level.column)} FROM ${rows} WHERE ${on}` +
|
|
153
|
+
` ORDER BY ${[...unset, ...order.map((column) => `${read(column)} DESC`)].join(', ')} LIMIT 1)`;
|
|
154
|
+
/* Read through the key it holds (`resident.name`): that record's column, from its table's own relation, so a row
|
|
155
|
+
policy on it narrows the name as it narrows a join to the same record. A key naming no row reads nothing. */
|
|
156
|
+
if (computed.through) {
|
|
157
|
+
const to = findTable(schema, computed.through.table);
|
|
158
|
+
if (!to?.columns.some((c) => c.name === computed.through.key) || !to.columns.some((c) => c.name === computed.through.column)) {
|
|
159
|
+
throw new PathError(`"${path}" reads "${computed.through.column}", which is not on ${computed.through.table} here.`, path, path.split('.').pop(), 0);
|
|
160
|
+
}
|
|
161
|
+
const alias = style.quote(plan.subAlias(to.name));
|
|
162
|
+
return (`(SELECT ${alias}.${style.quote(computed.through.column)} FROM ${relations ? relations.table(to.id) : plan.relationOf(to.id)} ${alias}` +
|
|
163
|
+
` WHERE ${alias}.${style.quote(computed.through.key)} = ${newestKey})`);
|
|
164
|
+
}
|
|
165
|
+
return newestKey;
|
|
166
|
+
}
|
|
167
|
+
/* A computed column is its expression over the child's own row, written as a list of the child writes it. */
|
|
168
|
+
const read = computed.of
|
|
169
|
+
? subquery(path, computed.of, child, childAlias)
|
|
170
|
+
: computed.expression
|
|
171
|
+
? compileComputed(computed.expression, style, own, (column) => columnRead(child.columns.find((c) => c.name === column)))
|
|
172
|
+
: computed.column && own(computed.column);
|
|
173
|
+
/* A yes-or-no is summed as 0 and 1 on every engine (aggregateInput). A
|
|
174
|
+
sum over no rows is 0, as a count over none is: a total of nothing is
|
|
175
|
+
nothing, and an empty one would read as unknown in a when or a
|
|
176
|
+
formula. The least, most and latest of no rows stay empty. */
|
|
177
|
+
const type = computed.expression ? computed.expression.type : child.columns.find((c) => c.name === computed.column)?.type;
|
|
178
|
+
const aggregate = `${computed.fn.toUpperCase()}(${computed.of ? read : aggregateInput(read, type, style.dialect)})`;
|
|
179
|
+
const expression = computed.fn === 'count'
|
|
180
|
+
? computed.of
|
|
181
|
+
? `COALESCE(SUM(${read}), 0)`
|
|
182
|
+
: 'COUNT(*)'
|
|
183
|
+
: computed.fn === 'sum'
|
|
184
|
+
? `COALESCE(${aggregate}, 0)`
|
|
185
|
+
: aggregate;
|
|
186
|
+
return `(SELECT ${expression} FROM ${source} ${style.quote(childAlias)} WHERE ${on})`;
|
|
187
|
+
};
|
|
188
|
+
/* A record's tags a path names (tagLists.ts): the view's own, pinned by the
|
|
189
|
+
server from the App's catalog, or the catalog's where it is the App's. */
|
|
190
|
+
const tagsAt = (path) => {
|
|
191
|
+
if (view.tagged && Object.hasOwn(view.tagged, path))
|
|
192
|
+
return view.tagged[path];
|
|
193
|
+
if (labelPrefix(path) !== undefined || path.split('.').pop() !== TAGS_COLUMN)
|
|
194
|
+
return undefined;
|
|
195
|
+
const found = tryResolvePath(schema, view.base, path).resolved;
|
|
196
|
+
return found?.tags ? { ...found.tags, on: path.split('.').slice(0, -1).join('.') } : undefined;
|
|
197
|
+
};
|
|
198
|
+
/* The link rows of the record at a tag path's prefix joined to their tags,
|
|
199
|
+
each through the statement's relations, and the condition tying them to
|
|
200
|
+
the record: what the list and `has` both read. */
|
|
201
|
+
const tagRows = (path, tags) => {
|
|
202
|
+
const { table } = prefixHops(tags.on);
|
|
203
|
+
if (tags.on)
|
|
204
|
+
plain(at(tags.on, table.columns[0].name));
|
|
205
|
+
const link = findTable(schema, tags.through), tag = findTable(schema, tags.to);
|
|
206
|
+
const has = (t, ...names) => Boolean(t && names.every((name) => !name || t.columns.some((c) => c.name === name)));
|
|
207
|
+
if (!has(link, tags.from, tags.via) ||
|
|
208
|
+
!has(tag, tags.tagKey, tags.label, tags.tone) ||
|
|
209
|
+
!table.columns.some((c) => c.name === tags.key)) {
|
|
210
|
+
throw new PathError(`"${path}" reads tags through "${tags.through}", which this catalog does not read whole.`, path, TAGS_COLUMN, 0);
|
|
211
|
+
}
|
|
212
|
+
const source = (id) => (relations ? relations.table(id) : plan.relationOf(id));
|
|
213
|
+
const q = style.quote;
|
|
214
|
+
const linkAlias = q(plan.subAlias(link.name)), tagAlias = q(plan.subAlias(tag.name));
|
|
215
|
+
return {
|
|
216
|
+
from: `${source(tags.through)} ${linkAlias} JOIN ${source(tags.to)} ${tagAlias} ON ${tagAlias}.${q(tags.tagKey)} = ${linkAlias}.${q(tags.via)}`,
|
|
217
|
+
on: `${linkAlias}.${q(tags.from)} = ${q(plan.aliasOfPrefix(tags.on))}.${q(tags.key)}`,
|
|
218
|
+
label: `${tagAlias}.${q(tags.label)}`,
|
|
219
|
+
tone: tags.tone ? `${tagAlias}.${q(tags.tone)}` : 'NULL',
|
|
220
|
+
};
|
|
221
|
+
};
|
|
222
|
+
/* Every tag of the record, as one JSON array of [label, tone] per row. */
|
|
223
|
+
const tagList = (path, tags) => {
|
|
224
|
+
const rows = tagRows(path, tags);
|
|
225
|
+
return `(SELECT ${tagPairs(style, rows.label, rows.tone)} FROM ${rows.from} WHERE ${rows.on})`;
|
|
226
|
+
};
|
|
227
|
+
/* `tags has (a, b)`: the record has a link row to a tag named any of them. */
|
|
228
|
+
/* One key of a JSON column (`specs.capacity`, definedFields.ts): the column
|
|
229
|
+
qualified as any column at its prefix is, read through the style. */
|
|
230
|
+
const jsonKeyAt = (path) => labelPrefix(path) === undefined ? tryResolvePath(schema, view.base, path).resolved?.jsonKey : undefined;
|
|
231
|
+
const jsonRead = (path, json, as) => {
|
|
232
|
+
if (!style.jsonKey)
|
|
233
|
+
throw new PathError(`"${path}" reads a key of a JSON column, which this database is not read for here.`, path, json.key, 0);
|
|
234
|
+
const prefix = path.split('.').slice(0, -2).join('.');
|
|
235
|
+
return style.jsonKey(plain(at(prefix, json.column)), json.key, as);
|
|
236
|
+
};
|
|
237
|
+
const membership = (path, holes) => {
|
|
238
|
+
const json = jsonKeyAt(path);
|
|
239
|
+
if (json) {
|
|
240
|
+
if (!style.jsonHas)
|
|
241
|
+
throw new PathError(`"${path}" reads a key of a JSON column, which this database is not read for here.`, path, json.key, 0);
|
|
242
|
+
return style.jsonHas(plain(at(path.split('.').slice(0, -2).join('.'), json.column)), json.key, holes);
|
|
243
|
+
}
|
|
244
|
+
const tags = tagsAt(path);
|
|
245
|
+
if (!tags)
|
|
246
|
+
throw new PathError(`"${path}" is not a record's tags, so "has" asks nothing of it.`, path, path.split('.').pop(), 0);
|
|
247
|
+
const rows = tagRows(path, tags);
|
|
248
|
+
return `EXISTS (SELECT 1 FROM ${rows.from} WHERE ${rows.on} AND ${rows.label} IN (${holes.join(', ')}))`;
|
|
249
|
+
};
|
|
250
|
+
/* `any opportunity where stage = won`: one of the rows that point at this one, under the statement's relations —
|
|
251
|
+
the child's scope, and a CTE for its own conditions (rowScope.ts `filtered`), which resolves each of them in
|
|
252
|
+
this catalog, so a reader's pruned one refuses a column they may not read. Planned once per condition, before
|
|
253
|
+
the scope prefix is frozen, and written the same each time `buildWhere` asks. */
|
|
254
|
+
const planned = new Map();
|
|
255
|
+
const exists = (rows) => {
|
|
256
|
+
const kept = planned.get(rows);
|
|
257
|
+
if (kept !== undefined)
|
|
258
|
+
return kept;
|
|
259
|
+
const match = backrefsTo(schema, view.base).find((b) => `${b.child}.${b.fk.from.columns.join('+')}` === rows.via);
|
|
260
|
+
const child = match && findTable(schema, match.child);
|
|
261
|
+
if (!match || !child || match.fk.stitched) {
|
|
262
|
+
const name = rows.via.slice(0, rows.via.lastIndexOf('.'));
|
|
263
|
+
throw new PathError(`"any ${name}" reads rows through "${rows.via}", which does not point at ${view.base} here.`, rows.via, name, 0);
|
|
264
|
+
}
|
|
265
|
+
if (rows.filter?.groups.length && !relations)
|
|
266
|
+
throw new Error(`"any ${child.name}" narrows its rows and needs the statement's relations.`);
|
|
267
|
+
const source = rows.filter?.groups.length
|
|
268
|
+
? relations.filtered(child.id, rows.filter)
|
|
269
|
+
: relations
|
|
270
|
+
? relations.table(child.id)
|
|
271
|
+
: plan.relationOf(child.id);
|
|
272
|
+
const q = style.quote;
|
|
273
|
+
const childAlias = q(plan.subAlias(child.name));
|
|
274
|
+
const on = match.fk.to.columns
|
|
275
|
+
.map((toCol, i) => `${childAlias}.${q(match.fk.from.columns[i] ?? match.fk.from.columns[0])} = ${q(plan.aliasOfPrefix(''))}.${q(toCol)}`)
|
|
276
|
+
.join(' AND ');
|
|
277
|
+
const text = `EXISTS (SELECT 1 FROM ${source} ${childAlias} WHERE ${on})`;
|
|
278
|
+
planned.set(rows, text);
|
|
279
|
+
return text;
|
|
280
|
+
};
|
|
281
|
+
/* A computed column a path names (computed.ts): the view's own, pinned by the
|
|
282
|
+
server from the App's catalog, or the catalog's where it is the App's. */
|
|
283
|
+
const expressionAt = (path) => {
|
|
284
|
+
if (view.expressions && Object.hasOwn(view.expressions, path))
|
|
285
|
+
return view.expressions[path];
|
|
286
|
+
if (labelPrefix(path) !== undefined)
|
|
287
|
+
return undefined;
|
|
288
|
+
const found = tryResolvePath(schema, view.base, path).resolved;
|
|
289
|
+
return found?.computed ? { ...found.computed, on: path.split('.').slice(0, -1).join('.') } : undefined;
|
|
290
|
+
};
|
|
291
|
+
/* What a path an expression reads is, as the compiler writes it: a yes-or-no column native or a 0/1 integer. */
|
|
292
|
+
const kindOf = (path) => {
|
|
293
|
+
const resolved = resolve(path);
|
|
294
|
+
if (resolved.rollup && !resolved.rollup.through)
|
|
295
|
+
return { kind: columnKind(resolved.column.type) === 'date' ? 'date' : 'number' };
|
|
296
|
+
return columnRead(resolved.column);
|
|
297
|
+
};
|
|
298
|
+
const expression = (computed) => compileComputed(computed, style, (read) => qualify(at(computed.on, read)), (read) => kindOf(at(computed.on, read)));
|
|
299
|
+
const resolve = (path) => {
|
|
300
|
+
const expressed = labelPrefix(path) === undefined ? expressionAt(path) : undefined;
|
|
301
|
+
if (expressed) {
|
|
302
|
+
const { table, hops, hopNames } = prefixHops(expressed.on);
|
|
303
|
+
return { path, hops, hopNames, table, column: computedColumnMeta(path.split('.').pop(), expressed), computed: expressed };
|
|
304
|
+
}
|
|
305
|
+
const computed = labelPrefix(path) === undefined ? computedAt(path) : undefined;
|
|
306
|
+
if (computed) {
|
|
307
|
+
const { table, hops, hopNames } = prefixHops(computed.on);
|
|
308
|
+
const name = path.split('.').pop();
|
|
309
|
+
return { path, hops, hopNames, table, column: rollupColumnMeta(name, computed), rollup: computed };
|
|
310
|
+
}
|
|
311
|
+
const tags = labelPrefix(path) === undefined ? tagsAt(path) : undefined;
|
|
312
|
+
if (tags) {
|
|
313
|
+
const { table, hops, hopNames } = prefixHops(tags.on);
|
|
314
|
+
return { path, hops, hopNames, table, column: tagsColumnMeta(), tags };
|
|
315
|
+
}
|
|
316
|
+
const prefix = labelPrefix(path);
|
|
317
|
+
if (prefix === undefined)
|
|
318
|
+
return resolvePath(schema, view.base, path);
|
|
319
|
+
const { table, parts } = template(path, prefix);
|
|
320
|
+
const first = parts.find((part) => 'path' in part);
|
|
321
|
+
const { hops, hopNames } = prefix ? resolvePath(schema, view.base, at(prefix, first.path)) : { hops: [], hopNames: [] };
|
|
322
|
+
const depth = prefix ? prefix.split('.').length : 0;
|
|
323
|
+
return { path, hops: hops.slice(0, depth), hopNames: hopNames.slice(0, depth), table, column: labelColumnMeta() };
|
|
324
|
+
};
|
|
325
|
+
const qualify = (path, condition) => {
|
|
326
|
+
const prefix = labelPrefix(path);
|
|
327
|
+
if (prefix === undefined) {
|
|
328
|
+
const json = jsonKeyAt(path);
|
|
329
|
+
if (json)
|
|
330
|
+
return jsonRead(path, json, !condition
|
|
331
|
+
? 'value'
|
|
332
|
+
: RANGES.has(condition.op) && typeof condition.value === 'number' && condition.other === undefined
|
|
333
|
+
? 'number'
|
|
334
|
+
: 'text');
|
|
335
|
+
const expressed = expressionAt(path);
|
|
336
|
+
if (expressed) {
|
|
337
|
+
// The joins to the record it is on, as any column there would plan them.
|
|
338
|
+
if (expressed.on)
|
|
339
|
+
plain(at(expressed.on, prefixHops(expressed.on).table.columns[0].name));
|
|
340
|
+
return `(${expression(expressed)})`;
|
|
341
|
+
}
|
|
342
|
+
const computed = computedAt(path);
|
|
343
|
+
if (computed)
|
|
344
|
+
return rollup(path, computed);
|
|
345
|
+
const tags = tagsAt(path);
|
|
346
|
+
return tags ? tagList(path, tags) : plain(path);
|
|
347
|
+
}
|
|
348
|
+
const { table, parts } = template(path, prefix);
|
|
349
|
+
const literal = (text) => `'${text.replace(/'/g, "''")}'`;
|
|
350
|
+
/* A record across a reference that reaches no row — none there, or none
|
|
351
|
+
this reader's scope admits — has no name: not the template's own
|
|
352
|
+
words around empty fields ("Points south for ", " ()"). */
|
|
353
|
+
const reached = prefix ? (table.columns.find((column) => column.primaryKey) ?? table.columns[0]) : undefined;
|
|
354
|
+
const named = (text) => (reached ? `CASE WHEN ${plain(at(prefix, reached.name))} IS NULL THEN NULL ELSE ${text} END` : text);
|
|
355
|
+
return named(style.concat(parts.map((part) => {
|
|
356
|
+
if ('text' in part)
|
|
357
|
+
return literal(part.text);
|
|
358
|
+
const value = style.text(plain(at(prefix, part.path)));
|
|
359
|
+
/* A masked column says its placeholder in the name too, computed here
|
|
360
|
+
like the rest of it, so no list, picker or breadcrumb reads the value. */
|
|
361
|
+
if (part.mask?.prefix) {
|
|
362
|
+
return `CASE WHEN SUBSTR(${value}, 1, ${[...part.mask.prefix].length}) = ${literal(part.mask.prefix)} THEN ${literal(part.mask.prefix + MASK)} ELSE COALESCE(${value}, '') END`;
|
|
363
|
+
}
|
|
364
|
+
if (part.mask)
|
|
365
|
+
return `CASE WHEN ${value} IS NULL THEN '' ELSE ${literal(MASK)} END`;
|
|
366
|
+
/* A stored value said as its display rule's word, as a cell says it:
|
|
367
|
+
the words are the catalog's, held to what every engine reads alike. */
|
|
368
|
+
if (part.words) {
|
|
369
|
+
const cases = Object.entries(part.words)
|
|
370
|
+
.map(([stored, word]) => `WHEN ${literal(stored)} THEN ${literal(word)}`)
|
|
371
|
+
.join(' ');
|
|
372
|
+
return `CASE ${value} ${cases} ELSE COALESCE(${value}, '') END`;
|
|
373
|
+
}
|
|
374
|
+
return `COALESCE(${value}, '')`;
|
|
375
|
+
})));
|
|
376
|
+
};
|
|
377
|
+
return { resolve, qualify, membership, exists };
|
|
378
|
+
}
|
|
379
|
+
/* What a stored column is to an expression that reads it: a yes-or-no column native or a 0/1 integer. */
|
|
380
|
+
function columnRead(column) {
|
|
381
|
+
if (!column)
|
|
382
|
+
return undefined;
|
|
383
|
+
if (isFlagColumn(column))
|
|
384
|
+
return { kind: 'boolean', native: columnKind(column.type) === 'boolean' };
|
|
385
|
+
const kind = columnKind(column.type);
|
|
386
|
+
return { kind: kind === 'other' ? 'text' : kind };
|
|
387
|
+
}
|
|
388
|
+
/* One aggregate of [label, tone] pairs, `[]` over no rows, in each engine's JSON. */
|
|
389
|
+
function tagPairs(style, label, tone) {
|
|
390
|
+
if (style.dialect === 'postgres')
|
|
391
|
+
return `COALESCE(json_agg(json_build_array(${label}, ${tone})), '[]'::json)`;
|
|
392
|
+
return `json_group_array(json_array(${label}, ${tone}))`;
|
|
393
|
+
}
|
|
394
|
+
/**
|
|
395
|
+
* The view with the record-label templates its `$label` paths need, read from
|
|
396
|
+
* a catalog that serves them (an App's, `TableMeta.labelTemplate`) — and with
|
|
397
|
+
* any it arrived with dropped, so a template is always the catalog's and
|
|
398
|
+
* never a request's words written into a statement.
|
|
399
|
+
*/
|
|
400
|
+
export function withViewLabels(schema, view) {
|
|
401
|
+
const { labels: _given, ...rest } = view;
|
|
402
|
+
const paths = [
|
|
403
|
+
...(view.columns ?? []).map((c) => c.path),
|
|
404
|
+
...(view.filter?.groups ?? []).flatMap((group) => group.flatMap((c) => [c.path, ...(c.other === undefined ? [] : [c.other])])),
|
|
405
|
+
...(view.orderBy ?? []).map((o) => o.path),
|
|
406
|
+
];
|
|
407
|
+
const labels = {};
|
|
408
|
+
for (const path of paths) {
|
|
409
|
+
const prefix = typeof path === 'string' ? labelPrefix(path) : undefined;
|
|
410
|
+
if (prefix === undefined || Object.hasOwn(labels, prefix))
|
|
411
|
+
continue;
|
|
412
|
+
const template = tableAtPrefix(schema, view.base, prefix)?.labelTemplate;
|
|
413
|
+
if (template)
|
|
414
|
+
labels[prefix] = template;
|
|
415
|
+
}
|
|
416
|
+
return Object.keys(labels).length ? { ...rest, labels } : rest;
|
|
417
|
+
}
|
|
418
|
+
/**
|
|
419
|
+
* The view with the rollups and the computed columns its paths name
|
|
420
|
+
* (rollups.ts, computed.ts), read from a catalog that serves them — an App's,
|
|
421
|
+
* `TableMeta.rollups` and `TableMeta.computed` — and with any it arrived with
|
|
422
|
+
* dropped: like a label template, each is always the catalog's, never a
|
|
423
|
+
* request's words about which rows to sum or what to write into the statement.
|
|
424
|
+
* A computed column's own reads come with it, a rollup among them too.
|
|
425
|
+
*/
|
|
426
|
+
export function withViewComputed(schema, view) {
|
|
427
|
+
const { computed: _given, expressions: _written, tagged: _tagged, ...rest } = view;
|
|
428
|
+
const paths = [
|
|
429
|
+
...(view.columns ?? []).map((c) => c.path),
|
|
430
|
+
...(view.filter?.groups ?? []).flatMap((group) => group.flatMap((c) => [c.path, ...(c.other === undefined ? [] : [c.other])])),
|
|
431
|
+
...(view.orderBy ?? []).filter((o) => !o.alias).map((o) => o.path),
|
|
432
|
+
];
|
|
433
|
+
const computed = {};
|
|
434
|
+
const expressions = {};
|
|
435
|
+
const tagged = {};
|
|
436
|
+
const pin = (path, depth = 0) => {
|
|
437
|
+
if (typeof path !== 'string' || Object.hasOwn(computed, path) || Object.hasOwn(expressions, path) || labelPrefix(path) !== undefined)
|
|
438
|
+
return;
|
|
439
|
+
const resolved = tryResolvePath(schema, view.base, path).resolved;
|
|
440
|
+
const on = path.split('.').slice(0, -1).join('.');
|
|
441
|
+
if (resolved?.rollup)
|
|
442
|
+
computed[path] = { ...resolved.rollup, on: resolved.rollupAt ?? on };
|
|
443
|
+
if (resolved?.tags)
|
|
444
|
+
tagged[path] = { ...resolved.tags, on };
|
|
445
|
+
if (resolved?.computed && depth === 0) {
|
|
446
|
+
expressions[path] = { ...resolved.computed, on };
|
|
447
|
+
for (const read of resolved.computed.reads)
|
|
448
|
+
pin(on ? `${on}.${read}` : read, depth + 1);
|
|
449
|
+
}
|
|
450
|
+
};
|
|
451
|
+
for (const path of paths)
|
|
452
|
+
pin(path);
|
|
453
|
+
return {
|
|
454
|
+
...rest,
|
|
455
|
+
...(Object.keys(computed).length ? { computed } : {}),
|
|
456
|
+
...(Object.keys(expressions).length ? { expressions } : {}),
|
|
457
|
+
...(Object.keys(tagged).length ? { tagged } : {}),
|
|
458
|
+
};
|
|
459
|
+
}
|