@rebasepro/server 0.21.0 → 0.21.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +29 -11
- package/dist/api/errors.d.ts +41 -0
- package/dist/auth/admin-user-ops.d.ts +23 -1
- package/dist/auth/auth-hooks.d.ts +4 -0
- package/dist/auth/reset-password-admin.d.ts +4 -0
- package/dist/auth/token-revocation.d.ts +39 -5
- package/dist/{auth-gzoRjnuh.js → auth-BS4WBA10.js} +1636 -1565
- package/dist/auth-BS4WBA10.js.map +1 -0
- package/dist/backup/backup-common.d.ts +2 -1
- package/dist/{backup-DGu0v9Ku.js → backup-DzI9jLwc.js} +38 -10
- package/dist/backup-DzI9jLwc.js.map +1 -0
- package/dist/collections/validate-config.d.ts +4 -2
- package/dist/{cron-routes-BamgO0Xr.js → cron-routes-B_wlLybo.js} +3 -3
- package/dist/{cron-routes-BamgO0Xr.js.map → cron-routes-B_wlLybo.js.map} +1 -1
- package/dist/{cron-scheduler-D47tdB9T.js → cron-scheduler-COPQxlEq.js} +59 -10
- package/dist/cron-scheduler-COPQxlEq.js.map +1 -0
- package/dist/{cron-store-yXOyIEmn.js → cron-store-Dp0X7zRB.js} +2 -2
- package/dist/{cron-store-yXOyIEmn.js.map → cron-store-Dp0X7zRB.js.map} +1 -1
- package/dist/ddl-bootstrap-CfNvxMuK.js.map +1 -1
- package/dist/deploy/pod-contract.d.ts +14 -0
- package/dist/{errors-DMImyqyR.js → errors-DWsX4yTd.js} +55 -18
- package/dist/errors-DWsX4yTd.js.map +1 -0
- package/dist/{function-routes-C4nB2h0z.js → function-routes-Chet4-lB.js} +2 -2
- package/dist/{function-routes-C4nB2h0z.js.map → function-routes-Chet4-lB.js.map} +1 -1
- package/dist/functions/index.js.map +1 -1
- package/dist/{history-recorder-hBGuXcZc.js → history-recorder-5VKT7nss.js} +2 -2
- package/dist/{history-recorder-hBGuXcZc.js.map → history-recorder-5VKT7nss.js.map} +1 -1
- package/dist/{history-store-C9EtGtoL.js → history-store-By2R_G1b.js} +2 -2
- package/dist/{history-store-C9EtGtoL.js.map → history-store-By2R_G1b.js.map} +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.es.js +286 -245
- package/dist/index.es.js.map +1 -1
- package/dist/init/middlewares.d.ts +19 -1
- package/dist/init/storage.d.ts +17 -0
- package/dist/init.d.ts +6 -2
- package/dist/{jobs-DZ8DLLcU.js → jobs-1IkI4Lle.js} +2 -2
- package/dist/{jobs-DZ8DLLcU.js.map → jobs-1IkI4Lle.js.map} +1 -1
- package/dist/{logs-routes-DnJINsMu.js → logs-routes-3EEzPjhl.js} +2 -2
- package/dist/{logs-routes-DnJINsMu.js.map → logs-routes-3EEzPjhl.js.map} +1 -1
- package/dist/{openapi-generator-CAFKF36E.js → openapi-generator-BDpoKZQ9.js} +2 -2
- package/dist/{openapi-generator-CAFKF36E.js.map → openapi-generator-BDpoKZQ9.js.map} +1 -1
- package/dist/{query-parser-uqzkZ82i.js → query-parser-C-rl30ce.js} +3 -3
- package/dist/{query-parser-uqzkZ82i.js.map → query-parser-C-rl30ce.js.map} +1 -1
- package/dist/{request-timeout-BR-OBwES.js → request-timeout-C_4C2BeR.js} +2 -2
- package/dist/{request-timeout-BR-OBwES.js.map → request-timeout-C_4C2BeR.js.map} +1 -1
- package/dist/{schema-editor-routes-BKOmdf4M.js → schema-editor-routes-DdLihzp0.js} +2 -2
- package/dist/{schema-editor-routes-BKOmdf4M.js.map → schema-editor-routes-DdLihzp0.js.map} +1 -1
- package/dist/src-Br6ARbs6.js.map +1 -1
- package/dist/{src-DW1cQ_28.js → src-Caz7nREj.js} +2 -3
- package/dist/src-Caz7nREj.js.map +1 -0
- package/package.json +5 -5
- package/dist/auth-gzoRjnuh.js.map +0 -1
- package/dist/backup-DGu0v9Ku.js.map +0 -1
- package/dist/cron-scheduler-D47tdB9T.js.map +0 -1
- package/dist/errors-DMImyqyR.js.map +0 -1
- package/dist/src-DW1cQ_28.js.map +0 -1
package/dist/index.es.js
CHANGED
|
@@ -2,33 +2,33 @@ import { createRequire as __rebaseCreateRequire } from "module";
|
|
|
2
2
|
import __rebaseProcess from "process";
|
|
3
3
|
globalThis.process ??= __rebaseProcess;
|
|
4
4
|
__rebaseCreateRequire(import.meta.url);
|
|
5
|
-
import { A as createDataSourceRegistry, B as findRelation, D as restrictedFieldNames, E as effectiveAccess, F as getJunctionConfigForRelation, G as buildCompositeId, I as getEffectiveSecurityRules, J as suggestNearMiss, K as resolvePrimaryKeys, M as resolveDataSource, O as defaultUsersCollection, P as revokeInternalTableSql, R as securityRuleToConditions, S as cursorToStartAfter, T as canWriteField, U as resolveCollectionRelations, V as getTableName, W as enumToObjectEntries, X as unref, Y as toSnakeCase, c as collectAllPages, dt as GeoPoint, et as BATCH_REF_KEY, ft as Vector, g as topLevelIncludeNames, gt as unsupportedMethod, h as serializeInclude, ht as isUnsupported, j as isRelationalCollection, k as CollectionRegistry, l as paginateFind, lt as EntityReference, mt as RebaseClientError, n as buildSdkData, nt as hasFieldOperation, o as serializeFilter, ot as JUNCTION_PIVOT_KEY, p as mergeIncludeSpecs, pt as RebaseApiError, q as hydrateRegExp, rt as isFieldOperation, s as serializeLogicalCondition, st as isManyToMany, t as buildRoutedRebaseData, tt as FIELD_OPERATORS, u as resolveFindWindow, ut as EntityRelation, v as normalizeOrderBy, y as serializeOrderBy, z as fieldKeyForColumn } from "./src-
|
|
5
|
+
import { A as createDataSourceRegistry, B as findRelation, D as restrictedFieldNames, E as effectiveAccess, F as getJunctionConfigForRelation, G as buildCompositeId, I as getEffectiveSecurityRules, J as suggestNearMiss, K as resolvePrimaryKeys, M as resolveDataSource, O as defaultUsersCollection, P as revokeInternalTableSql, R as securityRuleToConditions, S as cursorToStartAfter, T as canWriteField, U as resolveCollectionRelations, V as getTableName, W as enumToObjectEntries, X as unref, Y as toSnakeCase, c as collectAllPages, dt as GeoPoint, et as BATCH_REF_KEY, ft as Vector, g as topLevelIncludeNames, gt as unsupportedMethod, h as serializeInclude, ht as isUnsupported, j as isRelationalCollection, k as CollectionRegistry, l as paginateFind, lt as EntityReference, mt as RebaseClientError, n as buildSdkData, nt as hasFieldOperation, o as serializeFilter, ot as JUNCTION_PIVOT_KEY, p as mergeIncludeSpecs, pt as RebaseApiError, q as hydrateRegExp, rt as isFieldOperation, s as serializeLogicalCondition, st as isManyToMany, t as buildRoutedRebaseData, tt as FIELD_OPERATORS, u as resolveFindWindow, ut as EntityRelation, v as normalizeOrderBy, y as serializeOrderBy, z as fieldKeyForColumn } from "./src-Caz7nREj.js";
|
|
6
6
|
import { E as DEFAULT_DATA_SOURCE_KEY, F as sortKeyToString, I as toCanonicalOp, P as parseRelationAggregateSort, S as getCollectionDataPath, _ as resourceKinds, a as resourceToStorageSource, b as RLS_UID_SQL, c as DEFAULT_STORAGE_SOURCE_KEY, d as DEFAULT_RESOURCE_KEY, f as buildResourceGraph, g as resourceKind, h as resourceKeyOf, i as resourceToDataSource, l as findStorageSuffixCollision, m as resourceEnvSuffix, n as declaredQueueConsumers, o as setQueueRuntime, p as resolveResourceRefs, r as declaredSubscriptions, s as setTopicRuntime, u as storageEnvSuffix, v as RLS_JWT_SQL, w as isPostgresCollectionConfig, y as RLS_ROLES_SQL } from "./src-Br6ARbs6.js";
|
|
7
7
|
import { n as ADMIN_PROPERTY_KEYS, t as ADMIN_COLLECTION_KEYS } from "./admin_block-DxKLmdiv.js";
|
|
8
8
|
import { a as isDuplicateObjectRace, i as isConcurrentDdlRace, n as createDdlBootstrapper, o as isSQLAdmin, s as isSchemaEditingAdmin, t as CONCURRENT_DDL_SQLSTATES } from "./ddl-bootstrap-CfNvxMuK.js";
|
|
9
|
+
import { i as parseEnvBoolean, r as validateCronExpression, t as CronScheduler } from "./cron-scheduler-COPQxlEq.js";
|
|
9
10
|
import { i as SCHEMA_VERSION_HEADER, n as createContractRoutes, r as computeSchemaVersion } from "./contract-routes-eLxV0le1.js";
|
|
10
|
-
import { $ as
|
|
11
|
+
import { $ as requireAdmin, A as defaultAuthLimiter, B as resolveEmailLinkBase, C as providerVerifiedEmail, Ct as raw, D as DEFAULT_FUNCTIONS_ANONYMOUS_LIMIT, Dt as isPublicStoragePath, E as isBootstrapWindowOpen, Et as PUBLIC_STORAGE_PREFIX, F as extractLinks, G as createAdapterAuthMiddleware, H as hashPassword, I as registerDevEmailSink, J as extractUserFromToken, K as createAuthMiddleware, L as SMTPEmailService, M as activeDevEmailSink, N as clearActiveDevEmailSink, O as createDataRateLimiter, P as createDevEmailSink, Q as queryTokenAuth, R as createEmailService, S as pkceTokenParams, St as html, T as createBuiltinAuthAdapter, Tt as isOperationAllowed, U as validatePasswordStrength, V as resolveAuthHooks, W as verifyPassword, X as optionalAuth, Y as fileTokenAuth, Z as publicObjectAuth, _ as verifyOidcIdToken, _t as getUserInvitationTemplate, a as resolveRateLimitStoreKind, at as validateApiKey, b as createGoogleProvider, bt as RawHtml, c as createSlackProvider, ct as SERVICE_IDENTITY, d as createDiscordProvider, dt as completeUserCreation, et as requireAuth, f as createTwitterProvider, ft as generateSecurePassword, g as tryVerifyOidcIdToken, gt as getPasswordResetTemplate, h as createMicrosoftProvider, ht as getMagicLinkTemplate, i as createApiKeyStore, it as isApiKeyToken, j as MemoryRateLimitStore, k as createRateLimiter, l as createBitbucketProvider, lt as scopeDataDriver, m as createAppleProvider, mt as getEmailVerificationTemplate, n as createCustomAuthAdapter, nt as createFunctionApiKeyGuard, o as createSqlRateLimitStore, ot as extractBearerToken, p as createFacebookProvider, pt as getEmailOtpTemplate, q as createRequireAuth, r as createApiKeyRoutes, rt as createStorageApiKeyGuard, s as createSpotifyProvider, st as safeCompare, tt as createApiKeyPreAuth, u as createGitLabProvider, ut as supportsRlsScoping, v as createGitHubProvider, vt as getWelcomeEmailTemplate, w as createJwksRoutes, wt as httpMethodToOperation, x as oauthCodeFlowSchema, xt as escapeHtml, y as createLinkedinProvider, yt as resolveEmailBranding, z as assertEmailLinkBases } from "./auth-BS4WBA10.js";
|
|
11
12
|
import { i as rawQueryLoggingEnabled, n as describeCauseChain, o as setLogLevel, r as logger, s as hostEnv } from "./logger-DO2PZc4i.js";
|
|
12
|
-
import { n as
|
|
13
|
-
import { a as resolveListLimitParam, c as HARD_DELETE_QUERY_PARAM, i as parseQueryOptions, l as parseHardDelete, n as parseAggregateSelect, o as assertReadableFields, r as parseGroupBy, s as requestViewer, t as orderByEntriesToTuples } from "./query-parser-
|
|
13
|
+
import { i as schemaDriftRemedy, n as declaredErrorAnswer, r as errorHandler, t as ApiError } from "./errors-DWsX4yTd.js";
|
|
14
|
+
import { a as resolveListLimitParam, c as HARD_DELETE_QUERY_PARAM, i as parseQueryOptions, l as parseHardDelete, n as parseAggregateSelect, o as assertReadableFields, r as parseGroupBy, s as requestViewer, t as orderByEntriesToTuples } from "./query-parser-C-rl30ce.js";
|
|
14
15
|
import { D as sha256Bytes, O as sha256Hex, S as normalizePemFromEnv, T as randomHex, _ as verifyAccessToken, a as generateMcpAccessToken, f as hasAsymmetricSigningKey, g as signPurposeToken, i as generateDownloadToken, l as getJwks, m as isJwtConfigured, n as configureJwt, w as constantTimeEqual, x as verifyPurposeToken, y as verifyMcpAccessToken } from "./jwt-C4OW-DNq.js";
|
|
15
16
|
import { a as canonicalStorageKey, i as canonicalStorageId, n as InvalidStorageKeyError, r as canonicalStorageBucket, t as InvalidStorageBucketError } from "./keys-Qfc4XieN.js";
|
|
16
|
-
import { t as logMiddleware } from "./logs-routes-
|
|
17
|
+
import { t as logMiddleware } from "./logs-routes-3EEzPjhl.js";
|
|
17
18
|
import { n as DOCUMENT_MIME_TYPES, r as IMAGE_MIME_TYPES, t as DEFAULT_MAX_FILE_SIZE } from "./types-BfKcm9do.js";
|
|
18
19
|
import { t as S3StorageController } from "./S3StorageController-Dcuf8lMA.js";
|
|
19
20
|
import { t as GCSStorageController } from "./GCSStorageController-CLIJXwGS.js";
|
|
20
21
|
import { n as loadFunctionsFromDirectory, r as loadFunctionsWithDiagnostics } from "./function-loader-xnbDAPfa.js";
|
|
21
|
-
import { a as getDriver, c as getUser, d as identityResolved, f as isAdmin, i as getApiKey, l as getUserId, m as requireDriver, o as getRequestId, p as isAuthenticated, r as requireRole, s as getRoles, t as createFunctionRoutes, u as hasRole } from "./function-routes-
|
|
22
|
+
import { a as getDriver, c as getUser, d as identityResolved, f as isAdmin, i as getApiKey, l as getUserId, m as requireDriver, o as getRequestId, p as isAuthenticated, r as requireRole, s as getRoles, t as createFunctionRoutes, u as hasRole } from "./function-routes-Chet4-lB.js";
|
|
22
23
|
import "./proxy-Czngl3p9.js";
|
|
23
|
-
import "./request-timeout-
|
|
24
|
+
import "./request-timeout-C_4C2BeR.js";
|
|
24
25
|
import { t as FunctionSelectionError } from "./selection-CRpqKUbt.js";
|
|
25
26
|
import { n as loadCronJobsFromDirectory, r as loadCronJobsWithDiagnostics } from "./cron-loader-CQjvjpEw.js";
|
|
26
|
-
import {
|
|
27
|
-
import { t as
|
|
28
|
-
import {
|
|
29
|
-
import { a as
|
|
30
|
-
import {
|
|
31
|
-
import { t as METRIC_SERIES } from "./history-store-C9EtGtoL.js";
|
|
27
|
+
import { t as createCronRoutes } from "./cron-routes-B_wlLybo.js";
|
|
28
|
+
import { t as createCronStore } from "./cron-store-Dp0X7zRB.js";
|
|
29
|
+
import { a as parseBackupTimestamp, i as parseBackupDestination, n as createBackupRoutes, o as readBackupBytes, r as listBackupObjects } from "./backup-DzI9jLwc.js";
|
|
30
|
+
import { a as currentAmbientTransaction, i as createJobStore, n as createJobQueue, r as defaultBackoff } from "./jobs-1IkI4Lle.js";
|
|
31
|
+
import { t as METRIC_SERIES } from "./history-store-By2R_G1b.js";
|
|
32
32
|
import { createHash, createSign, randomBytes } from "node:crypto";
|
|
33
33
|
import * as fs$3 from "fs";
|
|
34
34
|
import fs, { existsSync } from "fs";
|
|
@@ -116,26 +116,19 @@ var CollectionConfigError = class extends Error {
|
|
|
116
116
|
/**
|
|
117
117
|
* Read the unknown-key policy from the environment.
|
|
118
118
|
*
|
|
119
|
-
* `REBASE_STRICT_COLLECTION_CONFIG` accepts `error`/`strict
|
|
120
|
-
* escalate, `
|
|
119
|
+
* `REBASE_STRICT_COLLECTION_CONFIG` accepts `error`/`strict` or any spelling of
|
|
120
|
+
* yes to escalate, `none` or any spelling of no to silence, and anything else
|
|
121
|
+
* warns. Yes and no are {@link parseEnvBoolean}'s, the same as every other
|
|
122
|
+
* variable's.
|
|
121
123
|
*/
|
|
122
124
|
function unknownKeyPolicyFromEnv(env = process.env) {
|
|
123
125
|
const raw = env.REBASE_STRICT_COLLECTION_CONFIG?.trim().toLowerCase();
|
|
124
126
|
if (!raw) return "warn";
|
|
125
|
-
if (
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
"yes"
|
|
131
|
-
].includes(raw)) return "error";
|
|
132
|
-
if ([
|
|
133
|
-
"off",
|
|
134
|
-
"0",
|
|
135
|
-
"false",
|
|
136
|
-
"no",
|
|
137
|
-
"none"
|
|
138
|
-
].includes(raw)) return "off";
|
|
127
|
+
if (raw === "error" || raw === "strict") return "error";
|
|
128
|
+
if (raw === "none") return "off";
|
|
129
|
+
const flag = parseEnvBoolean(raw);
|
|
130
|
+
if (flag === true) return "error";
|
|
131
|
+
if (flag === false) return "off";
|
|
139
132
|
return "warn";
|
|
140
133
|
}
|
|
141
134
|
var COLLECTION_KEYS = /* @__PURE__ */ new Set([
|
|
@@ -2031,11 +2024,11 @@ function createRoutedRealtimeService(opts) {
|
|
|
2031
2024
|
}
|
|
2032
2025
|
await fallback().handleClientMessage(clientId, message, authContext);
|
|
2033
2026
|
},
|
|
2034
|
-
subscribeToCollection(
|
|
2035
|
-
forPath(
|
|
2027
|
+
subscribeToCollection(...args) {
|
|
2028
|
+
forPath(args[1].path).subscribeToCollection(...args);
|
|
2036
2029
|
},
|
|
2037
|
-
subscribeToOne(
|
|
2038
|
-
forPath(
|
|
2030
|
+
subscribeToOne(...args) {
|
|
2031
|
+
forPath(args[1].path).subscribeToOne(...args);
|
|
2039
2032
|
},
|
|
2040
2033
|
unsubscribe(subscriptionId) {
|
|
2041
2034
|
for (const p of all()) p.unsubscribe(subscriptionId);
|
|
@@ -4002,19 +3995,15 @@ var RestApiGenerator = class {
|
|
|
4002
3995
|
collection: resolvedCollection,
|
|
4003
3996
|
status: "new"
|
|
4004
3997
|
});
|
|
4005
|
-
const
|
|
4006
|
-
|
|
4007
|
-
invitationSent: prepared.invitationSent
|
|
4008
|
-
} : this.authAdapter.finalizeUserCreation ? await this.authAdapter.finalizeUserCreation({
|
|
3998
|
+
const finalize = this.authAdapter.finalizeUserCreation?.bind(this.authAdapter);
|
|
3999
|
+
const delivery = await completeUserCreation(prepared, finalize && ((clearPassword) => finalize({
|
|
4009
4000
|
id: entity.id,
|
|
4010
4001
|
values: entity
|
|
4011
|
-
},
|
|
4002
|
+
}, clearPassword)));
|
|
4012
4003
|
const response = this.formatResponse(entity);
|
|
4013
4004
|
return c.json({
|
|
4014
4005
|
...response,
|
|
4015
|
-
|
|
4016
|
-
...result.temporaryPassword ? { temporaryPassword: result.temporaryPassword } : {},
|
|
4017
|
-
..."emailDeliveryFailed" in result && result.emailDeliveryFailed ? { emailDeliveryFailed: true } : {}
|
|
4006
|
+
...delivery
|
|
4018
4007
|
}, 201);
|
|
4019
4008
|
}
|
|
4020
4009
|
return this.runIdempotent(c, body, async () => {
|
|
@@ -4123,8 +4112,7 @@ var RestApiGenerator = class {
|
|
|
4123
4112
|
hard: parseHardDelete(c.req.query(HARD_DELETE_QUERY_PARAM)),
|
|
4124
4113
|
row: {
|
|
4125
4114
|
id: String(id),
|
|
4126
|
-
path: getCollectionDataPath(collection)
|
|
4127
|
-
values: existingEntity
|
|
4115
|
+
path: getCollectionDataPath(collection)
|
|
4128
4116
|
},
|
|
4129
4117
|
collection: resolvedCollection
|
|
4130
4118
|
});
|
|
@@ -4276,18 +4264,16 @@ var RestApiGenerator = class {
|
|
|
4276
4264
|
const driver = this.getScopedDriver(c);
|
|
4277
4265
|
this.enforceSubcollectionApiKeyPermission(c, parsed.collectionPath);
|
|
4278
4266
|
const hardDelete = parseHardDelete(c.req.query(HARD_DELETE_QUERY_PARAM));
|
|
4279
|
-
|
|
4267
|
+
if (!await driver.fetchOne({
|
|
4280
4268
|
path: parsed.collectionPath,
|
|
4281
4269
|
id: parsed.id,
|
|
4282
4270
|
withDeleted: hardDelete ? true : void 0
|
|
4283
|
-
});
|
|
4284
|
-
if (!existingEntity) throw this.entityNotFound(parsed.collectionPath, parsed.id);
|
|
4271
|
+
})) throw this.entityNotFound(parsed.collectionPath, parsed.id);
|
|
4285
4272
|
await driver.delete({
|
|
4286
4273
|
hard: hardDelete,
|
|
4287
4274
|
row: {
|
|
4288
4275
|
id: parsed.id,
|
|
4289
|
-
path: parsed.collectionPath
|
|
4290
|
-
values: existingEntity
|
|
4276
|
+
path: parsed.collectionPath
|
|
4291
4277
|
}
|
|
4292
4278
|
});
|
|
4293
4279
|
return new Response(null, { status: 204 });
|
|
@@ -4653,19 +4639,190 @@ function requestLogger(options) {
|
|
|
4653
4639
|
};
|
|
4654
4640
|
}
|
|
4655
4641
|
//#endregion
|
|
4642
|
+
//#region src/deploy/pod-contract.ts
|
|
4643
|
+
/**
|
|
4644
|
+
* What every deployment of this runtime must get right about the pod.
|
|
4645
|
+
*
|
|
4646
|
+
* There are two things that place a Rebase runtime in Kubernetes — the Helm
|
|
4647
|
+
* chart in `infra/charts/rebase`, for self-hosting, and the control plane's
|
|
4648
|
+
* `buildManagedContainer`, for cloud tenants — and they were written months
|
|
4649
|
+
* apart by people solving different problems. Rendering both for the same unit
|
|
4650
|
+
* and diffing them (2026-08-22) turned up four disagreements, and in three of
|
|
4651
|
+
* them the chart was doing the thing this runtime's own source warns against.
|
|
4652
|
+
*
|
|
4653
|
+
* The disagreements were not in the parts that *should* differ. A managed pod
|
|
4654
|
+
* takes its environment from a tenant Secret and a self-hosted one takes it from
|
|
4655
|
+
* a values file; a managed pod is scheduled onto spot capacity its plan sold it
|
|
4656
|
+
* and a self-hosted one goes where the operator says. Those are different jobs
|
|
4657
|
+
* and they produce different manifests, correctly.
|
|
4658
|
+
*
|
|
4659
|
+
* What must not differ is anything that is really a statement about *this
|
|
4660
|
+
* process*: which endpoint answers what, which variables decide the topology,
|
|
4661
|
+
* where the bundle is mounted. Those are not deployment preferences. They are
|
|
4662
|
+
* facts about the runtime, and a deployment that gets one wrong produces a
|
|
4663
|
+
* cluster that looks healthy — which is why they are stated here, in the
|
|
4664
|
+
* runtime, rather than twice in the things that deploy it.
|
|
4665
|
+
*
|
|
4666
|
+
* The chart cannot import this module. `tooling/scripts/check-chart.mjs` renders the
|
|
4667
|
+
* chart and asserts it against these values instead, so the chart conforms by
|
|
4668
|
+
* gate where the control plane conforms by construction.
|
|
4669
|
+
*/
|
|
4670
|
+
/**
|
|
4671
|
+
* Endpoints this runtime guarantees on every role, and what each one means.
|
|
4672
|
+
*
|
|
4673
|
+
* `/livez` is dependency-free — it answers "this process is running" and
|
|
4674
|
+
* nothing else. `/health` opens the default driver and every configured
|
|
4675
|
+
* secondary, and **answers 503 when any of them is unreachable**
|
|
4676
|
+
* (`boot.ts`, the `healthPaths` handler).
|
|
4677
|
+
*
|
|
4678
|
+
* That difference is the whole reason both exist, and it is stated at the
|
|
4679
|
+
* `/livez` registration in `boot.ts`: "`/health` touches the database, so a
|
|
4680
|
+
* database blip would make an orchestrator kill an otherwise healthy process."
|
|
4681
|
+
*/
|
|
4682
|
+
var RUNTIME_HEALTH_PATH = "/health";
|
|
4683
|
+
var RUNTIME_LIVENESS_PATH = "/livez";
|
|
4684
|
+
/**
|
|
4685
|
+
* Which endpoint each Kubernetes probe must target.
|
|
4686
|
+
*
|
|
4687
|
+
* The rule follows from what the probe *does* when it fails:
|
|
4688
|
+
*
|
|
4689
|
+
* - **liveness** restarts the container. A database outage must therefore never
|
|
4690
|
+
* fail it, or an unreachable database turns into a cluster-wide restart loop
|
|
4691
|
+
* that clears the moment the database returns and looks, in the logs, like
|
|
4692
|
+
* the application crashed. `/livez`.
|
|
4693
|
+
* - **readiness** removes the pod from its Service. That is exactly what should
|
|
4694
|
+
* happen when the database is unreachable — the pod cannot serve. `/health`.
|
|
4695
|
+
* - **startup** decides when the other two begin. Its job is "has this process
|
|
4696
|
+
* finished booting", and booting may include fetching a bundle, installing
|
|
4697
|
+
* dependencies and checking the schema. It must not also require the database
|
|
4698
|
+
* to be *up*, or a cold database is indistinguishable from a broken image:
|
|
4699
|
+
* the pod never passes startup, liveness never gets to run, and the pod
|
|
4700
|
+
* CrashLoops with nothing in its output about a database. `/livez`.
|
|
4701
|
+
*
|
|
4702
|
+
* A probe targeting the wrong one of these fails silently in the direction that
|
|
4703
|
+
* looks like an application bug, which is why this is a contract and not a
|
|
4704
|
+
* default.
|
|
4705
|
+
*/
|
|
4706
|
+
var RUNTIME_PROBE_PATHS = {
|
|
4707
|
+
liveness: RUNTIME_LIVENESS_PATH,
|
|
4708
|
+
readiness: RUNTIME_HEALTH_PATH,
|
|
4709
|
+
startup: RUNTIME_LIVENESS_PATH
|
|
4710
|
+
};
|
|
4711
|
+
/**
|
|
4712
|
+
* Environment variables that decide *topology* — which surfaces a process
|
|
4713
|
+
* mounts, which singletons it owns, where it forwards.
|
|
4714
|
+
*
|
|
4715
|
+
* These are the platform's or the operator's decision expressed by the thing
|
|
4716
|
+
* doing the deploying, and they must never be settable by whoever supplies the
|
|
4717
|
+
* project's own environment. The cloud learned this the expensive way: a tenant
|
|
4718
|
+
* who set `REBASE_ROLE=worker` in their project variables got a pod that served
|
|
4719
|
+
* no HTTP at all, and because `/health` answers on **every** role the readiness
|
|
4720
|
+
* probe passed, the rollout reported success, and every request 404'd.
|
|
4721
|
+
*
|
|
4722
|
+
* Kubernetes only lets `env` shadow `envFrom` for names it **lists**, so
|
|
4723
|
+
* neutralising one of these means naming it explicitly. An empty value is read
|
|
4724
|
+
* by the runtime as unset, which is why the cloud pins most of them to `""`
|
|
4725
|
+
* rather than to a value: the entry exists to take the decision away from the
|
|
4726
|
+
* project, not to make it here.
|
|
4727
|
+
*/
|
|
4728
|
+
var TOPOLOGY_ENV_VARS = [
|
|
4729
|
+
"REBASE_ROLE",
|
|
4730
|
+
"REBASE_FUNCTIONS_ONLY",
|
|
4731
|
+
"REBASE_FUNCTIONS_EXCLUDE",
|
|
4732
|
+
"REBASE_FUNCTIONS_UPSTREAM",
|
|
4733
|
+
"REBASE_CRON_SCHEDULER",
|
|
4734
|
+
"REBASE_JOB_WORKERS",
|
|
4735
|
+
"REBASE_RLS_AUDIT",
|
|
4736
|
+
"REBASE_MCP_ENABLED",
|
|
4737
|
+
"REBASE_MIGRATE_ON_BOOT",
|
|
4738
|
+
"TRUSTED_PROXY_HOPS",
|
|
4739
|
+
"REBASE_RATE_LIMIT_STORE",
|
|
4740
|
+
"REBASE_REQUIRE_SCHEMA_MATCH"
|
|
4741
|
+
];
|
|
4742
|
+
/** Whether a variable name is one the deployer owns rather than the project. */
|
|
4743
|
+
function isTopologyEnvVar(name) {
|
|
4744
|
+
return TOPOLOGY_ENV_VARS.includes(name);
|
|
4745
|
+
}
|
|
4746
|
+
/**
|
|
4747
|
+
* Seconds to keep answering after Kubernetes decides to remove this pod.
|
|
4748
|
+
*
|
|
4749
|
+
* `installShutdownHandlers` drains on SIGTERM — it stops the scheduler, tears
|
|
4750
|
+
* down realtime and closes the HTTP server, finishing what is in flight. What
|
|
4751
|
+
* it cannot do is stop *new* requests arriving: kubelet sends SIGTERM and the
|
|
4752
|
+
* endpoint controller removes the pod from its Service **concurrently**, so for
|
|
4753
|
+
* as long as endpoint removal takes to propagate, the ingress is still routing
|
|
4754
|
+
* to a process that has already stopped accepting connections.
|
|
4755
|
+
*
|
|
4756
|
+
* A `preStop` sleep is the only thing that orders those two. The pod keeps
|
|
4757
|
+
* serving for this long *before* SIGTERM is sent, which is time the ingress
|
|
4758
|
+
* uses to stop sending it anything.
|
|
4759
|
+
*
|
|
4760
|
+
* Anything greater than zero fixes the ordering; five seconds is what the
|
|
4761
|
+
* control plane has run in production.
|
|
4762
|
+
*/
|
|
4763
|
+
var RUNTIME_PRESTOP_DRAIN_SECONDS = 5;
|
|
4764
|
+
/**
|
|
4765
|
+
* The floor for `terminationGracePeriodSeconds`.
|
|
4766
|
+
*
|
|
4767
|
+
* The pod must outlive `preStop` *plus* the drain that follows it, or kubelet
|
|
4768
|
+
* SIGKILLs mid-drain and the graceful shutdown was decoration. The drain's own
|
|
4769
|
+
* default is 15s (`ShutdownHandlerOptions.timeoutMs`), and Kubernetes' default
|
|
4770
|
+
* grace period is 30s — so the stock configuration has room, and this exists to
|
|
4771
|
+
* say how much before someone raises the drain.
|
|
4772
|
+
*/
|
|
4773
|
+
var RUNTIME_MIN_TERMINATION_GRACE_SECONDS = 20;
|
|
4774
|
+
/**
|
|
4775
|
+
* How long a deployment must let this runtime take to answer for the first time.
|
|
4776
|
+
*
|
|
4777
|
+
* Nothing answers until boot is finished. `runFromBundle` binds the socket
|
|
4778
|
+
* **last** — after the bundle is read, the drivers connect and, on the process
|
|
4779
|
+
* that owns it, the schema DDL runs (`boot.ts`, "schema DDL happens during
|
|
4780
|
+
* boot, above"). So the gap between the container starting and `/livez`
|
|
4781
|
+
* answering is a whole provisioning run, not a framework warming up.
|
|
4782
|
+
*
|
|
4783
|
+
* A deployment with no startup probe measures that gap with its *liveness*
|
|
4784
|
+
* probe instead, and liveness restarts the container. On the control plane's
|
|
4785
|
+
* settings that is 20s of grace plus three 20s failures — 80 seconds — after
|
|
4786
|
+
* which a slow first boot is killed and retried, and each retry starts from the
|
|
4787
|
+
* beginning. It does not converge; it loops, and the logs show a pod that never
|
|
4788
|
+
* finished starting rather than a database that was slow.
|
|
4789
|
+
*
|
|
4790
|
+
* So a startup probe is not optional here, and its budget is this. A healthy
|
|
4791
|
+
* pod passes it on the first check and nothing is spent.
|
|
4792
|
+
*/
|
|
4793
|
+
var RUNTIME_STARTUP_BUDGET_SECONDS = 300;
|
|
4794
|
+
/** Where a bundle is mounted, and what the runtime is told to read. */
|
|
4795
|
+
var RUNTIME_BUNDLE_MOUNT = "/bundle";
|
|
4796
|
+
/**
|
|
4797
|
+
* The request-body limit every API route has by default (`maxBodySize`,
|
|
4798
|
+
* `REBASE_MAX_BODY_SIZE`), in bytes.
|
|
4799
|
+
*
|
|
4800
|
+
* It is not the largest body the runtime accepts. `POST /storage/upload` is
|
|
4801
|
+
* exempt from it and meets the storage config's `maxFileSize` instead, whose
|
|
4802
|
+
* default is `DEFAULT_MAX_FILE_SIZE` (`storage/types.ts`), 50 MB. A proxy in
|
|
4803
|
+
* front of the runtime has to allow more than the larger of the two. Otherwise
|
|
4804
|
+
* it refuses uploads the runtime would accept, with its own error page in
|
|
4805
|
+
* place of the runtime's JSON 413. The chart's ingress was left at 12m after
|
|
4806
|
+
* the upload route got its own limit, and admin-panel uploads between 12 and
|
|
4807
|
+
* 50 MB failed that way.
|
|
4808
|
+
*/
|
|
4809
|
+
var RUNTIME_DEFAULT_MAX_BODY_SIZE = 10 * 1024 * 1024;
|
|
4810
|
+
//#endregion
|
|
4656
4811
|
//#region src/init/middlewares.ts
|
|
4657
4812
|
function configureMiddlewares(app, basePath, isProduction, config) {
|
|
4813
|
+
const carriesOwnBodyLimit = /* @__PURE__ */ new Set();
|
|
4658
4814
|
app.use(`${basePath}/*`, requestId());
|
|
4659
4815
|
if (config.compression !== false) {
|
|
4660
4816
|
app.use(`${basePath}/*`, responseCompression());
|
|
4661
4817
|
logger.debug("Response compression enabled");
|
|
4662
4818
|
}
|
|
4663
|
-
const maxBodySize = config.maxBodySize ??
|
|
4819
|
+
const maxBodySize = config.maxBodySize ?? 10485760;
|
|
4664
4820
|
if (maxBodySize > 0) {
|
|
4665
|
-
|
|
4821
|
+
const limitBody = bodyLimit({
|
|
4666
4822
|
maxSize: maxBodySize,
|
|
4667
4823
|
onError: (c) => errorHandler(new ApiError(413, "PAYLOAD_TOO_LARGE", `Request body too large. Maximum size is ${Math.round(maxBodySize / 1024 / 1024)}MB.`), c)
|
|
4668
|
-
})
|
|
4824
|
+
});
|
|
4825
|
+
app.use(`${basePath}/*`, (c, next) => carriesOwnBodyLimit.has(c.req.path) ? next() : limitBody(c, next));
|
|
4669
4826
|
logger.debug("Request body limit configured", { maxSizeMB: Math.round(maxBodySize / 1024 / 1024) });
|
|
4670
4827
|
}
|
|
4671
4828
|
if (config.csrf?.origin) {
|
|
@@ -4675,6 +4832,9 @@ function configureMiddlewares(app, basePath, isProduction, config) {
|
|
|
4675
4832
|
if (!config.corsHandled && !process.env.CORS_ORIGINS && !process.env.FRONTEND_URL) logger.warn((isProduction ? "[PRODUCTION] " : "") + "No CORS configuration detected (CORS_ORIGINS / FRONTEND_URL not set). If your app does not install its own CORS middleware, the API may accept requests from any origin. Set CORS_ORIGINS to restrict access.");
|
|
4676
4833
|
app.use(`${basePath}/*`, requestLogger());
|
|
4677
4834
|
app.use(`${basePath}/*`, logMiddleware({ ignorePaths: [`${basePath}/logs/stream`] }));
|
|
4835
|
+
return { exemptFromBodyLimit: (path) => {
|
|
4836
|
+
carriesOwnBodyLimit.add(path);
|
|
4837
|
+
} };
|
|
4678
4838
|
}
|
|
4679
4839
|
//#endregion
|
|
4680
4840
|
//#region src/storage/LocalStorageController.ts
|
|
@@ -7013,6 +7173,25 @@ async function createStorageController(config) {
|
|
|
7013
7173
|
}
|
|
7014
7174
|
//#endregion
|
|
7015
7175
|
//#region src/init/storage.ts
|
|
7176
|
+
/**
|
|
7177
|
+
* Whether `FORCE_LOCAL_STORAGE` says a durable volume is mounted, so a `local`
|
|
7178
|
+
* backend may serve in production.
|
|
7179
|
+
*
|
|
7180
|
+
* The one reader of the variable: this guard and the `bucket` resolver that
|
|
7181
|
+
* `rebase status` asks both call it, so status cannot promise a backend boot
|
|
7182
|
+
* is about to drop. It used to be `!process.env.FORCE_LOCAL_STORAGE` in both,
|
|
7183
|
+
* which is a test for "set", not for "true" — `FORCE_LOCAL_STORAGE=false` and
|
|
7184
|
+
* `=0` read as forced, and the guard stood down for the operator who had just
|
|
7185
|
+
* said there was no volume.
|
|
7186
|
+
*
|
|
7187
|
+
* Only an explicit yes forces. `loadEnv` parses the variable to the same
|
|
7188
|
+
* boolean and refuses a value outside `true`/`false`/blank before storage is
|
|
7189
|
+
* initialised; this reads the raw environment because a backend assembled
|
|
7190
|
+
* without `loadEnv` still has to get the same answer.
|
|
7191
|
+
*/
|
|
7192
|
+
function localStorageForced(env = process.env) {
|
|
7193
|
+
return parseEnvBoolean(env.FORCE_LOCAL_STORAGE) === true;
|
|
7194
|
+
}
|
|
7016
7195
|
async function initializeStorage(storageConfig, isProduction) {
|
|
7017
7196
|
if (!storageConfig) return {};
|
|
7018
7197
|
logger.debug("Configuring storage");
|
|
@@ -7020,7 +7199,7 @@ async function initializeStorage(storageConfig, isProduction) {
|
|
|
7020
7199
|
const toController = async (entry, label) => {
|
|
7021
7200
|
if (typeof entry.putObject === "function") return entry;
|
|
7022
7201
|
const conf = entry;
|
|
7023
|
-
if (isProduction && conf.type === "local" && !
|
|
7202
|
+
if (isProduction && conf.type === "local" && !localStorageForced()) {
|
|
7024
7203
|
logger.error(`Storage backend "${label}" is set to "local" in production — DISABLED. Local storage is the container filesystem, so uploaded files would be destroyed on the next restart or redeploy. File uploads will be refused until storage is configured: set S3-compatible storage (STORAGE_TYPE=s3) or GCS (STORAGE_TYPE=gcs), or pass a custom StorageController. If this deployment really does have a durable volume mounted at the storage path, set FORCE_LOCAL_STORAGE=true.`);
|
|
7025
7204
|
return;
|
|
7026
7205
|
}
|
|
@@ -7200,7 +7379,7 @@ async function mountOpenApiDocs(app, basePath, enableSwagger, serverCollections,
|
|
|
7200
7379
|
basePath,
|
|
7201
7380
|
requireAuth
|
|
7202
7381
|
}));
|
|
7203
|
-
const { generateOpenApiSpec } = await import("./openapi-generator-
|
|
7382
|
+
const { generateOpenApiSpec } = await import("./openapi-generator-BDpoKZQ9.js");
|
|
7204
7383
|
generateOpenApiSpecFn = generateOpenApiSpec;
|
|
7205
7384
|
if (isPublic) app.get(`${basePath}/docs`, (c) => spec(c));
|
|
7206
7385
|
else app.get(`${basePath}/docs`, createRequireAuth({}), requireAdmin, (c) => spec(c));
|
|
@@ -8688,7 +8867,7 @@ var HANDLER_SLOT = Symbol.for("@rebasepro/server:unhandled-rejection-handler");
|
|
|
8688
8867
|
* was installed.
|
|
8689
8868
|
*/
|
|
8690
8869
|
function installUnhandledRejectionHandler() {
|
|
8691
|
-
if (process.env.REBASE_EXIT_ON_UNHANDLED_REJECTION ===
|
|
8870
|
+
if (parseEnvBoolean(process.env.REBASE_EXIT_ON_UNHANDLED_REJECTION) === true) return void 0;
|
|
8692
8871
|
const slot = globalThis;
|
|
8693
8872
|
if (slot[HANDLER_SLOT]) return void 0;
|
|
8694
8873
|
const handler = (reason) => {
|
|
@@ -13039,6 +13218,20 @@ function extractMessageError(message) {
|
|
|
13039
13218
|
};
|
|
13040
13219
|
}
|
|
13041
13220
|
/**
|
|
13221
|
+
* The error an `ERROR` frame describes, with the server's `details` when it
|
|
13222
|
+
* sent them — `{ stage, path }` for a collection-callback refusal, the object
|
|
13223
|
+
* the REST envelope carries for the same veto. `status` stays `undefined`:
|
|
13224
|
+
* a frame is not an HTTP response (see `RebaseErrorInit.status`).
|
|
13225
|
+
*/
|
|
13226
|
+
function frameError(message) {
|
|
13227
|
+
const { errorMessage, errorCode } = extractMessageError(message);
|
|
13228
|
+
const errPayload = message.payload?.error;
|
|
13229
|
+
return new RebaseApiError(errorMessage, {
|
|
13230
|
+
code: errorCode,
|
|
13231
|
+
details: typeof errPayload === "object" && errPayload !== null ? errPayload.details : void 0
|
|
13232
|
+
});
|
|
13233
|
+
}
|
|
13234
|
+
/**
|
|
13042
13235
|
* Broadcast and presence frames.
|
|
13043
13236
|
*
|
|
13044
13237
|
* Fire-and-forget (the server sends no response envelope), and exempt from the
|
|
@@ -13432,8 +13625,7 @@ var RebaseWebSocketClient = class {
|
|
|
13432
13625
|
else this.sendEntitySubscribe(subscriptionKey);
|
|
13433
13626
|
return;
|
|
13434
13627
|
}
|
|
13435
|
-
const
|
|
13436
|
-
const error = new RebaseApiError(errorMessage, { code: errorCode });
|
|
13628
|
+
const error = frameError(message);
|
|
13437
13629
|
if (messageType === "subscribe_collection") this.failCollectionSubscription(subscriptionKey, error);
|
|
13438
13630
|
else this.failEntitySubscription(subscriptionKey, error);
|
|
13439
13631
|
}).catch((err) => {
|
|
@@ -13450,17 +13642,13 @@ var RebaseWebSocketClient = class {
|
|
|
13450
13642
|
this.pendingRequests.delete(requestId);
|
|
13451
13643
|
this.handleAuthFailure().then((refreshed) => {
|
|
13452
13644
|
if (refreshed && pendingReq.message) this.doSendMessage(pendingReq.message, pendingReq.resolve, pendingReq.reject).catch(pendingReq.reject);
|
|
13453
|
-
else
|
|
13454
|
-
const { errorMessage, errorCode } = extractMessageError(message);
|
|
13455
|
-
pendingReq.reject(new RebaseApiError(errorMessage, { code: errorCode }));
|
|
13456
|
-
}
|
|
13645
|
+
else pendingReq.reject(frameError(message));
|
|
13457
13646
|
}).catch((err) => {
|
|
13458
13647
|
pendingReq.reject(err);
|
|
13459
13648
|
});
|
|
13460
13649
|
} else {
|
|
13461
13650
|
this.pendingRequests.delete(requestId);
|
|
13462
|
-
|
|
13463
|
-
pendingReq.reject(new RebaseApiError(errorMessage, { code: errorCode }));
|
|
13651
|
+
pendingReq.reject(frameError(message));
|
|
13464
13652
|
}
|
|
13465
13653
|
else {
|
|
13466
13654
|
this.pendingRequests.delete(requestId);
|
|
@@ -13544,8 +13732,7 @@ var RebaseWebSocketClient = class {
|
|
|
13544
13732
|
if (collectionSub.subscribeTimeout) clearTimeout(collectionSub.subscribeTimeout);
|
|
13545
13733
|
collectionSub.subscribeTimeout = void 0;
|
|
13546
13734
|
collectionSub.subscribeInFlight = false;
|
|
13547
|
-
const
|
|
13548
|
-
const error = new RebaseApiError(errorMessage, { code: errorCode });
|
|
13735
|
+
const error = frameError(message);
|
|
13549
13736
|
collectionSub.callbacks.forEach((callback) => {
|
|
13550
13737
|
if (callback.onError) callback.onError(error);
|
|
13551
13738
|
});
|
|
@@ -13563,8 +13750,7 @@ var RebaseWebSocketClient = class {
|
|
|
13563
13750
|
if (entitySub.subscribeTimeout) clearTimeout(entitySub.subscribeTimeout);
|
|
13564
13751
|
entitySub.subscribeTimeout = void 0;
|
|
13565
13752
|
entitySub.subscribeInFlight = false;
|
|
13566
|
-
const
|
|
13567
|
-
const error = new RebaseApiError(errorMessage, { code: errorCode });
|
|
13753
|
+
const error = frameError(message);
|
|
13568
13754
|
entitySub.callbacks.forEach((callback) => {
|
|
13569
13755
|
if (callback.onError) callback.onError(error);
|
|
13570
13756
|
});
|
|
@@ -18005,10 +18191,16 @@ function readAccountVar(env, base, suffix, accountSuffix) {
|
|
|
18005
18191
|
if (own !== void 0 || accountSuffix === void 0) return own;
|
|
18006
18192
|
return readVar(env, base, accountSuffix);
|
|
18007
18193
|
}
|
|
18194
|
+
/**
|
|
18195
|
+
* A boolean binding, spelled the way every other variable is.
|
|
18196
|
+
*
|
|
18197
|
+
* `undefined` when unset or unrecognised, which the S3 controller reads as
|
|
18198
|
+
* "decide from the endpoint". An exact `=== "true"` used to turn `=1` into an
|
|
18199
|
+
* explicit `false`, switching path-style off for a MinIO endpoint whose
|
|
18200
|
+
* default would have switched it on.
|
|
18201
|
+
*/
|
|
18008
18202
|
function readAccountBool(env, base, suffix, accountSuffix) {
|
|
18009
|
-
|
|
18010
|
-
if (raw === void 0) return void 0;
|
|
18011
|
-
return raw === "true";
|
|
18203
|
+
return parseEnvBoolean(readAccountVar(env, base, suffix, accountSuffix));
|
|
18012
18204
|
}
|
|
18013
18205
|
/**
|
|
18014
18206
|
* Guard against two distinct keys collapsing onto the same variable name.
|
|
@@ -18330,7 +18522,7 @@ var bucketResolver = {
|
|
|
18330
18522
|
standsIn: config.standsInFor,
|
|
18331
18523
|
detail: `${config.standsInFor} declared and unbound; a local directory stands in, in development only`
|
|
18332
18524
|
};
|
|
18333
|
-
if (config.type === "local") return context.production && !env
|
|
18525
|
+
if (config.type === "local") return context.production && !localStorageForced(env) ? {
|
|
18334
18526
|
state: "unbound",
|
|
18335
18527
|
detail: "local storage is dropped in production — a container's filesystem is erased on restart. Bind an object store, or set FORCE_LOCAL_STORAGE=true on a durable volume."
|
|
18336
18528
|
} : {
|
|
@@ -18649,7 +18841,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
18649
18841
|
});
|
|
18650
18842
|
installRootErrorHandler(config.app);
|
|
18651
18843
|
installUnmatchedApiEnvelope(config.app, basePath);
|
|
18652
|
-
configureMiddlewares(config.app, basePath, isProduction, config);
|
|
18844
|
+
const middlewares = configureMiddlewares(config.app, basePath, isProduction, config);
|
|
18653
18845
|
const collectionRegistry = new BackendCollectionRegistry();
|
|
18654
18846
|
const dataSourceRegistry = createDataSourceRegistry(declaredDataSources.length > 0 ? declaredDataSources : void 0);
|
|
18655
18847
|
collectionRegistry.setDataSources(dataSourceRegistry);
|
|
@@ -18979,7 +19171,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
18979
19171
|
]) {
|
|
18980
19172
|
const providerConfig = safeAuthConfig[key];
|
|
18981
19173
|
if (providerConfig && requiredFields.every((f) => Boolean(providerConfig[f]))) {
|
|
18982
|
-
const createFn = (await import("./auth-
|
|
19174
|
+
const createFn = (await import("./auth-BS4WBA10.js").then((n) => n.t))[factory];
|
|
18983
19175
|
oauthProviders.push(createFn(providerConfig));
|
|
18984
19176
|
}
|
|
18985
19177
|
}
|
|
@@ -19070,7 +19262,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19070
19262
|
publicUrl,
|
|
19071
19263
|
mcpPath,
|
|
19072
19264
|
authBasePath: `${basePath}/auth`,
|
|
19073
|
-
allowDynamicRegistration: process.env.REBASE_MCP_OPEN_REGISTRATION !==
|
|
19265
|
+
allowDynamicRegistration: parseEnvBoolean(process.env.REBASE_MCP_OPEN_REGISTRATION) !== false
|
|
19074
19266
|
}));
|
|
19075
19267
|
logger.info(`MCP endpoint mounted at ${publicUrl}${mcpPath} (OAuth at ${oauthBasePath})`);
|
|
19076
19268
|
}
|
|
@@ -19134,7 +19326,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19134
19326
|
let schemaEditorOff = schemaEditorUnavailable();
|
|
19135
19327
|
let schemaEditorRoutes;
|
|
19136
19328
|
if (!schemaEditorOff && config.collectionsDir) try {
|
|
19137
|
-
schemaEditorRoutes = (await import("./schema-editor-routes-
|
|
19329
|
+
schemaEditorRoutes = (await import("./schema-editor-routes-DdLihzp0.js")).createSchemaEditorRoutes(config.collectionsDir);
|
|
19138
19330
|
} catch (err) {
|
|
19139
19331
|
if (err?.code === "ERR_MODULE_NOT_FOUND") {
|
|
19140
19332
|
schemaEditorOff = {
|
|
@@ -19182,7 +19374,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19182
19374
|
commitPaths,
|
|
19183
19375
|
sourceEditingOff: schemaEditorOff,
|
|
19184
19376
|
usesVersionedMigrations: collectionsDir ? () => usesVersionedMigrations(collectionsDir) : void 0,
|
|
19185
|
-
policy: { allowMachineApply: config.liveSchema?.allowMachineApply ?? process.env.REBASE_LIVE_SCHEMA_ALLOW_MACHINE_APPLY ===
|
|
19377
|
+
policy: { allowMachineApply: config.liveSchema?.allowMachineApply ?? parseEnvBoolean(process.env.REBASE_LIVE_SCHEMA_ALLOW_MACHINE_APPLY) === true },
|
|
19186
19378
|
getCollections: () => collectionRegistry.getRawCollections(),
|
|
19187
19379
|
getAdmin: () => defaultDriver.admin,
|
|
19188
19380
|
getRepository: (author) => {
|
|
@@ -19247,7 +19439,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19247
19439
|
}
|
|
19248
19440
|
const storageAuthorizeData = {};
|
|
19249
19441
|
if (storageController) {
|
|
19250
|
-
const storageMaxSize = (config.storage && typeof config.storage === "object" && "type" in config.storage ? config.storage.maxFileSize : void 0) ??
|
|
19442
|
+
const storageMaxSize = (config.storage && typeof config.storage === "object" && "type" in config.storage ? config.storage.maxFileSize : void 0) ?? 52428800;
|
|
19251
19443
|
const storageAccessControl = resolveStorageAccessControl({
|
|
19252
19444
|
storagePolicies: config.storagePolicies,
|
|
19253
19445
|
storageAuthorize: config.storageAuthorize,
|
|
@@ -19275,12 +19467,16 @@ async function _initializeRebaseBackend(config) {
|
|
|
19275
19467
|
const storageRouter = new Hono();
|
|
19276
19468
|
if (apiKeyPreAuth) storageRouter.use("/*", apiKeyPreAuth, createStorageApiKeyGuard());
|
|
19277
19469
|
if (rateLimitConfig) storageRouter.use("/*", createDataRateLimiter(rateLimitConfig));
|
|
19278
|
-
|
|
19470
|
+
const uploadPath = "/upload";
|
|
19471
|
+
storageRouter.use(uploadPath, bodyLimit({
|
|
19279
19472
|
maxSize: storageMaxSize,
|
|
19280
19473
|
onError: (c) => errorHandler(new ApiError(413, "PAYLOAD_TOO_LARGE", `File too large. Maximum upload size is ${Math.round(storageMaxSize / 1024 / 1024)}MB.`), c)
|
|
19281
19474
|
}));
|
|
19282
19475
|
storageRouter.route("/", storageRoutes);
|
|
19283
|
-
if (surfaces.storage)
|
|
19476
|
+
if (surfaces.storage) {
|
|
19477
|
+
config.app.route(`${basePath}/storage`, storageRouter);
|
|
19478
|
+
middlewares.exemptFromBodyLimit(`${basePath}/storage${uploadPath}`);
|
|
19479
|
+
}
|
|
19284
19480
|
} else {
|
|
19285
19481
|
const storageStub = new Hono();
|
|
19286
19482
|
storageStub.all("/*", (c) => c.json({ error: {
|
|
@@ -19424,8 +19620,8 @@ async function _initializeRebaseBackend(config) {
|
|
|
19424
19620
|
injectCallbackClient(driverResults.values(), serverClient);
|
|
19425
19621
|
if (config.functionsDir && surfaces.functions) {
|
|
19426
19622
|
const { loadFunctionsWithDiagnostics } = await import("./function-loader-xnbDAPfa.js").then((n) => n.t);
|
|
19427
|
-
const { createFunctionRoutes } = await import("./function-routes-
|
|
19428
|
-
const { createFunctionsRequestTimeout, resolveFunctionsTimeoutMs } = await import("./request-timeout-
|
|
19623
|
+
const { createFunctionRoutes } = await import("./function-routes-Chet4-lB.js").then((n) => n.n);
|
|
19624
|
+
const { createFunctionsRequestTimeout, resolveFunctionsTimeoutMs } = await import("./request-timeout-C_4C2BeR.js").then((n) => n.t);
|
|
19429
19625
|
const { functions: allFunctions, problems } = await loadFunctionsWithDiagnostics(config.functionsDir);
|
|
19430
19626
|
const { selectFunctions } = await import("./selection-CRpqKUbt.js").then((n) => n.n);
|
|
19431
19627
|
const loadedFunctions = selectFunctions(allFunctions, config.functionsSelection);
|
|
@@ -19479,9 +19675,9 @@ async function _initializeRebaseBackend(config) {
|
|
|
19479
19675
|
let cronScheduler;
|
|
19480
19676
|
if (surfaces.cron || config.cronsDir && ownership.cronScheduler) {
|
|
19481
19677
|
const { loadCronJobsWithDiagnostics } = await import("./cron-loader-CQjvjpEw.js").then((n) => n.t);
|
|
19482
|
-
const { CronScheduler } = await import("./cron-scheduler-
|
|
19483
|
-
const { createCronRoutes } = await import("./cron-routes-
|
|
19484
|
-
const { createCronStore } = await import("./cron-store-
|
|
19678
|
+
const { CronScheduler } = await import("./cron-scheduler-COPQxlEq.js").then((n) => n.n);
|
|
19679
|
+
const { createCronRoutes } = await import("./cron-routes-B_wlLybo.js").then((n) => n.n);
|
|
19680
|
+
const { createCronStore } = await import("./cron-store-Dp0X7zRB.js").then((n) => n.n);
|
|
19485
19681
|
const { jobs: loadedCronJobs, problems: cronProblems } = config.cronsDir ? await loadCronJobsWithDiagnostics(config.cronsDir) : {
|
|
19486
19682
|
jobs: [],
|
|
19487
19683
|
problems: []
|
|
@@ -19538,7 +19734,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19538
19734
|
}
|
|
19539
19735
|
let metricsHistory;
|
|
19540
19736
|
try {
|
|
19541
|
-
const { createMetricsHistory } = await import("./history-recorder-
|
|
19737
|
+
const { createMetricsHistory } = await import("./history-recorder-5VKT7nss.js");
|
|
19542
19738
|
metricsHistory = createMetricsHistory(defaultDriver);
|
|
19543
19739
|
if (metricsHistory) {
|
|
19544
19740
|
await metricsHistory.ensure();
|
|
@@ -19550,7 +19746,7 @@ async function _initializeRebaseBackend(config) {
|
|
|
19550
19746
|
}
|
|
19551
19747
|
let jobQueue;
|
|
19552
19748
|
if (config.jobs?.enabled) {
|
|
19553
|
-
const { createJobStore, createJobQueue } = await import("./jobs-
|
|
19749
|
+
const { createJobStore, createJobQueue } = await import("./jobs-1IkI4Lle.js").then((n) => n.t);
|
|
19554
19750
|
const store = createJobStore(defaultDriver);
|
|
19555
19751
|
if (store) {
|
|
19556
19752
|
await store.ensureTable();
|
|
@@ -19576,7 +19772,7 @@ Use a driver that supports the job queue, or remove the declarations. Refusing t
|
|
|
19576
19772
|
}
|
|
19577
19773
|
let rlsAudit;
|
|
19578
19774
|
if (surfaces.admin) {
|
|
19579
|
-
const { createBackupRoutes, parseBackupDestination } = await import("./backup-
|
|
19775
|
+
const { createBackupRoutes, parseBackupDestination } = await import("./backup-DzI9jLwc.js").then((n) => n.t);
|
|
19580
19776
|
const backupRouter = new Hono();
|
|
19581
19777
|
applyAdminGate(backupRouter, "Backup");
|
|
19582
19778
|
backupRouter.route("/", createBackupRoutes({
|
|
@@ -19624,7 +19820,7 @@ Use a driver that supports the job queue, or remove the declarations. Refusing t
|
|
|
19624
19820
|
logger.debug("Development mailbox admin routes mounted", { path: `${basePath}/admin/dev/emails` });
|
|
19625
19821
|
}
|
|
19626
19822
|
if (surfaces.admin) {
|
|
19627
|
-
const { default: logsRoutes } = await import("./logs-routes-
|
|
19823
|
+
const { default: logsRoutes } = await import("./logs-routes-3EEzPjhl.js").then((n) => n.n);
|
|
19628
19824
|
const logsRouter = new Hono();
|
|
19629
19825
|
applyAdminGate(logsRouter, "Logs");
|
|
19630
19826
|
logsRouter.route("/", logsRoutes);
|
|
@@ -20860,7 +21056,7 @@ function listenWithPortRetry(server, startPort, options) {
|
|
|
20860
21056
|
const host = options?.host ?? "0.0.0.0";
|
|
20861
21057
|
const maxAttempts = options?.maxAttempts ?? MAX_PORT_ATTEMPTS;
|
|
20862
21058
|
const portFileDir = options?.portFileDir;
|
|
20863
|
-
const explicit = options?.explicit ?? process.env.REBASE_DEV_PORT_EXPLICIT ===
|
|
21059
|
+
const explicit = options?.explicit ?? parseEnvBoolean(process.env.REBASE_DEV_PORT_EXPLICIT) === true;
|
|
20864
21060
|
if (process.env.NODE_ENV === "production") return new Promise((resolve, reject) => {
|
|
20865
21061
|
const onError = (err) => {
|
|
20866
21062
|
reject(err);
|
|
@@ -23291,7 +23487,7 @@ async function bootStaticApp(bundle, devRoot, options) {
|
|
|
23291
23487
|
const isProduction = process.env.NODE_ENV === "production";
|
|
23292
23488
|
const requestedPort = Number(process.env.PORT ?? "3001") || 3001;
|
|
23293
23489
|
const basePath = process.env.REBASE_BASE_PATH || "/api";
|
|
23294
|
-
const metricsEnabled = process.env.REBASE_METRICS ===
|
|
23490
|
+
const metricsEnabled = parseEnvBoolean(process.env.REBASE_METRICS) === true;
|
|
23295
23491
|
const metricsToken = process.env.REBASE_METRICS_TOKEN;
|
|
23296
23492
|
const app = new Hono();
|
|
23297
23493
|
installRootErrorHandler(app);
|
|
@@ -23511,161 +23707,6 @@ function warnOnUnusableBundleShape(bundle) {
|
|
|
23511
23707
|
logger.warn(`This bundle declares collections at "${bundle.manifest.entry.collections}", but that directory did not resolve, so no collections were loaded and no tables will be created. Rebuild with \`rebase build\`.`);
|
|
23512
23708
|
}
|
|
23513
23709
|
//#endregion
|
|
23514
|
-
|
|
23515
|
-
/**
|
|
23516
|
-
* What every deployment of this runtime must get right about the pod.
|
|
23517
|
-
*
|
|
23518
|
-
* There are two things that place a Rebase runtime in Kubernetes — the Helm
|
|
23519
|
-
* chart in `infra/charts/rebase`, for self-hosting, and the control plane's
|
|
23520
|
-
* `buildManagedContainer`, for cloud tenants — and they were written months
|
|
23521
|
-
* apart by people solving different problems. Rendering both for the same unit
|
|
23522
|
-
* and diffing them (2026-08-22) turned up four disagreements, and in three of
|
|
23523
|
-
* them the chart was doing the thing this runtime's own source warns against.
|
|
23524
|
-
*
|
|
23525
|
-
* The disagreements were not in the parts that *should* differ. A managed pod
|
|
23526
|
-
* takes its environment from a tenant Secret and a self-hosted one takes it from
|
|
23527
|
-
* a values file; a managed pod is scheduled onto spot capacity its plan sold it
|
|
23528
|
-
* and a self-hosted one goes where the operator says. Those are different jobs
|
|
23529
|
-
* and they produce different manifests, correctly.
|
|
23530
|
-
*
|
|
23531
|
-
* What must not differ is anything that is really a statement about *this
|
|
23532
|
-
* process*: which endpoint answers what, which variables decide the topology,
|
|
23533
|
-
* where the bundle is mounted. Those are not deployment preferences. They are
|
|
23534
|
-
* facts about the runtime, and a deployment that gets one wrong produces a
|
|
23535
|
-
* cluster that looks healthy — which is why they are stated here, in the
|
|
23536
|
-
* runtime, rather than twice in the things that deploy it.
|
|
23537
|
-
*
|
|
23538
|
-
* The chart cannot import this module. `tooling/scripts/check-chart.mjs` renders the
|
|
23539
|
-
* chart and asserts it against these values instead, so the chart conforms by
|
|
23540
|
-
* gate where the control plane conforms by construction.
|
|
23541
|
-
*/
|
|
23542
|
-
/**
|
|
23543
|
-
* Endpoints this runtime guarantees on every role, and what each one means.
|
|
23544
|
-
*
|
|
23545
|
-
* `/livez` is dependency-free — it answers "this process is running" and
|
|
23546
|
-
* nothing else. `/health` opens the default driver and every configured
|
|
23547
|
-
* secondary, and **answers 503 when any of them is unreachable**
|
|
23548
|
-
* (`boot.ts`, the `healthPaths` handler).
|
|
23549
|
-
*
|
|
23550
|
-
* That difference is the whole reason both exist, and it is stated at the
|
|
23551
|
-
* `/livez` registration in `boot.ts`: "`/health` touches the database, so a
|
|
23552
|
-
* database blip would make an orchestrator kill an otherwise healthy process."
|
|
23553
|
-
*/
|
|
23554
|
-
var RUNTIME_HEALTH_PATH = "/health";
|
|
23555
|
-
var RUNTIME_LIVENESS_PATH = "/livez";
|
|
23556
|
-
/**
|
|
23557
|
-
* Which endpoint each Kubernetes probe must target.
|
|
23558
|
-
*
|
|
23559
|
-
* The rule follows from what the probe *does* when it fails:
|
|
23560
|
-
*
|
|
23561
|
-
* - **liveness** restarts the container. A database outage must therefore never
|
|
23562
|
-
* fail it, or an unreachable database turns into a cluster-wide restart loop
|
|
23563
|
-
* that clears the moment the database returns and looks, in the logs, like
|
|
23564
|
-
* the application crashed. `/livez`.
|
|
23565
|
-
* - **readiness** removes the pod from its Service. That is exactly what should
|
|
23566
|
-
* happen when the database is unreachable — the pod cannot serve. `/health`.
|
|
23567
|
-
* - **startup** decides when the other two begin. Its job is "has this process
|
|
23568
|
-
* finished booting", and booting may include fetching a bundle, installing
|
|
23569
|
-
* dependencies and checking the schema. It must not also require the database
|
|
23570
|
-
* to be *up*, or a cold database is indistinguishable from a broken image:
|
|
23571
|
-
* the pod never passes startup, liveness never gets to run, and the pod
|
|
23572
|
-
* CrashLoops with nothing in its output about a database. `/livez`.
|
|
23573
|
-
*
|
|
23574
|
-
* A probe targeting the wrong one of these fails silently in the direction that
|
|
23575
|
-
* looks like an application bug, which is why this is a contract and not a
|
|
23576
|
-
* default.
|
|
23577
|
-
*/
|
|
23578
|
-
var RUNTIME_PROBE_PATHS = {
|
|
23579
|
-
liveness: RUNTIME_LIVENESS_PATH,
|
|
23580
|
-
readiness: RUNTIME_HEALTH_PATH,
|
|
23581
|
-
startup: RUNTIME_LIVENESS_PATH
|
|
23582
|
-
};
|
|
23583
|
-
/**
|
|
23584
|
-
* Environment variables that decide *topology* — which surfaces a process
|
|
23585
|
-
* mounts, which singletons it owns, where it forwards.
|
|
23586
|
-
*
|
|
23587
|
-
* These are the platform's or the operator's decision expressed by the thing
|
|
23588
|
-
* doing the deploying, and they must never be settable by whoever supplies the
|
|
23589
|
-
* project's own environment. The cloud learned this the expensive way: a tenant
|
|
23590
|
-
* who set `REBASE_ROLE=worker` in their project variables got a pod that served
|
|
23591
|
-
* no HTTP at all, and because `/health` answers on **every** role the readiness
|
|
23592
|
-
* probe passed, the rollout reported success, and every request 404'd.
|
|
23593
|
-
*
|
|
23594
|
-
* Kubernetes only lets `env` shadow `envFrom` for names it **lists**, so
|
|
23595
|
-
* neutralising one of these means naming it explicitly. An empty value is read
|
|
23596
|
-
* by the runtime as unset, which is why the cloud pins most of them to `""`
|
|
23597
|
-
* rather than to a value: the entry exists to take the decision away from the
|
|
23598
|
-
* project, not to make it here.
|
|
23599
|
-
*/
|
|
23600
|
-
var TOPOLOGY_ENV_VARS = [
|
|
23601
|
-
"REBASE_ROLE",
|
|
23602
|
-
"REBASE_FUNCTIONS_ONLY",
|
|
23603
|
-
"REBASE_FUNCTIONS_EXCLUDE",
|
|
23604
|
-
"REBASE_FUNCTIONS_UPSTREAM",
|
|
23605
|
-
"REBASE_CRON_SCHEDULER",
|
|
23606
|
-
"REBASE_JOB_WORKERS",
|
|
23607
|
-
"REBASE_RLS_AUDIT",
|
|
23608
|
-
"REBASE_MCP_ENABLED",
|
|
23609
|
-
"REBASE_MIGRATE_ON_BOOT",
|
|
23610
|
-
"TRUSTED_PROXY_HOPS",
|
|
23611
|
-
"REBASE_RATE_LIMIT_STORE",
|
|
23612
|
-
"REBASE_REQUIRE_SCHEMA_MATCH"
|
|
23613
|
-
];
|
|
23614
|
-
/** Whether a variable name is one the deployer owns rather than the project. */
|
|
23615
|
-
function isTopologyEnvVar(name) {
|
|
23616
|
-
return TOPOLOGY_ENV_VARS.includes(name);
|
|
23617
|
-
}
|
|
23618
|
-
/**
|
|
23619
|
-
* Seconds to keep answering after Kubernetes decides to remove this pod.
|
|
23620
|
-
*
|
|
23621
|
-
* `installShutdownHandlers` drains on SIGTERM — it stops the scheduler, tears
|
|
23622
|
-
* down realtime and closes the HTTP server, finishing what is in flight. What
|
|
23623
|
-
* it cannot do is stop *new* requests arriving: kubelet sends SIGTERM and the
|
|
23624
|
-
* endpoint controller removes the pod from its Service **concurrently**, so for
|
|
23625
|
-
* as long as endpoint removal takes to propagate, the ingress is still routing
|
|
23626
|
-
* to a process that has already stopped accepting connections.
|
|
23627
|
-
*
|
|
23628
|
-
* A `preStop` sleep is the only thing that orders those two. The pod keeps
|
|
23629
|
-
* serving for this long *before* SIGTERM is sent, which is time the ingress
|
|
23630
|
-
* uses to stop sending it anything.
|
|
23631
|
-
*
|
|
23632
|
-
* Anything greater than zero fixes the ordering; five seconds is what the
|
|
23633
|
-
* control plane has run in production.
|
|
23634
|
-
*/
|
|
23635
|
-
var RUNTIME_PRESTOP_DRAIN_SECONDS = 5;
|
|
23636
|
-
/**
|
|
23637
|
-
* The floor for `terminationGracePeriodSeconds`.
|
|
23638
|
-
*
|
|
23639
|
-
* The pod must outlive `preStop` *plus* the drain that follows it, or kubelet
|
|
23640
|
-
* SIGKILLs mid-drain and the graceful shutdown was decoration. The drain's own
|
|
23641
|
-
* default is 15s (`ShutdownHandlerOptions.timeoutMs`), and Kubernetes' default
|
|
23642
|
-
* grace period is 30s — so the stock configuration has room, and this exists to
|
|
23643
|
-
* say how much before someone raises the drain.
|
|
23644
|
-
*/
|
|
23645
|
-
var RUNTIME_MIN_TERMINATION_GRACE_SECONDS = 20;
|
|
23646
|
-
/**
|
|
23647
|
-
* How long a deployment must let this runtime take to answer for the first time.
|
|
23648
|
-
*
|
|
23649
|
-
* Nothing answers until boot is finished. `runFromBundle` binds the socket
|
|
23650
|
-
* **last** — after the bundle is read, the drivers connect and, on the process
|
|
23651
|
-
* that owns it, the schema DDL runs (`boot.ts`, "schema DDL happens during
|
|
23652
|
-
* boot, above"). So the gap between the container starting and `/livez`
|
|
23653
|
-
* answering is a whole provisioning run, not a framework warming up.
|
|
23654
|
-
*
|
|
23655
|
-
* A deployment with no startup probe measures that gap with its *liveness*
|
|
23656
|
-
* probe instead, and liveness restarts the container. On the control plane's
|
|
23657
|
-
* settings that is 20s of grace plus three 20s failures — 80 seconds — after
|
|
23658
|
-
* which a slow first boot is killed and retried, and each retry starts from the
|
|
23659
|
-
* beginning. It does not converge; it loops, and the logs show a pod that never
|
|
23660
|
-
* finished starting rather than a database that was slow.
|
|
23661
|
-
*
|
|
23662
|
-
* So a startup probe is not optional here, and its budget is this. A healthy
|
|
23663
|
-
* pod passes it on the first check and nothing is spent.
|
|
23664
|
-
*/
|
|
23665
|
-
var RUNTIME_STARTUP_BUDGET_SECONDS = 300;
|
|
23666
|
-
/** Where a bundle is mounted, and what the runtime is told to read. */
|
|
23667
|
-
var RUNTIME_BUNDLE_MOUNT = "/bundle";
|
|
23668
|
-
//#endregion
|
|
23669
|
-
export { ACCOUNT_SCOPED_STORAGE_BASES, ApiError, BATCH_REF_KEY, BlockedUrlError, BundleError, CONCURRENT_DDL_SQLSTATES, CollectionConfigError, CronScheduler, DEFAULT_DRIVER_ID, DEFAULT_MAX_FILE_SIZE, DEFAULT_STORAGE_ID, DOCUMENT_MIME_TYPES, DefaultDriverRegistry, DefaultStorageRegistry, ETAG_HEADER, FIELD_OPERATORS, GCSStorageController, IF_MATCH_HEADER, IMAGE_MIME_TYPES, LocalStorageController, MetricsRegistry, RUNTIME_BUNDLE_MOUNT, RUNTIME_HEALTH_PATH, RUNTIME_LIVENESS_PATH, RUNTIME_MIN_TERMINATION_GRACE_SECONDS, RUNTIME_PRESTOP_DRAIN_SECONDS, RUNTIME_PROBE_PATHS, RUNTIME_STARTUP_BUDGET_SECONDS, RawHtml, S3StorageController, SMTPEmailService, StoragePolicyError, TOPOLOGY_ENV_VARS, TransformCache, TusHandler, UPLOAD_COLLECTION_FIELD, UPLOAD_PROPERTY_FIELD, UnknownStorageSourceError, WEBHOOK_DELIVERY_TASK, WebhookDispatcher, _resetRebaseMock, _setRebaseMock, activeDevEmailSink, applyCollectionDefaults, assertAllowedOutboundUrl, assertCollectionConfigs, assertDistinctSuffixes, assertEmailLinkBases, assertEveryKindBindable, assertFieldOpsValid, assertIfMatch, assertNoFieldOpsOnCreate, assertUploadWithinPropertyLimits, assertWriteRequestValid, authJwt, authRoles, authUid, blockedAddressReason, bootFromBundle, classifySurface, cleanupDevPortFile, clearActiveDevEmailSink, compileStoragePolicies, configureJwt, createAppleProvider, createBackupRoutes, createBitbucketProvider, createBuiltinAuthAdapter, createContractRoutes, createCronRoutes, createCronStore, createCustomAuthAdapter, createDdlBootstrapper, createDevEmailSink, createDiscordProvider, createEmailService, createFacebookProvider, createFunctionRoutes, createGitHubProvider, createGitLabProvider, createGoogleProvider, createHistoryRoutes, createJobQueue, createJobStore, createJwksRoutes, createLinkedinProvider, createMetricsMiddleware, createMetricsRoutes, createMicrosoftProvider, createRlsAudit, createSlackProvider, createSourceBundle, createSpotifyProvider, createStorageController, createStorageRoutes, createTwitterProvider, createUnconfiguredEmailService, createUploadConstraintResolver, declaredUniqueTargets, defaultBackoff, defineCron, defineFunction, drainBackgroundWork, envSuffixForKey, errorHandler, escapeHtml, extractLinks, extractUserFromToken, fileTokenAuth, findCollectionConfigProblems, generateSecurePassword, getApiKey, getDriver, getEmailOtpTemplate, getEmailVerificationTemplate, getEnv, getJwks, getMagicLinkTemplate, getPasswordResetTemplate, getRequestId, getRoles, getUser, getUserId, getUserInvitationTemplate, getWelcomeEmailTemplate, hasAsymmetricSigningKey, hasFieldOps, hasRole, hashPassword, html, httpMethodToOperation, identityResolved, implicitDeclaration, initializeDataSource, initializeDataSources, initializeRebaseBackend, installShutdownHandlers, isAcceptedFile, isAdmin, isApiKeyToken, isAuthAdapter, isAuthenticated, isConcurrentDdlRace, isDatabaseAdapter, isDuplicateObjectRace, isLocalhostOrigin, isNodeRuntime, isOperationAllowed, isTopologyEnvVar, isTransformableImage, isUncountedPath, lazyResource, listBackupObjects, listenWithPortRetry, loadBootEnv, loadBundle, loadBundleConfigExports, loadBundleSchema, loadCollectionsFromDirectory, loadCronJobsFromDirectory, loadCronJobsWithDiagnostics, loadEnv, loadFunctionsFromDirectory, loadFunctionsWithDiagnostics, loadUsersCollection, logger, looksLikeFieldOp, oauthCodeFlowSchema, optionalAuth, parseBackupDestination, parseBackupTimestamp, parseFieldOp, parseTransformOptions, pendingBackgroundWork, pkceTokenParams, providerVerifiedEmail, queryTokenAuth, raw, rawQueryLoggingEnabled, readBackupBytes, readBundleManifest, readUploadPropertyContext, rebase, registerDevEmailSink, registerResourceResolver, requireAdmin, requireAuth, requireDriver, requireEnv, requireRole, resolveAuthHooks, resolveAuthOptions, resolveBatchRefs, resolveConflictTarget, resolveCorsOrigin, resolveDataSources, resolveEmailBranding, resolveEmailLinkBase, resolveEmailOptions, resolveRequireAuth, resolveStorageAccessControl, resolveStorageBackend, resolveStorageSources, resourceResolver, resourceResolvers, rowETag, runFromBundle, runtimeKey, safeCompare, schemaDriftRemedy, serveSPA, splitFieldOps, summarize as summarizeRlsScan, transformImage, tryVerifyOidcIdToken, unbindableKinds, unknownKeyPolicyFromEnv, validateApiKey, validateCronExpression, validatePasswordStrength, verifyOidcIdToken, verifyPassword, versionProperty, waitUntil, z };
|
|
23710
|
+
export { ACCOUNT_SCOPED_STORAGE_BASES, ApiError, BATCH_REF_KEY, BlockedUrlError, BundleError, CONCURRENT_DDL_SQLSTATES, CollectionConfigError, CronScheduler, DEFAULT_DRIVER_ID, DEFAULT_MAX_FILE_SIZE, DEFAULT_STORAGE_ID, DOCUMENT_MIME_TYPES, DefaultDriverRegistry, DefaultStorageRegistry, ETAG_HEADER, FIELD_OPERATORS, GCSStorageController, IF_MATCH_HEADER, IMAGE_MIME_TYPES, LocalStorageController, MetricsRegistry, RUNTIME_BUNDLE_MOUNT, RUNTIME_DEFAULT_MAX_BODY_SIZE, RUNTIME_HEALTH_PATH, RUNTIME_LIVENESS_PATH, RUNTIME_MIN_TERMINATION_GRACE_SECONDS, RUNTIME_PRESTOP_DRAIN_SECONDS, RUNTIME_PROBE_PATHS, RUNTIME_STARTUP_BUDGET_SECONDS, RawHtml, S3StorageController, SMTPEmailService, StoragePolicyError, TOPOLOGY_ENV_VARS, TransformCache, TusHandler, UPLOAD_COLLECTION_FIELD, UPLOAD_PROPERTY_FIELD, UnknownStorageSourceError, WEBHOOK_DELIVERY_TASK, WebhookDispatcher, _resetRebaseMock, _setRebaseMock, activeDevEmailSink, applyCollectionDefaults, assertAllowedOutboundUrl, assertCollectionConfigs, assertDistinctSuffixes, assertEmailLinkBases, assertEveryKindBindable, assertFieldOpsValid, assertIfMatch, assertNoFieldOpsOnCreate, assertUploadWithinPropertyLimits, assertWriteRequestValid, authJwt, authRoles, authUid, blockedAddressReason, bootFromBundle, classifySurface, cleanupDevPortFile, clearActiveDevEmailSink, compileStoragePolicies, configureJwt, createAppleProvider, createBackupRoutes, createBitbucketProvider, createBuiltinAuthAdapter, createContractRoutes, createCronRoutes, createCronStore, createCustomAuthAdapter, createDdlBootstrapper, createDevEmailSink, createDiscordProvider, createEmailService, createFacebookProvider, createFunctionRoutes, createGitHubProvider, createGitLabProvider, createGoogleProvider, createHistoryRoutes, createJobQueue, createJobStore, createJwksRoutes, createLinkedinProvider, createMetricsMiddleware, createMetricsRoutes, createMicrosoftProvider, createRlsAudit, createSlackProvider, createSourceBundle, createSpotifyProvider, createStorageController, createStorageRoutes, createTwitterProvider, createUnconfiguredEmailService, createUploadConstraintResolver, declaredErrorAnswer, declaredUniqueTargets, defaultBackoff, defineCron, defineFunction, drainBackgroundWork, envSuffixForKey, errorHandler, escapeHtml, extractLinks, extractUserFromToken, fileTokenAuth, findCollectionConfigProblems, generateSecurePassword, getApiKey, getDriver, getEmailOtpTemplate, getEmailVerificationTemplate, getEnv, getJwks, getMagicLinkTemplate, getPasswordResetTemplate, getRequestId, getRoles, getUser, getUserId, getUserInvitationTemplate, getWelcomeEmailTemplate, hasAsymmetricSigningKey, hasFieldOps, hasRole, hashPassword, html, httpMethodToOperation, identityResolved, implicitDeclaration, initializeDataSource, initializeDataSources, initializeRebaseBackend, installShutdownHandlers, isAcceptedFile, isAdmin, isApiKeyToken, isAuthAdapter, isAuthenticated, isConcurrentDdlRace, isDatabaseAdapter, isDuplicateObjectRace, isLocalhostOrigin, isNodeRuntime, isOperationAllowed, isTopologyEnvVar, isTransformableImage, isUncountedPath, lazyResource, listBackupObjects, listenWithPortRetry, loadBootEnv, loadBundle, loadBundleConfigExports, loadBundleSchema, loadCollectionsFromDirectory, loadCronJobsFromDirectory, loadCronJobsWithDiagnostics, loadEnv, loadFunctionsFromDirectory, loadFunctionsWithDiagnostics, loadUsersCollection, logger, looksLikeFieldOp, oauthCodeFlowSchema, optionalAuth, parseBackupDestination, parseBackupTimestamp, parseFieldOp, parseTransformOptions, pendingBackgroundWork, pkceTokenParams, providerVerifiedEmail, queryTokenAuth, raw, rawQueryLoggingEnabled, readBackupBytes, readBundleManifest, readUploadPropertyContext, rebase, registerDevEmailSink, registerResourceResolver, requireAdmin, requireAuth, requireDriver, requireEnv, requireRole, resolveAuthHooks, resolveAuthOptions, resolveBatchRefs, resolveConflictTarget, resolveCorsOrigin, resolveDataSources, resolveEmailBranding, resolveEmailLinkBase, resolveEmailOptions, resolveRequireAuth, resolveStorageAccessControl, resolveStorageBackend, resolveStorageSources, resourceResolver, resourceResolvers, rowETag, runFromBundle, runtimeKey, safeCompare, schemaDriftRemedy, serveSPA, splitFieldOps, summarize as summarizeRlsScan, transformImage, tryVerifyOidcIdToken, unbindableKinds, unknownKeyPolicyFromEnv, validateApiKey, validateCronExpression, validatePasswordStrength, verifyOidcIdToken, verifyPassword, versionProperty, waitUntil, z };
|
|
23670
23711
|
|
|
23671
23712
|
//# sourceMappingURL=index.es.js.map
|