{
  "schema": "leumas.docs.page/1",
  "id": "pkg:@leumas/dynamic",
  "slug": "engines/dynamic",
  "kind": "capabilities",
  "bucket": "package",
  "title": "@leumas/dynamic — the Dynamic layer",
  "name": "@leumas/dynamic",
  "eyebrow": "the Dynamic layer",
  "chip": null,
  "summary": "The Dynamic layer — a Studio owner's OWN code, added to their own instance. Three parts behind one /api/dynamic prefix: SSR (register components/pages by local path, compile + server-render them...",
  "keywords": [
    "dynamic",
    "server-render",
    "locally-connected",
    "startup",
    "components",
    "dynamic api",
    "leumas dynamic",
    "compile"
  ],
  "audience": "both",
  "funnel": {
    "product": null,
    "cta": null
  },
  "body": "# `@leumas/dynamic` — the Dynamic layer\n\nA Studio owner's **own code**, on the instance they own. Three surfaces behind one `/api/dynamic`\nprefix; Studio's `Dynamic` domain is the UI.\n\n- **SSR** — register a `.jsx`/page/file **by local path**; compile it, server-render it, serve it to\n  any locally-connected app (React live+hydrated, a plain HTML page, or anything that speaks HTTP).\n- **Routers** — register express routers, whole servers, static folders or proxy targets; answer on\n  their mount paths from startup.\n- **Scripts** — a per-user script library: write, edit, run with typed props, sandboxed by default.\n\nFull narrative — the design decisions, the consumer snippets, the traps — lives in\n**`shared/services/knowledge/build-knowledge/dynamic-layer.md`**. This file is the map.\n\n## Mounting it\n\n```js\nimport { createDynamicLayer } from '@leumas/dynamic';\n\n// ONLY inside a caps.fileTools block. See \"The one gate\" below.\nconst dynamic = createDynamicLayer({\n  collStore, requireAuth, requireAdmin: requireRole('admin'),\n  isAdmin: (req) => hasRole(req, 'admin'),\n  roots: toolRoots,                 // the host's path allow-list\n  allowNative: caps.fileTools,\n  adapters, workDir, onEvent, logger,\n});\n\napp.use('/api/dynamic/ssr', dynamic.publicSsrRouter);   // pre-gate: public components only\napp.use('/api/dynamic', dynamic.router);\n// …after every product route:\napp.use((req, res, next) => dynamic.dispatch(req, res, next));\ndynamic.start({ legacyReadStore }).catch(() => {});\n```\n\n## The one gate\n\nEvery part of this engine names a file on the host's disk and then **executes** it. It must mount\nonly where the caller owns the machine — `appliance` and `dev`, never `platform` or `control`. The\nengine does not check that itself, on purpose: a capability check in two places eventually disagrees\nwith itself, and the API is where role lives. `pnpm check:dynamic` asserts the mount stayed there.\n\nWhat the engine *does* enforce, everywhere, with no opt-out:\n\n| Rule | Where |\n|---|---|\n| every path is inside the registered roots; empty list = refuse everything | `src/roots.js` `assertInsideRoots` |\n| the compiler re-checks every file it *reads*, not just the entry | `src/index.js` `onFile` |\n| no mount may shadow `/auth`, `/db`, `/api`, `/ws`… — refused at registration | `src/roots.js` `assertMountPath` |\n| every execution is a worker or a child process with a hard timeout | `src/ssr/render.js`, `src/scripts/run.js` |\n\n## Layout\n\n```\nsrc/roots.js            the ONE path allow-list + the reserved mount prefixes\nsrc/routers/            store.js (4 kinds) · mount.js (one dispatcher) · router.js (CRUD)\nsrc/ssr/                store.js · compile.js (sucrase) · render.js + renderWorker.mjs · embed.js · router.js\nsrc/scripts/            store.js (lmx_scripts, extended) · run.js (LMX | child process) · router.js\nclient/index.jsx        <LeumasComponent> — the React consumer. @leumas/dynamic/client\n```\n\n## Collections\n\n| Collection | Writes | Why |\n|---|---|---|\n| `dynamic_routers` | admin (`PLATFORM_COLLECTIONS`) | a row imports a module into this process, or spawns a program |\n| `ssr_components` | admin (`PLATFORM_COLLECTIONS`) | the server compiles and renders the file it names |\n| `lmx_scripts` | member | shared with the LMX Playground. Privilege is on the RUN, not the write |\n\n## Environment\n\n| Var | Effect |\n|---|---|\n| `DYNAMIC_ROOTS` | extra allowed trees (`;`-separated; **`;` only** on win32 — see `rootsFromEnv`) |\n| `DYNAMIC_SCRIPTS_EXEC=1` | allows `node`/`python`/`shell` scripts (still needs admin + `caps.fileTools`) |\n| `DYNAMIC_SSR_TIMEOUT_MS` | render deadline (default 5000, max 30000) |\n| `DYNAMIC_SCRIPTS_TIMEOUT_MS` | native script deadline (default 30000, max 300000) |\n| `PYTHON_BIN` · `POWERSHELL_BIN` · `SHELL_BIN` | interpreter overrides for the native lane |\n\n## Proving a change\n\n```sh\npnpm check:dynamic            # structural\npnpm check:dynamic:selftest   # proves each check still fires\npnpm smoke:dynamic            # 14 live checks against a booted API\n```\n",
  "source": {
    "path": "shared/engines/dynamic/README.md",
    "blobSha": "",
    "commit": "",
    "committedAt": "",
    "provenance": "no-git",
    "bytes": 4226,
    "hash": "11cf86a9d52d777c539924c2eb7619285a676795"
  },
  "urls": {
    "html": "/p/engines/dynamic",
    "json": "/docs/engines/dynamic.json",
    "md": "/docs/engines/dynamic.md"
  },
  "links": {
    "composes": [
      "pkg:@leumas/api-kit",
      "pkg:@leumas/lmx",
      "pkg:@leumas/schemas"
    ],
    "usedBy": [],
    "product": [],
    "howTo": [
      "how-to:dynamic-layer"
    ],
    "skills": []
  },
  "exports": null
}
