@lantos1618/better-ui 0.8.0 → 0.9.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,5 +1,6 @@
1
1
  import { T as Tool, g as ToolContext } from '../tool-yZTixiN2.mjs';
2
- import { z } from 'zod';
2
+ export { z as zodToJsonSchema } from '../schema-DdZf6066.mjs';
3
+ import 'zod';
3
4
  import 'react';
4
5
 
5
6
  /**
@@ -127,33 +128,4 @@ declare class MCPServer {
127
128
  */
128
129
  declare function createMCPServer(config: MCPServerConfig): MCPServer;
129
130
 
130
- /**
131
- * Lightweight Zod-to-JSON-Schema converter.
132
- * Handles common Zod types without requiring zod-to-json-schema dependency.
133
- */
134
-
135
- interface JsonSchema {
136
- type?: string;
137
- properties?: Record<string, JsonSchema>;
138
- required?: string[];
139
- items?: JsonSchema;
140
- enum?: unknown[];
141
- description?: string;
142
- default?: unknown;
143
- minimum?: number;
144
- maximum?: number;
145
- minLength?: number;
146
- maxLength?: number;
147
- pattern?: string;
148
- format?: string;
149
- anyOf?: JsonSchema[];
150
- oneOf?: JsonSchema[];
151
- nullable?: boolean;
152
- additionalProperties?: boolean | JsonSchema;
153
- [key: string]: unknown;
154
- }
155
- declare function zodToJsonSchema(schema: z.ZodType | {
156
- [key: string]: any;
157
- }): JsonSchema;
158
-
159
- export { MCPServer, type MCPServerConfig, createMCPServer, zodToJsonSchema };
131
+ export { MCPServer, type MCPServerConfig, createMCPServer };
@@ -1,5 +1,6 @@
1
1
  import { T as Tool, g as ToolContext } from '../tool-yZTixiN2.js';
2
- import { z } from 'zod';
2
+ export { z as zodToJsonSchema } from '../schema-DdZf6066.js';
3
+ import 'zod';
3
4
  import 'react';
4
5
 
5
6
  /**
@@ -127,33 +128,4 @@ declare class MCPServer {
127
128
  */
128
129
  declare function createMCPServer(config: MCPServerConfig): MCPServer;
129
130
 
130
- /**
131
- * Lightweight Zod-to-JSON-Schema converter.
132
- * Handles common Zod types without requiring zod-to-json-schema dependency.
133
- */
134
-
135
- interface JsonSchema {
136
- type?: string;
137
- properties?: Record<string, JsonSchema>;
138
- required?: string[];
139
- items?: JsonSchema;
140
- enum?: unknown[];
141
- description?: string;
142
- default?: unknown;
143
- minimum?: number;
144
- maximum?: number;
145
- minLength?: number;
146
- maxLength?: number;
147
- pattern?: string;
148
- format?: string;
149
- anyOf?: JsonSchema[];
150
- oneOf?: JsonSchema[];
151
- nullable?: boolean;
152
- additionalProperties?: boolean | JsonSchema;
153
- [key: string]: unknown;
154
- }
155
- declare function zodToJsonSchema(schema: z.ZodType | {
156
- [key: string]: any;
157
- }): JsonSchema;
158
-
159
- export { MCPServer, type MCPServerConfig, createMCPServer, zodToJsonSchema };
131
+ export { MCPServer, type MCPServerConfig, createMCPServer };
@@ -0,0 +1,113 @@
1
+ import { T as Tool } from '../tool-yZTixiN2.mjs';
2
+ import { J as JsonSchema } from '../schema-DdZf6066.mjs';
3
+ import 'zod';
4
+ import 'react';
5
+
6
+ /**
7
+ * OpenAPI 3.1 spec generator for Better UI tools.
8
+ *
9
+ * Converts a tool registry into a valid OpenAPI document.
10
+ * Each tool becomes a POST endpoint at `/api/tools/{toolName}`.
11
+ *
12
+ * @example
13
+ * ```typescript
14
+ * import { generateOpenAPISpec } from '@lantos1618/better-ui/openapi';
15
+ * import { tools } from './tools';
16
+ *
17
+ * const spec = generateOpenAPISpec({
18
+ * title: 'My AI Tools API',
19
+ * version: '1.0.0',
20
+ * tools,
21
+ * });
22
+ *
23
+ * // Serve as JSON
24
+ * app.get('/openapi.json', (req, res) => res.json(spec));
25
+ * ```
26
+ */
27
+
28
+ interface OpenAPISpecConfig {
29
+ /** API title */
30
+ title: string;
31
+ /** API version */
32
+ version: string;
33
+ /** Tool registry */
34
+ tools: Record<string, Tool>;
35
+ /** API description */
36
+ description?: string;
37
+ /** Base URL for servers (default: '/') */
38
+ serverUrl?: string;
39
+ /** Base path prefix for tool endpoints (default: '/api/tools') */
40
+ basePath?: string;
41
+ /** Tags to group endpoints */
42
+ tags?: Array<{
43
+ name: string;
44
+ description?: string;
45
+ }>;
46
+ }
47
+ interface OpenAPISpec {
48
+ openapi: '3.1.0';
49
+ info: {
50
+ title: string;
51
+ version: string;
52
+ description?: string;
53
+ };
54
+ servers: Array<{
55
+ url: string;
56
+ }>;
57
+ paths: Record<string, PathItem>;
58
+ components: {
59
+ schemas: Record<string, JsonSchema>;
60
+ };
61
+ tags?: Array<{
62
+ name: string;
63
+ description?: string;
64
+ }>;
65
+ }
66
+ interface PathItem {
67
+ post: {
68
+ operationId: string;
69
+ summary: string;
70
+ description?: string;
71
+ tags?: string[];
72
+ requestBody: {
73
+ required: true;
74
+ content: {
75
+ 'application/json': {
76
+ schema: {
77
+ $ref: string;
78
+ };
79
+ };
80
+ };
81
+ };
82
+ responses: Record<string, {
83
+ description: string;
84
+ content?: {
85
+ 'application/json': {
86
+ schema: {
87
+ $ref: string;
88
+ } | JsonSchema;
89
+ };
90
+ };
91
+ }>;
92
+ };
93
+ }
94
+ /**
95
+ * Generate an OpenAPI 3.1 spec from a Better UI tool registry.
96
+ */
97
+ declare function generateOpenAPISpec(config: OpenAPISpecConfig): OpenAPISpec;
98
+ /**
99
+ * Create a request handler that serves the OpenAPI spec as JSON.
100
+ *
101
+ * @example
102
+ * ```typescript
103
+ * // Next.js route: app/api/openapi/route.ts
104
+ * export const GET = openAPIHandler({
105
+ * title: 'My Tools',
106
+ * version: '1.0.0',
107
+ * tools,
108
+ * });
109
+ * ```
110
+ */
111
+ declare function openAPIHandler(config: OpenAPISpecConfig): (req: Request) => Response;
112
+
113
+ export { type OpenAPISpec, type OpenAPISpecConfig, generateOpenAPISpec, openAPIHandler };
@@ -0,0 +1,113 @@
1
+ import { T as Tool } from '../tool-yZTixiN2.js';
2
+ import { J as JsonSchema } from '../schema-DdZf6066.js';
3
+ import 'zod';
4
+ import 'react';
5
+
6
+ /**
7
+ * OpenAPI 3.1 spec generator for Better UI tools.
8
+ *
9
+ * Converts a tool registry into a valid OpenAPI document.
10
+ * Each tool becomes a POST endpoint at `/api/tools/{toolName}`.
11
+ *
12
+ * @example
13
+ * ```typescript
14
+ * import { generateOpenAPISpec } from '@lantos1618/better-ui/openapi';
15
+ * import { tools } from './tools';
16
+ *
17
+ * const spec = generateOpenAPISpec({
18
+ * title: 'My AI Tools API',
19
+ * version: '1.0.0',
20
+ * tools,
21
+ * });
22
+ *
23
+ * // Serve as JSON
24
+ * app.get('/openapi.json', (req, res) => res.json(spec));
25
+ * ```
26
+ */
27
+
28
+ interface OpenAPISpecConfig {
29
+ /** API title */
30
+ title: string;
31
+ /** API version */
32
+ version: string;
33
+ /** Tool registry */
34
+ tools: Record<string, Tool>;
35
+ /** API description */
36
+ description?: string;
37
+ /** Base URL for servers (default: '/') */
38
+ serverUrl?: string;
39
+ /** Base path prefix for tool endpoints (default: '/api/tools') */
40
+ basePath?: string;
41
+ /** Tags to group endpoints */
42
+ tags?: Array<{
43
+ name: string;
44
+ description?: string;
45
+ }>;
46
+ }
47
+ interface OpenAPISpec {
48
+ openapi: '3.1.0';
49
+ info: {
50
+ title: string;
51
+ version: string;
52
+ description?: string;
53
+ };
54
+ servers: Array<{
55
+ url: string;
56
+ }>;
57
+ paths: Record<string, PathItem>;
58
+ components: {
59
+ schemas: Record<string, JsonSchema>;
60
+ };
61
+ tags?: Array<{
62
+ name: string;
63
+ description?: string;
64
+ }>;
65
+ }
66
+ interface PathItem {
67
+ post: {
68
+ operationId: string;
69
+ summary: string;
70
+ description?: string;
71
+ tags?: string[];
72
+ requestBody: {
73
+ required: true;
74
+ content: {
75
+ 'application/json': {
76
+ schema: {
77
+ $ref: string;
78
+ };
79
+ };
80
+ };
81
+ };
82
+ responses: Record<string, {
83
+ description: string;
84
+ content?: {
85
+ 'application/json': {
86
+ schema: {
87
+ $ref: string;
88
+ } | JsonSchema;
89
+ };
90
+ };
91
+ }>;
92
+ };
93
+ }
94
+ /**
95
+ * Generate an OpenAPI 3.1 spec from a Better UI tool registry.
96
+ */
97
+ declare function generateOpenAPISpec(config: OpenAPISpecConfig): OpenAPISpec;
98
+ /**
99
+ * Create a request handler that serves the OpenAPI spec as JSON.
100
+ *
101
+ * @example
102
+ * ```typescript
103
+ * // Next.js route: app/api/openapi/route.ts
104
+ * export const GET = openAPIHandler({
105
+ * title: 'My Tools',
106
+ * version: '1.0.0',
107
+ * tools,
108
+ * });
109
+ * ```
110
+ */
111
+ declare function openAPIHandler(config: OpenAPISpecConfig): (req: Request) => Response;
112
+
113
+ export { type OpenAPISpec, type OpenAPISpecConfig, generateOpenAPISpec, openAPIHandler };
@@ -0,0 +1,260 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/openapi/index.ts
21
+ var openapi_exports = {};
22
+ __export(openapi_exports, {
23
+ generateOpenAPISpec: () => generateOpenAPISpec,
24
+ openAPIHandler: () => openAPIHandler
25
+ });
26
+ module.exports = __toCommonJS(openapi_exports);
27
+
28
+ // src/mcp/schema.ts
29
+ function zodToJsonSchema(schema) {
30
+ return convert(schema);
31
+ }
32
+ function convert(schema) {
33
+ const def = schema._def;
34
+ const typeName = def?.typeName;
35
+ switch (typeName) {
36
+ case "ZodString":
37
+ return convertString(def);
38
+ case "ZodNumber":
39
+ return convertNumber(def);
40
+ case "ZodBoolean":
41
+ return { type: "boolean" };
42
+ case "ZodNull":
43
+ return { type: "null" };
44
+ case "ZodLiteral":
45
+ return { enum: [def.value] };
46
+ case "ZodEnum":
47
+ return { type: "string", enum: def.values };
48
+ case "ZodNativeEnum":
49
+ return { enum: Object.values(def.values) };
50
+ case "ZodObject":
51
+ return convertObject(def);
52
+ case "ZodArray":
53
+ return convertArray(def);
54
+ case "ZodOptional":
55
+ return convert(def.innerType);
56
+ case "ZodNullable": {
57
+ const inner = convert(def.innerType);
58
+ return { anyOf: [inner, { type: "null" }] };
59
+ }
60
+ case "ZodDefault":
61
+ return { ...convert(def.innerType), default: def.defaultValue() };
62
+ case "ZodUnion":
63
+ return { anyOf: def.options.map((o) => convert(o)) };
64
+ case "ZodDiscriminatedUnion":
65
+ return { oneOf: [...def.options.values()].map((o) => convert(o)) };
66
+ case "ZodRecord":
67
+ return {
68
+ type: "object",
69
+ additionalProperties: convert(def.valueType)
70
+ };
71
+ case "ZodTuple": {
72
+ const items = def.items.map((item) => convert(item));
73
+ return { type: "array", items: items.length === 1 ? items[0] : void 0, prefixItems: items };
74
+ }
75
+ case "ZodEffects":
76
+ return convert(def.schema);
77
+ case "ZodPipeline":
78
+ return convert(def.in);
79
+ case "ZodLazy":
80
+ return convert(def.getter());
81
+ case "ZodAny":
82
+ return {};
83
+ case "ZodUnknown":
84
+ return {};
85
+ default:
86
+ return {};
87
+ }
88
+ }
89
+ function convertString(def) {
90
+ const schema = { type: "string" };
91
+ if (def.checks) {
92
+ for (const check of def.checks) {
93
+ switch (check.kind) {
94
+ case "min":
95
+ schema.minLength = check.value;
96
+ break;
97
+ case "max":
98
+ schema.maxLength = check.value;
99
+ break;
100
+ case "email":
101
+ schema.format = "email";
102
+ break;
103
+ case "url":
104
+ schema.format = "uri";
105
+ break;
106
+ case "uuid":
107
+ schema.format = "uuid";
108
+ break;
109
+ case "regex":
110
+ schema.pattern = check.regex.source;
111
+ break;
112
+ }
113
+ }
114
+ }
115
+ if (def.description) schema.description = def.description;
116
+ return schema;
117
+ }
118
+ function convertNumber(def) {
119
+ const schema = { type: "number" };
120
+ if (def.checks) {
121
+ for (const check of def.checks) {
122
+ switch (check.kind) {
123
+ case "min":
124
+ schema.minimum = check.value;
125
+ if (check.inclusive === false) schema.exclusiveMinimum = check.value;
126
+ break;
127
+ case "max":
128
+ schema.maximum = check.value;
129
+ if (check.inclusive === false) schema.exclusiveMaximum = check.value;
130
+ break;
131
+ case "int":
132
+ schema.type = "integer";
133
+ break;
134
+ }
135
+ }
136
+ }
137
+ if (def.description) schema.description = def.description;
138
+ return schema;
139
+ }
140
+ function convertObject(def) {
141
+ const shape = def.shape();
142
+ const properties = {};
143
+ const required = [];
144
+ for (const [key, value] of Object.entries(shape)) {
145
+ properties[key] = convert(value);
146
+ const fieldDef = value._def;
147
+ const isOptional = fieldDef?.typeName === "ZodOptional" || fieldDef?.typeName === "ZodDefault";
148
+ if (!isOptional) {
149
+ required.push(key);
150
+ }
151
+ }
152
+ const schema = { type: "object", properties };
153
+ if (required.length > 0) schema.required = required;
154
+ if (def.description) schema.description = def.description;
155
+ return schema;
156
+ }
157
+ function convertArray(def) {
158
+ const schema = {
159
+ type: "array",
160
+ items: convert(def.type)
161
+ };
162
+ if (def.minLength) schema.minItems = def.minLength.value;
163
+ if (def.maxLength) schema.maxItems = def.maxLength.value;
164
+ if (def.description) schema.description = def.description;
165
+ return schema;
166
+ }
167
+
168
+ // src/openapi/index.ts
169
+ function generateOpenAPISpec(config) {
170
+ const basePath = config.basePath ?? "/api/tools";
171
+ const paths = {};
172
+ const schemas = {};
173
+ const autoTags = /* @__PURE__ */ new Set();
174
+ for (const [key, tool] of Object.entries(config.tools)) {
175
+ const name = tool.name || key;
176
+ const inputSchemaName = `${name}Input`;
177
+ const outputSchemaName = `${name}Output`;
178
+ schemas[inputSchemaName] = zodToJsonSchema(tool.inputSchema);
179
+ if (tool.outputSchema) {
180
+ schemas[outputSchemaName] = zodToJsonSchema(tool.outputSchema);
181
+ }
182
+ const toolTags = tool.tags.length > 0 ? tool.tags : [name];
183
+ for (const t of toolTags) autoTags.add(t);
184
+ const responseSchema = tool.outputSchema ? { $ref: `#/components/schemas/${outputSchemaName}` } : { type: "object" };
185
+ const hints = [];
186
+ if (tool.hints.destructive) hints.push("destructive");
187
+ if (tool.hints.readOnly) hints.push("read-only");
188
+ if (tool.hints.idempotent) hints.push("idempotent");
189
+ if (tool.requiresConfirmation) hints.push("requires confirmation");
190
+ const hintsStr = hints.length > 0 ? ` [${hints.join(", ")}]` : "";
191
+ paths[`${basePath}/${name}`] = {
192
+ post: {
193
+ operationId: name,
194
+ summary: tool.description || name,
195
+ description: (tool.description || "") + hintsStr,
196
+ tags: tool.tags.length > 0 ? tool.tags : void 0,
197
+ requestBody: {
198
+ required: true,
199
+ content: {
200
+ "application/json": {
201
+ schema: { $ref: `#/components/schemas/${inputSchemaName}` }
202
+ }
203
+ }
204
+ },
205
+ responses: {
206
+ "200": {
207
+ description: "Successful tool execution",
208
+ content: {
209
+ "application/json": {
210
+ schema: {
211
+ type: "object",
212
+ properties: {
213
+ result: responseSchema
214
+ }
215
+ }
216
+ }
217
+ }
218
+ },
219
+ "400": {
220
+ description: "Invalid input (Zod validation error)"
221
+ },
222
+ "404": {
223
+ description: "Tool not found"
224
+ },
225
+ "500": {
226
+ description: "Tool execution failed"
227
+ }
228
+ }
229
+ }
230
+ };
231
+ }
232
+ const tags = config.tags ?? [...autoTags].map((t) => ({ name: t }));
233
+ return {
234
+ openapi: "3.1.0",
235
+ info: {
236
+ title: config.title,
237
+ version: config.version,
238
+ ...config.description ? { description: config.description } : {}
239
+ },
240
+ servers: [{ url: config.serverUrl ?? "/" }],
241
+ paths,
242
+ components: { schemas },
243
+ ...tags.length > 0 ? { tags } : {}
244
+ };
245
+ }
246
+ function openAPIHandler(config) {
247
+ const spec = generateOpenAPISpec(config);
248
+ const json = JSON.stringify(spec, null, 2);
249
+ return () => new Response(json, {
250
+ headers: {
251
+ "Content-Type": "application/json",
252
+ "Access-Control-Allow-Origin": "*"
253
+ }
254
+ });
255
+ }
256
+ // Annotate the CommonJS export names for ESM import in node:
257
+ 0 && (module.exports = {
258
+ generateOpenAPISpec,
259
+ openAPIHandler
260
+ });
@@ -0,0 +1,97 @@
1
+ import {
2
+ zodToJsonSchema
3
+ } from "../chunk-OH73K7I5.mjs";
4
+ import "../chunk-Y6FXYEAI.mjs";
5
+
6
+ // src/openapi/index.ts
7
+ function generateOpenAPISpec(config) {
8
+ const basePath = config.basePath ?? "/api/tools";
9
+ const paths = {};
10
+ const schemas = {};
11
+ const autoTags = /* @__PURE__ */ new Set();
12
+ for (const [key, tool] of Object.entries(config.tools)) {
13
+ const name = tool.name || key;
14
+ const inputSchemaName = `${name}Input`;
15
+ const outputSchemaName = `${name}Output`;
16
+ schemas[inputSchemaName] = zodToJsonSchema(tool.inputSchema);
17
+ if (tool.outputSchema) {
18
+ schemas[outputSchemaName] = zodToJsonSchema(tool.outputSchema);
19
+ }
20
+ const toolTags = tool.tags.length > 0 ? tool.tags : [name];
21
+ for (const t of toolTags) autoTags.add(t);
22
+ const responseSchema = tool.outputSchema ? { $ref: `#/components/schemas/${outputSchemaName}` } : { type: "object" };
23
+ const hints = [];
24
+ if (tool.hints.destructive) hints.push("destructive");
25
+ if (tool.hints.readOnly) hints.push("read-only");
26
+ if (tool.hints.idempotent) hints.push("idempotent");
27
+ if (tool.requiresConfirmation) hints.push("requires confirmation");
28
+ const hintsStr = hints.length > 0 ? ` [${hints.join(", ")}]` : "";
29
+ paths[`${basePath}/${name}`] = {
30
+ post: {
31
+ operationId: name,
32
+ summary: tool.description || name,
33
+ description: (tool.description || "") + hintsStr,
34
+ tags: tool.tags.length > 0 ? tool.tags : void 0,
35
+ requestBody: {
36
+ required: true,
37
+ content: {
38
+ "application/json": {
39
+ schema: { $ref: `#/components/schemas/${inputSchemaName}` }
40
+ }
41
+ }
42
+ },
43
+ responses: {
44
+ "200": {
45
+ description: "Successful tool execution",
46
+ content: {
47
+ "application/json": {
48
+ schema: {
49
+ type: "object",
50
+ properties: {
51
+ result: responseSchema
52
+ }
53
+ }
54
+ }
55
+ }
56
+ },
57
+ "400": {
58
+ description: "Invalid input (Zod validation error)"
59
+ },
60
+ "404": {
61
+ description: "Tool not found"
62
+ },
63
+ "500": {
64
+ description: "Tool execution failed"
65
+ }
66
+ }
67
+ }
68
+ };
69
+ }
70
+ const tags = config.tags ?? [...autoTags].map((t) => ({ name: t }));
71
+ return {
72
+ openapi: "3.1.0",
73
+ info: {
74
+ title: config.title,
75
+ version: config.version,
76
+ ...config.description ? { description: config.description } : {}
77
+ },
78
+ servers: [{ url: config.serverUrl ?? "/" }],
79
+ paths,
80
+ components: { schemas },
81
+ ...tags.length > 0 ? { tags } : {}
82
+ };
83
+ }
84
+ function openAPIHandler(config) {
85
+ const spec = generateOpenAPISpec(config);
86
+ const json = JSON.stringify(spec, null, 2);
87
+ return () => new Response(json, {
88
+ headers: {
89
+ "Content-Type": "application/json",
90
+ "Access-Control-Allow-Origin": "*"
91
+ }
92
+ });
93
+ }
94
+ export {
95
+ generateOpenAPISpec,
96
+ openAPIHandler
97
+ };
@@ -0,0 +1,32 @@
1
+ import { z } from 'zod';
2
+
3
+ /**
4
+ * Lightweight Zod-to-JSON-Schema converter.
5
+ * Handles common Zod types without requiring zod-to-json-schema dependency.
6
+ */
7
+
8
+ interface JsonSchema {
9
+ type?: string;
10
+ properties?: Record<string, JsonSchema>;
11
+ required?: string[];
12
+ items?: JsonSchema;
13
+ enum?: unknown[];
14
+ description?: string;
15
+ default?: unknown;
16
+ minimum?: number;
17
+ maximum?: number;
18
+ minLength?: number;
19
+ maxLength?: number;
20
+ pattern?: string;
21
+ format?: string;
22
+ anyOf?: JsonSchema[];
23
+ oneOf?: JsonSchema[];
24
+ nullable?: boolean;
25
+ additionalProperties?: boolean | JsonSchema;
26
+ [key: string]: unknown;
27
+ }
28
+ declare function zodToJsonSchema(schema: z.ZodType | {
29
+ [key: string]: any;
30
+ }): JsonSchema;
31
+
32
+ export { type JsonSchema as J, zodToJsonSchema as z };
@@ -0,0 +1,32 @@
1
+ import { z } from 'zod';
2
+
3
+ /**
4
+ * Lightweight Zod-to-JSON-Schema converter.
5
+ * Handles common Zod types without requiring zod-to-json-schema dependency.
6
+ */
7
+
8
+ interface JsonSchema {
9
+ type?: string;
10
+ properties?: Record<string, JsonSchema>;
11
+ required?: string[];
12
+ items?: JsonSchema;
13
+ enum?: unknown[];
14
+ description?: string;
15
+ default?: unknown;
16
+ minimum?: number;
17
+ maximum?: number;
18
+ minLength?: number;
19
+ maxLength?: number;
20
+ pattern?: string;
21
+ format?: string;
22
+ anyOf?: JsonSchema[];
23
+ oneOf?: JsonSchema[];
24
+ nullable?: boolean;
25
+ additionalProperties?: boolean | JsonSchema;
26
+ [key: string]: unknown;
27
+ }
28
+ declare function zodToJsonSchema(schema: z.ZodType | {
29
+ [key: string]: any;
30
+ }): JsonSchema;
31
+
32
+ export { type JsonSchema as J, zodToJsonSchema as z };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lantos1618/better-ui",
3
- "version": "0.8.0",
3
+ "version": "0.9.0",
4
4
  "description": "A minimal, type-safe AI-first UI framework for building tools",
5
5
  "main": "dist/index.js",
6
6
  "module": "dist/index.mjs",
@@ -41,6 +41,11 @@
41
41
  "import": "./dist/agui/index.mjs",
42
42
  "require": "./dist/agui/index.js"
43
43
  },
44
+ "./openapi": {
45
+ "types": "./dist/openapi/index.d.ts",
46
+ "import": "./dist/openapi/index.mjs",
47
+ "require": "./dist/openapi/index.js"
48
+ },
44
49
  "./theme.css": "./src/theme.css"
45
50
  },
46
51
  "files": [
@@ -69,7 +74,7 @@
69
74
  },
70
75
  "scripts": {
71
76
  "build": "npm run build:lib",
72
- "build:lib": "tsup src/index.ts src/react/index.ts src/components/index.ts src/auth/index.ts src/persistence/index.ts src/mcp/index.ts src/agui/index.ts --format cjs,esm --dts --clean --tsconfig tsconfig.lib.json",
77
+ "build:lib": "tsup src/index.ts src/react/index.ts src/components/index.ts src/auth/index.ts src/persistence/index.ts src/mcp/index.ts src/agui/index.ts src/openapi/index.ts --format cjs,esm --dts --clean --tsconfig tsconfig.lib.json",
73
78
  "test": "jest",
74
79
  "type-check": "tsc --noEmit",
75
80
  "prepublishOnly": "npm run build:lib"