@luckystack/core 0.7.5 → 0.8.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (28) hide show
  1. package/CHANGELOG.md +20 -0
  2. package/CLAUDE.md +5 -2
  3. package/dist/{chunk-DVGSWLLS.js → chunk-6HGH6S36.js} +2 -2
  4. package/dist/{chunk-DVGSWLLS.js.map → chunk-6HGH6S36.js.map} +1 -1
  5. package/dist/{chunk-AFG7KKMS.js → chunk-6K7MAXMT.js} +48 -33
  6. package/dist/{chunk-AFG7KKMS.js.map → chunk-6K7MAXMT.js.map} +1 -1
  7. package/dist/{chunk-J3UOWYT4.js → chunk-I4R7DMIX.js} +2 -2
  8. package/dist/{chunk-LTCDQU5Z.js → chunk-RH65K3US.js} +4 -1
  9. package/dist/{chunk-LTCDQU5Z.js.map → chunk-RH65K3US.js.map} +1 -1
  10. package/dist/client.d.ts +25 -4
  11. package/dist/client.js +223 -15
  12. package/dist/client.js.map +1 -1
  13. package/dist/{config-Dl2CBINY.d.ts → config-DV8DGNt6.d.ts} +7 -1
  14. package/dist/config.d.ts +2 -2
  15. package/dist/config.js +2 -2
  16. package/dist/index.d.ts +26 -6
  17. package/dist/index.js +61 -5
  18. package/dist/index.js.map +1 -1
  19. package/dist/{pageRouteValidation-CWkPqPW3.d.ts → pageRouteValidation-bz2LFVQq.d.ts} +7 -7
  20. package/dist/{projectConfig-DBLSQ3NY.js → projectConfig-PB5VK5AD.js} +2 -2
  21. package/dist/{sentrySetup-MF6JSVWA.js → sentrySetup-G7NGISBY.js} +3 -3
  22. package/dist/{sessionTypes-Dzen_rPK.d.ts → sessionTypes-iyUMf_pf.d.ts} +12 -1
  23. package/docs/app-bootstrap.md +14 -0
  24. package/docs/session-types.md +1 -1
  25. package/package.json +1 -1
  26. /package/dist/{chunk-J3UOWYT4.js.map → chunk-I4R7DMIX.js.map} +0 -0
  27. /package/dist/{projectConfig-DBLSQ3NY.js.map → projectConfig-PB5VK5AD.js.map} +0 -0
  28. /package/dist/{sentrySetup-MF6JSVWA.js.map → sentrySetup-G7NGISBY.js.map} +0 -0
package/dist/index.js CHANGED
@@ -49,7 +49,7 @@ import {
49
49
  tryCatchSync,
50
50
  validatePagePath,
51
51
  waitForSocket
52
- } from "./chunk-AFG7KKMS.js";
52
+ } from "./chunk-6K7MAXMT.js";
53
53
  import {
54
54
  getDeployConfig,
55
55
  getServicesConfig,
@@ -59,7 +59,7 @@ import {
59
59
  registerDeployConfig,
60
60
  registerSecretsResolvedListener,
61
61
  registerServicesConfig
62
- } from "./chunk-DVGSWLLS.js";
62
+ } from "./chunk-6HGH6S36.js";
63
63
  import {
64
64
  DEFAULT_REDACTED_LOG_KEYS,
65
65
  DEPTH_TRUNCATED_PLACEHOLDER,
@@ -93,7 +93,7 @@ import {
93
93
  startSpan,
94
94
  startSpanAcrossTrackers,
95
95
  startSpanHandle
96
- } from "./chunk-J3UOWYT4.js";
96
+ } from "./chunk-I4R7DMIX.js";
97
97
  import {
98
98
  DEFAULT_PROJECT_CONFIG,
99
99
  createRegistry,
@@ -103,7 +103,7 @@ import {
103
103
  isPlainObject,
104
104
  isProjectConfigRegistered,
105
105
  registerProjectConfig
106
- } from "./chunk-LTCDQU5Z.js";
106
+ } from "./chunk-RH65K3US.js";
107
107
 
108
108
  // src/escapeHtml.ts
109
109
  var HTML_ESCAPE_MAP = {
@@ -864,6 +864,7 @@ import { randomUUID } from "crypto";
864
864
  var BOOT_KEY_PREFIX = "luckystack:boot:";
865
865
  var DEFAULT_BOOT_KEY_TTL_SECONDS = 3600;
866
866
  var getBootKeyTtlSeconds = () => getDeployConfig().routing?.bootKeyTtlSeconds ?? DEFAULT_BOOT_KEY_TTL_SECONDS;
867
+ var getBootUuidRefreshIntervalMs = () => Math.max(100, Math.floor(getBootKeyTtlSeconds() * 1e3 / 3));
867
868
  var resolveEnvKey = () => {
868
869
  return process.env.LUCKYSTACK_ENV ?? process.env.NODE_ENV ?? "development";
869
870
  };
@@ -877,6 +878,45 @@ var readBootUuid = async (envKey) => {
877
878
  const key = envKey ?? resolveEnvKey();
878
879
  return redis.get(`${BOOT_KEY_PREFIX}${key}`);
879
880
  };
881
+ var refreshBootUuid = async (envKey) => {
882
+ const key = envKey ?? resolveEnvKey();
883
+ const refreshed = await redis.expire(`${BOOT_KEY_PREFIX}${key}`, getBootKeyTtlSeconds());
884
+ if (refreshed === 0) await writeBootUuid(key);
885
+ };
886
+ var startBootUuidHeartbeat = (envKey) => {
887
+ const key = envKey ?? resolveEnvKey();
888
+ let stopped = false;
889
+ let timer = null;
890
+ const schedule = () => {
891
+ if (stopped) return;
892
+ timer = setTimeout(() => {
893
+ timer = null;
894
+ void refreshBootUuid(key).then(
895
+ () => {
896
+ schedule();
897
+ },
898
+ (error) => {
899
+ getLogger().error(
900
+ `[boot-uuid] failed to refresh ${BOOT_KEY_PREFIX}${key}; readiness may degrade if the TTL expires`,
901
+ error instanceof Error ? error : new Error(String(error))
902
+ );
903
+ schedule();
904
+ }
905
+ );
906
+ }, getBootUuidRefreshIntervalMs());
907
+ timer.unref();
908
+ };
909
+ schedule();
910
+ return {
911
+ stop: () => {
912
+ stopped = true;
913
+ if (timer !== null) {
914
+ clearTimeout(timer);
915
+ timer = null;
916
+ }
917
+ }
918
+ };
919
+ };
880
920
 
881
921
  // src/synchronizedEnvHashes.ts
882
922
  import { createHash, createHmac } from "crypto";
@@ -1825,6 +1865,16 @@ var isPrimitiveMatch = (type, value) => {
1825
1865
  if (type === "Date") return value instanceof Date || typeof value === "string" && !Number.isNaN(Date.parse(value));
1826
1866
  return false;
1827
1867
  };
1868
+ var parseFiniteNumericLiteral = (type) => {
1869
+ const normalized = type.replaceAll("_", "");
1870
+ const decimal = /^-?(?:\d+(?:\.\d*)?|\.\d+)(?:e[+-]?\d+)?$/i;
1871
+ const nonDecimal = /^-?0(?:x[\da-f]+|b[01]+|o[0-7]+)$/i;
1872
+ if (!decimal.test(normalized) && !nonDecimal.test(normalized)) return null;
1873
+ const negative = normalized.startsWith("-");
1874
+ const unsigned = negative ? normalized.slice(1) : normalized;
1875
+ const parsed = Number(unsigned) * (negative ? -1 : 1);
1876
+ return Number.isFinite(parsed) ? parsed : null;
1877
+ };
1828
1878
  var isPrimitiveType = (type) => {
1829
1879
  return ["string", "number", "boolean", "true", "false", "null", "undefined", "Date"].includes(type);
1830
1880
  };
@@ -1903,6 +1953,10 @@ var validateType = (typeText, value, path4, depth = 0) => {
1903
1953
  const literal = type.slice(1, -1);
1904
1954
  return value === literal ? { status: "success" } : { status: "error", message: `${path4} should equal ${literal}` };
1905
1955
  }
1956
+ const numericLiteral = parseFiniteNumericLiteral(type);
1957
+ if (numericLiteral !== null) {
1958
+ return typeof value === "number" && value === numericLiteral ? { status: "success" } : { status: "error", message: `${path4} should equal ${type}` };
1959
+ }
1906
1960
  if (isPrimitiveMatch(type, value)) {
1907
1961
  return { status: "success" };
1908
1962
  }
@@ -2003,7 +2057,7 @@ var validateInputByType = async ({
2003
2057
  return { status: "success" };
2004
2058
  }
2005
2059
  if (resolveEnvKey() === "production") {
2006
- const { getProjectConfig: getProjectConfig2 } = await import("./projectConfig-DBLSQ3NY.js");
2060
+ const { getProjectConfig: getProjectConfig2 } = await import("./projectConfig-PB5VK5AD.js");
2007
2061
  if (getProjectConfig2().validation.runtimeMode === "off") {
2008
2062
  return { status: "success" };
2009
2063
  }
@@ -2349,6 +2403,7 @@ export {
2349
2403
  rebuildDefaultRedisClient,
2350
2404
  recordMetricAcrossTrackers,
2351
2405
  redis,
2406
+ refreshBootUuid,
2352
2407
  registerApiAbortController,
2353
2408
  registerApiMethodMap,
2354
2409
  registerAvatarConfig,
@@ -2418,6 +2473,7 @@ export {
2418
2473
  sleep,
2419
2474
  socket,
2420
2475
  socketEventNames,
2476
+ startBootUuidHeartbeat,
2421
2477
  startSpan,
2422
2478
  startSpanAcrossTrackers,
2423
2479
  startSpanHandle,