modelence 0.20.0 → 0.21.0-ml.dev.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.
Files changed (55) hide show
  1. package/dist/chunk-3MACQTB3.js +3 -0
  2. package/dist/chunk-3MACQTB3.js.map +1 -0
  3. package/dist/chunk-AIQUY53H.js +3 -0
  4. package/dist/chunk-AIQUY53H.js.map +1 -0
  5. package/dist/chunk-CIPGQ6HR.js +2 -0
  6. package/dist/chunk-CIPGQ6HR.js.map +1 -0
  7. package/dist/chunk-ENHGU3X4.js +3 -0
  8. package/dist/chunk-ENHGU3X4.js.map +1 -0
  9. package/dist/chunk-L4HA6WDS.js +2 -0
  10. package/dist/chunk-L4HA6WDS.js.map +1 -0
  11. package/dist/{chunk-SNADMLAT.js → chunk-NPAFMBRP.js} +2 -2
  12. package/dist/{chunk-SNADMLAT.js.map → chunk-NPAFMBRP.js.map} +1 -1
  13. package/dist/chunk-OMZEJGMN.js +2 -0
  14. package/dist/{chunk-YRR32LTF.js.map → chunk-OMZEJGMN.js.map} +1 -1
  15. package/dist/chunk-WAYG54Z2.js +35 -0
  16. package/dist/chunk-WAYG54Z2.js.map +1 -0
  17. package/dist/client.d.ts +48 -22
  18. package/dist/client.js +1 -1
  19. package/dist/index.d.ts +1 -1
  20. package/dist/{package-KMCDUMYP.js → package-TMVJXVUQ.js} +2 -2
  21. package/dist/{package-KMCDUMYP.js.map → package-TMVJXVUQ.js.map} +1 -1
  22. package/dist/render-6BXZA746.js +2 -0
  23. package/dist/{render-STDR67WK.js.map → render-6BXZA746.js.map} +1 -1
  24. package/dist/renderApp-GNV3UFAD.js +2 -0
  25. package/dist/{renderApp-ZDNATNY6.js.map → renderApp-GNV3UFAD.js.map} +1 -1
  26. package/dist/server-LJUY2OWZ.js +2 -0
  27. package/dist/{server-KXQSHJIH.js.map → server-LJUY2OWZ.js.map} +1 -1
  28. package/dist/server.d.ts +48 -10
  29. package/dist/server.js +1 -1
  30. package/dist/telemetry.d.ts +6 -1
  31. package/dist/telemetry.js +1 -1
  32. package/dist/transport-RAUEYIZV.js +2 -0
  33. package/dist/{transport-W6JIYZKZ.js.map → transport-RAUEYIZV.js.map} +1 -1
  34. package/dist/{types-B_R3eHmq.d.ts → types-B8uEAj0y.d.ts} +1 -1
  35. package/dist/{types-_BTBqn8b.d.ts → types-XQVUUWNK.d.ts} +1 -1
  36. package/dist/types.d.ts +2 -2
  37. package/package.json +1 -1
  38. package/dist/chunk-7LPSX5A6.js +0 -3
  39. package/dist/chunk-7LPSX5A6.js.map +0 -1
  40. package/dist/chunk-FCIMWI4V.js +0 -3
  41. package/dist/chunk-FCIMWI4V.js.map +0 -1
  42. package/dist/chunk-N7XT2ULQ.js +0 -2
  43. package/dist/chunk-N7XT2ULQ.js.map +0 -1
  44. package/dist/chunk-SD3ERG2G.js +0 -3
  45. package/dist/chunk-SD3ERG2G.js.map +0 -1
  46. package/dist/chunk-YLLX26A4.js +0 -2
  47. package/dist/chunk-YLLX26A4.js.map +0 -1
  48. package/dist/chunk-YRR32LTF.js +0 -2
  49. package/dist/chunk-ZBCGBZPH.js +0 -29
  50. package/dist/chunk-ZBCGBZPH.js.map +0 -1
  51. package/dist/render-STDR67WK.js +0 -2
  52. package/dist/renderApp-ZDNATNY6.js +0 -2
  53. package/dist/server-KXQSHJIH.js +0 -2
  54. package/dist/transport-W6JIYZKZ.js +0 -2
  55. package/dist/types-DLDzAym7.d.ts +0 -8
package/dist/client.d.ts CHANGED
@@ -1,9 +1,8 @@
1
- import { b as ClientInfo, c as ConfigKey, d as ConfigParams, A as AnyMethodShape, V as ValueType, e as ConfigType, O as OAuthProvider, W as WebsocketClientProvider, f as ClientChannel } from './types-B_R3eHmq.js';
1
+ import { b as ClientInfo, c as ConfigKey, d as ConfigParams, A as AnyMethodShape, V as ValueType, e as ConfigType, O as OAuthProvider, W as WebsocketClientProvider, f as ClientChannel } from './types-B8uEAj0y.js';
2
2
  import { ObjectId } from 'mongodb';
3
3
  import React, { ReactNode } from 'react';
4
4
  import * as react_jsx_runtime from 'react/jsx-runtime';
5
5
  import { QueryClient, DehydratedState } from '@tanstack/react-query';
6
- import { F as FileVisibility } from './types-DLDzAym7.js';
7
6
  import 'http';
8
7
  import 'express';
9
8
 
@@ -424,13 +423,57 @@ declare function logout(): Promise<void>;
424
423
  declare function sendResetPasswordToken(options: {
425
424
  email: string;
426
425
  }): Promise<void>;
426
+ /**
427
+ * Send a magic sign-in link to the given email address.
428
+ *
429
+ * Works for both existing and new users: clicking the emailed link signs the
430
+ * user in, creating the account first if the email is unknown. A generic
431
+ * response is always returned to avoid leaking account information.
432
+ *
433
+ * @example
434
+ * ```ts
435
+ * await sendMagicLink({ email: 'user@example.com' });
436
+ * ```
437
+ * @param options.email - The email address to send the magic link to.
438
+ */
439
+ declare function sendMagicLink(options: {
440
+ email: string;
441
+ }): Promise<void>;
442
+ /**
443
+ * Complete a magic link sign-in.
444
+ *
445
+ * Call this from the page the magic link landing route redirects to. The
446
+ * token is exchanged server-side via an httpOnly cookie, so no arguments are
447
+ * needed. Signs the user in — creating the account first when the email is
448
+ * not registered yet — and returns the logged-in user.
449
+ *
450
+ * @example
451
+ * ```ts
452
+ * const user = await loginWithMagicLink();
453
+ * ```
454
+ */
455
+ declare function loginWithMagicLink(): Promise<{
456
+ id: string;
457
+ handle: string;
458
+ roles: string[];
459
+ hasRole: (role: string) => boolean;
460
+ requireRole: (role: string) => void;
461
+ firstName?: string;
462
+ lastName?: string;
463
+ avatarUrl?: string;
464
+ } | null>;
427
465
  /**
428
466
  * Reset password.
429
- * @param options.token - The password reset token.
467
+ *
468
+ * The token is normally exchanged server-side via an httpOnly cookie, so the
469
+ * client only submits the new password. Pass `token` only for legacy flows
470
+ * that still carry it client-side (deprecated).
471
+ *
472
+ * @param options.token - Reset token (optional; read from the httpOnly cookie when omitted).
430
473
  * @param options.password - The new password.
431
474
  */
432
475
  declare function resetPassword(options: {
433
- token: string;
476
+ token?: string;
434
477
  password: string;
435
478
  }): Promise<void>;
436
479
  /**
@@ -471,23 +514,6 @@ declare function startWebsockets(props?: {
471
514
 
472
515
  declare function getLocalStorageSession(): any;
473
516
 
474
- type UploadFileParams = {
475
- filePath: string;
476
- contentType: string;
477
- visibility: FileVisibility;
478
- };
479
- type UploadFileResult = {
480
- filePath: string;
481
- };
482
- declare function uploadFile(file: File | Blob, { filePath, contentType, visibility }: UploadFileParams): Promise<UploadFileResult>;
483
- declare function deleteFile(filePath: string): Promise<void>;
484
- declare function downloadFile(filePath: string): Promise<{
485
- downloadUrl: string;
486
- }>;
487
- declare function getFileUrl(filePath: string): Promise<{
488
- url: string;
489
- }>;
490
-
491
517
  declare const AppProvider: any;
492
518
 
493
- export { AppProvider, type CallMethodOptions, ClientChannel, type ClientConfig, type MethodArgs, MethodError, ModelenceQueryClient, type ModelenceQueryKey, ModelenceQueryProvider, type UserInfo, ValueType, callMethod, configureClient, connectModelenceQueryClient, createClientModule, createQueryKey, deleteFile, disconnectModelenceQueryClient, downloadFile, getConfig, getFileUrl, getLocalStorageSession, getWebsocketClientProvider, linkOAuthProvider, loginWithPassword, logout, modelenceLiveQuery, modelenceMutation, modelenceQuery, renderApp, resendEmailVerification, resetPassword, sendResetPasswordToken, setWebsocketClientProvider, signupWithPassword, startWebsockets, subscribeLiveQuery, systemConfig, unlinkOAuthProvider, updateProfile, uploadFile, useSession, verifyEmail };
519
+ export { AppProvider, type CallMethodOptions, ClientChannel, type ClientConfig, type MethodArgs, MethodError, ModelenceQueryClient, type ModelenceQueryKey, ModelenceQueryProvider, type UserInfo, ValueType, callMethod, configureClient, connectModelenceQueryClient, createClientModule, createQueryKey, disconnectModelenceQueryClient, getConfig, getLocalStorageSession, getWebsocketClientProvider, linkOAuthProvider, loginWithMagicLink, loginWithPassword, logout, modelenceLiveQuery, modelenceMutation, modelenceQuery, renderApp, resendEmailVerification, resetPassword, sendMagicLink, sendResetPasswordToken, setWebsocketClientProvider, signupWithPassword, startWebsockets, subscribeLiveQuery, systemConfig, unlinkOAuthProvider, updateProfile, useSession, verifyEmail };
package/dist/client.js CHANGED
@@ -1,2 +1,2 @@
1
- export{j as AppProvider,e as ClientChannel,a as createClientModule,g as deleteFile,h as downloadFile,i as getFileUrl,d as renderApp,b as systemConfig,f as uploadFile}from'./chunk-N7XT2ULQ.js';export{i as ModelenceQueryClient,n as ModelenceQueryProvider,f as connectModelenceQueryClient,m as createQueryKey,h as disconnectModelenceQueryClient,d as getWebsocketClientProvider,k as modelenceLiveQuery,l as modelenceMutation,j as modelenceQuery,c as setWebsocketClientProvider,e as startWebsockets,b as subscribeLiveQuery}from'./chunk-YRR32LTF.js';export{q as MethodError,t as callMethod,b as configureClient,v as getConfig,a as getLocalStorageSession,l as linkOAuthProvider,e as loginWithPassword,i as logout,h as resendEmailVerification,k as resetPassword,j as sendResetPasswordToken,d as signupWithPassword,m as unlinkOAuthProvider,f as updateProfile,E as useSession,g as verifyEmail}from'./chunk-YLLX26A4.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=client.js.map
1
+ export{f as AppProvider,e as ClientChannel,a as createClientModule,d as renderApp,b as systemConfig}from'./chunk-CIPGQ6HR.js';export{i as ModelenceQueryClient,n as ModelenceQueryProvider,f as connectModelenceQueryClient,m as createQueryKey,h as disconnectModelenceQueryClient,d as getWebsocketClientProvider,k as modelenceLiveQuery,l as modelenceMutation,j as modelenceQuery,c as setWebsocketClientProvider,e as startWebsockets,b as subscribeLiveQuery}from'./chunk-OMZEJGMN.js';export{s as MethodError,v as callMethod,b as configureClient,x as getConfig,a as getLocalStorageSession,n as linkOAuthProvider,l as loginWithMagicLink,e as loginWithPassword,i as logout,h as resendEmailVerification,m as resetPassword,k as sendMagicLink,j as sendResetPasswordToken,d as signupWithPassword,o as unlinkOAuthProvider,f as updateProfile,G as useSession,g as verifyEmail}from'./chunk-L4HA6WDS.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=client.js.map
2
2
  //# sourceMappingURL=client.js.map
package/dist/index.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- export { C as ConfigSchema, W as WebsocketClientProvider, a as WebsocketServerProvider } from './types-B_R3eHmq.js';
1
+ export { C as ConfigSchema, W as WebsocketClientProvider, a as WebsocketServerProvider } from './types-B8uEAj0y.js';
2
2
  export { M as ModelenceConfig } from './index-CgNFVSg6.js';
3
3
  import 'http';
4
4
  import 'mongodb';
@@ -1,2 +1,2 @@
1
- export{l as author,i as bin,n as bugs,s as default,q as dependencies,d as description,p as devDependencies,g as exports,h as files,o as homepage,m as license,e as main,b as name,r as peerDependencies,k as repository,j as scripts,a as type,f as types,c as version}from'./chunk-FCIMWI4V.js';//# sourceMappingURL=package-KMCDUMYP.js.map
2
- //# sourceMappingURL=package-KMCDUMYP.js.map
1
+ export{l as author,i as bin,n as bugs,s as default,q as dependencies,d as description,p as devDependencies,g as exports,h as files,o as homepage,m as license,e as main,b as name,r as peerDependencies,k as repository,j as scripts,a as type,f as types,c as version}from'./chunk-3MACQTB3.js';//# sourceMappingURL=package-TMVJXVUQ.js.map
2
+ //# sourceMappingURL=package-TMVJXVUQ.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":[],"names":[],"mappings":"","file":"package-KMCDUMYP.js"}
1
+ {"version":3,"sources":[],"names":[],"mappings":"","file":"package-TMVJXVUQ.js"}
@@ -0,0 +1,2 @@
1
+ import {a,b,c}from'./chunk-NPAFMBRP.js';import'./chunk-AIQUY53H.js';import'./chunk-ENHGU3X4.js';import {a as a$1,n}from'./chunk-OMZEJGMN.js';import {E,w,F}from'./chunk-L4HA6WDS.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';import {renderToPipeableStream}from'react-dom/server';import {Writable}from'stream';import {QueryClient,dehydrate}from'@tanstack/react-query';import {jsx}from'react/jsx-runtime';var J=()=>{let r=c();return r?F(r.session.user):null},M=r=>{let o=c();if(o)return o.session.configs[r]?.value};function D(){E(J),w(M);}async function X(r){let{callContext:o,loadingElement:C,routesElement:S,router:u,location:x,onShellReady:E,onError:b$1}=r;D();let i=await a("_system.session.init",{},o),n$1=new QueryClient({defaultOptions:{queries:{retry:false,gcTime:0}}}),O=u?u({children:S,location:x}):S,Q=jsx(a$1,{loadingElement:C,children:jsx(n,{client:n$1,children:O})}),l=null;await new Promise((s,d)=>{b({callContext:o,queryClient:n$1,session:{user:i.user,configs:i.configs??{}}},()=>{let e=renderToPipeableStream(Q,{onShellReady(){l=e,E?.(),s(e);},onShellError(t){d(t);},onError(t){b$1?.(t);}});return e});});let a$2=null,_=s=>new Promise((d,e)=>{if(!l){e(new Error("SSR stream was not initialized"));return}let t=new Writable({write(m,c,I){s.write(m,N=>I(N??void 0));},final(m){try{let c=dehydrate(n$1);a$2=JSON.stringify(c);}finally{n$1.clear();}m(),d();}});t.on("error",e),s.on("error",e),l.pipe(t);});return {sessionState:JSON.stringify({session:i}),pipe:_,getQueryState:()=>{if(a$2===null)throw new Error("getQueryState() called before stream finished");return a$2}}}export{X as renderSsrTreeStream};//# sourceMappingURL=render-6BXZA746.js.map
2
+ //# sourceMappingURL=render-6BXZA746.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/ssr/render.tsx"],"names":["sessionResolver","ctx","getSsrContext","_parseSessionUser","configResolver","key","ensureSsrResolversInstalled","_setSsrSessionResolver","_setSsrConfigResolver","renderSsrTreeStream","options","callContext","loadingElement","routesElement","router","location","onShellReady","onError","sessionPayload","callInProcessMethod","queryClient","QueryClient","routedTree","tree","jsx","AppProvider","ModelenceQueryProvider","streamRef","resolve","reject","runWithSsrContext","stream","renderToPipeableStream","error","queryStateJson","pipe","destination","passthrough","Writable","chunk","_encoding","callback","err","dehydratedState","dehydrate"],"mappings":"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","file":"render-STDR67WK.js","sourcesContent":["import React from 'react';\nimport { renderToPipeableStream, type PipeableStream } from 'react-dom/server';\nimport { Writable } from 'node:stream';\nimport { QueryClient, dehydrate, type DehydratedState } from '@tanstack/react-query';\nimport { AppProvider } from '../client/AppProvider';\nimport { ModelenceQueryProvider } from '../client/queryProvider';\nimport { getSsrContext, runWithSsrContext } from './context';\nimport { callInProcessMethod } from './callInProcess';\nimport type { Context } from '../methods/types';\nimport {\n _parseSessionUser,\n _setSsrSessionResolver,\n type SessionInitPayload,\n} from '../client/session';\nimport { _setSsrConfigResolver } from '../config/client';\nimport type { ConfigKey, Configs } from '../config/types';\nimport type { SsrRouter } from '../client/renderApp';\n\nconst sessionResolver = () => {\n const ctx = getSsrContext();\n if (!ctx) {\n return null;\n }\n return _parseSessionUser(ctx.session.user);\n};\n\nconst configResolver = (key: ConfigKey) => {\n const ctx = getSsrContext();\n if (!ctx) {\n return undefined;\n }\n return ctx.session.configs[key]?.value;\n};\n\nfunction ensureSsrResolversInstalled() {\n _setSsrSessionResolver(sessionResolver);\n _setSsrConfigResolver(configResolver);\n}\n\nexport type SsrRenderOptions = {\n callContext: Context;\n loadingElement: React.ReactNode;\n routesElement: React.ReactNode;\n router?: SsrRouter;\n location?: string;\n};\n\nexport type SsrStreamHandle = {\n /** Session bootstrap payload — inline before the shell flushes. */\n sessionState: string;\n /** Pipe React's HTML into `destination`. Resolves when streaming finishes. */\n pipe: (destination: Writable) => Promise<void>;\n /** Dehydrated query state. Only call after `pipe()` resolves. */\n getQueryState: () => string;\n};\n\nexport type SsrStreamOptions = SsrRenderOptions & {\n /** Fires when the shell is flushed; caller writes prelude + state here. */\n onShellReady?: () => void;\n /** Non-fatal SSR errors (Suspense fallbacks, etc.). */\n onError?: (error: unknown) => void;\n};\n\nexport async function renderSsrTreeStream(options: SsrStreamOptions): Promise<SsrStreamHandle> {\n const { callContext, loadingElement, routesElement, router, location, onShellReady, onError } =\n options;\n\n ensureSsrResolversInstalled();\n\n const sessionPayload = await callInProcessMethod<SessionInitPayload>(\n '_system.session.init',\n {},\n callContext\n );\n\n const queryClient = new QueryClient({\n defaultOptions: {\n queries: {\n retry: false,\n gcTime: 0,\n },\n },\n });\n\n const routedTree = router ? router({ children: routesElement, location }) : routesElement;\n const tree = (\n <AppProvider loadingElement={loadingElement}>\n <ModelenceQueryProvider client={queryClient}>{routedTree}</ModelenceQueryProvider>\n </AppProvider>\n );\n\n let streamRef: PipeableStream | null = null;\n // Resolves with the stream once React renders above-fallback content;\n // rejects on shell errors so the caller can fall back to a static response.\n const shellReady = new Promise<PipeableStream>((resolve, reject) => {\n // Run the render inside the SSR context so components can resolve\n // session/config/query state from the per-request scope.\n runWithSsrContext(\n {\n callContext,\n queryClient,\n session: {\n user: sessionPayload.user,\n configs: (sessionPayload.configs as Configs) ?? {},\n },\n },\n () => {\n const stream = renderToPipeableStream(tree, {\n onShellReady() {\n streamRef = stream;\n onShellReady?.();\n resolve(stream);\n },\n onShellError(error) {\n reject(error);\n },\n onError(error) {\n onError?.(error);\n },\n });\n return stream;\n }\n );\n });\n\n // Await so shell errors surface before the caller starts piping.\n await shellReady;\n\n let queryStateJson: string | null = null;\n\n const pipe = (destination: Writable): Promise<void> => {\n return new Promise((resolve, reject) => {\n if (!streamRef) {\n reject(new Error('SSR stream was not initialized'));\n return;\n }\n\n // react-dom calls `destination.end()` when done. The caller still needs\n // to write the epilogue + query state, so wrap with a passthrough whose\n // `final()` resolves the pipe promise without closing the response.\n const passthrough = new Writable({\n write(chunk, _encoding, callback) {\n destination.write(chunk, (err) => callback(err ?? undefined));\n },\n final(callback) {\n try {\n const dehydratedState: DehydratedState = dehydrate(queryClient);\n queryStateJson = JSON.stringify(dehydratedState);\n } finally {\n queryClient.clear();\n }\n callback();\n resolve();\n },\n });\n\n passthrough.on('error', reject);\n destination.on('error', reject);\n\n streamRef.pipe(passthrough);\n });\n };\n\n return {\n sessionState: JSON.stringify({ session: sessionPayload }),\n pipe,\n getQueryState: () => {\n if (queryStateJson === null) {\n throw new Error('getQueryState() called before stream finished');\n }\n return queryStateJson;\n },\n };\n}\n"]}
1
+ {"version":3,"sources":["../src/ssr/render.tsx"],"names":["sessionResolver","ctx","getSsrContext","_parseSessionUser","configResolver","key","ensureSsrResolversInstalled","_setSsrSessionResolver","_setSsrConfigResolver","renderSsrTreeStream","options","callContext","loadingElement","routesElement","router","location","onShellReady","onError","sessionPayload","callInProcessMethod","queryClient","QueryClient","routedTree","tree","jsx","AppProvider","ModelenceQueryProvider","streamRef","resolve","reject","runWithSsrContext","stream","renderToPipeableStream","error","queryStateJson","pipe","destination","passthrough","Writable","chunk","_encoding","callback","err","dehydratedState","dehydrate"],"mappings":"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","file":"render-6BXZA746.js","sourcesContent":["import React from 'react';\nimport { renderToPipeableStream, type PipeableStream } from 'react-dom/server';\nimport { Writable } from 'node:stream';\nimport { QueryClient, dehydrate, type DehydratedState } from '@tanstack/react-query';\nimport { AppProvider } from '../client/AppProvider';\nimport { ModelenceQueryProvider } from '../client/queryProvider';\nimport { getSsrContext, runWithSsrContext } from './context';\nimport { callInProcessMethod } from './callInProcess';\nimport type { Context } from '../methods/types';\nimport {\n _parseSessionUser,\n _setSsrSessionResolver,\n type SessionInitPayload,\n} from '../client/session';\nimport { _setSsrConfigResolver } from '../config/client';\nimport type { ConfigKey, Configs } from '../config/types';\nimport type { SsrRouter } from '../client/renderApp';\n\nconst sessionResolver = () => {\n const ctx = getSsrContext();\n if (!ctx) {\n return null;\n }\n return _parseSessionUser(ctx.session.user);\n};\n\nconst configResolver = (key: ConfigKey) => {\n const ctx = getSsrContext();\n if (!ctx) {\n return undefined;\n }\n return ctx.session.configs[key]?.value;\n};\n\nfunction ensureSsrResolversInstalled() {\n _setSsrSessionResolver(sessionResolver);\n _setSsrConfigResolver(configResolver);\n}\n\nexport type SsrRenderOptions = {\n callContext: Context;\n loadingElement: React.ReactNode;\n routesElement: React.ReactNode;\n router?: SsrRouter;\n location?: string;\n};\n\nexport type SsrStreamHandle = {\n /** Session bootstrap payload — inline before the shell flushes. */\n sessionState: string;\n /** Pipe React's HTML into `destination`. Resolves when streaming finishes. */\n pipe: (destination: Writable) => Promise<void>;\n /** Dehydrated query state. Only call after `pipe()` resolves. */\n getQueryState: () => string;\n};\n\nexport type SsrStreamOptions = SsrRenderOptions & {\n /** Fires when the shell is flushed; caller writes prelude + state here. */\n onShellReady?: () => void;\n /** Non-fatal SSR errors (Suspense fallbacks, etc.). */\n onError?: (error: unknown) => void;\n};\n\nexport async function renderSsrTreeStream(options: SsrStreamOptions): Promise<SsrStreamHandle> {\n const { callContext, loadingElement, routesElement, router, location, onShellReady, onError } =\n options;\n\n ensureSsrResolversInstalled();\n\n const sessionPayload = await callInProcessMethod<SessionInitPayload>(\n '_system.session.init',\n {},\n callContext\n );\n\n const queryClient = new QueryClient({\n defaultOptions: {\n queries: {\n retry: false,\n gcTime: 0,\n },\n },\n });\n\n const routedTree = router ? router({ children: routesElement, location }) : routesElement;\n const tree = (\n <AppProvider loadingElement={loadingElement}>\n <ModelenceQueryProvider client={queryClient}>{routedTree}</ModelenceQueryProvider>\n </AppProvider>\n );\n\n let streamRef: PipeableStream | null = null;\n // Resolves with the stream once React renders above-fallback content;\n // rejects on shell errors so the caller can fall back to a static response.\n const shellReady = new Promise<PipeableStream>((resolve, reject) => {\n // Run the render inside the SSR context so components can resolve\n // session/config/query state from the per-request scope.\n runWithSsrContext(\n {\n callContext,\n queryClient,\n session: {\n user: sessionPayload.user,\n configs: (sessionPayload.configs as Configs) ?? {},\n },\n },\n () => {\n const stream = renderToPipeableStream(tree, {\n onShellReady() {\n streamRef = stream;\n onShellReady?.();\n resolve(stream);\n },\n onShellError(error) {\n reject(error);\n },\n onError(error) {\n onError?.(error);\n },\n });\n return stream;\n }\n );\n });\n\n // Await so shell errors surface before the caller starts piping.\n await shellReady;\n\n let queryStateJson: string | null = null;\n\n const pipe = (destination: Writable): Promise<void> => {\n return new Promise((resolve, reject) => {\n if (!streamRef) {\n reject(new Error('SSR stream was not initialized'));\n return;\n }\n\n // react-dom calls `destination.end()` when done. The caller still needs\n // to write the epilogue + query state, so wrap with a passthrough whose\n // `final()` resolves the pipe promise without closing the response.\n const passthrough = new Writable({\n write(chunk, _encoding, callback) {\n destination.write(chunk, (err) => callback(err ?? undefined));\n },\n final(callback) {\n try {\n const dehydratedState: DehydratedState = dehydrate(queryClient);\n queryStateJson = JSON.stringify(dehydratedState);\n } finally {\n queryClient.clear();\n }\n callback();\n resolve();\n },\n });\n\n passthrough.on('error', reject);\n destination.on('error', reject);\n\n streamRef.pipe(passthrough);\n });\n };\n\n return {\n sessionState: JSON.stringify({ session: sessionPayload }),\n pipe,\n getQueryState: () => {\n if (queryStateJson === null) {\n throw new Error('getQueryState() called before stream finished');\n }\n return queryStateJson;\n },\n };\n}\n"]}
@@ -0,0 +1,2 @@
1
+ export{c as _getSsrSnapshot,d as renderApp}from'./chunk-CIPGQ6HR.js';import'./chunk-OMZEJGMN.js';import'./chunk-L4HA6WDS.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=renderApp-GNV3UFAD.js.map
2
+ //# sourceMappingURL=renderApp-GNV3UFAD.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":[],"names":[],"mappings":"","file":"renderApp-ZDNATNY6.js"}
1
+ {"version":3,"sources":[],"names":[],"mappings":"","file":"renderApp-GNV3UFAD.js"}
@@ -0,0 +1,2 @@
1
+ export{g as getCallContext,f as startServer}from'./chunk-WAYG54Z2.js';import'./chunk-3MACQTB3.js';import'./chunk-AIQUY53H.js';import'./chunk-MIRF7FP3.js';import'./chunk-ENHGU3X4.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=server-LJUY2OWZ.js.map
2
+ //# sourceMappingURL=server-LJUY2OWZ.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":[],"names":[],"mappings":"","file":"server-KXQSHJIH.js"}
1
+ {"version":3,"sources":[],"names":[],"mappings":"","file":"server-LJUY2OWZ.js"}
package/dist/server.d.ts CHANGED
@@ -1,13 +1,12 @@
1
1
  import { A as AppServer } from './index-CgNFVSg6.js';
2
- import { d as ConfigParams, C as ConfigSchema, A as AnyMethodShape, S as ServerChannel, V as ValueType, g as SignupProps, U as UpdateProfileProps, h as AuthSuccessProps, i as AuthErrorProps, j as ConnectionInfo, k as User, l as OAuthErrorInfo, a as WebsocketServerProvider, R as RoleDefinition, M as MethodDefinition, m as Session, c as ConfigKey, n as AppConfig, o as UserInfo, p as Role } from './types-B_R3eHmq.js';
3
- export { e as ConfigType } from './types-B_R3eHmq.js';
4
- import { S as Store, R as RouteDefinition, C as CronJobInputParams, a as RateLimitRule, E as EmailProvider, b as RateLimitType, I as InferDocumentType, c as EmailPayload } from './types-_BTBqn8b.js';
5
- export { H as HttpMethod, d as RouteHandler, e as RouteParams, f as RouteResponse, s as schema } from './types-_BTBqn8b.js';
2
+ import { d as ConfigParams, C as ConfigSchema, A as AnyMethodShape, S as ServerChannel, V as ValueType, g as SignupProps, U as UpdateProfileProps, h as AuthSuccessProps, i as AuthErrorProps, j as ConnectionInfo, k as User, l as OAuthErrorInfo, a as WebsocketServerProvider, R as RoleDefinition, M as MethodDefinition, m as Session, c as ConfigKey, n as AppConfig, o as UserInfo, p as Role } from './types-B8uEAj0y.js';
3
+ export { e as ConfigType } from './types-B8uEAj0y.js';
4
+ import { S as Store, R as RouteDefinition, C as CronJobInputParams, a as RateLimitRule, E as EmailProvider, b as RateLimitType, I as InferDocumentType, c as EmailPayload } from './types-XQVUUWNK.js';
5
+ export { H as HttpMethod, d as RouteHandler, e as RouteParams, f as RouteResponse, s as schema } from './types-XQVUUWNK.js';
6
6
  import { ObjectId as ObjectId$1 } from 'mongodb';
7
7
  export { ObjectId } from 'mongodb';
8
8
  import * as zod from 'zod';
9
9
  import { Response } from 'express';
10
- import { F as FileVisibility, G as GetUploadUrlResult } from './types-DLDzAym7.js';
11
10
  import 'http';
12
11
 
13
12
  /** Array of Store instances that will be provisioned when the module is loaded */
@@ -127,6 +126,16 @@ type EmailConfig = {
127
126
  }) => string;
128
127
  redirectUrl?: string;
129
128
  };
129
+ magicLink?: {
130
+ subject?: string;
131
+ template?: (props: {
132
+ name: string;
133
+ email: string;
134
+ magicLinkUrl: string;
135
+ }) => string;
136
+ /** SPA page the landing route redirects to; it must call `loginWithMagicLink()`. */
137
+ redirectUrl?: string;
138
+ };
130
139
  emailVerifiedRedirectUrl?: string;
131
140
  };
132
141
 
@@ -208,6 +217,8 @@ type AuthRateLimitsConfig = {
208
217
  verification?: AuthRateLimitOverride[];
209
218
  /** Rate limits for password reset requests. */
210
219
  passwordReset?: AuthRateLimitOverride[];
220
+ /** Rate limits for magic link requests. */
221
+ magicLink?: AuthRateLimitOverride[];
211
222
  };
212
223
  type GenerateHandleProps = {
213
224
  email: string;
@@ -227,8 +238,8 @@ type BeforeSignupProps = {
227
238
  firstName?: string;
228
239
  lastName?: string;
229
240
  handle?: string;
230
- /** Provider that initiated the signup. Currently only `'email'`. */
231
- provider: 'email';
241
+ /** Provider that initiated the signup: `'email'` or `'magicLink'`. */
242
+ provider: 'email' | 'magicLink';
232
243
  connectionInfo?: ConnectionInfo;
233
244
  };
234
245
  /**
@@ -317,8 +328,8 @@ type AuthConfig = {
317
328
  * email-domain verification service) without having to disable the built-in
318
329
  * disposable-email check.
319
330
  *
320
- * Currently only invoked for `'email'` provider signups. OAuth signups are
321
- * not gated because OAuth providers (Google, GitHub, etc.) do not issue
331
+ * Invoked for `'email'` and `'magicLink'` provider signups. OAuth signups
332
+ * are not gated because OAuth providers (Google, GitHub, etc.) do not issue
322
333
  * disposable accounts.
323
334
  */
324
335
  onBeforeSignup?: (props: BeforeSignupProps) => void | Promise<void>;
@@ -367,6 +378,26 @@ type AuthConfig = {
367
378
  login?: AuthOption;
368
379
  /** @deprecated Use {@link AuthConfig.onAfterSignup} and {@link AuthConfig.onSignupError} instead. */
369
380
  signup?: AuthOption;
381
+ /**
382
+ * Enables passwordless magic link authentication. Disabled by default —
383
+ * magic link doubles as sign-up (an unknown email gets an account created
384
+ * when the link is used), so it must be opted into explicitly.
385
+ *
386
+ * Requires an email provider and delivery settings under the `email` option
387
+ * (see `EmailConfig.magicLink`).
388
+ *
389
+ * @example
390
+ * ```typescript
391
+ * startApp({
392
+ * auth: {
393
+ * magicLink: { enabled: true },
394
+ * },
395
+ * });
396
+ * ```
397
+ */
398
+ magicLink?: {
399
+ enabled?: boolean;
400
+ };
370
401
  /**
371
402
  * Controls how OAuth providers handle existing accounts with matching email.
372
403
  * - 'manual' (default): Returns an error when an OAuth login matches an existing email.
@@ -927,6 +958,13 @@ declare function authenticate(authToken: string | null): Promise<{
927
958
 
928
959
  declare function sendEmail(payload: EmailPayload): Promise<void> | undefined;
929
960
 
961
+ type FileVisibility = 'public' | 'private';
962
+ type GetUploadUrlResult = {
963
+ url: string;
964
+ fields: Record<string, string>;
965
+ filePath: string;
966
+ };
967
+
930
968
  type DownloadFileResult = {
931
969
  downloadUrl: string;
932
970
  };
@@ -942,4 +980,4 @@ declare function deleteFile(filePath: string): Promise<void>;
942
980
  declare function downloadFile(filePath: string): Promise<DownloadFileResult>;
943
981
  declare function getFileUrl(filePath: string): Promise<GetFileUrlResult>;
944
982
 
945
- export { type AppOptions, type AuthConfig, type AuthOption, type AuthRateLimitOverride, type AuthRateLimitsConfig, type CloudBackendConnectResponse, ConfigSchema, CronJobInputParams, FileVisibility, LiveData, type LiveDataConfig, type LiveQueryCleanup, type LiveQueryPublish, type LiveQueryWatch, Module, RateLimitRule, RateLimitType, RoleDefinition, RouteDefinition, type SecurityConfig, ServerChannel, Store, UserInfo, ValueType, authenticate, clearSessionUser, consumeRateLimit, createQuery, createSession, sessionsCollection as dbSessions, usersCollection as dbUsers, deleteFile, deleteUser, disableUser, downloadFile, getConfig, getFileUrl, getUploadUrl, invalidateAllUserSessions, obtainSession, sendEmail, setAuthTokenCookie, setSessionUser, startApp };
983
+ export { type AppOptions, type AuthConfig, type AuthOption, type AuthRateLimitOverride, type AuthRateLimitsConfig, type CloudBackendConnectResponse, ConfigSchema, CronJobInputParams, type FileVisibility, LiveData, type LiveDataConfig, type LiveQueryCleanup, type LiveQueryPublish, type LiveQueryWatch, Module, RateLimitRule, RateLimitType, RoleDefinition, RouteDefinition, type SecurityConfig, ServerChannel, Store, UserInfo, ValueType, authenticate, clearSessionUser, consumeRateLimit, createQuery, createSession, sessionsCollection as dbSessions, usersCollection as dbUsers, deleteFile, deleteUser, disableUser, downloadFile, getConfig, getFileUrl, getUploadUrl, invalidateAllUserSessions, obtainSession, sendEmail, setAuthTokenCookie, setSessionUser, startApp };
package/dist/server.js CHANGED
@@ -1,2 +1,2 @@
1
- export{m as ObjectId,k as ServerChannel,a as consumeRateLimit,c as deleteFile,j as deleteUser,i as disableUser,d as downloadFile,e as getFileUrl,b as getUploadUrl,l as sendEmail,h as startApp}from'./chunk-ZBCGBZPH.js';import'./chunk-FCIMWI4V.js';export{v as LiveData,a as Module,b as Store,u as authenticate,i as clearSessionUser,x as createQuery,k as createSession,f as dbSessions,o as dbUsers,j as invalidateAllUserSessions,g as obtainSession,c as schema,l as setAuthTokenCookie,h as setSessionUser}from'./chunk-SD3ERG2G.js';import'./chunk-MIRF7FP3.js';export{a as getConfig}from'./chunk-7LPSX5A6.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=server.js.map
1
+ export{m as ObjectId,k as ServerChannel,a as consumeRateLimit,c as deleteFile,j as deleteUser,i as disableUser,d as downloadFile,e as getFileUrl,b as getUploadUrl,l as sendEmail,h as startApp}from'./chunk-WAYG54Z2.js';import'./chunk-3MACQTB3.js';export{w as LiveData,a as Module,b as Store,v as authenticate,i as clearSessionUser,y as createQuery,k as createSession,f as dbSessions,o as dbUsers,j as invalidateAllUserSessions,g as obtainSession,c as schema,l as setAuthTokenCookie,h as setSessionUser}from'./chunk-AIQUY53H.js';import'./chunk-MIRF7FP3.js';export{a as getConfig}from'./chunk-ENHGU3X4.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';//# sourceMappingURL=server.js.map
2
2
  //# sourceMappingURL=server.js.map
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Deep-copies `value`, replacing any {@link SENSITIVE_KEYS} match with
3
+ * `'[redacted]'`. Non-object values pass through unchanged.
4
+ */
5
+ declare function redactSensitive(value: unknown): unknown;
1
6
  declare function logDebug(message: string, args: object): void;
2
7
  declare function logInfo(message: string, args: object): void;
3
8
  declare function logError(message: string, args: object): void;
@@ -8,4 +13,4 @@ interface WrappedTransaction {
8
13
  declare function startTransaction(type: 'method' | 'cron' | 'ai' | 'custom' | 'route', name: string, context?: Record<string, unknown>): WrappedTransaction;
9
14
  declare function captureError(error: Error): void;
10
15
 
11
- export { captureError, logDebug, logError, logInfo, startTransaction };
16
+ export { captureError, logDebug, logError, logInfo, redactSensitive, startTransaction };
package/dist/telemetry.js CHANGED
@@ -1,2 +1,2 @@
1
- export{m as captureError,i as logDebug,k as logError,j as logInfo,l as startTransaction}from'./chunk-7LPSX5A6.js';//# sourceMappingURL=telemetry.js.map
1
+ export{n as captureError,j as logDebug,l as logError,k as logInfo,i as redactSensitive,m as startTransaction}from'./chunk-ENHGU3X4.js';//# sourceMappingURL=telemetry.js.map
2
2
  //# sourceMappingURL=telemetry.js.map
@@ -0,0 +1,2 @@
1
+ import {c,a}from'./chunk-NPAFMBRP.js';import'./chunk-AIQUY53H.js';import'./chunk-ENHGU3X4.js';import {u,t}from'./chunk-L4HA6WDS.js';import'./chunk-5M6FUMUK.js';import'./chunk-DO5TZLF5.js';function d(){return u(async(t$1,r)=>{let o=c();return o?a(t$1,r,o.callContext):t(t$1,r)})}export{d as installSsrCallMethodTransport};//# sourceMappingURL=transport-RAUEYIZV.js.map
2
+ //# sourceMappingURL=transport-RAUEYIZV.js.map
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/ssr/transport.ts"],"names":["installSsrCallMethodTransport","setCallMethodTransport","methodName","args","ssrCtx","getSsrContext","callInProcessMethod","defaultCallMethodTransport"],"mappings":"4LAcO,SAASA,CAAAA,EAA4C,CAC1D,OAAOC,CAAAA,CAAuB,MAAUC,EAAoBC,GAAAA,GAAqB,CAC/E,IAAMC,CAAAA,CAASC,CAAAA,EAAc,CAC7B,OAAKD,CAAAA,CAIEE,CAAAA,CAAuBJ,CAAAA,CAAYC,GAAAA,CAAMC,CAAAA,CAAO,WAAW,CAAA,CAHzDG,CAAAA,CAA8BL,CAAAA,CAAYC,GAAI,CAIzD,CAAC,CACH","file":"transport-W6JIYZKZ.js","sourcesContent":["import {\n setCallMethodTransport,\n defaultCallMethodTransport,\n type MethodArgs,\n} from '../client/method';\nimport { callInProcessMethod } from './callInProcess';\nimport { getSsrContext } from './context';\n\n/**\n * Routes `callMethod` through `runMethod` in-process during an active SSR\n * render. Outside a render (e.g. server-side `callMethod` from jobs or other\n * non-render code) there is no request context, so it falls back to the\n * default HTTP transport — installing SSR must not break those call sites.\n */\nexport function installSsrCallMethodTransport(): () => void {\n return setCallMethodTransport(async <T>(methodName: string, args: MethodArgs) => {\n const ssrCtx = getSsrContext();\n if (!ssrCtx) {\n return defaultCallMethodTransport<T>(methodName, args);\n }\n\n return callInProcessMethod<T>(methodName, args, ssrCtx.callContext);\n });\n}\n"]}
1
+ {"version":3,"sources":["../src/ssr/transport.ts"],"names":["installSsrCallMethodTransport","setCallMethodTransport","methodName","args","ssrCtx","getSsrContext","callInProcessMethod","defaultCallMethodTransport"],"mappings":"4LAcO,SAASA,CAAAA,EAA4C,CAC1D,OAAOC,CAAAA,CAAuB,MAAUC,IAAoBC,CAAAA,GAAqB,CAC/E,IAAMC,CAAAA,CAASC,CAAAA,EAAc,CAC7B,OAAKD,CAAAA,CAIEE,CAAAA,CAAuBJ,GAAAA,CAAYC,CAAAA,CAAMC,CAAAA,CAAO,WAAW,CAAA,CAHzDG,CAAAA,CAA8BL,GAAAA,CAAYC,CAAI,CAIzD,CAAC,CACH","file":"transport-RAUEYIZV.js","sourcesContent":["import {\n setCallMethodTransport,\n defaultCallMethodTransport,\n type MethodArgs,\n} from '../client/method';\nimport { callInProcessMethod } from './callInProcess';\nimport { getSsrContext } from './context';\n\n/**\n * Routes `callMethod` through `runMethod` in-process during an active SSR\n * render. Outside a render (e.g. server-side `callMethod` from jobs or other\n * non-render code) there is no request context, so it falls back to the\n * default HTTP transport — installing SSR must not break those call sites.\n */\nexport function installSsrCallMethodTransport(): () => void {\n return setCallMethodTransport(async <T>(methodName: string, args: MethodArgs) => {\n const ssrCtx = getSsrContext();\n if (!ssrCtx) {\n return defaultCallMethodTransport<T>(methodName, args);\n }\n\n return callInProcessMethod<T>(methodName, args, ssrCtx.callContext);\n });\n}\n"]}
@@ -150,7 +150,7 @@ type RoleDefinition = {
150
150
  };
151
151
  declare const SUPPORTED_OAUTH_PROVIDERS: readonly ["google", "github"];
152
152
  type OAuthProvider = (typeof SUPPORTED_OAUTH_PROVIDERS)[number];
153
- type AuthProvider = OAuthProvider | 'email';
153
+ type AuthProvider = OAuthProvider | 'email' | 'magicLink';
154
154
  type AuthSuccessProps = {
155
155
  provider: AuthProvider;
156
156
  user: User;
@@ -1,5 +1,5 @@
1
1
  import './index-CgNFVSg6.js';
2
- import { q as Context } from './types-B_R3eHmq.js';
2
+ import { q as Context } from './types-B8uEAj0y.js';
3
3
  import * as mongodb from 'mongodb';
4
4
  import { WithId, IndexDescription, SearchIndexDescription, MongoClient, Collection, FilterOperators, Document, FindOptions, ObjectId, SortDirection, OptionalUnlessRequiredId, ClientSession, InsertOneResult, InsertManyResult, UpdateFilter, UpdateResult, DeleteResult, FindOneAndUpdateOptions, FindOneAndDeleteOptions, WithoutId, FindOneAndReplaceOptions, ReplaceOptions, DistinctOptions, ChangeStreamOptions, ChangeStream, AggregateOptions, AggregationCursor, AnyBulkWriteOperation, BulkWriteResult } from 'mongodb';
5
5
  import { z, ZodNumber, ZodArray } from 'zod';
package/dist/types.d.ts CHANGED
@@ -1,6 +1,6 @@
1
1
  export { A as AppServer, a as AppServerInitOptions, E as ExpressMiddleware, M as ModelenceConfig } from './index-CgNFVSg6.js';
2
- export { A as AnyMethodShape, n as AppConfig, r as Args, i as AuthErrorProps, s as AuthProvider, h as AuthSuccessProps, b as ClientInfo, c as ConfigKey, d as ConfigParams, C as ConfigSchema, e as ConfigType, t as Configs, j as ConnectionInfo, q as Context, D as DefaultRoles, H as Handler, u as Method, M as MethodDefinition, v as MethodType, l as OAuthErrorInfo, O as OAuthProvider, P as Permission, p as Role, R as RoleDefinition, w as SUPPORTED_OAUTH_PROVIDERS, m as Session, g as SignupProps, U as UpdateProfileProps, k as User, x as UserEmail, o as UserInfo, V as ValueType, W as WebsocketClientProvider, a as WebsocketServerProvider } from './types-B_R3eHmq.js';
3
- export { B as BodyConfig, g as CronJob, C as CronJobInputParams, h as CronJobMetadata, i as EmailAttachment, c as EmailPayload, E as EmailProvider, j as ExpressHandler, H as HttpMethod, I as InferDocumentType, M as ModelSchema, a as RateLimitRule, b as RateLimitType, R as RouteDefinition, d as RouteHandler, k as RouteHandlers, e as RouteParams, f as RouteResponse, s as schema } from './types-_BTBqn8b.js';
2
+ export { A as AnyMethodShape, n as AppConfig, r as Args, i as AuthErrorProps, s as AuthProvider, h as AuthSuccessProps, b as ClientInfo, c as ConfigKey, d as ConfigParams, C as ConfigSchema, e as ConfigType, t as Configs, j as ConnectionInfo, q as Context, D as DefaultRoles, H as Handler, u as Method, M as MethodDefinition, v as MethodType, l as OAuthErrorInfo, O as OAuthProvider, P as Permission, p as Role, R as RoleDefinition, w as SUPPORTED_OAUTH_PROVIDERS, m as Session, g as SignupProps, U as UpdateProfileProps, k as User, x as UserEmail, o as UserInfo, V as ValueType, W as WebsocketClientProvider, a as WebsocketServerProvider } from './types-B8uEAj0y.js';
3
+ export { B as BodyConfig, g as CronJob, C as CronJobInputParams, h as CronJobMetadata, i as EmailAttachment, c as EmailPayload, E as EmailProvider, j as ExpressHandler, H as HttpMethod, I as InferDocumentType, M as ModelSchema, a as RateLimitRule, b as RateLimitType, R as RouteDefinition, d as RouteHandler, k as RouteHandlers, e as RouteParams, f as RouteResponse, s as schema } from './types-XQVUUWNK.js';
4
4
  import 'express';
5
5
  import 'http';
6
6
  import 'mongodb';
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "type": "module",
3
3
  "name": "modelence",
4
- "version": "0.20.0",
4
+ "version": "0.21.0-ml.dev.1",
5
5
  "description": "The Node.js Framework for Real-Time MongoDB Apps",
6
6
  "main": "dist/index.js",
7
7
  "types": "dist/global.d.ts",
@@ -1,3 +0,0 @@
1
- import N from'elastic-apm-node';import A from'winston';import {ElasticsearchTransport}from'winston-elasticsearch';import c from'process';var g={},L={},x=false;function p(t){return L[t]?.value??g[t]?.default}function G(){if(!x)throw new Error("Config is not initialized: an attempt was made to access configs before they were loaded");return Object.fromEntries(Object.entries(g).filter(([t,e])=>e.isPublic).map(([t,e])=>[t,{key:t,type:e.type,value:L[t]?.value??e.default}]))}function V(t){t.forEach(({key:e,type:o,value:r})=>{!e.toLowerCase().startsWith("_system.")&&!g[e]||(L[e]={key:e,type:o,value:r});}),x=true;}function $(){return g}function F(t){Object.entries(t).forEach(([e,o])=>{let{type:r,isPublic:n}=o;if(r==="secret"&&n)throw new Error(`Config ${e} with type "secret" cannot be public`)}),g=t;}var i={stdout:[{log:"",timestamp:null}],stderr:[{log:"",timestamp:null}]},z=1;function S({elasticCloudId:t,elasticApiKey:e}){let o=c.stdout.write,r=c.stderr.write;c.stdout.write=function(n,...s){return h(n.toString(),i.stdout),o.call(c.stdout,n,...s)},c.stderr.write=function(n,...s){return h(n.toString(),i.stderr),r.call(c.stderr,n,...s)},I();}function h(t,e){if(t.length===0)return;let o=new Date;for(let r=0;r<t.length;r++){let n=e[e.length-1];n.timestamp||(n.timestamp=o,n.sequenceId=z++),t[r]===`
2
- `?e.push({log:"",timestamp:null}):n.log+=t[r];}}async function O(){let t=i.stdout.slice(0,-1);i.stdout=[i.stdout[i.stdout.length-1]];let e=i.stderr.slice(0,-1);i.stderr=[i.stderr[i.stderr.length-1]],t.forEach(({log:o,timestamp:r,sequenceId:n})=>{b(o,{timestamp:r,source:"console",sequenceId:n});}),e.forEach(({log:o,timestamp:r,sequenceId:n})=>{v(o,{timestamp:r,source:"console",sequenceId:n});});}function I(){setTimeout(()=>{O(),I();},1e3);}var l=null;function Y(){}function Z(t){l=Object.assign({},l,t);}function T(){return l?.environmentId}function K(){return l?.appAlias}function M(){return l?.environmentAlias}function j(){return l?.telemetry?.serviceName}function a(){return !!l?.telemetry?.isEnabled}var R=false,d=null,m=null,st=async()=>{if(R)throw new Error('Metrics are already initialized, duplicate "initMetrics" call received');R=true,a()&&await D();};async function D(){let t=p("_system.elastic.apmEndpoint"),e=p("_system.elastic.cloudId"),o=p("_system.elastic.apiKey"),r=K()??"unknown",n=M()??"unknown",s=T()??"unknown",f=j();d=N.start({serviceName:f,apiKey:o,serverUrl:t,transactionSampleRate:1,centralConfig:false,globalLabels:{modelenceEnv:"dev",appEnv:"dev",environmentId:s,appAlias:r,environmentAlias:n}});let u=new ElasticsearchTransport({apm:d,level:"debug",clientOpts:{cloud:{id:e},auth:{apiKey:o},requestTimeout:1e4,tls:{rejectUnauthorized:false}},bufferLimit:1e3,silent:false});u.on("error",_=>{console.error("Elasticsearch Transport Error:",_);}),m=A.createLogger({level:"debug",defaultMeta:{serviceName:f},format:A.format.combine(A.format.json()),transports:[u]}),S({elasticCloudId:e,elasticApiKey:o});}function C(){if(!d)throw new Error("APM is not initialized");return d}function E(){return m!==null}function y(){if(!m)throw new Error("Logger is not initialized");return m}function w(){let t="";return a()||(t="info"),process.env.MODELENCE_LOG_LEVEL||t}function W(t,e){a()&&E()&&y().debug(t,e),w()==="debug"&&console.debug(t,e);}function b(t,e){a()&&E()&&y().info(t,e),["debug","info"].includes(w())&&console.info(t,e);}function v(t,e){a()&&E()&&y().error(t,e),["debug","info","error"].includes(w())&&console.error(t,e);}function q(t,e,o){if(!a())return {end:()=>{},setContext:()=>{}};let r=C(),n=r.startTransaction(e,t);return o&&r.setCustomContext(o),{end:(s,{endTime:f,context:u}={})=>{u&&r.setCustomContext(u),n.end(s,f);},setContext:s=>{r.setCustomContext(s);}}}function U(t){if(!a()){console.error(t);return}C().captureError(t);}export{p as a,G as b,V as c,$ as d,F as e,Y as f,Z as g,st as h,W as i,b as j,v as k,q as l,U as m};//# sourceMappingURL=chunk-7LPSX5A6.js.map
3
- //# sourceMappingURL=chunk-7LPSX5A6.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/config/server.ts","../src/app/loggerProcess.ts","../src/app/state.ts","../src/app/metrics.ts","../src/telemetry/index.ts"],"names":["configSchema","config","isInitialized","getConfig","key","getPublicConfigs","_","schema","loadConfigs","configs","type","value","getSchema","setSchema","isPublic","buffer","sequenceId","startLoggerProcess","_elasticCloudId","_elasticApiKey","originalStdoutWrite","process","originalStderrWrite","chunk","args","addToBuffer","loopSendLogs","timestamp","i","current","sendLogs","stdoutLogs","stderrLogs","log","logInfo","logError","metadata","markAppStarted","setMetadata","_metadata","getEnvironmentId","getAppAlias","getEnvironmentAlias","getTelemetryServiceName","isTelemetryEnabled","apm","logger","initMetrics","initElasticApm","elasticApmEndpoint","elasticCloudId","elasticApiKey","appAlias","environmentAlias","environmentId","serviceName","elasticApm","esTransport","ElasticsearchTransport","error","winston","getApm","isLoggerReady","getLogger","getLogLevel","defaultLoglevel","logDebug","message","startTransaction","name","context","transaction","result","endTime","captureError"],"mappings":"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","file":"chunk-7LPSX5A6.js","sourcesContent":["import { AppConfig, ConfigKey, ConfigSchema } from './types';\n\nlet configSchema: ConfigSchema = {};\nlet config: Record<ConfigKey, AppConfig> = {};\nlet isInitialized = false;\n\n/**\n * @sidebarTitle getConfig (server)\n *\n * @param key - The configuration key to retrieve\n * @returns The configuration value (string, number, or boolean)\n *\n * @example\n * ```ts\n * import { getConfig } from 'modelence/server';\n *\n * // Get the site URL\n * const siteUrl = getConfig('_system.site.url');\n * ```\n *\n * Set via environment variable:\n * ```bash\n * MODELENCE_SITE_URL=https://myapp.com\n * ```\n *\n * @example\n * ```ts\n * import { getConfig } from 'modelence/server';\n *\n * // Get the current environment (e.g., 'development', 'staging', 'production')\n * const env = getConfig('_system.env');\n *\n * if (env === 'production') {\n * // Enable production features\n * }\n * ```\n *\n * Set via environment variable:\n * ```bash\n * MODELENCE_SITE_ENV=production\n * ```\n */\nexport function getConfig(key: ConfigKey): string | number | boolean | undefined {\n return config[key]?.value ?? configSchema[key]?.default;\n}\n\nexport function getPublicConfigs() {\n if (!isInitialized) {\n throw new Error(\n 'Config is not initialized: an attempt was made to access configs before they were loaded'\n );\n }\n\n return Object.fromEntries(\n Object.entries(configSchema)\n .filter(([_, schema]) => schema.isPublic)\n .map(([key, schema]) => {\n return [\n key,\n {\n key,\n type: schema.type,\n value: config[key]?.value ?? schema.default,\n },\n ];\n })\n );\n}\n\nexport function loadConfigs(configs: AppConfig[]) {\n configs.forEach(({ key, type, value }) => {\n const isSystemConfig = key.toLowerCase().startsWith('_system.');\n\n if (!isSystemConfig && !configSchema[key]) {\n // Ignore unknown configs\n return;\n }\n\n config[key] = {\n key,\n type,\n value,\n };\n });\n\n isInitialized = true;\n}\n\nexport function getSchema() {\n return configSchema;\n}\n\nexport function setSchema(schema: ConfigSchema) {\n // TODO: more validation on the schema structure\n Object.entries(schema).forEach(([key, value]) => {\n const { type, isPublic } = value;\n\n if (type === 'secret' && isPublic) {\n throw new Error(`Config ${key} with type \"secret\" cannot be public`);\n }\n });\n\n configSchema = schema;\n}\n","// import { spawn } from 'child_process';\n// import { fileURLToPath } from 'url';\n// import { dirname, join } from 'path';\nimport { logInfo, logError } from '@/telemetry';\nimport process from 'process';\n\ntype LogEntry = { log: string; timestamp: Date | null; sequenceId?: number };\ntype LogBuffer = LogEntry[];\n\nconst buffer: { stdout: LogBuffer; stderr: LogBuffer } = {\n stdout: [{ log: '', timestamp: null }],\n stderr: [{ log: '', timestamp: null }],\n};\n\nlet sequenceId = 1;\n\nexport function startLoggerProcess({\n elasticCloudId: _elasticCloudId,\n elasticApiKey: _elasticApiKey,\n}: {\n elasticCloudId: string;\n elasticApiKey: string;\n}) {\n const originalStdoutWrite = process.stdout.write;\n const originalStderrWrite = process.stderr.write;\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n process.stdout.write = function (chunk: string | Uint8Array, ...args: any[]) {\n addToBuffer(chunk.toString(), buffer.stdout);\n return originalStdoutWrite.call(process.stdout, chunk, ...args);\n };\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n process.stderr.write = function (chunk: string | Uint8Array, ...args: any[]) {\n addToBuffer(chunk.toString(), buffer.stderr);\n return originalStderrWrite.call(process.stderr, chunk, ...args);\n };\n\n loopSendLogs();\n\n // const currentFilePath = fileURLToPath(import.meta.url);\n // const projectRoot = dirname(dirname(currentFilePath));\n // const loggerPath = join(projectRoot, 'bin', 'modelence-logger', 'index.js');\n // const logger = spawn(process.execPath, [loggerPath], {\n // env: {\n // NODE_ENV: process.env.NODE_ENV,\n // ELASTIC_CLOUD_ID: elasticCloudId,\n // ELASTIC_API_KEY: elasticApiKey\n // },\n // stdio: ['pipe', 'inherit', 'inherit'],\n // detached: true\n // });\n\n // const originalStdoutWrite = process.stdout.write;\n // const originalStderrWrite = process.stderr.write;\n\n // process.stdout.write = function(chunk: any, ...args: any[]) {\n // logger.stdin.write(chunk);\n // return originalStdoutWrite.apply(process.stdout, [chunk, ...args]);\n // };\n\n // process.stderr.write = function(chunk: any, ...args: any[]) {\n // logger.stdin.write(chunk);\n // return originalStderrWrite.apply(process.stderr, [chunk, ...args]);\n // };\n\n // process.on('exit', () => {\n // process.stdout.write = originalStdoutWrite;\n // process.stderr.write = originalStderrWrite;\n // });\n\n // logger.unref();\n}\n\nfunction addToBuffer(chunk: string, buffer: LogBuffer) {\n if (chunk.length === 0) {\n return;\n }\n\n const timestamp = new Date();\n\n for (let i = 0; i < chunk.length; i++) {\n const current = buffer[buffer.length - 1];\n if (!current.timestamp) {\n current.timestamp = timestamp;\n current.sequenceId = sequenceId++;\n }\n\n if (chunk[i] === '\\n') {\n buffer.push({ log: '', timestamp: null });\n } else {\n current.log += chunk[i];\n }\n }\n}\n\nasync function sendLogs() {\n const stdoutLogs = buffer.stdout.slice(0, -1);\n buffer.stdout = [buffer.stdout[buffer.stdout.length - 1]];\n\n const stderrLogs = buffer.stderr.slice(0, -1);\n buffer.stderr = [buffer.stderr[buffer.stderr.length - 1]];\n\n stdoutLogs.forEach(({ log, timestamp, sequenceId }: LogEntry) => {\n logInfo(log, { timestamp, source: 'console', sequenceId });\n });\n stderrLogs.forEach(({ log, timestamp, sequenceId }: LogEntry) => {\n logError(log, { timestamp, source: 'console', sequenceId });\n });\n}\n\nfunction loopSendLogs() {\n setTimeout(() => {\n void sendLogs();\n loopSendLogs();\n }, 1000);\n}\n","type AppMetadata = {\n environmentId: string;\n appAlias: string;\n environmentAlias: string;\n telemetry: {\n isEnabled: boolean;\n serviceName: string;\n };\n};\n\nlet appStarted = false;\nlet metadata: AppMetadata | null = null;\n\nexport function markAppStarted() {\n appStarted = true;\n}\n\nexport function isAppStarted() {\n return appStarted;\n}\n\nexport function setMetadata(_metadata: AppMetadata) {\n metadata = Object.assign({}, metadata, _metadata);\n}\n\nexport function getEnvironmentId() {\n return metadata?.environmentId;\n}\n\nexport function getAppAlias() {\n return metadata?.appAlias;\n}\n\nexport function getEnvironmentAlias() {\n return metadata?.environmentAlias;\n}\n\nexport function getTelemetryServiceName() {\n return metadata?.telemetry?.serviceName;\n}\n\nexport function isTelemetryEnabled() {\n return Boolean(metadata?.telemetry?.isEnabled);\n}\n","import elasticApm from 'elastic-apm-node';\nimport winston from 'winston';\nimport { ElasticsearchTransport } from 'winston-elasticsearch';\n\nimport { getConfig } from '../config/server';\nimport { startLoggerProcess } from './loggerProcess';\nimport {\n getAppAlias,\n getEnvironmentAlias,\n getEnvironmentId,\n getTelemetryServiceName,\n isTelemetryEnabled,\n} from './state';\n\nlet isInitialized = false;\nlet apm: typeof elasticApm | null = null;\nlet logger: winston.Logger | null = null;\n\nexport const initMetrics = async () => {\n if (isInitialized) {\n throw new Error('Metrics are already initialized, duplicate \"initMetrics\" call received');\n }\n\n isInitialized = true;\n\n if (isTelemetryEnabled()) {\n await initElasticApm();\n }\n};\n\nasync function initElasticApm() {\n const elasticApmEndpoint = getConfig('_system.elastic.apmEndpoint') as string;\n const elasticCloudId = getConfig('_system.elastic.cloudId') as string;\n const elasticApiKey = getConfig('_system.elastic.apiKey') as string;\n\n const appAlias = getAppAlias() ?? 'unknown';\n const environmentAlias = getEnvironmentAlias() ?? 'unknown';\n const environmentId = getEnvironmentId() ?? 'unknown';\n const serviceName = getTelemetryServiceName();\n\n apm = elasticApm.start({\n serviceName,\n apiKey: elasticApiKey,\n serverUrl: elasticApmEndpoint,\n // environment: 'dev',\n transactionSampleRate: 1.0,\n centralConfig: false,\n globalLabels: {\n modelenceEnv: 'dev',\n appEnv: 'dev',\n environmentId,\n appAlias,\n environmentAlias,\n },\n // logLevel: 'debug'\n });\n\n const esTransport = new ElasticsearchTransport({\n apm,\n level: 'debug',\n clientOpts: {\n cloud: {\n id: elasticCloudId,\n },\n auth: {\n apiKey: elasticApiKey,\n },\n requestTimeout: 10000,\n tls: {\n rejectUnauthorized: false,\n },\n },\n bufferLimit: 1000,\n silent: false,\n });\n\n esTransport.on('error', (error) => {\n console.error('Elasticsearch Transport Error:', error);\n });\n\n logger = winston.createLogger({\n level: 'debug',\n defaultMeta: {\n serviceName,\n },\n format: winston.format.combine(winston.format.json()),\n transports: [\n // new winston.transports.Console(), // TODO: remove, just for debugging\n esTransport,\n ],\n });\n\n startLoggerProcess({\n elasticCloudId,\n elasticApiKey,\n });\n}\n\nexport function getApm() {\n if (!apm) {\n throw new Error('APM is not initialized');\n }\n return apm;\n}\n\nexport function isLoggerReady() {\n return logger !== null;\n}\n\nexport function getLogger() {\n if (!logger) {\n throw new Error('Logger is not initialized');\n }\n return logger;\n}\n","import { getLogger, getApm, isLoggerReady } from '@/app/metrics';\nimport { isTelemetryEnabled } from '@/app/state';\n\ntype LogLevel = 'error' | 'info' | 'debug' | '';\n\n/**\n * Gets the logging level for console logs based on the MODELENCE_LOG_LEVEL environment variable.\n *\n * @returns The log level ('error' | 'info' | 'debug' | '')\n *\n * Behavior:\n * - If MODELENCE_LOG_LEVEL is set, returns that value\n * - If telemetry is disabled and MODELENCE_LOG_LEVEL is not set, defaults to 'info'\n * - If telemetry is enabled and MODELENCE_LOG_LEVEL is not set, returns '' (no console logging)\n */\nfunction getLogLevel(): LogLevel {\n let defaultLoglevel: LogLevel = '';\n if (!isTelemetryEnabled()) {\n defaultLoglevel = 'info';\n }\n\n return (process.env.MODELENCE_LOG_LEVEL as LogLevel) || defaultLoglevel;\n}\n\nexport function logDebug(message: string, args: object) {\n if (isTelemetryEnabled() && isLoggerReady()) {\n getLogger().debug(message, args);\n }\n if (getLogLevel() === 'debug') {\n console.debug(message, args);\n }\n}\n\nexport function logInfo(message: string, args: object) {\n if (isTelemetryEnabled() && isLoggerReady()) {\n getLogger().info(message, args);\n }\n if (['debug', 'info'].includes(getLogLevel())) {\n console.info(message, args);\n }\n}\n\nexport function logError(message: string, args: object) {\n if (isTelemetryEnabled() && isLoggerReady()) {\n getLogger().error(message, args);\n }\n if (['debug', 'info', 'error'].includes(getLogLevel())) {\n console.error(message, args);\n }\n}\n\ninterface WrappedTransaction {\n end(result?: string, context?: Record<string, unknown>): void;\n setContext(context: Record<string, unknown>): void;\n}\n\nexport function startTransaction(\n type: 'method' | 'cron' | 'ai' | 'custom' | 'route',\n name: string,\n context?: Record<string, unknown>\n): WrappedTransaction {\n if (!isTelemetryEnabled()) {\n return {\n end: () => {\n // do nothing\n },\n setContext: () => {\n // do nothing\n },\n };\n }\n\n const apm = getApm();\n const transaction = apm.startTransaction(name, type);\n if (context) {\n apm.setCustomContext(context);\n }\n\n return {\n end: (\n result?: string,\n { endTime, context }: { endTime?: number; context?: Record<string, unknown> } = {}\n ) => {\n if (context) {\n apm.setCustomContext(context);\n }\n transaction.end(result, endTime);\n },\n setContext: (context: Record<string, unknown>) => {\n apm.setCustomContext(context);\n },\n };\n}\n\nexport function captureError(error: Error) {\n if (!isTelemetryEnabled()) {\n console.error(error);\n return;\n }\n\n getApm().captureError(error);\n}\n"]}
@@ -1,3 +0,0 @@
1
- var s="module",i="modelence",r="0.20.0",c="The Node.js Framework for Real-Time MongoDB Apps",n="dist/index.js",o="dist/global.d.ts",p={".":"./dist/index.js","./client":"./dist/client.js","./server":"./dist/server.js","./telemetry":"./dist/telemetry.js","./mongodb":"./dist/mongo.js","./types":{types:"./dist/types.d.ts",default:"./dist/types.js"}},d=["dist","dist/bin"],a={modelence:"./dist/bin/modelence.js"},l={build:"tsup",dev:"tsup --watch",format:'prettier --write "src/**/*.{ts,tsx,js,jsx,json,css,md}"',"format:check":'prettier --check "src/**/*.{ts,tsx,js,jsx,json,css,md}"',lint:"eslint src --ext .ts,.tsx --fix","lint:check":"eslint src --ext .ts,.tsx",prepublishOnly:"npm run build",bench:"tsx src/bench/index.ts",test:"vitest run","test:watch":"vitest","test:coverage":"vitest run --coverage",postversion:"git push && git push --tags",prepare:"cd ../.. && git config core.hooksPath .husky"},m={type:"git",url:"git+https://github.com/modelence/modelence.git"},y="Modelence",u="SEE LICENSE IN LICENSE",g={url:"https://github.com/modelence/modelence/issues"},h="https://modelence.com",v={"@tanstack/react-query":"^5.100.7","@types/archiver":"^6.0.3","@types/bcrypt":"^6.0.0","@types/cookie-parser":"^1.4.9","@types/express":"^5.0.0","@types/fs-extra":"^11.0.4","@types/node":"^22.5.1","@types/react":"^19.0.0","@types/react-dom":"^19.0.1","@types/socket.io":"^3.0.1","@typescript-eslint/eslint-plugin":"^8.17.0","@typescript-eslint/parser":"^8.17.0",eslint:"^9.37.0",husky:"^9.1.7","lint-staged":"^16.2.7",prettier:"^3.6.2",react:"^19.0.0","react-dom":"^19.0.0","ts-node":"^10.9.2",vitest:"^2.1.8","@vitest/coverage-v8":"^2.1.8","vite-tsconfig-paths":"^5.1.4"},x={"@socket.io/mongo-adapter":"^0.4.0","@vitejs/plugin-react":"^4.3.4",archiver:"^7.0.1",bcrypt:"^6.0.0",commander:"^12.0.0","cookie-parser":"^1.4.7",dotenv:"^16.4.5","elastic-apm-node":"^4.15.0",express:"^4.21.0","fs-extra":"^11.2.0",jiti:"^2.4.2",mongodb:"^6.8.1",open:"^10.1.0","socket.io":"^4.8.1","socket.io-client":"^4.8.1",tsup:"^8.3.6",tsx:"^4.19.3",typescript:"^5.7.2",vite:"^6.0.3","vite-plugin-eslint":"^1.8.1",winston:"^3.15.0","winston-elasticsearch":"^0.19.0",zod:"^3.23.8",zustand:"^5.0.2"},j={"@tanstack/react-query":">=5.0.0",react:">=18.0.0","react-dom":">=18.0.0"},b={type:s,name:i,version:r,description:c,main:n,types:o,exports:p,files:d,bin:a,scripts:l,"lint-staged":{"src/**/*.{ts,tsx,js,jsx,json,css,md}":"prettier --write"},repository:m,author:y,license:u,bugs:g,homepage:h,devDependencies:v,dependencies:x,peerDependencies:j};
2
- export{s as a,i as b,r as c,c as d,n as e,o as f,p as g,d as h,a as i,l as j,m as k,y as l,u as m,g as n,h as o,v as p,x as q,j as r,b as s};//# sourceMappingURL=chunk-FCIMWI4V.js.map
3
- //# sourceMappingURL=chunk-FCIMWI4V.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../package.json"],"names":["type","name","version","description","main","types","exports","files","bin","scripts","repository","author","license","bugs","homepage","devDependencies","dependencies","peerDependencies","package_default"],"mappings":"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","file":"chunk-FCIMWI4V.js","sourcesContent":["{\n \"type\": \"module\",\n \"name\": \"modelence\",\n \"version\": \"0.20.0\",\n \"description\": \"The Node.js Framework for Real-Time MongoDB Apps\",\n \"main\": \"dist/index.js\",\n \"types\": \"dist/global.d.ts\",\n \"exports\": {\n \".\": \"./dist/index.js\",\n \"./client\": \"./dist/client.js\",\n \"./server\": \"./dist/server.js\",\n \"./telemetry\": \"./dist/telemetry.js\",\n \"./mongodb\": \"./dist/mongo.js\",\n \"./types\": {\n \"types\": \"./dist/types.d.ts\",\n \"default\": \"./dist/types.js\"\n }\n },\n \"files\": [\n \"dist\",\n \"dist/bin\"\n ],\n \"bin\": {\n \"modelence\": \"./dist/bin/modelence.js\"\n },\n \"scripts\": {\n \"build\": \"tsup\",\n \"dev\": \"tsup --watch\",\n \"format\": \"prettier --write \\\"src/**/*.{ts,tsx,js,jsx,json,css,md}\\\"\",\n \"format:check\": \"prettier --check \\\"src/**/*.{ts,tsx,js,jsx,json,css,md}\\\"\",\n \"lint\": \"eslint src --ext .ts,.tsx --fix\",\n \"lint:check\": \"eslint src --ext .ts,.tsx\",\n \"prepublishOnly\": \"npm run build\",\n \"bench\": \"tsx src/bench/index.ts\",\n \"test\": \"vitest run\",\n \"test:watch\": \"vitest\",\n \"test:coverage\": \"vitest run --coverage\",\n \"postversion\": \"git push && git push --tags\",\n \"prepare\": \"cd ../.. && git config core.hooksPath .husky\"\n },\n \"lint-staged\": {\n \"src/**/*.{ts,tsx,js,jsx,json,css,md}\": \"prettier --write\"\n },\n \"repository\": {\n \"type\": \"git\",\n \"url\": \"git+https://github.com/modelence/modelence.git\"\n },\n \"author\": \"Modelence\",\n \"license\": \"SEE LICENSE IN LICENSE\",\n \"bugs\": {\n \"url\": \"https://github.com/modelence/modelence/issues\"\n },\n \"homepage\": \"https://modelence.com\",\n \"devDependencies\": {\n \"@tanstack/react-query\": \"^5.100.7\",\n \"@types/archiver\": \"^6.0.3\",\n \"@types/bcrypt\": \"^6.0.0\",\n \"@types/cookie-parser\": \"^1.4.9\",\n \"@types/express\": \"^5.0.0\",\n \"@types/fs-extra\": \"^11.0.4\",\n \"@types/node\": \"^22.5.1\",\n \"@types/react\": \"^19.0.0\",\n \"@types/react-dom\": \"^19.0.1\",\n \"@types/socket.io\": \"^3.0.1\",\n \"@typescript-eslint/eslint-plugin\": \"^8.17.0\",\n \"@typescript-eslint/parser\": \"^8.17.0\",\n \"eslint\": \"^9.37.0\",\n \"husky\": \"^9.1.7\",\n \"lint-staged\": \"^16.2.7\",\n \"prettier\": \"^3.6.2\",\n \"react\": \"^19.0.0\",\n \"react-dom\": \"^19.0.0\",\n \"ts-node\": \"^10.9.2\",\n \"vitest\": \"^2.1.8\",\n \"@vitest/coverage-v8\": \"^2.1.8\",\n \"vite-tsconfig-paths\": \"^5.1.4\"\n },\n \"dependencies\": {\n \"@socket.io/mongo-adapter\": \"^0.4.0\",\n \"@vitejs/plugin-react\": \"^4.3.4\",\n \"archiver\": \"^7.0.1\",\n \"bcrypt\": \"^6.0.0\",\n \"commander\": \"^12.0.0\",\n \"cookie-parser\": \"^1.4.7\",\n \"dotenv\": \"^16.4.5\",\n \"elastic-apm-node\": \"^4.15.0\",\n \"express\": \"^4.21.0\",\n \"fs-extra\": \"^11.2.0\",\n \"jiti\": \"^2.4.2\",\n \"mongodb\": \"^6.8.1\",\n \"open\": \"^10.1.0\",\n \"socket.io\": \"^4.8.1\",\n \"socket.io-client\": \"^4.8.1\",\n \"tsup\": \"^8.3.6\",\n \"tsx\": \"^4.19.3\",\n \"typescript\": \"^5.7.2\",\n \"vite\": \"^6.0.3\",\n \"vite-plugin-eslint\": \"^1.8.1\",\n \"winston\": \"^3.15.0\",\n \"winston-elasticsearch\": \"^0.19.0\",\n \"zod\": \"^3.23.8\",\n \"zustand\": \"^5.0.2\"\n },\n \"peerDependencies\": {\n \"@tanstack/react-query\": \">=5.0.0\",\n \"react\": \">=18.0.0\",\n \"react-dom\": \">=18.0.0\"\n }\n}\n"]}
@@ -1,2 +0,0 @@
1
- import {a,d,g,n}from'./chunk-YRR32LTF.js';import {t,v,p,w as w$1,A}from'./chunk-YLLX26A4.js';import C from'react';import v$1 from'react-dom/client';import {jsx}from'react/jsx-runtime';function h(e){return {getConfig(t){return v(`${e}.${t}`)},query(t$1,...r){let o=r[0]??{};return {queryKey:[e,t$1,o],queryFn:()=>t(`${e}.${t$1}`,o)}},mutation(t$1){return {mutationFn:r=>t(`${e}.${t$1}`,r)}},infiniteQuery(t$1,r){return {queryKey:[e,t$1,"infinite",r(void 0)],initialPageParam:void 0,queryFn:({pageParam:o})=>t(`${e}.${t$1}`,r(o))}}}}var F=h("_system");var M=class{constructor(t,r){this.category=t,this.onMessage=r;}init(){d()?.on({category:this.category,listener:this.onMessage});}joinChannel(t){d()?.joinChannel({category:this.category,id:t});}leaveChannel(t){d()?.leaveChannel({category:this.category,id:t});}};async function _(e,{filePath:t$1,contentType:r,visibility:o}){let{url:l,fields:d,filePath:c}=await t("_system.files.getUploadUrl",{filePath:t$1,contentType:r,visibility:o}),i=new FormData;for(let[p,u]of Object.entries(d))i.append(p,u);i.append("file",e);let s=await fetch(l,{method:"POST",body:i});if(!s.ok)throw new Error(`Failed to upload file: HTTP status: ${s.status}`);return {filePath:c}}async function O(e){await t("_system.files.deleteFile",{filePath:e});}async function q(e){return t("_system.files.downloadFile",{filePath:e})}async function U(e){return t("_system.files.getFileUrl",{filePath:e})}var K="useClient"in C?C.useClient(a):a;var b="__MODELENCE_STATE__";function I(){return typeof document>"u"?false:document.getElementById(b)!==null}function W(){if(typeof document>"u")return null;let e=document.getElementById(b);if(!e)return null;try{return JSON.parse(e.textContent??"")}catch(t){return console.error("Modelence: failed to parse SSR state",t),null}}var w="__modelence_ssr_snapshot__";function $(e){globalThis[w]=e;}function ze(){return globalThis[w]??null}function Q(e){if(typeof window>"u"){$(e);return}let{loadingElement:t,routesElement:r,favicon:o,errorHandler:l,router:d}=e;l&&p(l),window.addEventListener("unload",()=>{});let c=I(),i=W();i?.session&&(w$1(i.session),A());let s=document.getElementById("root"),p$1=window.location.pathname+window.location.search,u=d?d({children:r,location:p$1}):r,k=g()?u:jsx(n,{children:u}),T=jsx(C.StrictMode,{children:jsx(K,{loadingElement:t,children:k})});if(c?v$1.hydrateRoot(s,T):v$1.createRoot(s).render(T),o){let x=document.querySelector("link[rel~='icon']");if(x)x.href=o;else {let f=document.createElement("link");f.rel="icon",f.href=o,document.head.appendChild(f);}}}export{h as a,F as b,ze as c,Q as d,M as e,_ as f,O as g,q as h,U as i,K as j};//# sourceMappingURL=chunk-N7XT2ULQ.js.map
2
- //# sourceMappingURL=chunk-N7XT2ULQ.js.map
@@ -1 +0,0 @@
1
- {"version":3,"sources":["../src/client/module.ts","../src/system/client.ts","../src/websocket/clientChannel.ts","../src/files/client.ts","../src/client.ts","../src/client/renderApp.tsx"],"names":["createClientModule","moduleName","key","getConfig","name","rest","args","callMethod","getArgs","pageParam","systemConfig","ClientChannel","category","onMessage","getWebsocketClientProvider","id","uploadFile","file","filePath","contentType","visibility","url","fields","resolvedFilePath","formData","value","uploadResponse","deleteFile","downloadFile","getFileUrl","AppProvider","React","SSR_STATE_SCRIPT_ID","hasSsrMarker","readSsrState","node","e","SNAPSHOT_KEY","setSnapshot","snapshot","_getSsrSnapshot","renderApp","options","loadingElement","routesElement","favicon","errorHandler","router","setErrorHandler","isHydrating","ssrState","hydrateSession","startSessionHeartbeat","container","location","routedTree","appTree","hasConnectedQueryClient","jsx","ModelenceQueryProvider","tree","ReactDOM","link","newLink"],"mappings":"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","file":"chunk-N7XT2ULQ.js","sourcesContent":["'use client';\n\nimport type { ObjectId } from 'mongodb';\nimport type { ConfigParams, ConfigType, ValueType } from '../config/types';\nimport { callMethod, type MethodArgs } from './method';\nimport type { AnyMethodShape } from '../methods/types';\n\n// Pulls the config store value without importing server-side code\nimport { getConfig as _getClientConfig } from '../config/client';\n\n// ── type helpers ─────────────────────────────────────────────────────────────\n\n/**\n * Recursively maps ObjectId → string to match the sanitized runtime values\n * sent over the wire. Dates are preserved (revived via typeMap on the client).\n */\ntype Sanitized<T> = T extends ObjectId\n ? string\n : T extends Date\n ? Date\n : T extends (infer U)[]\n ? Sanitized<U>[]\n : T extends object\n ? { [K in keyof T]: Sanitized<T[K]> }\n : T;\n\ntype ExtractArgs<M> = M extends (args: infer A, ...rest: any[]) => any // eslint-disable-line @typescript-eslint/no-explicit-any\n ? A\n : M extends { handler: (args: infer A, ...rest: any[]) => any } // eslint-disable-line @typescript-eslint/no-explicit-any\n ? A\n : MethodArgs;\n\ntype ExtractResult<M> = M extends (...args: any[]) => Promise<infer R> // eslint-disable-line @typescript-eslint/no-explicit-any\n ? Sanitized<R>\n : M extends { handler: (...args: any[]) => Promise<infer R> } // eslint-disable-line @typescript-eslint/no-explicit-any\n ? Sanitized<R>\n : unknown;\n\ntype PublicKeyOf<TSchema extends Record<string, ConfigParams>> = {\n [K in keyof TSchema as TSchema[K] extends ConfigParams<ConfigType, true>\n ? string & K\n : never]: ValueType<TSchema[K]['type']>;\n};\n\ntype AnyModule = {\n name: string;\n configSchema: Record<string, ConfigParams>;\n queries: Record<string, AnyMethodShape>;\n mutations: Record<string, AnyMethodShape>;\n};\n\n// ── createClientModule ────────────────────────────────────────────────────────\n\n/**\n * Creates a typed client accessor for a module's public configs, queries, and mutations.\n *\n * Use `import type` to reference the module so no server code is bundled on the client.\n * Arg and return types for queries and mutations are inferred automatically from the\n * server-side handler signatures.\n *\n * @param moduleName - The module's name as passed to `new Module(name, ...)`.\n *\n * @example\n * ```ts\n * // src/client/payments.ts\n * import type paymentsModule from '../server/payments';\n * import { createClientModule } from 'modelence/client';\n *\n * export const payments = createClientModule<typeof paymentsModule>('payments');\n * ```\n *\n * ```ts\n * // src/components/Checkout.tsx\n * import { useQuery, useMutation } from '@tanstack/react-query';\n * import { payments } from '../client/payments';\n *\n * // Typed config — public keys only, private and secret keys excluded:\n * const currency = payments.getConfig('currency'); // string | undefined\n *\n * // Typed query — pass directly to useQuery:\n * const { data: products } = useQuery(payments.query('getProducts', { page: 1 }));\n *\n * // Typed mutation — pass directly to useMutation:\n * const { mutate: charge } = useMutation(payments.mutation('charge'));\n * charge({ amount: 100 }); // args typed from handler signature\n * ```\n */\nexport function createClientModule<TModule extends AnyModule>(moduleName: string) {\n return {\n getConfig<K extends keyof PublicKeyOf<TModule['configSchema']> & string>(\n key: K\n ): PublicKeyOf<TModule['configSchema']>[K] | undefined {\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n return _getClientConfig(`${moduleName}.${key}`) as any;\n },\n\n query<K extends keyof TModule['queries'] & string>(\n name: K,\n ...rest: {} extends ExtractArgs<TModule['queries'][K]>\n ? [args?: ExtractArgs<TModule['queries'][K]>]\n : [args: ExtractArgs<TModule['queries'][K]>]\n ) {\n const args = (rest[0] ?? {}) as ExtractArgs<TModule['queries'][K]>;\n return {\n queryKey: [moduleName, name, args] as const,\n queryFn: (): Promise<ExtractResult<TModule['queries'][K]>> =>\n callMethod<ExtractResult<TModule['queries'][K]>>(\n `${moduleName}.${name}`,\n args as MethodArgs\n ),\n };\n },\n\n mutation<K extends keyof TModule['mutations'] & string>(name: K) {\n return {\n mutationFn: (\n args: ExtractArgs<TModule['mutations'][K]>\n ): Promise<ExtractResult<TModule['mutations'][K]>> =>\n callMethod<ExtractResult<TModule['mutations'][K]>>(\n `${moduleName}.${name}`,\n args as MethodArgs\n ),\n };\n },\n\n /**\n * Returns options for `useInfiniteQuery`. The `getArgs` callback receives the\n * current `pageParam` and returns the args to pass to the query handler.\n * Spread the result into `useInfiniteQuery` alongside `getNextPageParam`.\n *\n * Annotate the `pageParam` type in the callback so TypeScript can infer the\n * page param type — no manual generic needed on `useInfiniteQuery`.\n */\n infiniteQuery<K extends keyof TModule['queries'] & string, TPageParam = unknown>(\n name: K,\n getArgs: (pageParam: TPageParam | undefined) => ExtractArgs<TModule['queries'][K]>\n ) {\n return {\n queryKey: [moduleName, name, 'infinite', getArgs(undefined)] as const,\n // Included so TanStack infers TPageParam from the callback type, not from a bare `undefined`.\n initialPageParam: undefined as TPageParam | undefined,\n queryFn: ({\n pageParam,\n }: {\n pageParam: TPageParam | undefined;\n }): Promise<ExtractResult<TModule['queries'][K]>> =>\n callMethod<ExtractResult<TModule['queries'][K]>>(\n `${moduleName}.${name}`,\n getArgs(pageParam) as MethodArgs\n ),\n };\n },\n };\n}\n","import type systemModule from './index';\nimport { createClientModule } from '../client/module';\n\nexport const systemConfig = createClientModule<typeof systemModule>('_system');\n","import { getWebsocketClientProvider } from './client';\n\nexport class ClientChannel<T = unknown> {\n public readonly category: string;\n private readonly onMessage: (data: T) => void;\n\n constructor(category: string, onMessage: (data: T) => void) {\n this.category = category;\n this.onMessage = onMessage;\n }\n\n init() {\n getWebsocketClientProvider()?.on({\n category: this.category,\n listener: this.onMessage,\n });\n }\n\n joinChannel(id: string) {\n getWebsocketClientProvider()?.joinChannel({\n category: this.category,\n id,\n });\n }\n\n leaveChannel(id: string) {\n getWebsocketClientProvider()?.leaveChannel({\n category: this.category,\n id,\n });\n }\n}\n","import { callMethod } from '../client/method';\nimport type { FileVisibility, GetUploadUrlResult } from './types';\n\ntype UploadFileParams = {\n filePath: string;\n contentType: string;\n visibility: FileVisibility;\n};\n\ntype UploadFileResult = {\n filePath: string;\n};\n\nexport async function uploadFile(\n file: File | Blob,\n { filePath, contentType, visibility }: UploadFileParams\n): Promise<UploadFileResult> {\n const {\n url,\n fields,\n filePath: resolvedFilePath,\n } = await callMethod<GetUploadUrlResult>('_system.files.getUploadUrl', {\n filePath,\n contentType,\n visibility,\n });\n\n const formData = new FormData();\n for (const [key, value] of Object.entries(fields)) {\n formData.append(key, value);\n }\n formData.append('file', file);\n\n const uploadResponse = await fetch(url, {\n method: 'POST',\n body: formData,\n });\n\n if (!uploadResponse.ok) {\n throw new Error(`Failed to upload file: HTTP status: ${uploadResponse.status}`);\n }\n\n return { filePath: resolvedFilePath };\n}\n\nexport async function deleteFile(filePath: string): Promise<void> {\n await callMethod('_system.files.deleteFile', { filePath });\n}\n\nexport async function downloadFile(filePath: string): Promise<{ downloadUrl: string }> {\n return callMethod('_system.files.downloadFile', { filePath });\n}\n\nexport async function getFileUrl(filePath: string): Promise<{ url: string }> {\n return callMethod('_system.files.getFileUrl', { filePath });\n}\n","import React from 'react';\n\nimport { AppProvider as OriginalAppProvider } from './client/AppProvider';\n\nexport { configureClient, type ClientConfig } from './client/clientConfig';\nexport { getConfig } from './config/client';\nexport { createClientModule } from './client/module';\nexport type { ValueType } from './config/types';\nexport { systemConfig } from './system/client';\n\nexport const AppProvider =\n 'useClient' in React\n ? // @ts-ignore: React.useClient only exists in Next.js\n React.useClient(OriginalAppProvider)\n : OriginalAppProvider;\n\nexport { renderApp } from './client/renderApp';\nexport { ModelenceQueryProvider } from './client/queryProvider';\nexport {\n modelenceQuery,\n modelenceLiveQuery,\n modelenceMutation,\n createQueryKey,\n connectModelenceQueryClient,\n disconnectModelenceQueryClient,\n ModelenceQueryClient,\n type ModelenceQueryKey,\n} from './client/query';\nexport { callMethod, MethodError, type MethodArgs, type CallMethodOptions } from './client/method';\nexport { useSession } from './client/session';\nexport {\n signupWithPassword,\n loginWithPassword,\n verifyEmail,\n updateProfile,\n resendEmailVerification,\n logout,\n sendResetPasswordToken,\n resetPassword,\n linkOAuthProvider,\n unlinkOAuthProvider,\n type UserInfo,\n} from './auth/client';\nexport {\n getWebsocketClientProvider,\n setWebsocketClientProvider,\n startWebsockets,\n subscribeLiveQuery,\n} from './websocket/client';\nexport { ClientChannel } from './websocket/clientChannel';\nexport { getLocalStorageSession } from './client/localStorage';\nexport { uploadFile, deleteFile, downloadFile, getFileUrl } from './files/client';\n","import React from 'react';\nimport ReactDOM from 'react-dom/client';\nimport { AppProvider } from '../client';\nimport { setErrorHandler, ErrorHandler } from './errorHandler';\nimport { hydrateSession, startSessionHeartbeat, type SessionInitPayload } from './session';\nimport { ModelenceQueryProvider } from './queryProvider';\nimport { hasConnectedQueryClient } from './query';\n\nconst SSR_STATE_SCRIPT_ID = '__MODELENCE_STATE__';\n\ntype SsrState = {\n session?: SessionInitPayload;\n};\n\nfunction hasSsrMarker(): boolean {\n if (typeof document === 'undefined') {\n return false;\n }\n return document.getElementById(SSR_STATE_SCRIPT_ID) !== null;\n}\n\nfunction readSsrState(): SsrState | null {\n if (typeof document === 'undefined') {\n return null;\n }\n\n const node = document.getElementById(SSR_STATE_SCRIPT_ID);\n if (!node) {\n return null;\n }\n\n try {\n return JSON.parse(node.textContent ?? '') as SsrState;\n } catch (e) {\n // Caller must still hydrate (marker presence drives that, not parsed payload).\n console.error('Modelence: failed to parse SSR state', e);\n return null;\n }\n}\n\nexport type SsrRouter = (props: {\n children: React.ReactNode;\n location?: string;\n}) => React.ReactElement;\n\nexport interface RenderAppOptions {\n loadingElement: React.ReactNode;\n routesElement: React.ReactNode;\n favicon?: string;\n errorHandler?: ErrorHandler;\n router?: SsrRouter;\n}\n\n// Shared via globalThis: ssrLoadModule loads the user's entry in a separate\n// module graph from the framework runtime.\nconst SNAPSHOT_KEY = '__modelence_ssr_snapshot__';\n\ntype GlobalWithSnapshot = typeof globalThis & {\n [SNAPSHOT_KEY]?: RenderAppOptions | null;\n};\n\nfunction setSnapshot(snapshot: RenderAppOptions | null) {\n (globalThis as GlobalWithSnapshot)[SNAPSHOT_KEY] = snapshot;\n}\n\n/** @internal Used by the SSR runtime after evaluating the user's entry. */\nexport function _getSsrSnapshot(): RenderAppOptions | null {\n return (globalThis as GlobalWithSnapshot)[SNAPSHOT_KEY] ?? null;\n}\n\nexport function renderApp(options: RenderAppOptions) {\n if (typeof window === 'undefined') {\n setSnapshot(options);\n return;\n }\n\n const { loadingElement, routesElement, favicon, errorHandler, router } = options;\n\n if (errorHandler) {\n setErrorHandler(errorHandler);\n }\n\n // Empty 'unload' handler prevents bfcache in most browsers.\n window.addEventListener('unload', () => {});\n\n // Hydrate session BEFORE building the tree so `isSessionInitialized()` is\n // true on the first render and matches the server output. Hydration mode\n // tracks marker presence (not parse success): a parse failure still leaves\n // server-rendered DOM that must be hydrated, not replaced.\n const isHydrating = hasSsrMarker();\n const ssrState = readSsrState();\n if (ssrState?.session) {\n hydrateSession(ssrState.session);\n // Fire-and-forget: the heartbeat loop runs in the background.\n void startSessionHeartbeat();\n }\n\n const container = document.getElementById('root')!;\n // Pass the same location the server used (req.originalUrl == path + search;\n // the hash is never sent to the server) so a location-driven router (e.g. a\n // static router) resolves the same route on hydration as it did during SSR,\n // avoiding hydration mismatches.\n const location = window.location.pathname + window.location.search;\n const routedTree = router ? router({ children: routesElement, location }) : routesElement;\n\n // If the app already connected its own QueryClient (the documented\n // bring-your-own-provider pattern connects before calling renderApp), don't\n // inject ours. A second provider would shadow the user's client: useQuery\n // would read the inner client while live-query updates write to the outer\n // one, so real-time queries would never update.\n const appTree = hasConnectedQueryClient() ? (\n routedTree\n ) : (\n <ModelenceQueryProvider>{routedTree}</ModelenceQueryProvider>\n );\n\n const tree = (\n <React.StrictMode>\n <AppProvider loadingElement={loadingElement}>{appTree}</AppProvider>\n </React.StrictMode>\n );\n\n if (isHydrating) {\n ReactDOM.hydrateRoot(container, tree);\n } else {\n ReactDOM.createRoot(container).render(tree);\n }\n\n if (favicon) {\n const link = document.querySelector(\"link[rel~='icon']\") as HTMLLinkElement;\n if (!link) {\n const newLink = document.createElement('link');\n newLink.rel = 'icon';\n newLink.href = favicon;\n document.head.appendChild(newLink);\n } else {\n link.href = favicon;\n }\n }\n}\n"]}