@fogui/react 0.1.0 → 0.3.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.
@@ -1,7 +1,15 @@
1
- import React from 'react';
2
1
  import { jsxs, jsx } from 'react/jsx-runtime';
2
+ import React2, { createContext, useContext } from 'react';
3
3
 
4
- // src/components/FogUIRenderer.tsx
4
+ // src/components/ComponentRegistry.tsx
5
+ function mergeRegistries(...registries) {
6
+ return registries.reduce((merged, registry) => {
7
+ if (registry) {
8
+ return { ...merged, ...registry };
9
+ }
10
+ return merged;
11
+ }, {});
12
+ }
5
13
  function DefaultCard({ title, description, data }) {
6
14
  return /* @__PURE__ */ jsxs("div", { style: { border: "1px solid #e5e7eb", borderRadius: "8px", padding: "16px", marginBottom: "12px" }, children: [
7
15
  title && /* @__PURE__ */ jsx("h3", { style: { margin: "0 0 8px", fontSize: "18px", fontWeight: 600 }, children: title }),
@@ -56,12 +64,26 @@ function DynamicComponent({ block, registry = defaultComponentRegistry }) {
56
64
  }
57
65
  return /* @__PURE__ */ jsx(Component, { ...props });
58
66
  }
59
- function FogUIRenderer({ response, componentRegistry, className }) {
60
- const registry = componentRegistry || defaultComponentRegistry;
67
+ var FogUIContext = createContext(null);
68
+ function useFogUIContext() {
69
+ const context = useContext(FogUIContext);
70
+ if (!context) {
71
+ throw new Error('useFogUI must be used within a FogUIProvider. Wrap your app with <FogUIProvider apiKey="...">');
72
+ }
73
+ return context;
74
+ }
75
+ function FogUIRenderer({ response, componentRegistry, className, style }) {
76
+ let contextRegistry;
77
+ try {
78
+ const context = useFogUIContext();
79
+ contextRegistry = context.componentRegistry;
80
+ } catch {
81
+ }
82
+ const registry = mergeRegistries(defaultComponentRegistry, contextRegistry, componentRegistry);
61
83
  if (!response || !response.content) {
62
84
  return null;
63
85
  }
64
- return /* @__PURE__ */ jsx("div", { className, children: response.content.map((block, index) => /* @__PURE__ */ jsx(
86
+ return /* @__PURE__ */ jsx("div", { className, style, children: response.content.map((block, index) => /* @__PURE__ */ jsx(
65
87
  ContentBlockRenderer,
66
88
  {
67
89
  block,
@@ -72,7 +94,7 @@ function FogUIRenderer({ response, componentRegistry, className }) {
72
94
  }
73
95
  function ContentBlockRenderer({ block, registry }) {
74
96
  if (block.type === "text") {
75
- return /* @__PURE__ */ jsx("div", { style: { marginBottom: "12px", lineHeight: 1.6 }, children: block.value.split("\n").map((line, i) => /* @__PURE__ */ jsxs(React.Fragment, { children: [
97
+ return /* @__PURE__ */ jsx("div", { style: { marginBottom: "12px", lineHeight: 1.6 }, children: block.value.split("\n").map((line, i) => /* @__PURE__ */ jsxs(React2.Fragment, { children: [
76
98
  line,
77
99
  i < block.value.split("\n").length - 1 && /* @__PURE__ */ jsx("br", {})
78
100
  ] }, i)) });
@@ -1 +1 @@
1
- {"version":3,"sources":["../../src/components/ComponentRegistry.tsx","../../src/components/FogUIRenderer.tsx"],"names":["jsx","jsxs"],"mappings":"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","file":"index.mjs","sourcesContent":["import React from 'react';\nimport type { ComponentBlock } from '../types';\n\n/**\n * Default component implementations.\n * These provide basic rendering - users should customize for their design system.\n */\n\n// Card Component\nfunction DefaultCard({ title, description, data }: { title?: string; description?: string; data?: Record<string, unknown> }) {\n return (\n <div style={{ border: '1px solid #e5e7eb', borderRadius: '8px', padding: '16px', marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 8px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n {description && <p style={{ margin: '0 0 12px', color: '#6b7280' }}>{description}</p>}\n {data && (\n <div style={{ fontSize: '14px' }}>\n {Object.entries(data).map(([key, value]) => (\n <div key={key} style={{ display: 'flex', justifyContent: 'space-between', padding: '4px 0' }}>\n <span style={{ color: '#6b7280' }}>{key}</span>\n <span style={{ fontWeight: 500 }}>{String(value)}</span>\n </div>\n ))}\n </div>\n )}\n </div>\n );\n}\n\n// List Component\nfunction DefaultList({ title, items }: { title?: string; items: unknown[] }) {\n return (\n <div style={{ marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 12px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n <ul style={{ margin: 0, paddingLeft: '20px' }}>\n {items.map((item, i) => (\n <li key={i} style={{ marginBottom: '8px' }}>\n {typeof item === 'object' ? JSON.stringify(item) : String(item)}\n </li>\n ))}\n </ul>\n </div>\n );\n}\n\n// Table Component\nfunction DefaultTable({ columns, rows }: { columns: string[]; rows: Record<string, unknown>[] }) {\n return (\n <div style={{ overflowX: 'auto', marginBottom: '12px' }}>\n <table style={{ width: '100%', borderCollapse: 'collapse', fontSize: '14px' }}>\n <thead>\n <tr>\n {columns.map((col) => (\n <th key={col} style={{ textAlign: 'left', padding: '12px 8px', borderBottom: '2px solid #e5e7eb', fontWeight: 600 }}>\n {col}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {rows.map((row, i) => (\n <tr key={i}>\n {columns.map((col) => (\n <td key={col} style={{ padding: '12px 8px', borderBottom: '1px solid #e5e7eb' }}>\n {String(row[col] ?? '')}\n </td>\n ))}\n </tr>\n ))}\n </tbody>\n </table>\n </div>\n );\n}\n\n// Callout Component\nfunction DefaultCallout({ title, message, variant = 'info' }: { title?: string; message: string; variant?: 'info' | 'warning' | 'tip' }) {\n const colors = {\n info: { bg: '#eff6ff', border: '#3b82f6', text: '#1e40af' },\n warning: { bg: '#fffbeb', border: '#f59e0b', text: '#92400e' },\n tip: { bg: '#f0fdf4', border: '#22c55e', text: '#166534' },\n };\n const c = colors[variant];\n return (\n <div style={{ backgroundColor: c.bg, borderLeft: `4px solid ${c.border}`, padding: '12px 16px', marginBottom: '12px', borderRadius: '0 8px 8px 0' }}>\n {title && <strong style={{ color: c.text, display: 'block', marginBottom: '4px' }}>{title}</strong>}\n <span style={{ color: c.text }}>{message}</span>\n </div>\n );\n}\n\n/**\n * Default component registry mapping componentType to React components.\n * Users can override this with their own components.\n */\nexport const defaultComponentRegistry: Record<string, React.ComponentType<any>> = {\n card: DefaultCard,\n list: DefaultList,\n table: DefaultTable,\n callout: DefaultCallout,\n};\n\ninterface DynamicComponentProps {\n block: ComponentBlock;\n registry?: Record<string, React.ComponentType<any>>;\n}\n\n/**\n * DynamicComponent - Renders a component based on componentType.\n */\nexport function DynamicComponent({ block, registry = defaultComponentRegistry }: DynamicComponentProps) {\n const { componentType, props } = block;\n const Component = registry[componentType];\n\n if (!Component) {\n return (\n <div style={{ padding: '12px', backgroundColor: '#fef3c7', border: '1px solid #fcd34d', borderRadius: '8px', fontSize: '14px' }}>\n <strong>Unknown component: {componentType}</strong>\n <pre style={{ margin: '8px 0 0', fontSize: '12px', overflow: 'auto' }}>\n {JSON.stringify(props, null, 2)}\n </pre>\n </div>\n );\n }\n\n return <Component {...props} />;\n}\n","import React from 'react';\nimport type { FogUIResponse, ContentBlock } from '../types';\nimport { DynamicComponent, defaultComponentRegistry } from './ComponentRegistry';\n\ninterface FogUIRendererProps {\n /**\n * The FogUIResponse to render\n */\n response: FogUIResponse;\n /**\n * Custom component registry to override default components\n */\n componentRegistry?: Record<string, React.ComponentType<any>>;\n /**\n * Custom className for the container\n */\n className?: string;\n}\n\n/**\n * FogUIRenderer - Renders a FogUIResponse as React components.\n * \n * @example\n * ```tsx\n * import { FogUIRenderer } from '@fogui/react';\n * \n * function Chat({ response }) {\n * return <FogUIRenderer response={response} />;\n * }\n * ```\n */\nexport function FogUIRenderer({ response, componentRegistry, className }: FogUIRendererProps) {\n const registry = componentRegistry || defaultComponentRegistry;\n\n if (!response || !response.content) {\n return null;\n }\n\n return (\n <div className={className}>\n {response.content.map((block, index) => (\n <ContentBlockRenderer \n key={index} \n block={block} \n registry={registry}\n />\n ))}\n </div>\n );\n}\n\ninterface ContentBlockRendererProps {\n block: ContentBlock;\n registry: Record<string, React.ComponentType<any>>;\n}\n\nfunction ContentBlockRenderer({ block, registry }: ContentBlockRendererProps) {\n if (block.type === 'text') {\n return (\n <div style={{ marginBottom: '12px', lineHeight: 1.6 }}>\n {block.value.split('\\n').map((line, i) => (\n <React.Fragment key={i}>\n {line}\n {i < block.value.split('\\n').length - 1 && <br />}\n </React.Fragment>\n ))}\n </div>\n );\n }\n\n if (block.type === 'component') {\n return <DynamicComponent block={block} registry={registry} />;\n }\n\n return null;\n}\n"]}
1
+ {"version":3,"sources":["../../src/components/ComponentRegistry.tsx","../../src/FogUIProvider.tsx","../../src/components/FogUIRenderer.tsx"],"names":["jsx","jsxs","React"],"mappings":"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","file":"index.mjs","sourcesContent":["import React from 'react';\nimport type { ComponentBlock } from '../types';\n\n/**\n * Component registry type - maps componentType strings to React components.\n * \n * Each component receives props that match the FogUI DSL for that component type.\n */\nexport type ComponentRegistry = Record<string, React.ComponentType<any>>;\n\n/**\n * Standard prop interfaces for built-in FogUI component types.\n * Useful for implementing custom components that match the expected API.\n */\nexport interface CardProps {\n title?: string;\n description?: string;\n data?: Record<string, unknown>;\n children?: React.ReactNode;\n}\n\nexport interface ListProps {\n title?: string;\n items: unknown[];\n ordered?: boolean;\n}\n\nexport interface TableProps {\n columns: string[];\n rows: Record<string, unknown>[];\n title?: string;\n}\n\nexport interface CalloutProps {\n title?: string;\n message: string;\n variant?: 'info' | 'warning' | 'tip' | 'error';\n}\n\n/**\n * Merge multiple component registries with later registries taking precedence.\n * Useful for layering: defaults → context → prop overrides.\n */\nexport function mergeRegistries(\n ...registries: (ComponentRegistry | undefined)[]\n): ComponentRegistry {\n return registries.reduce<ComponentRegistry>((merged, registry) => {\n if (registry) {\n return { ...merged, ...registry };\n }\n return merged;\n }, {});\n}\n\n/**\n * Create a component registry from an adapter.\n * This is a convenience function for creating type-safe registries.\n * \n * @example\n * ```tsx\n * import { createRegistry } from '@fogui/react';\n * import { Card } from '@/components/ui/card';\n * \n * const myRegistry = createRegistry({\n * card: MyCardComponent,\n * table: MyTableComponent,\n * });\n * ```\n */\nexport function createRegistry(components: Partial<{\n card: React.ComponentType<CardProps>;\n list: React.ComponentType<ListProps>;\n table: React.ComponentType<TableProps>;\n callout: React.ComponentType<CalloutProps>;\n [key: string]: React.ComponentType<any>;\n}>): ComponentRegistry {\n return components as ComponentRegistry;\n}\n\n/**\n * Default component implementations.\n * These provide basic rendering - users should customize for their design system.\n */\n\n// Card Component\nfunction DefaultCard({ title, description, data }: { title?: string; description?: string; data?: Record<string, unknown> }) {\n return (\n <div style={{ border: '1px solid #e5e7eb', borderRadius: '8px', padding: '16px', marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 8px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n {description && <p style={{ margin: '0 0 12px', color: '#6b7280' }}>{description}</p>}\n {data && (\n <div style={{ fontSize: '14px' }}>\n {Object.entries(data).map(([key, value]) => (\n <div key={key} style={{ display: 'flex', justifyContent: 'space-between', padding: '4px 0' }}>\n <span style={{ color: '#6b7280' }}>{key}</span>\n <span style={{ fontWeight: 500 }}>{String(value)}</span>\n </div>\n ))}\n </div>\n )}\n </div>\n );\n}\n\n// List Component\nfunction DefaultList({ title, items }: { title?: string; items: unknown[] }) {\n return (\n <div style={{ marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 12px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n <ul style={{ margin: 0, paddingLeft: '20px' }}>\n {items.map((item, i) => (\n <li key={i} style={{ marginBottom: '8px' }}>\n {typeof item === 'object' ? JSON.stringify(item) : String(item)}\n </li>\n ))}\n </ul>\n </div>\n );\n}\n\n// Table Component\nfunction DefaultTable({ columns, rows }: { columns: string[]; rows: Record<string, unknown>[] }) {\n return (\n <div style={{ overflowX: 'auto', marginBottom: '12px' }}>\n <table style={{ width: '100%', borderCollapse: 'collapse', fontSize: '14px' }}>\n <thead>\n <tr>\n {columns.map((col) => (\n <th key={col} style={{ textAlign: 'left', padding: '12px 8px', borderBottom: '2px solid #e5e7eb', fontWeight: 600 }}>\n {col}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {rows.map((row, i) => (\n <tr key={i}>\n {columns.map((col) => (\n <td key={col} style={{ padding: '12px 8px', borderBottom: '1px solid #e5e7eb' }}>\n {String(row[col] ?? '')}\n </td>\n ))}\n </tr>\n ))}\n </tbody>\n </table>\n </div>\n );\n}\n\n// Callout Component\nfunction DefaultCallout({ title, message, variant = 'info' }: { title?: string; message: string; variant?: 'info' | 'warning' | 'tip' }) {\n const colors = {\n info: { bg: '#eff6ff', border: '#3b82f6', text: '#1e40af' },\n warning: { bg: '#fffbeb', border: '#f59e0b', text: '#92400e' },\n tip: { bg: '#f0fdf4', border: '#22c55e', text: '#166534' },\n };\n const c = colors[variant];\n return (\n <div style={{ backgroundColor: c.bg, borderLeft: `4px solid ${c.border}`, padding: '12px 16px', marginBottom: '12px', borderRadius: '0 8px 8px 0' }}>\n {title && <strong style={{ color: c.text, display: 'block', marginBottom: '4px' }}>{title}</strong>}\n <span style={{ color: c.text }}>{message}</span>\n </div>\n );\n}\n\n/**\n * Default component registry mapping componentType to React components.\n * Users can override this with their own components.\n */\nexport const defaultComponentRegistry: Record<string, React.ComponentType<any>> = {\n card: DefaultCard,\n list: DefaultList,\n table: DefaultTable,\n callout: DefaultCallout,\n};\n\ninterface DynamicComponentProps {\n block: ComponentBlock;\n registry?: Record<string, React.ComponentType<any>>;\n}\n\n/**\n * DynamicComponent - Renders a component based on componentType.\n */\nexport function DynamicComponent({ block, registry = defaultComponentRegistry }: DynamicComponentProps) {\n const { componentType, props } = block;\n const Component = registry[componentType];\n\n if (!Component) {\n return (\n <div style={{ padding: '12px', backgroundColor: '#fef3c7', border: '1px solid #fcd34d', borderRadius: '8px', fontSize: '14px' }}>\n <strong>Unknown component: {componentType}</strong>\n <pre style={{ margin: '8px 0 0', fontSize: '12px', overflow: 'auto' }}>\n {JSON.stringify(props, null, 2)}\n </pre>\n </div>\n );\n }\n\n return <Component {...props} />;\n}\n","import React, { createContext, useContext, useMemo } from 'react';\n\n/**\n * FogUI Platform API endpoint\n */\nconst FOGUI_API_ENDPOINT = 'https://api.virtuoapps.com';\n\n/**\n * Component registry type - maps componentType to React components\n */\nexport type ComponentRegistry = Record<string, React.ComponentType<any>>;\n\ninterface FogUIContextValue {\n apiKey: string;\n endpoint: string;\n componentRegistry?: ComponentRegistry;\n}\n\nconst FogUIContext = createContext<FogUIContextValue | null>(null);\n\nexport interface FogUIProviderProps {\n children: React.ReactNode;\n /**\n * Your FogUI API key (get it from https://fogui.dev/dashboard)\n */\n apiKey: string;\n /**\n * Custom API endpoint (for self-hosted deployments)\n * @default 'https://api.virtuoapps.com'\n */\n endpoint?: string;\n /**\n * Custom component registry for your design system.\n * Map FogUI component types to your own React components.\n * \n * @example\n * ```tsx\n * import { Card, Table } from '@/components/ui';\n * \n * <FogUIProvider \n * apiKey=\"fog_xxx\"\n * components={{\n * card: MyCard,\n * table: MyTable,\n * list: MyList,\n * }}\n * >\n * ```\n */\n components?: ComponentRegistry;\n}\n\n/**\n * FogUIProvider - Provides FogUI configuration to the component tree.\n * \n * @example Basic usage\n * ```tsx\n * import { FogUIProvider } from '@fogui/react';\n * \n * function App() {\n * return (\n * <FogUIProvider apiKey=\"fog_xxxx\">\n * <MyApp />\n * </FogUIProvider>\n * );\n * }\n * ```\n * \n * @example With custom design system (e.g., Shadcn)\n * ```tsx\n * import { FogUIProvider } from '@fogui/react';\n * import { Card, CardHeader, CardContent } from '@/components/ui/card';\n * import { Table, TableHeader, TableBody, TableRow, TableCell } from '@/components/ui/table';\n * \n * // Map FogUI component types to your design system\n * const myComponents = {\n * card: ({ title, description, data }) => (\n * <Card>\n * <CardHeader>{title}</CardHeader>\n * <CardContent>{description}</CardContent>\n * </Card>\n * ),\n * table: MyTableComponent,\n * list: MyListComponent,\n * };\n * \n * function App() {\n * return (\n * <FogUIProvider apiKey=\"fog_xxxx\" components={myComponents}>\n * <MyApp />\n * </FogUIProvider>\n * );\n * }\n * ```\n * \n * @example Self-hosted deployment\n * ```tsx\n * <FogUIProvider \n * apiKey=\"fog_xxxx\" \n * endpoint=\"https://fogui.mycompany.com\"\n * >\n * <MyApp />\n * </FogUIProvider>\n * ```\n */\nexport function FogUIProvider({ children, apiKey, endpoint, components }: FogUIProviderProps) {\n if (!apiKey) {\n console.warn('[FogUI] API key is required. Get one at https://fogui.dev/dashboard');\n }\n\n const value = useMemo<FogUIContextValue>(() => ({\n apiKey,\n endpoint: endpoint || FOGUI_API_ENDPOINT,\n componentRegistry: components,\n }), [apiKey, endpoint, components]);\n\n return (\n <FogUIContext.Provider value={value}>\n {children}\n </FogUIContext.Provider>\n );\n}\n\n/**\n * Hook to access FogUI context\n * @internal\n */\nexport function useFogUIContext(): FogUIContextValue {\n const context = useContext(FogUIContext);\n if (!context) {\n throw new Error('useFogUI must be used within a FogUIProvider. Wrap your app with <FogUIProvider apiKey=\"...\">');\n }\n return context;\n}\n","import type { ContentBlock, FogUIResponse } from '../types';\nimport { DynamicComponent, defaultComponentRegistry, mergeRegistries } from './ComponentRegistry';\n\nimport React from 'react';\nimport { useFogUIContext } from '../FogUIProvider';\n\ninterface FogUIRendererProps {\n /**\n * The FogUIResponse to render\n */\n response: FogUIResponse;\n /**\n * Custom component registry to override context/default components.\n * If not provided, uses the registry from FogUIProvider (if any),\n * falling back to defaultComponentRegistry.\n */\n componentRegistry?: Record<string, React.ComponentType<any>>;\n /**\n * Custom className for the container\n */\n className?: string;\n /**\n * Custom styles for the container\n */\n style?: React.CSSProperties;\n}\n\n/**\n * FogUIRenderer - Renders a FogUIResponse as React components.\n * \n * Uses the component registry from FogUIProvider if configured,\n * otherwise falls back to default components.\n * \n * @example Basic usage\n * ```tsx\n * import { FogUIRenderer } from '@fogui/react';\n * \n * function Chat({ response }) {\n * return <FogUIRenderer response={response} />;\n * }\n * ```\n * \n * @example With inline component override\n * ```tsx\n * <FogUIRenderer \n * response={response} \n * componentRegistry={{ card: MySpecialCard }}\n * />\n * ```\n */\nexport function FogUIRenderer({ response, componentRegistry, className, style }: FogUIRendererProps) {\n // Try to get registry from context (set in FogUIProvider)\n let contextRegistry: Record<string, React.ComponentType<any>> | undefined;\n try {\n const context = useFogUIContext();\n contextRegistry = context.componentRegistry;\n } catch {\n // Not inside FogUIProvider, use defaults\n }\n\n // Merge: prop registry > context registry > default registry\n const registry = mergeRegistries(defaultComponentRegistry, contextRegistry, componentRegistry);\n\n if (!response || !response.content) {\n return null;\n }\n\n return (\n <div className={className} style={style}>\n {response.content.map((block, index) => (\n <ContentBlockRenderer \n key={index} \n block={block} \n registry={registry}\n />\n ))}\n </div>\n );\n}\n\ninterface ContentBlockRendererProps {\n block: ContentBlock;\n registry: Record<string, React.ComponentType<any>>;\n}\n\nfunction ContentBlockRenderer({ block, registry }: ContentBlockRendererProps) {\n if (block.type === 'text') {\n return (\n <div style={{ marginBottom: '12px', lineHeight: 1.6 }}>\n {block.value.split('\\n').map((line, i) => (\n <React.Fragment key={i}>\n {line}\n {i < block.value.split('\\n').length - 1 && <br />}\n </React.Fragment>\n ))}\n </div>\n );\n }\n\n if (block.type === 'component') {\n return <DynamicComponent block={block} registry={registry} />;\n }\n\n return null;\n}\n"]}
package/dist/index.d.mts CHANGED
@@ -1,11 +1,17 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
2
  import React from 'react';
3
- import { U as UseFogUIReturn } from './index-BcLda68r.mjs';
4
- export { d as ComponentBlock, C as ContentBlock, D as DynamicComponent, F as FogUIConfig, f as FogUIRenderer, b as FogUIResponse, S as StreamEvent, c as TextBlock, e as ThinkingItem, T as TransformOptions, a as TransformResult, g as defaultComponentRegistry } from './index-BcLda68r.mjs';
3
+ import { U as UseFogUIReturn } from './ComponentRegistry-BFgVIcHz.mjs';
4
+ export { j as CalloutProps, h as CardProps, d as ComponentBlock, C as ContentBlock, D as DynamicComponent, F as FogUIConfig, b as FogUIResponse, L as ListProps, S as StreamEvent, i as TableProps, c as TextBlock, e as ThinkingItem, T as TransformOptions, a as TransformResult, g as createRegistry, f as defaultComponentRegistry, m as mergeRegistries } from './ComponentRegistry-BFgVIcHz.mjs';
5
+ export { FogUIRenderer } from './components/index.mjs';
5
6
 
7
+ /**
8
+ * Component registry type - maps componentType to React components
9
+ */
10
+ type ComponentRegistry = Record<string, React.ComponentType<any>>;
6
11
  interface FogUIContextValue {
7
12
  apiKey: string;
8
13
  endpoint: string;
14
+ componentRegistry?: ComponentRegistry;
9
15
  }
10
16
  interface FogUIProviderProps {
11
17
  children: React.ReactNode;
@@ -13,11 +19,35 @@ interface FogUIProviderProps {
13
19
  * Your FogUI API key (get it from https://fogui.dev/dashboard)
14
20
  */
15
21
  apiKey: string;
22
+ /**
23
+ * Custom API endpoint (for self-hosted deployments)
24
+ * @default 'https://api.virtuoapps.com'
25
+ */
26
+ endpoint?: string;
27
+ /**
28
+ * Custom component registry for your design system.
29
+ * Map FogUI component types to your own React components.
30
+ *
31
+ * @example
32
+ * ```tsx
33
+ * import { Card, Table } from '@/components/ui';
34
+ *
35
+ * <FogUIProvider
36
+ * apiKey="fog_xxx"
37
+ * components={{
38
+ * card: MyCard,
39
+ * table: MyTable,
40
+ * list: MyList,
41
+ * }}
42
+ * >
43
+ * ```
44
+ */
45
+ components?: ComponentRegistry;
16
46
  }
17
47
  /**
18
48
  * FogUIProvider - Provides FogUI configuration to the component tree.
19
49
  *
20
- * @example
50
+ * @example Basic usage
21
51
  * ```tsx
22
52
  * import { FogUIProvider } from '@fogui/react';
23
53
  *
@@ -29,8 +59,45 @@ interface FogUIProviderProps {
29
59
  * );
30
60
  * }
31
61
  * ```
62
+ *
63
+ * @example With custom design system (e.g., Shadcn)
64
+ * ```tsx
65
+ * import { FogUIProvider } from '@fogui/react';
66
+ * import { Card, CardHeader, CardContent } from '@/components/ui/card';
67
+ * import { Table, TableHeader, TableBody, TableRow, TableCell } from '@/components/ui/table';
68
+ *
69
+ * // Map FogUI component types to your design system
70
+ * const myComponents = {
71
+ * card: ({ title, description, data }) => (
72
+ * <Card>
73
+ * <CardHeader>{title}</CardHeader>
74
+ * <CardContent>{description}</CardContent>
75
+ * </Card>
76
+ * ),
77
+ * table: MyTableComponent,
78
+ * list: MyListComponent,
79
+ * };
80
+ *
81
+ * function App() {
82
+ * return (
83
+ * <FogUIProvider apiKey="fog_xxxx" components={myComponents}>
84
+ * <MyApp />
85
+ * </FogUIProvider>
86
+ * );
87
+ * }
88
+ * ```
89
+ *
90
+ * @example Self-hosted deployment
91
+ * ```tsx
92
+ * <FogUIProvider
93
+ * apiKey="fog_xxxx"
94
+ * endpoint="https://fogui.mycompany.com"
95
+ * >
96
+ * <MyApp />
97
+ * </FogUIProvider>
98
+ * ```
32
99
  */
33
- declare function FogUIProvider({ children, apiKey }: FogUIProviderProps): react_jsx_runtime.JSX.Element;
100
+ declare function FogUIProvider({ children, apiKey, endpoint, components }: FogUIProviderProps): react_jsx_runtime.JSX.Element;
34
101
  /**
35
102
  * Hook to access FogUI context
36
103
  * @internal
@@ -66,4 +133,4 @@ declare function useFogUIContext(): FogUIContextValue;
66
133
  */
67
134
  declare function useFogUI(): UseFogUIReturn;
68
135
 
69
- export { FogUIProvider, type FogUIProviderProps, UseFogUIReturn, useFogUI, useFogUIContext };
136
+ export { type ComponentRegistry, FogUIProvider, type FogUIProviderProps, UseFogUIReturn, useFogUI, useFogUIContext };
package/dist/index.d.ts CHANGED
@@ -1,11 +1,17 @@
1
1
  import * as react_jsx_runtime from 'react/jsx-runtime';
2
2
  import React from 'react';
3
- import { U as UseFogUIReturn } from './index-BcLda68r.js';
4
- export { d as ComponentBlock, C as ContentBlock, D as DynamicComponent, F as FogUIConfig, f as FogUIRenderer, b as FogUIResponse, S as StreamEvent, c as TextBlock, e as ThinkingItem, T as TransformOptions, a as TransformResult, g as defaultComponentRegistry } from './index-BcLda68r.js';
3
+ import { U as UseFogUIReturn } from './ComponentRegistry-BFgVIcHz.js';
4
+ export { j as CalloutProps, h as CardProps, d as ComponentBlock, C as ContentBlock, D as DynamicComponent, F as FogUIConfig, b as FogUIResponse, L as ListProps, S as StreamEvent, i as TableProps, c as TextBlock, e as ThinkingItem, T as TransformOptions, a as TransformResult, g as createRegistry, f as defaultComponentRegistry, m as mergeRegistries } from './ComponentRegistry-BFgVIcHz.js';
5
+ export { FogUIRenderer } from './components/index.js';
5
6
 
7
+ /**
8
+ * Component registry type - maps componentType to React components
9
+ */
10
+ type ComponentRegistry = Record<string, React.ComponentType<any>>;
6
11
  interface FogUIContextValue {
7
12
  apiKey: string;
8
13
  endpoint: string;
14
+ componentRegistry?: ComponentRegistry;
9
15
  }
10
16
  interface FogUIProviderProps {
11
17
  children: React.ReactNode;
@@ -13,11 +19,35 @@ interface FogUIProviderProps {
13
19
  * Your FogUI API key (get it from https://fogui.dev/dashboard)
14
20
  */
15
21
  apiKey: string;
22
+ /**
23
+ * Custom API endpoint (for self-hosted deployments)
24
+ * @default 'https://api.virtuoapps.com'
25
+ */
26
+ endpoint?: string;
27
+ /**
28
+ * Custom component registry for your design system.
29
+ * Map FogUI component types to your own React components.
30
+ *
31
+ * @example
32
+ * ```tsx
33
+ * import { Card, Table } from '@/components/ui';
34
+ *
35
+ * <FogUIProvider
36
+ * apiKey="fog_xxx"
37
+ * components={{
38
+ * card: MyCard,
39
+ * table: MyTable,
40
+ * list: MyList,
41
+ * }}
42
+ * >
43
+ * ```
44
+ */
45
+ components?: ComponentRegistry;
16
46
  }
17
47
  /**
18
48
  * FogUIProvider - Provides FogUI configuration to the component tree.
19
49
  *
20
- * @example
50
+ * @example Basic usage
21
51
  * ```tsx
22
52
  * import { FogUIProvider } from '@fogui/react';
23
53
  *
@@ -29,8 +59,45 @@ interface FogUIProviderProps {
29
59
  * );
30
60
  * }
31
61
  * ```
62
+ *
63
+ * @example With custom design system (e.g., Shadcn)
64
+ * ```tsx
65
+ * import { FogUIProvider } from '@fogui/react';
66
+ * import { Card, CardHeader, CardContent } from '@/components/ui/card';
67
+ * import { Table, TableHeader, TableBody, TableRow, TableCell } from '@/components/ui/table';
68
+ *
69
+ * // Map FogUI component types to your design system
70
+ * const myComponents = {
71
+ * card: ({ title, description, data }) => (
72
+ * <Card>
73
+ * <CardHeader>{title}</CardHeader>
74
+ * <CardContent>{description}</CardContent>
75
+ * </Card>
76
+ * ),
77
+ * table: MyTableComponent,
78
+ * list: MyListComponent,
79
+ * };
80
+ *
81
+ * function App() {
82
+ * return (
83
+ * <FogUIProvider apiKey="fog_xxxx" components={myComponents}>
84
+ * <MyApp />
85
+ * </FogUIProvider>
86
+ * );
87
+ * }
88
+ * ```
89
+ *
90
+ * @example Self-hosted deployment
91
+ * ```tsx
92
+ * <FogUIProvider
93
+ * apiKey="fog_xxxx"
94
+ * endpoint="https://fogui.mycompany.com"
95
+ * >
96
+ * <MyApp />
97
+ * </FogUIProvider>
98
+ * ```
32
99
  */
33
- declare function FogUIProvider({ children, apiKey }: FogUIProviderProps): react_jsx_runtime.JSX.Element;
100
+ declare function FogUIProvider({ children, apiKey, endpoint, components }: FogUIProviderProps): react_jsx_runtime.JSX.Element;
34
101
  /**
35
102
  * Hook to access FogUI context
36
103
  * @internal
@@ -66,4 +133,4 @@ declare function useFogUIContext(): FogUIContextValue;
66
133
  */
67
134
  declare function useFogUI(): UseFogUIReturn;
68
135
 
69
- export { FogUIProvider, type FogUIProviderProps, UseFogUIReturn, useFogUI, useFogUIContext };
136
+ export { type ComponentRegistry, FogUIProvider, type FogUIProviderProps, UseFogUIReturn, useFogUI, useFogUIContext };
package/dist/index.js CHANGED
@@ -8,16 +8,17 @@ function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
8
8
  var React2__default = /*#__PURE__*/_interopDefault(React2);
9
9
 
10
10
  // src/FogUIProvider.tsx
11
- var FOGUI_API_ENDPOINT = "https://api.fogui.dev";
11
+ var FOGUI_API_ENDPOINT = "https://api.virtuoapps.com";
12
12
  var FogUIContext = React2.createContext(null);
13
- function FogUIProvider({ children, apiKey }) {
13
+ function FogUIProvider({ children, apiKey, endpoint, components }) {
14
14
  if (!apiKey) {
15
15
  console.warn("[FogUI] API key is required. Get one at https://fogui.dev/dashboard");
16
16
  }
17
17
  const value = React2.useMemo(() => ({
18
18
  apiKey,
19
- endpoint: FOGUI_API_ENDPOINT
20
- }), [apiKey]);
19
+ endpoint: endpoint || FOGUI_API_ENDPOINT,
20
+ componentRegistry: components
21
+ }), [apiKey, endpoint, components]);
21
22
  return /* @__PURE__ */ jsxRuntime.jsx(FogUIContext.Provider, { value, children });
22
23
  }
23
24
  function useFogUIContext() {
@@ -143,6 +144,17 @@ function useFogUI() {
143
144
  clearError
144
145
  };
145
146
  }
147
+ function mergeRegistries(...registries) {
148
+ return registries.reduce((merged, registry) => {
149
+ if (registry) {
150
+ return { ...merged, ...registry };
151
+ }
152
+ return merged;
153
+ }, {});
154
+ }
155
+ function createRegistry(components) {
156
+ return components;
157
+ }
146
158
  function DefaultCard({ title, description, data }) {
147
159
  return /* @__PURE__ */ jsxRuntime.jsxs("div", { style: { border: "1px solid #e5e7eb", borderRadius: "8px", padding: "16px", marginBottom: "12px" }, children: [
148
160
  title && /* @__PURE__ */ jsxRuntime.jsx("h3", { style: { margin: "0 0 8px", fontSize: "18px", fontWeight: 600 }, children: title }),
@@ -197,12 +209,18 @@ function DynamicComponent({ block, registry = defaultComponentRegistry }) {
197
209
  }
198
210
  return /* @__PURE__ */ jsxRuntime.jsx(Component, { ...props });
199
211
  }
200
- function FogUIRenderer({ response, componentRegistry, className }) {
201
- const registry = componentRegistry || defaultComponentRegistry;
212
+ function FogUIRenderer({ response, componentRegistry, className, style }) {
213
+ let contextRegistry;
214
+ try {
215
+ const context = useFogUIContext();
216
+ contextRegistry = context.componentRegistry;
217
+ } catch {
218
+ }
219
+ const registry = mergeRegistries(defaultComponentRegistry, contextRegistry, componentRegistry);
202
220
  if (!response || !response.content) {
203
221
  return null;
204
222
  }
205
- return /* @__PURE__ */ jsxRuntime.jsx("div", { className, children: response.content.map((block, index) => /* @__PURE__ */ jsxRuntime.jsx(
223
+ return /* @__PURE__ */ jsxRuntime.jsx("div", { className, style, children: response.content.map((block, index) => /* @__PURE__ */ jsxRuntime.jsx(
206
224
  ContentBlockRenderer,
207
225
  {
208
226
  block,
@@ -227,7 +245,9 @@ function ContentBlockRenderer({ block, registry }) {
227
245
  exports.DynamicComponent = DynamicComponent;
228
246
  exports.FogUIProvider = FogUIProvider;
229
247
  exports.FogUIRenderer = FogUIRenderer;
248
+ exports.createRegistry = createRegistry;
230
249
  exports.defaultComponentRegistry = defaultComponentRegistry;
250
+ exports.mergeRegistries = mergeRegistries;
231
251
  exports.useFogUI = useFogUI;
232
252
  exports.useFogUIContext = useFogUIContext;
233
253
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/FogUIProvider.tsx","../src/useFogUI.ts","../src/components/ComponentRegistry.tsx","../src/components/FogUIRenderer.tsx"],"names":["createContext","useMemo","jsx","useContext","useState","useCallback","jsxs","React"],"mappings":"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","file":"index.js","sourcesContent":["import React, { createContext, useContext, useMemo } from 'react';\n\n/**\n * FogUI Platform API endpoint\n */\nconst FOGUI_API_ENDPOINT = 'https://api.fogui.dev';\n\ninterface FogUIContextValue {\n apiKey: string;\n endpoint: string;\n}\n\nconst FogUIContext = createContext<FogUIContextValue | null>(null);\n\nexport interface FogUIProviderProps {\n children: React.ReactNode;\n /**\n * Your FogUI API key (get it from https://fogui.dev/dashboard)\n */\n apiKey: string;\n}\n\n/**\n * FogUIProvider - Provides FogUI configuration to the component tree.\n * \n * @example\n * ```tsx\n * import { FogUIProvider } from '@fogui/react';\n * \n * function App() {\n * return (\n * <FogUIProvider apiKey=\"fog_xxxx\">\n * <MyApp />\n * </FogUIProvider>\n * );\n * }\n * ```\n */\nexport function FogUIProvider({ children, apiKey }: FogUIProviderProps) {\n if (!apiKey) {\n console.warn('[FogUI] API key is required. Get one at https://fogui.dev/dashboard');\n }\n\n const value = useMemo<FogUIContextValue>(() => ({\n apiKey,\n endpoint: FOGUI_API_ENDPOINT,\n }), [apiKey]);\n\n return (\n <FogUIContext.Provider value={value}>\n {children}\n </FogUIContext.Provider>\n );\n}\n\n/**\n * Hook to access FogUI context\n * @internal\n */\nexport function useFogUIContext(): FogUIContextValue {\n const context = useContext(FogUIContext);\n if (!context) {\n throw new Error('useFogUI must be used within a FogUIProvider. Wrap your app with <FogUIProvider apiKey=\"...\">');\n }\n return context;\n}\n","import { useState, useCallback } from 'react';\nimport { useFogUIContext } from './FogUIProvider';\nimport type { TransformOptions, TransformResult, UseFogUIReturn, StreamEvent } from './types';\n\n/**\n * useFogUI - Main hook for transforming LLM output into structured UI.\n * \n * @example\n * ```tsx\n * import { useFogUI, FogUIRenderer } from '@fogui/react';\n * \n * function Chat() {\n * const { transform, isLoading } = useFogUI();\n * const [ui, setUI] = useState(null);\n * \n * const handleLLMResponse = async (llmOutput: string) => {\n * const result = await transform(llmOutput);\n * if (result.success) {\n * setUI(result.result);\n * }\n * };\n * \n * return (\n * <div>\n * {isLoading && <p>Transforming...</p>}\n * {ui && <FogUIRenderer response={ui} />}\n * </div>\n * );\n * }\n * ```\n */\nexport function useFogUI(): UseFogUIReturn {\n const { endpoint, apiKey } = useFogUIContext();\n const [isLoading, setIsLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n\n /**\n * Transform raw LLM text into structured UI (non-streaming)\n */\n const transform = useCallback(async (\n content: string,\n options: TransformOptions = {}\n ): Promise<TransformResult> => {\n setIsLoading(true);\n setError(null);\n\n try {\n const response = await fetch(`${endpoint}/fogui/transform`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Authorization': `Bearer ${apiKey}`,\n },\n body: JSON.stringify({\n content,\n context: options.intent || options.preferredComponents || options.instructions ? {\n intent: options.intent,\n preferredComponents: options.preferredComponents,\n instructions: options.instructions,\n } : undefined,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new Error(errorData.error || `HTTP ${response.status}`);\n }\n\n const result: TransformResult = await response.json();\n \n if (!result.success) {\n setError(result.error || 'Transformation failed');\n }\n\n return result;\n\n } catch (err) {\n const message = err instanceof Error ? err.message : 'Unknown error';\n setError(message);\n return { success: false, error: message };\n } finally {\n setIsLoading(false);\n }\n }, [endpoint, apiKey]);\n\n /**\n * Transform with streaming - returns an async generator\n */\n const transformStream = useCallback(async function* (\n content: string,\n options: TransformOptions = {}\n ): AsyncGenerator<StreamEvent> {\n setIsLoading(true);\n setError(null);\n\n try {\n const response = await fetch(`${endpoint}/fogui/transform/stream`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Authorization': `Bearer ${apiKey}`,\n },\n body: JSON.stringify({\n content,\n context: options.intent || options.instructions ? {\n intent: options.intent,\n instructions: options.instructions,\n } : undefined,\n streaming: true,\n }),\n });\n\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}`);\n }\n\n const reader = response.body?.getReader();\n if (!reader) {\n throw new Error('No response body');\n }\n\n const decoder = new TextDecoder();\n let buffer = '';\n let currentEvent = '';\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split('\\n');\n buffer = lines.pop() || '';\n\n for (const line of lines) {\n if (line.startsWith('event:')) {\n currentEvent = line.substring(6).trim();\n } else if (line.startsWith('data:')) {\n const data = line.substring(5).trim();\n \n if (data === '[DONE]') {\n yield { type: 'done', data: null };\n continue;\n }\n\n if (data) {\n try {\n const parsed = JSON.parse(data);\n yield { type: currentEvent as StreamEvent['type'], data: parsed };\n } catch {\n if (currentEvent === 'chunk') {\n yield { type: 'chunk', data };\n }\n }\n }\n }\n }\n }\n\n } catch (err) {\n const message = err instanceof Error ? err.message : 'Unknown error';\n setError(message);\n yield { type: 'error', data: { error: message } };\n } finally {\n setIsLoading(false);\n }\n }, [endpoint, apiKey]);\n\n const clearError = useCallback(() => {\n setError(null);\n }, []);\n\n return {\n transform,\n transformStream,\n isLoading,\n error,\n clearError,\n };\n}\n","import React from 'react';\nimport type { ComponentBlock } from '../types';\n\n/**\n * Default component implementations.\n * These provide basic rendering - users should customize for their design system.\n */\n\n// Card Component\nfunction DefaultCard({ title, description, data }: { title?: string; description?: string; data?: Record<string, unknown> }) {\n return (\n <div style={{ border: '1px solid #e5e7eb', borderRadius: '8px', padding: '16px', marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 8px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n {description && <p style={{ margin: '0 0 12px', color: '#6b7280' }}>{description}</p>}\n {data && (\n <div style={{ fontSize: '14px' }}>\n {Object.entries(data).map(([key, value]) => (\n <div key={key} style={{ display: 'flex', justifyContent: 'space-between', padding: '4px 0' }}>\n <span style={{ color: '#6b7280' }}>{key}</span>\n <span style={{ fontWeight: 500 }}>{String(value)}</span>\n </div>\n ))}\n </div>\n )}\n </div>\n );\n}\n\n// List Component\nfunction DefaultList({ title, items }: { title?: string; items: unknown[] }) {\n return (\n <div style={{ marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 12px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n <ul style={{ margin: 0, paddingLeft: '20px' }}>\n {items.map((item, i) => (\n <li key={i} style={{ marginBottom: '8px' }}>\n {typeof item === 'object' ? JSON.stringify(item) : String(item)}\n </li>\n ))}\n </ul>\n </div>\n );\n}\n\n// Table Component\nfunction DefaultTable({ columns, rows }: { columns: string[]; rows: Record<string, unknown>[] }) {\n return (\n <div style={{ overflowX: 'auto', marginBottom: '12px' }}>\n <table style={{ width: '100%', borderCollapse: 'collapse', fontSize: '14px' }}>\n <thead>\n <tr>\n {columns.map((col) => (\n <th key={col} style={{ textAlign: 'left', padding: '12px 8px', borderBottom: '2px solid #e5e7eb', fontWeight: 600 }}>\n {col}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {rows.map((row, i) => (\n <tr key={i}>\n {columns.map((col) => (\n <td key={col} style={{ padding: '12px 8px', borderBottom: '1px solid #e5e7eb' }}>\n {String(row[col] ?? '')}\n </td>\n ))}\n </tr>\n ))}\n </tbody>\n </table>\n </div>\n );\n}\n\n// Callout Component\nfunction DefaultCallout({ title, message, variant = 'info' }: { title?: string; message: string; variant?: 'info' | 'warning' | 'tip' }) {\n const colors = {\n info: { bg: '#eff6ff', border: '#3b82f6', text: '#1e40af' },\n warning: { bg: '#fffbeb', border: '#f59e0b', text: '#92400e' },\n tip: { bg: '#f0fdf4', border: '#22c55e', text: '#166534' },\n };\n const c = colors[variant];\n return (\n <div style={{ backgroundColor: c.bg, borderLeft: `4px solid ${c.border}`, padding: '12px 16px', marginBottom: '12px', borderRadius: '0 8px 8px 0' }}>\n {title && <strong style={{ color: c.text, display: 'block', marginBottom: '4px' }}>{title}</strong>}\n <span style={{ color: c.text }}>{message}</span>\n </div>\n );\n}\n\n/**\n * Default component registry mapping componentType to React components.\n * Users can override this with their own components.\n */\nexport const defaultComponentRegistry: Record<string, React.ComponentType<any>> = {\n card: DefaultCard,\n list: DefaultList,\n table: DefaultTable,\n callout: DefaultCallout,\n};\n\ninterface DynamicComponentProps {\n block: ComponentBlock;\n registry?: Record<string, React.ComponentType<any>>;\n}\n\n/**\n * DynamicComponent - Renders a component based on componentType.\n */\nexport function DynamicComponent({ block, registry = defaultComponentRegistry }: DynamicComponentProps) {\n const { componentType, props } = block;\n const Component = registry[componentType];\n\n if (!Component) {\n return (\n <div style={{ padding: '12px', backgroundColor: '#fef3c7', border: '1px solid #fcd34d', borderRadius: '8px', fontSize: '14px' }}>\n <strong>Unknown component: {componentType}</strong>\n <pre style={{ margin: '8px 0 0', fontSize: '12px', overflow: 'auto' }}>\n {JSON.stringify(props, null, 2)}\n </pre>\n </div>\n );\n }\n\n return <Component {...props} />;\n}\n","import React from 'react';\nimport type { FogUIResponse, ContentBlock } from '../types';\nimport { DynamicComponent, defaultComponentRegistry } from './ComponentRegistry';\n\ninterface FogUIRendererProps {\n /**\n * The FogUIResponse to render\n */\n response: FogUIResponse;\n /**\n * Custom component registry to override default components\n */\n componentRegistry?: Record<string, React.ComponentType<any>>;\n /**\n * Custom className for the container\n */\n className?: string;\n}\n\n/**\n * FogUIRenderer - Renders a FogUIResponse as React components.\n * \n * @example\n * ```tsx\n * import { FogUIRenderer } from '@fogui/react';\n * \n * function Chat({ response }) {\n * return <FogUIRenderer response={response} />;\n * }\n * ```\n */\nexport function FogUIRenderer({ response, componentRegistry, className }: FogUIRendererProps) {\n const registry = componentRegistry || defaultComponentRegistry;\n\n if (!response || !response.content) {\n return null;\n }\n\n return (\n <div className={className}>\n {response.content.map((block, index) => (\n <ContentBlockRenderer \n key={index} \n block={block} \n registry={registry}\n />\n ))}\n </div>\n );\n}\n\ninterface ContentBlockRendererProps {\n block: ContentBlock;\n registry: Record<string, React.ComponentType<any>>;\n}\n\nfunction ContentBlockRenderer({ block, registry }: ContentBlockRendererProps) {\n if (block.type === 'text') {\n return (\n <div style={{ marginBottom: '12px', lineHeight: 1.6 }}>\n {block.value.split('\\n').map((line, i) => (\n <React.Fragment key={i}>\n {line}\n {i < block.value.split('\\n').length - 1 && <br />}\n </React.Fragment>\n ))}\n </div>\n );\n }\n\n if (block.type === 'component') {\n return <DynamicComponent block={block} registry={registry} />;\n }\n\n return null;\n}\n"]}
1
+ {"version":3,"sources":["../src/FogUIProvider.tsx","../src/useFogUI.ts","../src/components/ComponentRegistry.tsx","../src/components/FogUIRenderer.tsx"],"names":["createContext","useMemo","jsx","useContext","useState","useCallback","jsxs","React"],"mappings":"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","file":"index.js","sourcesContent":["import React, { createContext, useContext, useMemo } from 'react';\n\n/**\n * FogUI Platform API endpoint\n */\nconst FOGUI_API_ENDPOINT = 'https://api.virtuoapps.com';\n\n/**\n * Component registry type - maps componentType to React components\n */\nexport type ComponentRegistry = Record<string, React.ComponentType<any>>;\n\ninterface FogUIContextValue {\n apiKey: string;\n endpoint: string;\n componentRegistry?: ComponentRegistry;\n}\n\nconst FogUIContext = createContext<FogUIContextValue | null>(null);\n\nexport interface FogUIProviderProps {\n children: React.ReactNode;\n /**\n * Your FogUI API key (get it from https://fogui.dev/dashboard)\n */\n apiKey: string;\n /**\n * Custom API endpoint (for self-hosted deployments)\n * @default 'https://api.virtuoapps.com'\n */\n endpoint?: string;\n /**\n * Custom component registry for your design system.\n * Map FogUI component types to your own React components.\n * \n * @example\n * ```tsx\n * import { Card, Table } from '@/components/ui';\n * \n * <FogUIProvider \n * apiKey=\"fog_xxx\"\n * components={{\n * card: MyCard,\n * table: MyTable,\n * list: MyList,\n * }}\n * >\n * ```\n */\n components?: ComponentRegistry;\n}\n\n/**\n * FogUIProvider - Provides FogUI configuration to the component tree.\n * \n * @example Basic usage\n * ```tsx\n * import { FogUIProvider } from '@fogui/react';\n * \n * function App() {\n * return (\n * <FogUIProvider apiKey=\"fog_xxxx\">\n * <MyApp />\n * </FogUIProvider>\n * );\n * }\n * ```\n * \n * @example With custom design system (e.g., Shadcn)\n * ```tsx\n * import { FogUIProvider } from '@fogui/react';\n * import { Card, CardHeader, CardContent } from '@/components/ui/card';\n * import { Table, TableHeader, TableBody, TableRow, TableCell } from '@/components/ui/table';\n * \n * // Map FogUI component types to your design system\n * const myComponents = {\n * card: ({ title, description, data }) => (\n * <Card>\n * <CardHeader>{title}</CardHeader>\n * <CardContent>{description}</CardContent>\n * </Card>\n * ),\n * table: MyTableComponent,\n * list: MyListComponent,\n * };\n * \n * function App() {\n * return (\n * <FogUIProvider apiKey=\"fog_xxxx\" components={myComponents}>\n * <MyApp />\n * </FogUIProvider>\n * );\n * }\n * ```\n * \n * @example Self-hosted deployment\n * ```tsx\n * <FogUIProvider \n * apiKey=\"fog_xxxx\" \n * endpoint=\"https://fogui.mycompany.com\"\n * >\n * <MyApp />\n * </FogUIProvider>\n * ```\n */\nexport function FogUIProvider({ children, apiKey, endpoint, components }: FogUIProviderProps) {\n if (!apiKey) {\n console.warn('[FogUI] API key is required. Get one at https://fogui.dev/dashboard');\n }\n\n const value = useMemo<FogUIContextValue>(() => ({\n apiKey,\n endpoint: endpoint || FOGUI_API_ENDPOINT,\n componentRegistry: components,\n }), [apiKey, endpoint, components]);\n\n return (\n <FogUIContext.Provider value={value}>\n {children}\n </FogUIContext.Provider>\n );\n}\n\n/**\n * Hook to access FogUI context\n * @internal\n */\nexport function useFogUIContext(): FogUIContextValue {\n const context = useContext(FogUIContext);\n if (!context) {\n throw new Error('useFogUI must be used within a FogUIProvider. Wrap your app with <FogUIProvider apiKey=\"...\">');\n }\n return context;\n}\n","import { useState, useCallback } from 'react';\nimport { useFogUIContext } from './FogUIProvider';\nimport type { TransformOptions, TransformResult, UseFogUIReturn, StreamEvent } from './types';\n\n/**\n * useFogUI - Main hook for transforming LLM output into structured UI.\n * \n * @example\n * ```tsx\n * import { useFogUI, FogUIRenderer } from '@fogui/react';\n * \n * function Chat() {\n * const { transform, isLoading } = useFogUI();\n * const [ui, setUI] = useState(null);\n * \n * const handleLLMResponse = async (llmOutput: string) => {\n * const result = await transform(llmOutput);\n * if (result.success) {\n * setUI(result.result);\n * }\n * };\n * \n * return (\n * <div>\n * {isLoading && <p>Transforming...</p>}\n * {ui && <FogUIRenderer response={ui} />}\n * </div>\n * );\n * }\n * ```\n */\nexport function useFogUI(): UseFogUIReturn {\n const { endpoint, apiKey } = useFogUIContext();\n const [isLoading, setIsLoading] = useState(false);\n const [error, setError] = useState<string | null>(null);\n\n /**\n * Transform raw LLM text into structured UI (non-streaming)\n */\n const transform = useCallback(async (\n content: string,\n options: TransformOptions = {}\n ): Promise<TransformResult> => {\n setIsLoading(true);\n setError(null);\n\n try {\n const response = await fetch(`${endpoint}/fogui/transform`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Authorization': `Bearer ${apiKey}`,\n },\n body: JSON.stringify({\n content,\n context: options.intent || options.preferredComponents || options.instructions ? {\n intent: options.intent,\n preferredComponents: options.preferredComponents,\n instructions: options.instructions,\n } : undefined,\n }),\n });\n\n if (!response.ok) {\n const errorData = await response.json().catch(() => ({}));\n throw new Error(errorData.error || `HTTP ${response.status}`);\n }\n\n const result: TransformResult = await response.json();\n \n if (!result.success) {\n setError(result.error || 'Transformation failed');\n }\n\n return result;\n\n } catch (err) {\n const message = err instanceof Error ? err.message : 'Unknown error';\n setError(message);\n return { success: false, error: message };\n } finally {\n setIsLoading(false);\n }\n }, [endpoint, apiKey]);\n\n /**\n * Transform with streaming - returns an async generator\n */\n const transformStream = useCallback(async function* (\n content: string,\n options: TransformOptions = {}\n ): AsyncGenerator<StreamEvent> {\n setIsLoading(true);\n setError(null);\n\n try {\n const response = await fetch(`${endpoint}/fogui/transform/stream`, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/json',\n 'Authorization': `Bearer ${apiKey}`,\n },\n body: JSON.stringify({\n content,\n context: options.intent || options.instructions ? {\n intent: options.intent,\n instructions: options.instructions,\n } : undefined,\n streaming: true,\n }),\n });\n\n if (!response.ok) {\n throw new Error(`HTTP ${response.status}`);\n }\n\n const reader = response.body?.getReader();\n if (!reader) {\n throw new Error('No response body');\n }\n\n const decoder = new TextDecoder();\n let buffer = '';\n let currentEvent = '';\n\n while (true) {\n const { done, value } = await reader.read();\n if (done) break;\n\n buffer += decoder.decode(value, { stream: true });\n const lines = buffer.split('\\n');\n buffer = lines.pop() || '';\n\n for (const line of lines) {\n if (line.startsWith('event:')) {\n currentEvent = line.substring(6).trim();\n } else if (line.startsWith('data:')) {\n const data = line.substring(5).trim();\n \n if (data === '[DONE]') {\n yield { type: 'done', data: null };\n continue;\n }\n\n if (data) {\n try {\n const parsed = JSON.parse(data);\n yield { type: currentEvent as StreamEvent['type'], data: parsed };\n } catch {\n if (currentEvent === 'chunk') {\n yield { type: 'chunk', data };\n }\n }\n }\n }\n }\n }\n\n } catch (err) {\n const message = err instanceof Error ? err.message : 'Unknown error';\n setError(message);\n yield { type: 'error', data: { error: message } };\n } finally {\n setIsLoading(false);\n }\n }, [endpoint, apiKey]);\n\n const clearError = useCallback(() => {\n setError(null);\n }, []);\n\n return {\n transform,\n transformStream,\n isLoading,\n error,\n clearError,\n };\n}\n","import React from 'react';\nimport type { ComponentBlock } from '../types';\n\n/**\n * Component registry type - maps componentType strings to React components.\n * \n * Each component receives props that match the FogUI DSL for that component type.\n */\nexport type ComponentRegistry = Record<string, React.ComponentType<any>>;\n\n/**\n * Standard prop interfaces for built-in FogUI component types.\n * Useful for implementing custom components that match the expected API.\n */\nexport interface CardProps {\n title?: string;\n description?: string;\n data?: Record<string, unknown>;\n children?: React.ReactNode;\n}\n\nexport interface ListProps {\n title?: string;\n items: unknown[];\n ordered?: boolean;\n}\n\nexport interface TableProps {\n columns: string[];\n rows: Record<string, unknown>[];\n title?: string;\n}\n\nexport interface CalloutProps {\n title?: string;\n message: string;\n variant?: 'info' | 'warning' | 'tip' | 'error';\n}\n\n/**\n * Merge multiple component registries with later registries taking precedence.\n * Useful for layering: defaults → context → prop overrides.\n */\nexport function mergeRegistries(\n ...registries: (ComponentRegistry | undefined)[]\n): ComponentRegistry {\n return registries.reduce<ComponentRegistry>((merged, registry) => {\n if (registry) {\n return { ...merged, ...registry };\n }\n return merged;\n }, {});\n}\n\n/**\n * Create a component registry from an adapter.\n * This is a convenience function for creating type-safe registries.\n * \n * @example\n * ```tsx\n * import { createRegistry } from '@fogui/react';\n * import { Card } from '@/components/ui/card';\n * \n * const myRegistry = createRegistry({\n * card: MyCardComponent,\n * table: MyTableComponent,\n * });\n * ```\n */\nexport function createRegistry(components: Partial<{\n card: React.ComponentType<CardProps>;\n list: React.ComponentType<ListProps>;\n table: React.ComponentType<TableProps>;\n callout: React.ComponentType<CalloutProps>;\n [key: string]: React.ComponentType<any>;\n}>): ComponentRegistry {\n return components as ComponentRegistry;\n}\n\n/**\n * Default component implementations.\n * These provide basic rendering - users should customize for their design system.\n */\n\n// Card Component\nfunction DefaultCard({ title, description, data }: { title?: string; description?: string; data?: Record<string, unknown> }) {\n return (\n <div style={{ border: '1px solid #e5e7eb', borderRadius: '8px', padding: '16px', marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 8px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n {description && <p style={{ margin: '0 0 12px', color: '#6b7280' }}>{description}</p>}\n {data && (\n <div style={{ fontSize: '14px' }}>\n {Object.entries(data).map(([key, value]) => (\n <div key={key} style={{ display: 'flex', justifyContent: 'space-between', padding: '4px 0' }}>\n <span style={{ color: '#6b7280' }}>{key}</span>\n <span style={{ fontWeight: 500 }}>{String(value)}</span>\n </div>\n ))}\n </div>\n )}\n </div>\n );\n}\n\n// List Component\nfunction DefaultList({ title, items }: { title?: string; items: unknown[] }) {\n return (\n <div style={{ marginBottom: '12px' }}>\n {title && <h3 style={{ margin: '0 0 12px', fontSize: '18px', fontWeight: 600 }}>{title}</h3>}\n <ul style={{ margin: 0, paddingLeft: '20px' }}>\n {items.map((item, i) => (\n <li key={i} style={{ marginBottom: '8px' }}>\n {typeof item === 'object' ? JSON.stringify(item) : String(item)}\n </li>\n ))}\n </ul>\n </div>\n );\n}\n\n// Table Component\nfunction DefaultTable({ columns, rows }: { columns: string[]; rows: Record<string, unknown>[] }) {\n return (\n <div style={{ overflowX: 'auto', marginBottom: '12px' }}>\n <table style={{ width: '100%', borderCollapse: 'collapse', fontSize: '14px' }}>\n <thead>\n <tr>\n {columns.map((col) => (\n <th key={col} style={{ textAlign: 'left', padding: '12px 8px', borderBottom: '2px solid #e5e7eb', fontWeight: 600 }}>\n {col}\n </th>\n ))}\n </tr>\n </thead>\n <tbody>\n {rows.map((row, i) => (\n <tr key={i}>\n {columns.map((col) => (\n <td key={col} style={{ padding: '12px 8px', borderBottom: '1px solid #e5e7eb' }}>\n {String(row[col] ?? '')}\n </td>\n ))}\n </tr>\n ))}\n </tbody>\n </table>\n </div>\n );\n}\n\n// Callout Component\nfunction DefaultCallout({ title, message, variant = 'info' }: { title?: string; message: string; variant?: 'info' | 'warning' | 'tip' }) {\n const colors = {\n info: { bg: '#eff6ff', border: '#3b82f6', text: '#1e40af' },\n warning: { bg: '#fffbeb', border: '#f59e0b', text: '#92400e' },\n tip: { bg: '#f0fdf4', border: '#22c55e', text: '#166534' },\n };\n const c = colors[variant];\n return (\n <div style={{ backgroundColor: c.bg, borderLeft: `4px solid ${c.border}`, padding: '12px 16px', marginBottom: '12px', borderRadius: '0 8px 8px 0' }}>\n {title && <strong style={{ color: c.text, display: 'block', marginBottom: '4px' }}>{title}</strong>}\n <span style={{ color: c.text }}>{message}</span>\n </div>\n );\n}\n\n/**\n * Default component registry mapping componentType to React components.\n * Users can override this with their own components.\n */\nexport const defaultComponentRegistry: Record<string, React.ComponentType<any>> = {\n card: DefaultCard,\n list: DefaultList,\n table: DefaultTable,\n callout: DefaultCallout,\n};\n\ninterface DynamicComponentProps {\n block: ComponentBlock;\n registry?: Record<string, React.ComponentType<any>>;\n}\n\n/**\n * DynamicComponent - Renders a component based on componentType.\n */\nexport function DynamicComponent({ block, registry = defaultComponentRegistry }: DynamicComponentProps) {\n const { componentType, props } = block;\n const Component = registry[componentType];\n\n if (!Component) {\n return (\n <div style={{ padding: '12px', backgroundColor: '#fef3c7', border: '1px solid #fcd34d', borderRadius: '8px', fontSize: '14px' }}>\n <strong>Unknown component: {componentType}</strong>\n <pre style={{ margin: '8px 0 0', fontSize: '12px', overflow: 'auto' }}>\n {JSON.stringify(props, null, 2)}\n </pre>\n </div>\n );\n }\n\n return <Component {...props} />;\n}\n","import type { ContentBlock, FogUIResponse } from '../types';\nimport { DynamicComponent, defaultComponentRegistry, mergeRegistries } from './ComponentRegistry';\n\nimport React from 'react';\nimport { useFogUIContext } from '../FogUIProvider';\n\ninterface FogUIRendererProps {\n /**\n * The FogUIResponse to render\n */\n response: FogUIResponse;\n /**\n * Custom component registry to override context/default components.\n * If not provided, uses the registry from FogUIProvider (if any),\n * falling back to defaultComponentRegistry.\n */\n componentRegistry?: Record<string, React.ComponentType<any>>;\n /**\n * Custom className for the container\n */\n className?: string;\n /**\n * Custom styles for the container\n */\n style?: React.CSSProperties;\n}\n\n/**\n * FogUIRenderer - Renders a FogUIResponse as React components.\n * \n * Uses the component registry from FogUIProvider if configured,\n * otherwise falls back to default components.\n * \n * @example Basic usage\n * ```tsx\n * import { FogUIRenderer } from '@fogui/react';\n * \n * function Chat({ response }) {\n * return <FogUIRenderer response={response} />;\n * }\n * ```\n * \n * @example With inline component override\n * ```tsx\n * <FogUIRenderer \n * response={response} \n * componentRegistry={{ card: MySpecialCard }}\n * />\n * ```\n */\nexport function FogUIRenderer({ response, componentRegistry, className, style }: FogUIRendererProps) {\n // Try to get registry from context (set in FogUIProvider)\n let contextRegistry: Record<string, React.ComponentType<any>> | undefined;\n try {\n const context = useFogUIContext();\n contextRegistry = context.componentRegistry;\n } catch {\n // Not inside FogUIProvider, use defaults\n }\n\n // Merge: prop registry > context registry > default registry\n const registry = mergeRegistries(defaultComponentRegistry, contextRegistry, componentRegistry);\n\n if (!response || !response.content) {\n return null;\n }\n\n return (\n <div className={className} style={style}>\n {response.content.map((block, index) => (\n <ContentBlockRenderer \n key={index} \n block={block} \n registry={registry}\n />\n ))}\n </div>\n );\n}\n\ninterface ContentBlockRendererProps {\n block: ContentBlock;\n registry: Record<string, React.ComponentType<any>>;\n}\n\nfunction ContentBlockRenderer({ block, registry }: ContentBlockRendererProps) {\n if (block.type === 'text') {\n return (\n <div style={{ marginBottom: '12px', lineHeight: 1.6 }}>\n {block.value.split('\\n').map((line, i) => (\n <React.Fragment key={i}>\n {line}\n {i < block.value.split('\\n').length - 1 && <br />}\n </React.Fragment>\n ))}\n </div>\n );\n }\n\n if (block.type === 'component') {\n return <DynamicComponent block={block} registry={registry} />;\n }\n\n return null;\n}\n"]}
package/dist/index.mjs CHANGED
@@ -2,16 +2,17 @@ import React2, { createContext, useMemo, useContext, useState, useCallback } fro
2
2
  import { jsx, jsxs } from 'react/jsx-runtime';
3
3
 
4
4
  // src/FogUIProvider.tsx
5
- var FOGUI_API_ENDPOINT = "https://api.fogui.dev";
5
+ var FOGUI_API_ENDPOINT = "https://api.virtuoapps.com";
6
6
  var FogUIContext = createContext(null);
7
- function FogUIProvider({ children, apiKey }) {
7
+ function FogUIProvider({ children, apiKey, endpoint, components }) {
8
8
  if (!apiKey) {
9
9
  console.warn("[FogUI] API key is required. Get one at https://fogui.dev/dashboard");
10
10
  }
11
11
  const value = useMemo(() => ({
12
12
  apiKey,
13
- endpoint: FOGUI_API_ENDPOINT
14
- }), [apiKey]);
13
+ endpoint: endpoint || FOGUI_API_ENDPOINT,
14
+ componentRegistry: components
15
+ }), [apiKey, endpoint, components]);
15
16
  return /* @__PURE__ */ jsx(FogUIContext.Provider, { value, children });
16
17
  }
17
18
  function useFogUIContext() {
@@ -137,6 +138,17 @@ function useFogUI() {
137
138
  clearError
138
139
  };
139
140
  }
141
+ function mergeRegistries(...registries) {
142
+ return registries.reduce((merged, registry) => {
143
+ if (registry) {
144
+ return { ...merged, ...registry };
145
+ }
146
+ return merged;
147
+ }, {});
148
+ }
149
+ function createRegistry(components) {
150
+ return components;
151
+ }
140
152
  function DefaultCard({ title, description, data }) {
141
153
  return /* @__PURE__ */ jsxs("div", { style: { border: "1px solid #e5e7eb", borderRadius: "8px", padding: "16px", marginBottom: "12px" }, children: [
142
154
  title && /* @__PURE__ */ jsx("h3", { style: { margin: "0 0 8px", fontSize: "18px", fontWeight: 600 }, children: title }),
@@ -191,12 +203,18 @@ function DynamicComponent({ block, registry = defaultComponentRegistry }) {
191
203
  }
192
204
  return /* @__PURE__ */ jsx(Component, { ...props });
193
205
  }
194
- function FogUIRenderer({ response, componentRegistry, className }) {
195
- const registry = componentRegistry || defaultComponentRegistry;
206
+ function FogUIRenderer({ response, componentRegistry, className, style }) {
207
+ let contextRegistry;
208
+ try {
209
+ const context = useFogUIContext();
210
+ contextRegistry = context.componentRegistry;
211
+ } catch {
212
+ }
213
+ const registry = mergeRegistries(defaultComponentRegistry, contextRegistry, componentRegistry);
196
214
  if (!response || !response.content) {
197
215
  return null;
198
216
  }
199
- return /* @__PURE__ */ jsx("div", { className, children: response.content.map((block, index) => /* @__PURE__ */ jsx(
217
+ return /* @__PURE__ */ jsx("div", { className, style, children: response.content.map((block, index) => /* @__PURE__ */ jsx(
200
218
  ContentBlockRenderer,
201
219
  {
202
220
  block,
@@ -218,6 +236,6 @@ function ContentBlockRenderer({ block, registry }) {
218
236
  return null;
219
237
  }
220
238
 
221
- export { DynamicComponent, FogUIProvider, FogUIRenderer, defaultComponentRegistry, useFogUI, useFogUIContext };
239
+ export { DynamicComponent, FogUIProvider, FogUIRenderer, createRegistry, defaultComponentRegistry, mergeRegistries, useFogUI, useFogUIContext };
222
240
  //# sourceMappingURL=index.mjs.map
223
241
  //# sourceMappingURL=index.mjs.map