lecodes-sdk 0.19.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.
- package/README.md +114 -0
- package/dist/global.d.ts +503 -0
- package/dist/host.d.ts +61 -0
- package/dist/inject.js +4730 -0
- package/dist/types/animate/animate.d.ts +20 -0
- package/dist/types/animate/bezier.d.ts +2 -0
- package/dist/types/animate/easings.d.ts +21 -0
- package/dist/types/canvas/Canvas.d.ts +168 -0
- package/dist/types/core/Aspect.d.ts +171 -0
- package/dist/types/core/InspectorUI.d.ts +88 -0
- package/dist/types/core/StateMachine.d.ts +81 -0
- package/dist/types/core/color.d.ts +13 -0
- package/dist/types/core/compWrite.d.ts +11 -0
- package/dist/types/core/events.d.ts +11 -0
- package/dist/types/core/fields.d.ts +58 -0
- package/dist/types/core/registry.d.ts +7 -0
- package/dist/types/core/signals.d.ts +29 -0
- package/dist/types/core/time.d.ts +31 -0
- package/dist/types/g2/Camera2D.d.ts +19 -0
- package/dist/types/g2/CharacterController2D.d.ts +134 -0
- package/dist/types/g2/Node2D.d.ts +91 -0
- package/dist/types/g2/OneWay2D.d.ts +24 -0
- package/dist/types/g2/Physics2D.d.ts +147 -0
- package/dist/types/g2/Scene2D.d.ts +72 -0
- package/dist/types/g2/Shape2D.d.ts +58 -0
- package/dist/types/g2/Sprite.d.ts +51 -0
- package/dist/types/g2/SpriteAnimation.d.ts +50 -0
- package/dist/types/g2/SpriteSheet.d.ts +69 -0
- package/dist/types/g2/Texture2D.d.ts +16 -0
- package/dist/types/g2/Tilemap.d.ts +20 -0
- package/dist/types/g2/Tileset.d.ts +32 -0
- package/dist/types/g2/Trigger2D.d.ts +20 -0
- package/dist/types/g2/autotile.d.ts +133 -0
- package/dist/types/g2/cells.d.ts +14 -0
- package/dist/types/g2/defineScene2d.d.ts +141 -0
- package/dist/types/g2/groups2d.d.ts +16 -0
- package/dist/types/g2/loop.d.ts +4 -0
- package/dist/types/g2/scenarios2d.d.ts +30 -0
- package/dist/types/g2/touch.d.ts +2 -0
- package/dist/types/gl/Camera.d.ts +79 -0
- package/dist/types/gl/CameraPlace.d.ts +26 -0
- package/dist/types/gl/CharacterController.d.ts +98 -0
- package/dist/types/gl/Gearbox.d.ts +86 -0
- package/dist/types/gl/Geometry.d.ts +39 -0
- package/dist/types/gl/IK.d.ts +53 -0
- package/dist/types/gl/InstancedMesh.d.ts +46 -0
- package/dist/types/gl/Light.d.ts +73 -0
- package/dist/types/gl/Lightmap.d.ts +85 -0
- package/dist/types/gl/Locomotion.d.ts +279 -0
- package/dist/types/gl/Material.d.ts +100 -0
- package/dist/types/gl/Mesh.d.ts +33 -0
- package/dist/types/gl/Model.d.ts +53 -0
- package/dist/types/gl/NavAgent.d.ts +99 -0
- package/dist/types/gl/NavMesh.d.ts +169 -0
- package/dist/types/gl/Node.d.ts +99 -0
- package/dist/types/gl/Noise.d.ts +20 -0
- package/dist/types/gl/Particles.d.ts +277 -0
- package/dist/types/gl/Physics.d.ts +91 -0
- package/dist/types/gl/Plane.d.ts +19 -0
- package/dist/types/gl/Ragdoll.d.ts +86 -0
- package/dist/types/gl/Ray.d.ts +8 -0
- package/dist/types/gl/Scene.d.ts +221 -0
- package/dist/types/gl/Shape.d.ts +122 -0
- package/dist/types/gl/Terrain.d.ts +280 -0
- package/dist/types/gl/Texture.d.ts +27 -0
- package/dist/types/gl/Trigger.d.ts +10 -0
- package/dist/types/gl/Vehicle.d.ts +191 -0
- package/dist/types/gl/Wheel.d.ts +95 -0
- package/dist/types/gl/animation/AnimationClip.d.ts +60 -0
- package/dist/types/gl/animation/Animator.d.ts +219 -0
- package/dist/types/gl/animation/Layer.d.ts +31 -0
- package/dist/types/gl/animation/Loop.d.ts +17 -0
- package/dist/types/gl/animation/Playback.d.ts +36 -0
- package/dist/types/gl/animation/core.d.ts +367 -0
- package/dist/types/gl/controls.d.ts +19 -0
- package/dist/types/gl/physicsEvents.d.ts +1 -0
- package/dist/types/gl/scenarios.d.ts +98 -0
- package/dist/types/gl/state.d.ts +5 -0
- package/dist/types/gl/terrainMesh.d.ts +46 -0
- package/dist/types/gl/touch.d.ts +2 -0
- package/dist/types/inject.d.ts +123 -0
- package/dist/types/math/Mathf.d.ts +39 -0
- package/dist/types/math/mat4.d.ts +66 -0
- package/dist/types/math/quat.d.ts +53 -0
- package/dist/types/math/vec.d.ts +129 -0
- package/dist/types/net/codec.d.ts +25 -0
- package/dist/types/net/core.d.ts +106 -0
- package/dist/types/net/index.d.ts +80 -0
- package/dist/types/net/replication.d.ts +101 -0
- package/dist/types/plugins/camera.d.ts +25 -0
- package/dist/types/plugins/geolocation.d.ts +39 -0
- package/dist/types/plugins/oauth.d.ts +25 -0
- package/dist/types/plugins/permission.d.ts +1 -0
- package/dist/types/plugins/push.d.ts +46 -0
- package/dist/types/plugins/qr.d.ts +21 -0
- package/dist/types/plugins/service.d.ts +33 -0
- package/dist/types/runtime/app.d.ts +67 -0
- package/dist/types/runtime/appEvents.d.ts +7 -0
- package/dist/types/runtime/channel.d.ts +1 -0
- package/dist/types/runtime/clipboard.d.ts +7 -0
- package/dist/types/runtime/datetime.d.ts +80 -0
- package/dist/types/runtime/device.d.ts +126 -0
- package/dist/types/runtime/fetch.d.ts +31 -0
- package/dist/types/runtime/files.d.ts +33 -0
- package/dist/types/runtime/input.d.ts +121 -0
- package/dist/types/runtime/media.d.ts +46 -0
- package/dist/types/runtime/misc.d.ts +11 -0
- package/dist/types/runtime/net.d.ts +15 -0
- package/dist/types/runtime/rpc.d.ts +44 -0
- package/dist/types/runtime/service.d.ts +1 -0
- package/dist/types/runtime/share.d.ts +2 -0
- package/dist/types/runtime/storage.d.ts +5 -0
- package/dist/types/runtime/touch.d.ts +56 -0
- package/dist/types/scene/defineScene.d.ts +296 -0
- package/dist/types/scene/editorPlugins.d.ts +82 -0
- package/dist/types/scene/gizmos.d.ts +56 -0
- package/dist/types/scene/grammar.d.ts +56 -0
- package/dist/types/scene/level.d.ts +98 -0
- package/dist/types/scene/material.d.ts +76 -0
- package/dist/types/server/auth/appConfig.d.ts +16 -0
- package/dist/types/server/auth/global.d.ts +56 -0
- package/dist/types/server/auth/models.d.ts +164 -0
- package/dist/types/server/auth/types.d.ts +56 -0
- package/dist/types/server/channel.d.ts +28 -0
- package/dist/types/server/context.d.ts +27 -0
- package/dist/types/server/db/defineDb.d.ts +36 -0
- package/dist/types/server/db/fields.d.ts +146 -0
- package/dist/types/server/db/index.d.ts +6 -0
- package/dist/types/server/db/marci/query.d.ts +326 -0
- package/dist/types/server/db/types.d.ts +163 -0
- package/dist/types/server/errors.d.ts +8 -0
- package/dist/types/server/inject.d.ts +5 -0
- package/dist/types/ui/NativeView.d.ts +38 -0
- package/dist/types/ui/UI.d.ts +27 -0
- package/dist/types/ui/UIBottomSheet.d.ts +71 -0
- package/dist/types/ui/UIButton.d.ts +30 -0
- package/dist/types/ui/UIContainer.d.ts +33 -0
- package/dist/types/ui/UIImage.d.ts +35 -0
- package/dist/types/ui/UIInput.d.ts +110 -0
- package/dist/types/ui/UIModal.d.ts +70 -0
- package/dist/types/ui/UINode.d.ts +363 -0
- package/dist/types/ui/UIPager.d.ts +123 -0
- package/dist/types/ui/UIPopover.d.ts +39 -0
- package/dist/types/ui/UIScreen.d.ts +57 -0
- package/dist/types/ui/UIScrollable.d.ts +40 -0
- package/dist/types/ui/UISpacer.d.ts +9 -0
- package/dist/types/ui/UITabs.d.ts +96 -0
- package/dist/types/ui/UIText.d.ts +19 -0
- package/dist/types/ui/UIVideo.d.ts +28 -0
- package/dist/types/ui/UIVirtualizedList.d.ts +97 -0
- package/dist/types/ui/UIWidget.d.ts +65 -0
- package/dist/types/ui/fonts.d.ts +9 -0
- package/dist/types/ui/presentable.d.ts +68 -0
- package/dist/types/ui/router.d.ts +40 -0
- package/dist/types/ui/theme.d.ts +26 -0
- package/dist/types.json +1 -0
- package/package.json +46 -0
- package/prompts/2d.md +395 -0
- package/prompts/3d-scene-files.md +113 -0
- package/prompts/3d-scene.md +119 -0
- package/prompts/3d.md +303 -0
- package/prompts/README.md +142 -0
- package/prompts/ar.md +109 -0
- package/prompts/canvas.md +27 -0
- package/prompts/compose.ts +46 -0
- package/prompts/concept.md +49 -0
- package/prompts/core-design.md +75 -0
- package/prompts/core.md +264 -0
- package/prompts/design.md +218 -0
- package/prompts/dist/2d-game.md +1530 -0
- package/prompts/dist/3d-app.md +1672 -0
- package/prompts/dist/ar-app.md +1548 -0
- package/prompts/dist/concept.md +49 -0
- package/prompts/dist/design.md +498 -0
- package/prompts/dist/ui-app.md +1134 -0
- package/prompts/index.md +37 -0
- package/prompts/intake-prompt.md +33 -0
- package/prompts/namer-prompt.md +12 -0
- package/prompts/router-prompt.md +50 -0
- package/prompts/select.ts +111 -0
- package/prompts/ui-design.md +203 -0
- package/prompts/ui.md +803 -0
- package/src/animate/animate.ts +238 -0
- package/src/animate/bezier.ts +138 -0
- package/src/animate/easings.ts +126 -0
- package/src/bridges.d.ts +1345 -0
- package/src/canvas/Canvas.ts +305 -0
- package/src/compile/__tests__/assetIconMacro.test.ts +219 -0
- package/src/compile/__tests__/assetMacro.test.ts +74 -0
- package/src/compile/__tests__/assetName.test.ts +55 -0
- package/src/compile/__tests__/compile.test.ts +287 -0
- package/src/compile/__tests__/detectEntry.test.ts +132 -0
- package/src/compile/__tests__/fontMacro.test.ts +199 -0
- package/src/compile/aspectMacro.ts +86 -0
- package/src/compile/assetIconMacro.ts +384 -0
- package/src/compile/assetMacro.ts +146 -0
- package/src/compile/assetName.ts +50 -0
- package/src/compile/bundler.ts +287 -0
- package/src/compile/compileProject.ts +127 -0
- package/src/compile/detectEntry.ts +128 -0
- package/src/compile/fontMacro.ts +459 -0
- package/src/compile/fontRegistry.ts +78 -0
- package/src/compile/header.ts +67 -0
- package/src/compile/index.ts +100 -0
- package/src/compile/libraryImports.ts +52 -0
- package/src/compile/liteMaterial.ts +247 -0
- package/src/compile/sceneEditor.ts +88 -0
- package/src/compile/serverSplit.ts +233 -0
- package/src/compile/serverTypes.ts +227 -0
- package/src/compile/sfnt.ts +98 -0
- package/src/compile/shaderSchema.ts +202 -0
- package/src/compile/shaderTargets.ts +77 -0
- package/src/compile/sourcemap.ts +25 -0
- package/src/core/Aspect.ts +568 -0
- package/src/core/InspectorUI.ts +212 -0
- package/src/core/StateMachine.ts +308 -0
- package/src/core/__tests__/stateMachine.test.ts +132 -0
- package/src/core/color.ts +66 -0
- package/src/core/compWrite.ts +42 -0
- package/src/core/events.ts +38 -0
- package/src/core/fields.ts +120 -0
- package/src/core/registry.ts +23 -0
- package/src/core/signals.ts +277 -0
- package/src/core/time.ts +84 -0
- package/src/g2/Camera2D.ts +40 -0
- package/src/g2/CharacterController2D.ts +276 -0
- package/src/g2/Node2D.ts +267 -0
- package/src/g2/OneWay2D.ts +66 -0
- package/src/g2/Physics2D.ts +346 -0
- package/src/g2/Scene2D.ts +209 -0
- package/src/g2/Shape2D.ts +259 -0
- package/src/g2/Sprite.ts +89 -0
- package/src/g2/SpriteAnimation.ts +171 -0
- package/src/g2/SpriteSheet.ts +166 -0
- package/src/g2/Texture2D.ts +47 -0
- package/src/g2/Tilemap.ts +41 -0
- package/src/g2/Tileset.ts +71 -0
- package/src/g2/Trigger2D.ts +77 -0
- package/src/g2/autotile.ts +433 -0
- package/src/g2/cells.ts +91 -0
- package/src/g2/defineScene2d.ts +381 -0
- package/src/g2/groups2d.ts +106 -0
- package/src/g2/loop.ts +50 -0
- package/src/g2/scenarios2d.ts +69 -0
- package/src/g2/touch.ts +83 -0
- package/src/gl/Camera.ts +160 -0
- package/src/gl/CameraPlace.ts +52 -0
- package/src/gl/CharacterController.ts +238 -0
- package/src/gl/Gearbox.ts +212 -0
- package/src/gl/Geometry.ts +279 -0
- package/src/gl/IK.ts +193 -0
- package/src/gl/InstancedMesh.ts +132 -0
- package/src/gl/Light.ts +135 -0
- package/src/gl/Lightmap.ts +402 -0
- package/src/gl/Locomotion.ts +498 -0
- package/src/gl/Material.ts +279 -0
- package/src/gl/Mesh.ts +83 -0
- package/src/gl/Model.ts +124 -0
- package/src/gl/NavAgent.ts +337 -0
- package/src/gl/NavMesh.ts +397 -0
- package/src/gl/Node.ts +350 -0
- package/src/gl/Noise.ts +30 -0
- package/src/gl/Particles.ts +676 -0
- package/src/gl/Physics.ts +222 -0
- package/src/gl/Plane.ts +53 -0
- package/src/gl/Ragdoll.ts +270 -0
- package/src/gl/Ray.ts +16 -0
- package/src/gl/Scene.ts +505 -0
- package/src/gl/Shape.ts +409 -0
- package/src/gl/Terrain.ts +1092 -0
- package/src/gl/Texture.ts +63 -0
- package/src/gl/Trigger.ts +45 -0
- package/src/gl/Vehicle.ts +473 -0
- package/src/gl/Wheel.ts +240 -0
- package/src/gl/animation/AnimationClip.ts +204 -0
- package/src/gl/animation/Animator.ts +329 -0
- package/src/gl/animation/Layer.ts +39 -0
- package/src/gl/animation/Loop.ts +31 -0
- package/src/gl/animation/Playback.ts +52 -0
- package/src/gl/animation/core.ts +670 -0
- package/src/gl/controls.ts +95 -0
- package/src/gl/physicsEvents.ts +20 -0
- package/src/gl/scenarios.ts +291 -0
- package/src/gl/state.ts +6 -0
- package/src/gl/terrainMesh.ts +219 -0
- package/src/gl/touch.ts +68 -0
- package/src/host.d.ts +61 -0
- package/src/inject.ts +203 -0
- package/src/math/Mathf.ts +118 -0
- package/src/math/mat4.ts +278 -0
- package/src/math/quat.ts +232 -0
- package/src/math/vec.ts +255 -0
- package/src/net/codec.ts +119 -0
- package/src/net/core.ts +384 -0
- package/src/net/index.ts +181 -0
- package/src/net/replication.ts +622 -0
- package/src/plugins/camera.ts +81 -0
- package/src/plugins/geolocation.ts +123 -0
- package/src/plugins/oauth.ts +61 -0
- package/src/plugins/permission.ts +7 -0
- package/src/plugins/push.ts +132 -0
- package/src/plugins/qr.ts +73 -0
- package/src/plugins/service.ts +47 -0
- package/src/runtime/app.ts +101 -0
- package/src/runtime/appEvents.ts +54 -0
- package/src/runtime/channel.ts +61 -0
- package/src/runtime/clipboard.ts +20 -0
- package/src/runtime/datetime.ts +329 -0
- package/src/runtime/device.ts +293 -0
- package/src/runtime/fetch.ts +77 -0
- package/src/runtime/files.ts +108 -0
- package/src/runtime/input.ts +175 -0
- package/src/runtime/media.ts +111 -0
- package/src/runtime/misc.ts +16 -0
- package/src/runtime/net.ts +36 -0
- package/src/runtime/rpc.ts +218 -0
- package/src/runtime/service.ts +83 -0
- package/src/runtime/share.ts +9 -0
- package/src/runtime/storage.ts +13 -0
- package/src/runtime/touch.ts +76 -0
- package/src/scene/defineScene.ts +1396 -0
- package/src/scene/editorPlugins.ts +110 -0
- package/src/scene/gizmos.ts +148 -0
- package/src/scene/grammar.ts +120 -0
- package/src/scene/level.ts +296 -0
- package/src/scene/material.ts +188 -0
- package/src/server/auth/appConfig.ts +12 -0
- package/src/server/auth/global.ts +80 -0
- package/src/server/auth/host.ts +318 -0
- package/src/server/auth/models.ts +83 -0
- package/src/server/auth/types.ts +50 -0
- package/src/server/channel.ts +56 -0
- package/src/server/context.ts +36 -0
- package/src/server/db/defineDb.ts +237 -0
- package/src/server/db/fields.ts +132 -0
- package/src/server/db/httpTransport.ts +93 -0
- package/src/server/db/index.ts +7 -0
- package/src/server/db/marci/query.ts +412 -0
- package/src/server/db/types.ts +202 -0
- package/src/server/errors.ts +12 -0
- package/src/server/host.ts +74 -0
- package/src/server/inject.ts +13 -0
- package/src/server/runtime.ts +133 -0
- package/src/server/validate.ts +87 -0
- package/src/ui/NativeView.ts +142 -0
- package/src/ui/UI.ts +39 -0
- package/src/ui/UIBottomSheet.ts +139 -0
- package/src/ui/UIButton.ts +101 -0
- package/src/ui/UIContainer.ts +60 -0
- package/src/ui/UIImage.ts +83 -0
- package/src/ui/UIInput.ts +185 -0
- package/src/ui/UIModal.ts +139 -0
- package/src/ui/UINode.ts +830 -0
- package/src/ui/UIPager.ts +362 -0
- package/src/ui/UIPopover.ts +100 -0
- package/src/ui/UIScreen.ts +123 -0
- package/src/ui/UIScrollable.ts +87 -0
- package/src/ui/UISpacer.ts +14 -0
- package/src/ui/UITabs.ts +236 -0
- package/src/ui/UIText.ts +51 -0
- package/src/ui/UIVideo.ts +88 -0
- package/src/ui/UIVirtualizedList.ts +241 -0
- package/src/ui/UIWidget.ts +127 -0
- package/src/ui/fonts.ts +13 -0
- package/src/ui/presentable.ts +117 -0
- package/src/ui/router.ts +132 -0
- package/src/ui/theme.ts +84 -0
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Shared shapes of the auth layer (docs/backend-plan.md §3.4). Two sides meet through them:
|
|
3
|
+
* - the BUNDLE side (`auth` global, ./global.ts) — what `*.server.ts` code calls;
|
|
4
|
+
* - the HOST side (./host.ts) — sessions, email codes and OAuth binding, run by the runner with the
|
|
5
|
+
* project's db handle and the platform's secrets. Installed on `globalThis.__lecodesAuth`.
|
|
6
|
+
*/
|
|
7
|
+
import type { RequestContext } from "../context";
|
|
8
|
+
import type { AuthProvider } from "./models";
|
|
9
|
+
/** The built-in user row — what `auth.user` is typed with (custom fields exist at runtime; select them via `db.user`). */
|
|
10
|
+
export type AuthUser = {
|
|
11
|
+
id: number;
|
|
12
|
+
email: string | null;
|
|
13
|
+
name: string | null;
|
|
14
|
+
avatar: string | null;
|
|
15
|
+
role: string;
|
|
16
|
+
createdAt: number;
|
|
17
|
+
};
|
|
18
|
+
/** Per-request auth state, resolved by the host before the endpoint runs (`RequestContext.auth`). */
|
|
19
|
+
export type AuthState = {
|
|
20
|
+
sessionId: number;
|
|
21
|
+
userId: number | null;
|
|
22
|
+
user: AuthUser | null;
|
|
23
|
+
/** A token to hand back to the client in this response (a new guest session, or a rotation). */
|
|
24
|
+
issuedToken?: string;
|
|
25
|
+
};
|
|
26
|
+
/** What an OAuth provider hands the runner after a successful web sign-in. */
|
|
27
|
+
export type OAuthProfile = {
|
|
28
|
+
sub: string;
|
|
29
|
+
email?: string | null;
|
|
30
|
+
emailVerified?: boolean;
|
|
31
|
+
name?: string | null;
|
|
32
|
+
avatar?: string | null;
|
|
33
|
+
};
|
|
34
|
+
/** A credential a NATIVE provider SDK produced in the app (client plugin `OAuth.signIn`): an access token
|
|
35
|
+
* (Yandex, VK ID) or an OpenID identity token (Google, Apple). Verified server-side, never trusted as-is. */
|
|
36
|
+
export type OAuthCredential = {
|
|
37
|
+
accessToken?: string;
|
|
38
|
+
idToken?: string;
|
|
39
|
+
name?: string | null;
|
|
40
|
+
email?: string | null;
|
|
41
|
+
};
|
|
42
|
+
/** Host operations the bundle's `auth` global forwards to (all request-scoped through `ctx`). */
|
|
43
|
+
export type AuthOps = {
|
|
44
|
+
email: {
|
|
45
|
+
sendCode(ctx: RequestContext, email: string): Promise<void>;
|
|
46
|
+
verify(ctx: RequestContext, email: string, code: string): Promise<AuthUser>;
|
|
47
|
+
};
|
|
48
|
+
oauth: {
|
|
49
|
+
url(ctx: RequestContext, provider: Exclude<AuthProvider, "email">): Promise<string>;
|
|
50
|
+
signIn(ctx: RequestContext, provider: Exclude<AuthProvider, "email">, credential: OAuthCredential): Promise<AuthUser>;
|
|
51
|
+
};
|
|
52
|
+
signIn(ctx: RequestContext, userId: number): Promise<AuthUser>;
|
|
53
|
+
signOut(ctx: RequestContext): Promise<void>;
|
|
54
|
+
/** `db.session` filtered to the current user's sessions (or just this device's, when signed out). */
|
|
55
|
+
sessions(ctx: RequestContext): any;
|
|
56
|
+
};
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Server side of channels (docs/backend-plan.md §3.3): typed pub/sub, server → client only.
|
|
3
|
+
*
|
|
4
|
+
* type ChatEvents = { message: { from: string; text: string }; typing: { from: string } }
|
|
5
|
+
* export const chat = channel<ChatEvents>({ onJoin: room => { auth.requireUser() } })
|
|
6
|
+
* chat.publish(room, "message", { from, text })
|
|
7
|
+
*
|
|
8
|
+
* A channel's identity is its export (`<path>#<name>`), assigned by the runtime when the bundle is
|
|
9
|
+
* loaded (`loadServerModules`); `publish` before that is an error. Delivery goes through the
|
|
10
|
+
* `globalThis.__lecodesPublish` seam the runner installs (same reason as ./context.ts: the bundle
|
|
11
|
+
* carries its own SDK copy).
|
|
12
|
+
*/
|
|
13
|
+
export type ChannelEvents = Record<string, unknown>;
|
|
14
|
+
export type ChannelOptions = {
|
|
15
|
+
/** Called when a client subscribes to `topic`; throw (e.g. `ApiError(403)`) to refuse. */
|
|
16
|
+
onJoin?: (topic: string) => void | Promise<void>;
|
|
17
|
+
};
|
|
18
|
+
export interface Channel<E extends ChannelEvents> {
|
|
19
|
+
readonly options: ChannelOptions;
|
|
20
|
+
/** Deliver `event` with `payload` to every subscriber of `topic` (at-most-once). */
|
|
21
|
+
publish<K extends keyof E & string>(topic: string, event: K, payload: E[K]): void;
|
|
22
|
+
}
|
|
23
|
+
type Publisher = (channelId: string, topic: string, event: string, payload: unknown) => void;
|
|
24
|
+
/** Host hook (runner / test harness): where `publish` delivers to. */
|
|
25
|
+
export declare const setChannelPublisher: (publisher: Publisher | null) => void;
|
|
26
|
+
export declare const channel: <E extends ChannelEvents>(options?: ChannelOptions) => Channel<E>;
|
|
27
|
+
export declare const isChannel: (v: unknown) => v is Channel<any>;
|
|
28
|
+
export {};
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Request context for server code. The runner keeps the current request in an AsyncLocalStorage
|
|
3
|
+
* and exposes it through `globalThis.__lecodesRequest` — a *global* seam on purpose: the compiled
|
|
4
|
+
* server bundle carries its own copy of this module (chisel bundles the SDK in), so the host can't
|
|
5
|
+
* hand it a value by import. `request` reads through that seam; outside a request (module load,
|
|
6
|
+
* timers after the response) every member is undefined.
|
|
7
|
+
*/
|
|
8
|
+
export type RequestContext = {
|
|
9
|
+
/** Endpoint id `<path>#<export>` (or the channel id for `onJoin`). */
|
|
10
|
+
id: string;
|
|
11
|
+
headers: Record<string, string>;
|
|
12
|
+
ip?: string;
|
|
13
|
+
/** Bearer session token as sent by the client transport (raw; auth resolves it). */
|
|
14
|
+
sessionToken?: string;
|
|
15
|
+
/** Set by the auth runtime after resolving the token — read via `auth.*`, not here. */
|
|
16
|
+
auth?: unknown;
|
|
17
|
+
};
|
|
18
|
+
type Provider = () => RequestContext | undefined;
|
|
19
|
+
/** Host hook (runner / test harness): install the current-request provider. */
|
|
20
|
+
export declare const setRequestProvider: (provider: Provider | null) => void;
|
|
21
|
+
/** The current request (server global). Undefined members outside a request. */
|
|
22
|
+
export declare const request: {
|
|
23
|
+
readonly id: string | undefined;
|
|
24
|
+
readonly headers: Record<string, string>;
|
|
25
|
+
readonly ip: string | undefined;
|
|
26
|
+
};
|
|
27
|
+
export {};
|
|
@@ -0,0 +1,36 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `model({...})` + `defineDb({ User, Post })` — the schema registry and the typed db handle.
|
|
3
|
+
*
|
|
4
|
+
* Runtime responsibilities: validate relation names, resolve `t.many()` back-fields, emit the `.marci`
|
|
5
|
+
* schema text (`db.$schema`), and turn collection calls into lazy `Op`s over a `MarciTransport`
|
|
6
|
+
* (`marcidb-embedded` handle, HTTP client, or a test fake). The transport is either passed to
|
|
7
|
+
* `defineDb(models, { transport })` or provided by the host through `setDbTransport()` — user code
|
|
8
|
+
* never sees a connection string.
|
|
9
|
+
*/
|
|
10
|
+
import type { FieldDef } from "./fields";
|
|
11
|
+
import { type MarciTransport } from "./marci/query";
|
|
12
|
+
import type { Db, Fields, Model, Schema, ValidateRefs } from "./types";
|
|
13
|
+
export declare const model: <F extends Fields>(fields: F) => Model<F>;
|
|
14
|
+
/** Host hook: the runner/dev-server installs the project's transport before loading user code. */
|
|
15
|
+
export declare const setDbTransport: (transport: MarciTransport | null) => void;
|
|
16
|
+
/**
|
|
17
|
+
* Every `defineDb` call registers its handle here so the host finds the schema whether or not the
|
|
18
|
+
* project exports `db` (`const db = defineDb(...)` used only inside endpoints is the common case).
|
|
19
|
+
* The host reads and clears the list after evaluating a bundle (`loadServerModules`).
|
|
20
|
+
*/
|
|
21
|
+
export declare const takeRegisteredDbs: () => Db<any>[];
|
|
22
|
+
/** A reference to a previous operation's result inside `$transaction` (resolved server-side): `ref("0.id")`. */
|
|
23
|
+
export declare const ref: (path: string) => any;
|
|
24
|
+
type ModelMeta = {
|
|
25
|
+
name: string;
|
|
26
|
+
fields: Record<string, FieldDef>;
|
|
27
|
+
idKeys: string[];
|
|
28
|
+
/** id is a single uuid key we generate on insert. */
|
|
29
|
+
uuidId: boolean;
|
|
30
|
+
};
|
|
31
|
+
export declare const toMarci: (metas: Record<string, ModelMeta>) => string;
|
|
32
|
+
export type DefineDbOptions = {
|
|
33
|
+
transport?: MarciTransport;
|
|
34
|
+
};
|
|
35
|
+
export declare const defineDb: <const S extends Schema>(declared: S & ValidateRefs<S>, options?: DefineDbOptions) => Db<S>;
|
|
36
|
+
export {};
|
|
@@ -0,0 +1,146 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* `t` — field builders for `model({...})`. Each builder returns an immutable `Field` carrying a runtime
|
|
3
|
+
* `FieldDef` (what `.marci` is emitted from) and two phantom type parameters: the TS value type and a
|
|
4
|
+
* `FieldMeta` record (kind / optional / default / …) that `defineDb`'s type layer projects into row,
|
|
5
|
+
* insert, update, select and where types. Chained modifiers return a NEW field (builders are never
|
|
6
|
+
* mutated), so `const s = t.string(); { a: s, b: s.optional() }` behaves as expected.
|
|
7
|
+
*/
|
|
8
|
+
import type { JsonValue } from "./marci/query";
|
|
9
|
+
export type ScalarKind = "string" | "int" | "float" | "bool" | "date" | "uuid" | "";
|
|
10
|
+
export type FieldKind = "scalar" | "json" | "enum" | "struct" | "one" | "many" | "list";
|
|
11
|
+
export type OnDelete = "cascade" | "setNull" | "restrict";
|
|
12
|
+
/** Phantom metadata — the type-level twin of `FieldDef`. */
|
|
13
|
+
export type FieldMeta = {
|
|
14
|
+
kind: FieldKind;
|
|
15
|
+
scalar: ScalarKind;
|
|
16
|
+
optional: boolean;
|
|
17
|
+
hasDefault: boolean;
|
|
18
|
+
array: boolean;
|
|
19
|
+
isId: boolean;
|
|
20
|
+
/** Related model name for one/many/list; "" otherwise. */
|
|
21
|
+
model: string;
|
|
22
|
+
};
|
|
23
|
+
type DefaultMeta = {
|
|
24
|
+
kind: "scalar";
|
|
25
|
+
scalar: "";
|
|
26
|
+
optional: false;
|
|
27
|
+
hasDefault: false;
|
|
28
|
+
array: false;
|
|
29
|
+
isId: false;
|
|
30
|
+
model: "";
|
|
31
|
+
};
|
|
32
|
+
export type Meta<O extends Partial<FieldMeta>> = {
|
|
33
|
+
[P in keyof FieldMeta]: P extends keyof O ? O[P] : DefaultMeta[P];
|
|
34
|
+
};
|
|
35
|
+
type SetMeta<M extends FieldMeta, K extends keyof FieldMeta, V> = {
|
|
36
|
+
[P in keyof FieldMeta]: P extends K ? V : M[P];
|
|
37
|
+
};
|
|
38
|
+
/** Runtime field definition — everything the `.marci` emitter and the runtime need. */
|
|
39
|
+
export type FieldDef = {
|
|
40
|
+
kind: FieldKind;
|
|
41
|
+
scalar?: ScalarKind;
|
|
42
|
+
optional: boolean;
|
|
43
|
+
unique: boolean;
|
|
44
|
+
index: boolean;
|
|
45
|
+
hasDefault: boolean;
|
|
46
|
+
default?: unknown;
|
|
47
|
+
array: boolean;
|
|
48
|
+
isId: boolean;
|
|
49
|
+
onDelete?: OnDelete;
|
|
50
|
+
fulltext?: "multi" | "english" | "russian";
|
|
51
|
+
vector?: {
|
|
52
|
+
size: number;
|
|
53
|
+
metric: "cosine" | "euclidean";
|
|
54
|
+
};
|
|
55
|
+
/** enum */
|
|
56
|
+
values?: readonly string[];
|
|
57
|
+
/** struct */
|
|
58
|
+
fields?: Record<string, Field<any, any>>;
|
|
59
|
+
/** one / many / list */
|
|
60
|
+
model?: string;
|
|
61
|
+
/** many: the field on the related model that holds the reference (`@bind`); resolved by defineDb when omitted. */
|
|
62
|
+
back?: string;
|
|
63
|
+
};
|
|
64
|
+
type DefaultOf<T, M extends FieldMeta> = M["scalar"] extends "date" ? "now" | number : M["array"] extends true ? T[] : T;
|
|
65
|
+
export interface Field<T, M extends FieldMeta = FieldMeta> {
|
|
66
|
+
/** phantom (type-level only — never set at runtime) */ readonly __t?: T;
|
|
67
|
+
/** phantom (type-level only — never set at runtime) */ readonly __m?: M;
|
|
68
|
+
readonly def: FieldDef;
|
|
69
|
+
/** Nullable column (`String?`). */
|
|
70
|
+
optional(): Field<T, SetMeta<M, "optional", true>>;
|
|
71
|
+
/** `@unique` (on a relation: one-to-one). */
|
|
72
|
+
unique(): Field<T, M>;
|
|
73
|
+
/** `@index` — used by `$where`, `$order`, aggregations. */
|
|
74
|
+
index(): Field<T, M>;
|
|
75
|
+
/** `@default(...)`; `"now"` on `t.date()` → `now()`. Makes the field optional on insert. */
|
|
76
|
+
default(value: DefaultOf<T, M>): Field<T, SetMeta<M, "hasDefault", true>>;
|
|
77
|
+
/** Primitive list (`String[]`). */
|
|
78
|
+
array(): Field<T, SetMeta<M, "array", true>>;
|
|
79
|
+
/** `@id` — primary key (several → composite). A field literally named `id` is the key implicitly. */
|
|
80
|
+
id(): Field<T, SetMeta<M, "isId", true>>;
|
|
81
|
+
/** Referential policy for `t.one()` (defaults: required → restrict, optional → setNull). */
|
|
82
|
+
onDelete(policy: OnDelete): Field<T, M>;
|
|
83
|
+
/** `@fulltext(...)` module index on a string field; query with `$search`. */
|
|
84
|
+
fulltext(lang?: "multi" | "english" | "russian"): Field<T, M>;
|
|
85
|
+
/** `Float[n] @vector(metric)` — nearest-neighbour index; query with `$near`. */
|
|
86
|
+
vector(size: number, metric?: "cosine" | "euclidean"): Field<T, M>;
|
|
87
|
+
}
|
|
88
|
+
export declare const t: {
|
|
89
|
+
string: () => Field<string, Meta<{
|
|
90
|
+
kind: "scalar";
|
|
91
|
+
scalar: "string";
|
|
92
|
+
}>>;
|
|
93
|
+
/** 64-bit signed integer. */
|
|
94
|
+
int: () => Field<number, Meta<{
|
|
95
|
+
kind: "scalar";
|
|
96
|
+
scalar: "int";
|
|
97
|
+
}>>;
|
|
98
|
+
/** 64-bit float. */
|
|
99
|
+
float: () => Field<number, Meta<{
|
|
100
|
+
kind: "scalar";
|
|
101
|
+
scalar: "float";
|
|
102
|
+
}>>;
|
|
103
|
+
bool: () => Field<boolean, Meta<{
|
|
104
|
+
kind: "scalar";
|
|
105
|
+
scalar: "bool";
|
|
106
|
+
}>>;
|
|
107
|
+
/** Epoch milliseconds — reads and writes as `number`. */
|
|
108
|
+
date: () => Field<number, Meta<{
|
|
109
|
+
kind: "scalar";
|
|
110
|
+
scalar: "date";
|
|
111
|
+
}>>;
|
|
112
|
+
/** UUID string (16 bytes in storage). On an `id` field the runtime generates it on insert. */
|
|
113
|
+
uuid: () => Field<string, Meta<{
|
|
114
|
+
kind: "scalar";
|
|
115
|
+
scalar: "uuid";
|
|
116
|
+
}>>;
|
|
117
|
+
/** Any JSON value; `J` is TS-only (marcidb stores it schemaless). Filter by dot-path in `$where`. */
|
|
118
|
+
json: <J = JsonValue>() => Field<J, Meta<{
|
|
119
|
+
kind: "json";
|
|
120
|
+
}>>;
|
|
121
|
+
/** String enum: `t.enum("draft", "published")`. */
|
|
122
|
+
enum: <const V extends readonly [string, ...string[]]>(...values: V) => Field<V[number], Meta<{
|
|
123
|
+
kind: "enum";
|
|
124
|
+
}>>;
|
|
125
|
+
/** Owned nested object (marcidb `struct`): created/updated with the parent, no id of its own. */
|
|
126
|
+
struct: <F extends Record<string, Field<any, any>>>(fields: F) => Field<F, Meta<{
|
|
127
|
+
kind: "struct";
|
|
128
|
+
}>>;
|
|
129
|
+
/** Reference to one row of `model` (by id). Required unless `.optional()`. */
|
|
130
|
+
one: <N extends string>(model: N) => Field<never, Meta<{
|
|
131
|
+
kind: "one";
|
|
132
|
+
model: N;
|
|
133
|
+
}>>;
|
|
134
|
+
/** Reverse side of a `t.one()` on `model` (the field is inferred when unambiguous). Read-only list. */
|
|
135
|
+
many: <N extends string>(model: N, backField?: string) => Field<never, Meta<{
|
|
136
|
+
kind: "many";
|
|
137
|
+
model: N;
|
|
138
|
+
}>>;
|
|
139
|
+
/** Ordered relation list stored inline (`@list`) — hand-arranged collections, duplicates allowed. */
|
|
140
|
+
list: <N extends string>(model: N) => Field<never, Meta<{
|
|
141
|
+
kind: "list";
|
|
142
|
+
model: N;
|
|
143
|
+
}>>;
|
|
144
|
+
};
|
|
145
|
+
export type T = typeof t;
|
|
146
|
+
export {};
|
|
@@ -0,0 +1,6 @@
|
|
|
1
|
+
export { t } from "./fields";
|
|
2
|
+
export type { Field, FieldDef, FieldMeta } from "./fields";
|
|
3
|
+
export { model, defineDb, ref, setDbTransport, toMarci } from "./defineDb";
|
|
4
|
+
export type { DefineDbOptions } from "./defineDb";
|
|
5
|
+
export type { Db, Model, Schema, Row, Id, Insert, Update, Select, Where, Query, QueryObject, Result, Collection, ScalarSelect, Types } from "./types";
|
|
6
|
+
export type { Op, MarciOp, MarciTransport, JsonValue, Sub } from "./marci/query";
|
|
@@ -0,0 +1,326 @@
|
|
|
1
|
+
export type ServiceKeys = "$where" | "$order" | "$limit" | "$skip" | "$cursor";
|
|
2
|
+
export type JsonValue = string | number | boolean | null | JsonValue[] | {
|
|
3
|
+
[key: string]: JsonValue;
|
|
4
|
+
};
|
|
5
|
+
export type AggregateKeys = {
|
|
6
|
+
$count: true;
|
|
7
|
+
} | {
|
|
8
|
+
$sum: string;
|
|
9
|
+
} | {
|
|
10
|
+
$avg: string;
|
|
11
|
+
} | {
|
|
12
|
+
$min: string;
|
|
13
|
+
} | {
|
|
14
|
+
$max: string;
|
|
15
|
+
};
|
|
16
|
+
export type GetResult<TModel, TSelect> = TModel extends any ? {
|
|
17
|
+
-readonly [K in keyof Omit<TSelect, ServiceKeys> as TSelect[K] extends false | undefined ? never : K extends keyof TModel ? K : never]: K extends keyof TModel ? TSelect[K] extends true ? TModel[K] : TSelect[K] extends Record<string, any> ? TModel[K] extends readonly object[] ? TSelect[K] extends AggregateKeys ? AggregateResult<NonNullable<TModel[K][number]>, TSelect[K]> : GetResult<NonNullable<TModel[K][number]>, TSelect[K]>[] : GetResult<NonNullable<TModel[K]>, TSelect[K]> | Extract<TModel[K], null> : TModel[K] : never;
|
|
18
|
+
} : never;
|
|
19
|
+
export type RefUpdate<I> = {
|
|
20
|
+
"$connect"?: I;
|
|
21
|
+
};
|
|
22
|
+
export type RefUpdateStruct<I, U> = {
|
|
23
|
+
"$update"?: U;
|
|
24
|
+
"$ensure"?: I;
|
|
25
|
+
"$set"?: I;
|
|
26
|
+
};
|
|
27
|
+
/** Relation to independent rows — link operations only, the rows themselves are never created
|
|
28
|
+
* or deleted. `$set` replaces link membership with exactly the given set (missing links are
|
|
29
|
+
* disconnected, new ones connected); `$connect` links (idempotent); `$remove` unlinks. */
|
|
30
|
+
export type RefListUpdate<I> = {
|
|
31
|
+
"$set"?: I[];
|
|
32
|
+
"$connect"?: I | I[];
|
|
33
|
+
"$remove"?: I | I[];
|
|
34
|
+
};
|
|
35
|
+
/** `@list` relation: an ordered inline id array — a sequence, so the same id may appear several
|
|
36
|
+
* times. `$set` replaces the whole array (also the reorder operation); `$connect` appends at the
|
|
37
|
+
* end (an already-present id gains another occurrence); `$connectUnique` appends only ids not
|
|
38
|
+
* already present; `$remove` removes every occurrence. */
|
|
39
|
+
export type RefListUpdateOrdered<I> = {
|
|
40
|
+
"$set"?: I[];
|
|
41
|
+
"$connect"?: I | I[];
|
|
42
|
+
"$connectUnique"?: I | I[];
|
|
43
|
+
"$remove"?: I | I[];
|
|
44
|
+
};
|
|
45
|
+
/** Owned (struct) list: the children live and die with the parent. `$push` creates children,
|
|
46
|
+
* `$update` edits single children in place (each item is the child's id fields — the shape
|
|
47
|
+
* query results return — plus the changes under `data`), `$remove` deletes children by id,
|
|
48
|
+
* `$set` replaces all children (deletes the current ones, creates the new). */
|
|
49
|
+
export type RefListUpdateStruct<I, U, Id> = {
|
|
50
|
+
"$push"?: I | I[];
|
|
51
|
+
"$update"?: (Id & {
|
|
52
|
+
data: U;
|
|
53
|
+
}) | (Id & {
|
|
54
|
+
data: U;
|
|
55
|
+
})[];
|
|
56
|
+
"$remove"?: Id | Id[];
|
|
57
|
+
"$set"?: I[];
|
|
58
|
+
};
|
|
59
|
+
/** Variable-length primitive array — a sequence, so the same value may appear several times.
|
|
60
|
+
* `$push` appends at the end (duplicates kept); `$pushUnique` appends only values not already
|
|
61
|
+
* present; `$remove` removes every occurrence; `$set` replaces the whole array (also the
|
|
62
|
+
* positional-edit path — send the full new array). One operator per update. */
|
|
63
|
+
export type PrimitiveListUpdate<T> = {
|
|
64
|
+
"$set"?: T[];
|
|
65
|
+
"$push"?: T | T[];
|
|
66
|
+
"$pushUnique"?: T | T[];
|
|
67
|
+
"$remove"?: T | T[];
|
|
68
|
+
};
|
|
69
|
+
export type Never<T> = {
|
|
70
|
+
[K in keyof T]?: never;
|
|
71
|
+
};
|
|
72
|
+
export type FieldOps = {
|
|
73
|
+
"$eq": unknown;
|
|
74
|
+
"$ne": unknown;
|
|
75
|
+
"$not": unknown;
|
|
76
|
+
"$in": unknown;
|
|
77
|
+
"$notIn": unknown;
|
|
78
|
+
"$gt": unknown;
|
|
79
|
+
"$gte": unknown;
|
|
80
|
+
"$lt": unknown;
|
|
81
|
+
"$lte": unknown;
|
|
82
|
+
"$startsWith": unknown;
|
|
83
|
+
"$includes": unknown;
|
|
84
|
+
"$every": unknown;
|
|
85
|
+
"$some": unknown;
|
|
86
|
+
"$none": unknown;
|
|
87
|
+
"$near": unknown;
|
|
88
|
+
"$search": unknown;
|
|
89
|
+
};
|
|
90
|
+
export type Only<K extends keyof FieldOps, V> = {
|
|
91
|
+
[P in K]: V;
|
|
92
|
+
} & Never<Omit<FieldOps, K>>;
|
|
93
|
+
export type WhereValue<T> = (T & Never<{
|
|
94
|
+
"$and": unknown;
|
|
95
|
+
"$or": unknown;
|
|
96
|
+
"$not": unknown;
|
|
97
|
+
}>) | ({
|
|
98
|
+
"$and": WhereValue<T>[];
|
|
99
|
+
} & Never<T> & Never<{
|
|
100
|
+
"$or": unknown;
|
|
101
|
+
"$not": unknown;
|
|
102
|
+
}>) | ({
|
|
103
|
+
"$or": WhereValue<T>[];
|
|
104
|
+
} & Never<T> & Never<{
|
|
105
|
+
"$and": unknown;
|
|
106
|
+
"$not": unknown;
|
|
107
|
+
}>) | ({
|
|
108
|
+
"$not": WhereValue<T>;
|
|
109
|
+
} & Never<T> & Never<{
|
|
110
|
+
"$and": unknown;
|
|
111
|
+
"$or": unknown;
|
|
112
|
+
}>);
|
|
113
|
+
export type ValueOps<T> = {
|
|
114
|
+
"$eq"?: T;
|
|
115
|
+
"$ne"?: T;
|
|
116
|
+
"$not"?: T;
|
|
117
|
+
"$in"?: T[];
|
|
118
|
+
"$notIn"?: T[];
|
|
119
|
+
};
|
|
120
|
+
export type NumOps<T> = {
|
|
121
|
+
"$gt"?: T;
|
|
122
|
+
"$gte"?: T;
|
|
123
|
+
"$lt"?: T;
|
|
124
|
+
"$lte"?: T;
|
|
125
|
+
};
|
|
126
|
+
export type StrOps = {
|
|
127
|
+
"$includes"?: string;
|
|
128
|
+
"$startsWith"?: string;
|
|
129
|
+
};
|
|
130
|
+
export type CompareValue<T> = T | (ValueOps<T> & Never<Omit<FieldOps, keyof ValueOps<T>>>);
|
|
131
|
+
export type CompareNumValue<T> = ValueOps<T> & NumOps<T> & Never<Omit<FieldOps, keyof ValueOps<T> | keyof NumOps<T>>>;
|
|
132
|
+
export type CompareStrValue<T> = ValueOps<T> & StrOps & Never<Omit<FieldOps, keyof ValueOps<T> | keyof StrOps>>;
|
|
133
|
+
export type UpdateNumValue = {
|
|
134
|
+
"$increment": number;
|
|
135
|
+
};
|
|
136
|
+
export type JsonType = "string" | "number" | "boolean" | "object" | "array" | "null";
|
|
137
|
+
export type JsonCondition = JsonValue | {
|
|
138
|
+
"$eq"?: JsonValue;
|
|
139
|
+
"$ne"?: JsonValue;
|
|
140
|
+
"$not"?: JsonValue;
|
|
141
|
+
"$gt"?: number | string;
|
|
142
|
+
"$gte"?: number | string;
|
|
143
|
+
"$lt"?: number | string;
|
|
144
|
+
"$lte"?: number | string;
|
|
145
|
+
"$in"?: JsonValue[];
|
|
146
|
+
"$notIn"?: JsonValue[];
|
|
147
|
+
"$startsWith"?: string;
|
|
148
|
+
"$includes"?: string;
|
|
149
|
+
"$contains"?: JsonValue;
|
|
150
|
+
"$exists"?: boolean;
|
|
151
|
+
"$type"?: JsonType;
|
|
152
|
+
};
|
|
153
|
+
export type JsonPathWhere = {
|
|
154
|
+
[path: string]: JsonCondition;
|
|
155
|
+
};
|
|
156
|
+
export type CompareRefValue<T> = T | Only<"$not", T>;
|
|
157
|
+
export type CompareRefListValue<T> = Only<"$every", T> | Only<"$some", T> | Only<"$none", T>;
|
|
158
|
+
export type VectorSearch = {
|
|
159
|
+
vector: number[];
|
|
160
|
+
k?: number;
|
|
161
|
+
threshold?: number;
|
|
162
|
+
};
|
|
163
|
+
export type FullTextSearch = string | {
|
|
164
|
+
query: string;
|
|
165
|
+
limit?: number;
|
|
166
|
+
};
|
|
167
|
+
export type CustomSearch = Record<string, any>;
|
|
168
|
+
export type CustomSearchValue<P> = Only<"$near", P> | Only<"$search", P>;
|
|
169
|
+
export type AggregateResult<TModel, T> = (T extends {
|
|
170
|
+
$count: true;
|
|
171
|
+
} ? {
|
|
172
|
+
count: number;
|
|
173
|
+
} : {}) & (T extends {
|
|
174
|
+
$sum: string;
|
|
175
|
+
} ? {
|
|
176
|
+
sum: number | null;
|
|
177
|
+
} : {}) & (T extends {
|
|
178
|
+
$avg: string;
|
|
179
|
+
} ? {
|
|
180
|
+
avg: number | null;
|
|
181
|
+
} : {}) & (T extends {
|
|
182
|
+
$min: infer F;
|
|
183
|
+
} ? {
|
|
184
|
+
min: (F extends keyof TModel ? TModel[F] : never) | null;
|
|
185
|
+
} : {}) & (T extends {
|
|
186
|
+
$max: infer F;
|
|
187
|
+
} ? {
|
|
188
|
+
max: (F extends keyof TModel ? TModel[F] : never) | null;
|
|
189
|
+
} : {});
|
|
190
|
+
declare const __op: unique symbol;
|
|
191
|
+
export type Op<T> = PromiseLike<T> & {
|
|
192
|
+
readonly [__op]: T;
|
|
193
|
+
};
|
|
194
|
+
export type MarciOp = {
|
|
195
|
+
model: string;
|
|
196
|
+
action: string;
|
|
197
|
+
query?: any;
|
|
198
|
+
data?: any;
|
|
199
|
+
id?: any;
|
|
200
|
+
};
|
|
201
|
+
export type MarciTransport = {
|
|
202
|
+
exec(op: MarciOp): Promise<any>;
|
|
203
|
+
batch(ops: MarciOp[]): Promise<any[]>;
|
|
204
|
+
};
|
|
205
|
+
export type ModelTypes = {
|
|
206
|
+
name: string;
|
|
207
|
+
model: any;
|
|
208
|
+
id: Record<string, any>;
|
|
209
|
+
/** What an empty select returns: id + every scalar field, as a `{ field: true }` shape. */
|
|
210
|
+
scalars: Record<string, true>;
|
|
211
|
+
select: Record<string, any>;
|
|
212
|
+
query: Record<string, any>;
|
|
213
|
+
where: any;
|
|
214
|
+
order: Record<string, any>;
|
|
215
|
+
insert: any;
|
|
216
|
+
update: any;
|
|
217
|
+
aggregate: Record<string, any>;
|
|
218
|
+
reindex: boolean;
|
|
219
|
+
};
|
|
220
|
+
declare const __sub: unique symbol;
|
|
221
|
+
declare const __sel: unique symbol;
|
|
222
|
+
export type Sub<Name extends string, Shape = any> = {
|
|
223
|
+
readonly [__sub]: Name;
|
|
224
|
+
readonly [__sel]: Shape;
|
|
225
|
+
};
|
|
226
|
+
export type Effective<T extends ModelTypes, S> = [Exclude<keyof S, ServiceKeys>] extends [never] ? T["scalars"] : S;
|
|
227
|
+
export type Resolve<S> = S extends {
|
|
228
|
+
readonly [__sel]: infer X;
|
|
229
|
+
} ? Resolve<X> : S extends object ? {
|
|
230
|
+
[K in keyof S]: K extends `$${string}` ? S[K] : Resolve<S[K]>;
|
|
231
|
+
} : S;
|
|
232
|
+
export type Rows<T extends ModelTypes, Sel> = GetResult<T["model"], Resolve<Effective<T, Sel>>>;
|
|
233
|
+
export type BareId<I> = I extends {
|
|
234
|
+
id: infer V;
|
|
235
|
+
} ? V : never;
|
|
236
|
+
export type IdArg<I> = I | BareId<I>;
|
|
237
|
+
/**
|
|
238
|
+
* A lazy, immutable query over one model — `db.user` itself is one. Every clause returns a new query, so
|
|
239
|
+
* queries compose (`const active = db.user.where({ active: true })`). `await` runs it as `findMany`; passing
|
|
240
|
+
* it to `$transaction` batches it; placing it in another query's select makes it a sub-select. `Sel` is the
|
|
241
|
+
* projection: id + scalars until `select(...)` sets a shape.
|
|
242
|
+
*/
|
|
243
|
+
export interface Query<T extends ModelTypes, Sel = T["scalars"]> extends PromiseLike<Rows<T, Sel>[]> {
|
|
244
|
+
readonly [__op]: Rows<T, Sel>[];
|
|
245
|
+
readonly [__sub]: T["name"];
|
|
246
|
+
readonly [__sel]: Effective<T, Sel>;
|
|
247
|
+
/** Filter (marcidb `$where`). Repeated calls are ANDed. */
|
|
248
|
+
where(where: T["where"]): Query<T, Sel>;
|
|
249
|
+
/** Sort by one field: `order("age", "desc")` or `order({ age: "desc" })`. */
|
|
250
|
+
order(field: keyof T["order"] & string, direction?: "asc" | "desc"): Query<T, Sel>;
|
|
251
|
+
order(order: T["order"]): Query<T, Sel>;
|
|
252
|
+
limit(n: number): Query<T, Sel>;
|
|
253
|
+
skip(n: number): Query<T, Sel>;
|
|
254
|
+
/** Keyset cursor: rows strictly after this id in the current order (`$cursor`). */
|
|
255
|
+
after(id: IdArg<T["id"]>): Query<T, Sel>;
|
|
256
|
+
/**
|
|
257
|
+
* The projection. Values are `true`, a nested shape, or a sub-query of the relation's model
|
|
258
|
+
* (`posts: db.post.limit(5)`, `posts: db.post.where({ published: true }).count()`). No argument, or no
|
|
259
|
+
* field keys, selects id + every scalar. `$`-clauses are accepted here too (the object form).
|
|
260
|
+
*/
|
|
261
|
+
select<S extends T["query"] = T["scalars"]>(shape?: S): Query<T, S>;
|
|
262
|
+
/** The first matching row or `null`. */
|
|
263
|
+
first(): Op<Rows<T, Sel> | null>;
|
|
264
|
+
/** Row count; inside a select it becomes `{ count }` for the relation. */
|
|
265
|
+
count(): Op<number> & Sub<T["name"], {
|
|
266
|
+
$count: true;
|
|
267
|
+
}>;
|
|
268
|
+
/** @deprecated pass the filter through the chain: `db.user.where(w).count()` (removed in the next minor). */
|
|
269
|
+
count(query: {
|
|
270
|
+
$where?: T["where"];
|
|
271
|
+
}): Op<number> & Sub<T["name"], {
|
|
272
|
+
$count: true;
|
|
273
|
+
}>;
|
|
274
|
+
aggregate<A extends T["aggregate"]>(query: A): Op<AggregateResult<T["model"], A>> & Sub<T["name"], NoInfer<A>>;
|
|
275
|
+
insert(data: T["insert"]): Op<T["id"]>;
|
|
276
|
+
update(id: IdArg<T["id"]>, data: T["update"]): Op<void>;
|
|
277
|
+
/** Applies `data` to every row the chain's `where` matches (all rows without one); resolves to the number of rows. */
|
|
278
|
+
updateMany(data: T["update"]): Op<number>;
|
|
279
|
+
/** @deprecated pass the filter through the chain: `db.user.where(w).updateMany(data)` (removed in the next minor). */
|
|
280
|
+
updateMany(query: {
|
|
281
|
+
$where?: T["where"];
|
|
282
|
+
}, data: T["update"]): Op<number>;
|
|
283
|
+
delete(id: IdArg<T["id"]>): Op<void>;
|
|
284
|
+
/**
|
|
285
|
+
* Deletes every row the chain's `where` matches (cascades apply, as for `delete`); resolves to the number
|
|
286
|
+
* deleted. Refuses to run without a `where` — write `.where({})` to mean "every row".
|
|
287
|
+
*/
|
|
288
|
+
deleteMany(): Op<number>;
|
|
289
|
+
/** @deprecated use `.select(query)` — it takes the same object, merged with the chain (removed in the next minor). */
|
|
290
|
+
findMany<Q extends T["query"] = {}>(query?: Q): Op<Rows<T, Q>[]>;
|
|
291
|
+
/** @deprecated use `.select(query).first()` (removed in the next minor). */
|
|
292
|
+
findFirst<Q extends T["query"] = {}>(query?: Q): Op<Rows<T, Q> | null>;
|
|
293
|
+
}
|
|
294
|
+
/** `db.<model>`: the root query, plus `reindex()` for models with a `@custom` (vector / full-text) index. */
|
|
295
|
+
export type Collection<T extends ModelTypes> = Query<T> & (T["reindex"] extends true ? {
|
|
296
|
+
reindex(): Op<{
|
|
297
|
+
ok: boolean;
|
|
298
|
+
indexed: number;
|
|
299
|
+
}>;
|
|
300
|
+
} : {});
|
|
301
|
+
/** One field of a model, in slot order: `n` name, `k` key | body | one | many, `m` the relation's target model. */
|
|
302
|
+
export type FieldDesc = {
|
|
303
|
+
n: string;
|
|
304
|
+
k: "key" | "body" | "one" | "many";
|
|
305
|
+
t?: string | null;
|
|
306
|
+
m?: string;
|
|
307
|
+
};
|
|
308
|
+
/** Model name → its field descriptors (structs included, as relation targets). */
|
|
309
|
+
export type ModelsMeta = Record<string, readonly FieldDesc[]>;
|
|
310
|
+
export type QueryLayerOptions = {
|
|
311
|
+
models: ModelsMeta;
|
|
312
|
+
/** Runs one operation (a query, or a write) and resolves its result. */
|
|
313
|
+
run(op: MarciOp): Promise<any>;
|
|
314
|
+
/** Hook for `insert` payloads (the lecodes SDK generates uuid ids here). */
|
|
315
|
+
prepareInsert?(model: string, data: any): any;
|
|
316
|
+
};
|
|
317
|
+
/**
|
|
318
|
+
* The query builder over a set of models and a `run` function. Returns `op(descriptor)` — a lazy operation
|
|
319
|
+
* (`await` runs it, `$transaction` takes its `__op`) — and `collection(model)`, the immutable `db.<model>`
|
|
320
|
+
* root query. Transport-agnostic: the generated client and the embedded/HTTP transports supply `run`.
|
|
321
|
+
*/
|
|
322
|
+
export declare function createQueryLayer(options: QueryLayerOptions): {
|
|
323
|
+
op: (descriptor: MarciOp) => any;
|
|
324
|
+
collection: (model: string) => any;
|
|
325
|
+
};
|
|
326
|
+
export {};
|