How Server-Driven UI Passes Schemas to JavaScript

Server-driven UI (SDUI) architecture allows backend services to control the structure, styling, and behavior of a frontend interface by transmitting declarative layout schemas directly to client-side JavaScript. Instead of relying on hardcoded client component hierarchies, the server serializes UI definitions—typically via structured JSON or GraphQL payloads—over standard network protocols. The client JavaScript application then parses this schema, maps abstract component definitions to a local component registry, and dynamically renders the user interface in real time.

1. Schema Definition and Structure

The server constructs the UI using a standardized data format, universally represented as a nested JSON tree. This schema decouples the data model from presentation logic while specifying exactly how components should be arranged and configured.

A typical SDUI schema object contains: * type / component: The identifier matching a corresponding frontend component (e.g., "Carousel", "Button", "Banner"). * id: A unique key for UI reconciliation, accessibility, and state tracking. * props / attributes: Visual properties such as text, colors, layout alignment, and margins. * children: An array of nested schema objects that define child elements. * actions: Definitions for user interactions (e.g., navigation events, analytic triggers, or API calls).

{
  "type": "Card",
  "id": "card-101",
  "props": {
    "elevation": 2,
    "padding": "16px"
  },
  "children": [
    {
      "type": "Text",
      "props": {
        "content": "Special Promotion",
        "variant": "headline"
      }
    },
    {
      "type": "Button",
      "props": {
        "label": "Claim Offer"
      },
      "action": {
        "type": "NAVIGATE",
        "payload": { "url": "/offers/claim" }
      }
    }
  ]
}

2. Network Transport and Delivery

The backend passes the generated schema to the client runtime through standard network communication layers:

3. Client Component Registry Mapping

The core of the client-side JavaScript architecture is the component registry—a lookup table mapping incoming schema type strings to actual frontend components (e.g., React, Vue, Svelte, or native Web Components).

import Button from './components/Button';
import Card from './components/Card';
import Text from './components/Text';

const COMPONENT_REGISTRY = {
  Button,
  Card,
  Text,
};

4. Schema Parsing and Dynamic Rendering

Once the JSON payload arrives, the client processes the node tree recursively. A recursive rendering engine reads each node, validates it, and instantiates the target component from the registry with the provided properties.

function RenderNode({ node }) {
  const Component = COMPONENT_REGISTRY[node.type];

  if (!Component) {
    console.warn(`Unsupported component type: ${node.type}`);
    return null;
  }

  const renderedChildren = node.children 
    ? node.children.map(child => <RenderNode key={child.id} node={child} />)
    : null;

  return (
    <Component {...node.props} action={node.action}>
      {renderedChildren}
    </Component>
  );
}

5. Action and State Binding

The client-side JavaScript infrastructure intercepts declarative action definitions contained in the schema and binds them to local execution handlers.

When a user triggers an event (like a click), the client resolves the action metadata via an action dispatcher: * Navigation Actions: Handled by the client-side router without a full page reload. * API Requests: Dispatched to update server state, which can respond with a new UI schema fragment. * Local State Updates: Processed through client-side state managers (e.g., Redux, Zustand) to toggle local visibility, input forms, or animations.