Skip to content

Commit c36462a

Browse files
authored
Merge pull request #22 from objectstack-ai/copilot/define-object-ui-types
2 parents 3b34d27 + b7346ed commit c36462a

19 files changed

Lines changed: 4932 additions & 0 deletions

packages/types/.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
dist/
2+
node_modules/

packages/types/README.md

Lines changed: 304 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,304 @@
1+
# @object-ui/types
2+
3+
Pure TypeScript type definitions for Object UI - **The Protocol Layer**.
4+
5+
## Features
6+
7+
- 🎯 **Complete Type Coverage** - Every component has full TypeScript definitions
8+
- 📦 **Zero Dependencies** - Pure types with no runtime dependencies
9+
- 🔌 **Framework Agnostic** - Use with React, Vue, or any framework
10+
- 🌍 **Backend Agnostic** - Works with REST, GraphQL, ObjectQL, or local data
11+
- 🎨 **Tailwind Native** - Designed for Tailwind CSS styling
12+
- 📚 **Comprehensive JSDoc** - Every type is fully documented
13+
14+
## Installation
15+
16+
```bash
17+
npm install @object-ui/types
18+
# or
19+
yarn add @object-ui/types
20+
# or
21+
pnpm add @object-ui/types
22+
```
23+
24+
**Important:** This package has **ZERO runtime dependencies**. It's pure TypeScript types.
25+
26+
## Philosophy
27+
28+
Object UI follows a **"Protocol First"** approach:
29+
30+
```
31+
@object-ui/types (Protocol)
32+
33+
@object-ui/core (Engine)
34+
35+
@object-ui/react (Framework)
36+
37+
@object-ui/components (UI Implementation)
38+
```
39+
40+
This separation allows:
41+
- ✅ Multiple UI implementations (Shadcn, Material, Ant Design)
42+
- ✅ Multiple framework bindings (React, Vue, Svelte)
43+
- ✅ Multiple backend adapters (REST, GraphQL, ObjectQL)
44+
- ✅ Static analysis and validation without runtime dependencies
45+
46+
## Usage
47+
48+
### Basic Example
49+
50+
```typescript
51+
import type { FormSchema, InputSchema, ButtonSchema } from '@object-ui/types';
52+
53+
const loginForm: FormSchema = {
54+
type: 'form',
55+
fields: [
56+
{
57+
name: 'email',
58+
type: 'input',
59+
inputType: 'email',
60+
label: 'Email',
61+
required: true,
62+
},
63+
{
64+
name: 'password',
65+
type: 'input',
66+
inputType: 'password',
67+
label: 'Password',
68+
required: true,
69+
}
70+
],
71+
submitLabel: 'Sign In'
72+
};
73+
```
74+
75+
### Advanced Example
76+
77+
```typescript
78+
import type { DataTableSchema, FlexSchema, CardSchema } from '@object-ui/types';
79+
80+
const dashboard: CardSchema = {
81+
type: 'card',
82+
title: 'User Management',
83+
content: {
84+
type: 'data-table',
85+
columns: [
86+
{ header: 'Name', accessorKey: 'name' },
87+
{ header: 'Email', accessorKey: 'email' },
88+
{ header: 'Role', accessorKey: 'role' }
89+
],
90+
data: [], // Connected to data source
91+
pagination: true,
92+
searchable: true,
93+
selectable: true
94+
}
95+
};
96+
```
97+
98+
### Type Narrowing
99+
100+
```typescript
101+
import type { AnySchema, SchemaByType } from '@object-ui/types';
102+
103+
function renderComponent(schema: AnySchema) {
104+
if (schema.type === 'input') {
105+
// TypeScript automatically narrows to InputSchema
106+
console.log(schema.placeholder);
107+
}
108+
}
109+
110+
// Or use the utility type
111+
type ButtonSchema = SchemaByType<'button'>;
112+
```
113+
114+
## Type Categories
115+
116+
### Base Types
117+
118+
Foundation types that all components build upon:
119+
120+
- `BaseSchema` - The base interface for all components
121+
- `SchemaNode` - Union type for schema nodes (objects, strings, numbers, etc.)
122+
- `ComponentMeta` - Metadata for component registration
123+
- `ComponentInput` - Input field definitions for designers/editors
124+
125+
### Layout Components
126+
127+
Structure and organization:
128+
129+
- `ContainerSchema` - Max-width container
130+
- `FlexSchema` - Flexbox layout
131+
- `GridSchema` - CSS Grid layout
132+
- `CardSchema` - Card container
133+
- `TabsSchema` - Tabbed interface
134+
135+
### Form Components
136+
137+
User input and interaction:
138+
139+
- `FormSchema` - Complete form with validation
140+
- `InputSchema` - Text input field
141+
- `SelectSchema` - Dropdown select
142+
- `CheckboxSchema` - Checkbox input
143+
- `RadioGroupSchema` - Radio button group
144+
- `DatePickerSchema` - Date selection
145+
- And 10+ more form components
146+
147+
### Data Display Components
148+
149+
Information presentation:
150+
151+
- `DataTableSchema` - Enterprise data table with sorting, filtering, pagination
152+
- `TableSchema` - Simple table
153+
- `ListSchema` - List with items
154+
- `ChartSchema` - Charts and graphs
155+
- `TreeViewSchema` - Hierarchical tree
156+
- `TimelineSchema` - Timeline visualization
157+
158+
### Feedback Components
159+
160+
Status and progress:
161+
162+
- `LoadingSchema` - Loading spinner
163+
- `ProgressSchema` - Progress bar
164+
- `SkeletonSchema` - Loading placeholder
165+
- `ToastSchema` - Toast notifications
166+
167+
### Overlay Components
168+
169+
Modals and popovers:
170+
171+
- `DialogSchema` - Modal dialog
172+
- `SheetSchema` - Side panel/drawer
173+
- `PopoverSchema` - Popover
174+
- `TooltipSchema` - Tooltip
175+
- `DropdownMenuSchema` - Dropdown menu
176+
177+
### Navigation Components
178+
179+
Menus and navigation:
180+
181+
- `HeaderBarSchema` - Top navigation bar
182+
- `SidebarSchema` - Side navigation
183+
- `BreadcrumbSchema` - Breadcrumb navigation
184+
- `PaginationSchema` - Pagination controls
185+
186+
### Complex Components
187+
188+
Advanced composite components:
189+
190+
- `KanbanSchema` - Kanban board
191+
- `CalendarViewSchema` - Calendar with events
192+
- `FilterBuilderSchema` - Advanced filter builder
193+
- `CarouselSchema` - Image/content carousel
194+
- `ChatbotSchema` - Chat interface
195+
196+
### Data Management
197+
198+
Backend integration:
199+
200+
- `DataSource` - Universal data adapter interface
201+
- `QueryParams` - Query parameters (OData-style)
202+
- `QueryResult` - Paginated query results
203+
- `DataBinding` - Data binding configuration
204+
205+
## Design Principles
206+
207+
### 1. Protocol Agnostic
208+
209+
Types don't assume any specific backend:
210+
211+
```typescript
212+
interface DataSource<T = any> {
213+
find(resource: string, params?: QueryParams): Promise<QueryResult<T>>;
214+
create(resource: string, data: Partial<T>): Promise<T>;
215+
// Works with REST, GraphQL, ObjectQL, or anything
216+
}
217+
```
218+
219+
### 2. Tailwind Native
220+
221+
All components support `className` for Tailwind styling:
222+
223+
```typescript
224+
const button: ButtonSchema = {
225+
type: 'button',
226+
label: 'Click Me',
227+
className: 'bg-blue-500 hover:bg-blue-600 text-white font-bold py-2 px-4 rounded'
228+
};
229+
```
230+
231+
### 3. Type Safe
232+
233+
Full TypeScript support with discriminated unions:
234+
235+
```typescript
236+
type AnySchema =
237+
| InputSchema
238+
| ButtonSchema
239+
| FormSchema
240+
| /* 50+ more */;
241+
242+
function render(schema: AnySchema) {
243+
switch (schema.type) {
244+
case 'input': /* schema is InputSchema */ break;
245+
case 'button': /* schema is ButtonSchema */ break;
246+
}
247+
}
248+
```
249+
250+
### 4. Composable
251+
252+
Components can nest indefinitely:
253+
254+
```typescript
255+
const page: FlexSchema = {
256+
type: 'flex',
257+
direction: 'col',
258+
children: [
259+
{ type: 'header-bar', title: 'My App' },
260+
{
261+
type: 'flex',
262+
direction: 'row',
263+
children: [
264+
{ type: 'sidebar', nav: [...] },
265+
{ type: 'container', children: [...] }
266+
]
267+
}
268+
]
269+
};
270+
```
271+
272+
## Comparison
273+
274+
### vs Amis Types
275+
276+
-**Lighter** - No runtime dependencies
277+
-**Tailwind Native** - Built for Tailwind CSS
278+
-**Better TypeScript** - Full type inference
279+
-**Framework Agnostic** - Not tied to React
280+
281+
### vs Formily Types
282+
283+
-**Full Pages** - Not just forms, entire UIs
284+
-**Simpler** - More straightforward API
285+
-**Better Docs** - Comprehensive JSDoc
286+
287+
## Contributing
288+
289+
We follow these constraints for this package:
290+
291+
1. **ZERO runtime dependencies** - Only TypeScript types
292+
2. **No React imports** - Framework agnostic
293+
3. **Comprehensive JSDoc** - Every property documented
294+
4. **Protocol first** - Types define the contract
295+
296+
## License
297+
298+
MIT
299+
300+
## Links
301+
302+
- [Documentation](https://objectui.org/docs/types)
303+
- [GitHub](https://github.com/objectstack-ai/objectui)
304+
- [NPM](https://www.npmjs.com/package/@object-ui/types)
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
/**
2+
* Example: Dashboard Layout
3+
*
4+
* This example demonstrates a complete dashboard layout with
5+
* sidebar, header, and data table.
6+
*/
7+
8+
import type { FlexSchema, SidebarSchema, HeaderBarSchema, CardSchema, DataTableSchema } from '../src/index';
9+
10+
export const dashboardSchema: FlexSchema = {
11+
type: 'flex',
12+
direction: 'col',
13+
className: 'h-screen',
14+
15+
children: [
16+
// Header
17+
{
18+
type: 'header-bar',
19+
title: 'Object UI Dashboard',
20+
logo: '/logo.svg',
21+
sticky: true,
22+
right: [
23+
{
24+
type: 'button',
25+
label: 'Profile',
26+
variant: 'ghost',
27+
icon: 'User'
28+
}
29+
]
30+
} as HeaderBarSchema,
31+
32+
// Main content with sidebar
33+
{
34+
type: 'flex',
35+
direction: 'row',
36+
className: 'flex-1',
37+
children: [
38+
// Sidebar
39+
{
40+
type: 'sidebar',
41+
collapsible: true,
42+
nav: [
43+
{ label: 'Dashboard', href: '/', icon: 'Home', active: true },
44+
{ label: 'Users', href: '/users', icon: 'Users' },
45+
{ label: 'Settings', href: '/settings', icon: 'Settings' }
46+
]
47+
} as SidebarSchema,
48+
49+
// Main content area
50+
{
51+
type: 'container',
52+
className: 'flex-1 p-6',
53+
children: [
54+
{
55+
type: 'card',
56+
title: 'User Management',
57+
description: 'Manage your users and permissions',
58+
content: {
59+
type: 'data-table',
60+
columns: [
61+
{ header: 'ID', accessorKey: 'id', width: '80px' },
62+
{ header: 'Name', accessorKey: 'name' },
63+
{ header: 'Email', accessorKey: 'email' },
64+
{ header: 'Role', accessorKey: 'role' },
65+
{ header: 'Status', accessorKey: 'status' }
66+
],
67+
data: [
68+
{ id: 1, name: 'John Doe', email: 'john@example.com', role: 'Admin', status: 'Active' },
69+
{ id: 2, name: 'Jane Smith', email: 'jane@example.com', role: 'User', status: 'Active' },
70+
{ id: 3, name: 'Bob Johnson', email: 'bob@example.com', role: 'User', status: 'Inactive' }
71+
],
72+
pagination: true,
73+
pageSize: 10,
74+
searchable: true,
75+
selectable: true,
76+
sortable: true,
77+
exportable: true,
78+
rowActions: true,
79+
onRowEdit: (row) => console.log('Edit:', row),
80+
onRowDelete: (row) => console.log('Delete:', row)
81+
} as DataTableSchema
82+
} as CardSchema
83+
]
84+
}
85+
]
86+
}
87+
]
88+
};

0 commit comments

Comments
 (0)