npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@siciyuan404/llm2ui-renderer

v0.1.2

Published

LLM2UI JSON Renderer SDK - Render UI from JSON schemas with a simple API, similar to amis low-code framework

Readme

@llm2ui/renderer

JSON Renderer SDK for LLM2UI - Render UI from JSON schemas with a simple API, similar to amis low-code framework.

Features

  • 🚀 Simple API: render(schema, container) - just like amis
  • 🎨 Multi-platform: Support for PC Web, Mobile Web, Mobile Native, PC Desktop
  • ⚛️ React Integration: <LLM2UI /> component for declarative usage
  • 💚 Vue Integration: Vue 3 component and composable support
  • 🔌 Custom Components: Register your own components easily
  • 📦 Tree-shakable: Only bundle what you use
  • 📝 TypeScript: Full type definitions included

Installation

npm install @llm2ui/renderer
# or
yarn add @llm2ui/renderer
# or
pnpm add @llm2ui/renderer

Styling Setup

The renderer comes with pre-compiled CSS that includes all necessary Tailwind utilities. Just import the styles file:

// In your main entry file (e.g., main.tsx or App.tsx)
import '@siciyuan404/llm2ui-renderer/styles.css';

That's it! The styles.css file includes:

  • All Tailwind CSS utilities used by the components
  • CSS variables for theming (light/dark mode)
  • Base styles and resets

Advanced: Custom Tailwind Setup

If you want to customize the theme or use your own Tailwind configuration:

// tailwind.config.js
const llm2uiConfig = require('@siciyuan404/llm2ui-renderer/tailwind.config');

module.exports = {
  presets: [llm2uiConfig],
  content: [
    './src/**/*.{js,ts,jsx,tsx}',
    // Include renderer's dist files for Tailwind to scan
    './node_modules/@siciyuan404/llm2ui-renderer/dist/**/*.{js,cjs}',
  ],
  // Add your customizations here
  theme: {
    extend: {
      // Custom colors, etc.
    }
  }
};

Quick Start

Basic Rendering

import { render } from '@llm2ui/renderer';

const schema = {
  version: '1.0',
  root: {
    id: 'root',
    type: 'Container',
    children: [
      { 
        id: 'btn', 
        type: 'Button', 
        props: { children: 'Click me' } 
      }
    ]
  }
};

const renderer = render(schema, document.getElementById('app'));

With Options

import { createRenderer } from '@llm2ui/renderer';

const renderer = createRenderer({
  theme: 'dark',
  onEvent: (action, event, componentId) => {
    console.log('Event:', action.type, componentId);
  }
});

renderer.render(schema, container);
renderer.on('click', (event) => console.log('Clicked:', event.componentId));

React Component

import { LLM2UI, type LLM2UIEvent } from '@llm2ui/renderer';

function App() {
  const handleEvent = (event: LLM2UIEvent) => {
    console.log('Event:', event.type, event.componentId);
  };

  return (
    <LLM2UI 
      schema={schema}
      data={{ user: { name: 'John' } }}
      onEvent={handleEvent}
      theme="light"
    />
  );
}

Vue Component

<template>
  <LLM2UI 
    :schema="schema"
    :data="{ user: { name: 'John' } }"
    @event="handleEvent"
    theme="light"
  />
</template>

<script setup lang="ts">
import { LLM2UIVue as LLM2UI, type LLM2UIVueEvent } from '@llm2ui/renderer';

const schema = { /* ... */ };

function handleEvent(event: LLM2UIVueEvent) {
  console.log('Event:', event.type, event.componentId);
}
</script>

Custom Components

Simple Registration

import { createRenderer } from '@llm2ui/renderer';

const renderer = createRenderer({
  customComponents: {
    MyButton: ({ children, ...props }) => (
      <button className="my-btn" {...props}>{children}</button>
    )
  }
});

With Full Metadata

import { registerCustomComponent } from '@llm2ui/renderer';

registerCustomComponent({
  name: 'MyButton',
  component: MyButtonComponent,
  description: 'A custom button with variants',
  category: 'input',
  propsSchema: {
    variant: { type: 'string', enum: ['primary', 'secondary', 'danger'] },
    disabled: { type: 'boolean', default: false },
    size: { type: 'string', enum: ['sm', 'md', 'lg'], default: 'md' }
  },
  tags: ['button', 'action', 'interactive']
});

API Reference

render(schema, container, options?)

Renders a UISchema to a DOM container.

  • schema: UISchema - The schema to render
  • container: HTMLElement - Target DOM element
  • options: RendererOptions - Optional configuration
  • Returns: LLM2UIRenderer instance

createRenderer(options?)

Creates a new renderer instance.

  • options: RendererOptions - Configuration options
  • Returns: LLM2UIRenderer instance

LLM2UIRenderer

Main renderer class with lifecycle methods:

| Method | Description | |--------|-------------| | render(schema, container) | Render schema to container | | update(schema) | Update with new schema | | destroy() | Clean up and unmount | | on(event, handler) | Add event listener | | off(event, handler?) | Remove event listener | | registerComponent(definition) | Register a custom component | | getSchema() | Get current schema | | isMounted() | Check if mounted |

LLM2UI (React Component)

<LLM2UI
  schema={schema}
  data={{ user: { name: 'John' } }}
  onEvent={(event) => console.log(event.type)}
  theme="dark"
  customComponents={{ MyButton }}
  showErrors={true}
/>

| Prop | Type | Description | |------|------|-------------| | schema | UISchema | The schema to render (required) | | data | DataContext | Additional data context | | onEvent | LLM2UIEventCallback | Event handler callback | | platform | PlatformType | Target platform | | theme | 'light' \| 'dark' | Theme mode | | customComponents | Record<string, ComponentType> | Custom components | | showErrors | boolean | Show error boundaries |

UISchema Format

interface UISchema {
  version: string;
  root: UIComponent;
  data?: DataContext;
  theme?: ThemeConfig;
}

interface UIComponent {
  id: string;
  type: string;
  props?: Record<string, unknown>;
  children?: UIComponent[];
  events?: EventBinding[];
  style?: StyleProps;
  conditional?: ConditionalConfig;
}

Built-in Components

The SDK includes a comprehensive set of UI components:

  • Input: Button, Input, Checkbox, Radio, Select, Switch, Slider
  • Layout: Container, Grid, Flex, Card, Accordion, Tabs
  • Display: Text, Image, Avatar, Badge, Table
  • Feedback: Alert, Toast, Dialog, Tooltip
  • Navigation: Menu, Breadcrumb, Pagination

Tree-shaking

This package is fully tree-shakable. Only the components and utilities you actually use will be included in your final bundle.

How it works

  1. ES Modules: The package exports ES modules that bundlers can statically analyze
  2. Side-effect free: All modules are marked as side-effect free (except CSS)
  3. Preserved module structure: Each module is kept separate for granular imports
  4. Named exports: All exports are named, allowing bundlers to eliminate unused code

Best practices for optimal tree-shaking

// ✅ Good - Import only what you need
import { render, LLM2UI } from '@llm2ui/renderer';
import { LLM2UI } from '@llm2ui/renderer/react';

// ❌ Avoid - Importing everything
import * as LLM2UIRenderer from '@llm2ui/renderer';

Bundle size optimization

For the smallest possible bundle:

  1. Use specific entry points (@llm2ui/renderer/react or @llm2ui/renderer/vue)
  2. Only import the components you need
  3. Use a modern bundler (Vite, Webpack 5+, Rollup, esbuild)
  4. Enable production mode for dead code elimination

License

MIT © LLM2UI Team