mirror of
https://github.com/vercel-labs/json-render.git
synced 2026-10-20 06:19:57 +08:00
* add rate limits
* fix lint
* better
generate prompt
update examples
* fixes
* fixes
* new api
* update docs
* fixes
* fixes
* generated prompt
* Add tests for catalog validation and prompt generation
- Test generateSystemPrompt with components, actions, custom rules
- Test new defineCatalog API from schema system
- Test catalog.prompt() method with custom rules
- Test catalog.validate() for valid and invalid specs
- Test catalog.zodSchema() for custom validation
- Test catalog.jsonSchema() for structured outputs
- Add tests for nested specs with children
- Add tests for rejecting invalid component types
* Fix lint: pass children as nested elements in renderer
Change from children={...} prop to nested children pattern
to satisfy react/no-children-prop rule.
* Fix lint errors in dashboard and web apps
- Disable react/prop-types in both eslint configs (TypeScript handles this)
- Allow styled-jsx 'jsx' property in dashboard
- Add DATABASE_URL to turbo env allowlist
- Remove unused drizzle-orm imports (and, sql)
- Suppress unused variable warnings where intentional
* Add server entry point for @json-render/remotion
The main package entry includes React components that require
client-side context (React.createContext). This causes build
failures when importing in server-side API routes.
Added `@json-render/remotion/server` entry point that exports
only schema and catalog definitions without React dependencies:
- schema, RemotionSchema, RemotionSpec
- standardComponentDefinitions, standardTransitionDefinitions
- standardEffectDefinitions
- Type exports for catalogs
Updated remotion example to import from /server in catalog.ts
* Make dashboard database connection lazy-initialized
The database connection threw an error at module load time if
DATABASE_URL was not set, causing builds to fail in CI where
the database is not available.
Changed to lazy initialization using a Proxy so the error only
occurs when the database is actually used at runtime, not at
build time.
* Fix previousSpec property name and lazy rate limiting
- Fix property name mismatch: playground now passes previousSpec
instead of previousTree to match what useUIStream hook expects
- Make rate limiting lazy-initialized to avoid runtime errors when
Redis env vars (KV_REST_API_URL, KV_REST_API_TOKEN) are not set
- Rate limiting gracefully becomes a no-op when Redis is unavailable
134 lines
3.9 KiB
TypeScript
134 lines
3.9 KiB
TypeScript
import {
|
|
pgTable,
|
|
varchar,
|
|
text,
|
|
integer,
|
|
decimal,
|
|
timestamp,
|
|
pgEnum,
|
|
jsonb,
|
|
} from "drizzle-orm/pg-core";
|
|
|
|
// Enums
|
|
export const customerStatusEnum = pgEnum("customer_status", [
|
|
"active",
|
|
"inactive",
|
|
]);
|
|
|
|
export const invoiceStatusEnum = pgEnum("invoice_status", [
|
|
"draft",
|
|
"sent",
|
|
"paid",
|
|
"overdue",
|
|
]);
|
|
|
|
export const expenseStatusEnum = pgEnum("expense_status", [
|
|
"pending",
|
|
"approved",
|
|
"rejected",
|
|
]);
|
|
|
|
export const accountTypeEnum = pgEnum("account_type", [
|
|
"bank",
|
|
"credit_card",
|
|
"cash",
|
|
]);
|
|
|
|
export const transactionTypeEnum = pgEnum("transaction_type", [
|
|
"income",
|
|
"expense",
|
|
"transfer",
|
|
]);
|
|
|
|
// Tables
|
|
export const customers = pgTable("customers", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
name: varchar("name", { length: 255 }).notNull(),
|
|
email: varchar("email", { length: 255 }).notNull(),
|
|
phone: varchar("phone", { length: 50 }),
|
|
balance: decimal("balance", { precision: 12, scale: 2 })
|
|
.notNull()
|
|
.default("0"),
|
|
status: customerStatusEnum("status").notNull().default("active"),
|
|
createdAt: timestamp("created_at").notNull().defaultNow(),
|
|
});
|
|
|
|
export const invoices = pgTable("invoices", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
customerId: varchar("customer_id", { length: 50 })
|
|
.notNull()
|
|
.references(() => customers.id),
|
|
customerName: varchar("customer_name", { length: 255 }).notNull(),
|
|
amount: decimal("amount", { precision: 12, scale: 2 }).notNull(),
|
|
status: invoiceStatusEnum("status").notNull().default("draft"),
|
|
dueDate: timestamp("due_date").notNull(),
|
|
createdAt: timestamp("created_at").notNull().defaultNow(),
|
|
items: jsonb("items").$type<InvoiceItem[]>().notNull().default([]),
|
|
});
|
|
|
|
export const expenses = pgTable("expenses", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
vendor: varchar("vendor", { length: 255 }).notNull(),
|
|
category: varchar("category", { length: 100 }).notNull(),
|
|
amount: decimal("amount", { precision: 12, scale: 2 }).notNull(),
|
|
date: timestamp("date").notNull(),
|
|
status: expenseStatusEnum("status").notNull().default("pending"),
|
|
description: text("description"),
|
|
});
|
|
|
|
export const accounts = pgTable("accounts", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
name: varchar("name", { length: 255 }).notNull(),
|
|
type: accountTypeEnum("type").notNull(),
|
|
balance: decimal("balance", { precision: 12, scale: 2 }).notNull(),
|
|
lastSync: timestamp("last_sync").notNull().defaultNow(),
|
|
});
|
|
|
|
export const transactions = pgTable("transactions", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
accountId: varchar("account_id", { length: 50 })
|
|
.notNull()
|
|
.references(() => accounts.id),
|
|
type: transactionTypeEnum("type").notNull(),
|
|
amount: decimal("amount", { precision: 12, scale: 2 }).notNull(),
|
|
description: text("description").notNull(),
|
|
category: varchar("category", { length: 100 }).notNull(),
|
|
date: timestamp("date").notNull(),
|
|
});
|
|
|
|
export const widgets = pgTable("widgets", {
|
|
id: varchar("id", { length: 50 }).primaryKey(),
|
|
prompt: text("prompt").notNull(),
|
|
spec: jsonb("spec").$type<WidgetSpec>().notNull(),
|
|
order: integer("order").notNull().default(0),
|
|
createdAt: timestamp("created_at").notNull().defaultNow(),
|
|
updatedAt: timestamp("updated_at").notNull().defaultNow(),
|
|
});
|
|
|
|
// Types
|
|
export interface WidgetSpec {
|
|
root: string;
|
|
elements: Record<string, unknown>;
|
|
}
|
|
export interface InvoiceItem {
|
|
description: string;
|
|
quantity: number;
|
|
rate: number;
|
|
amount: number;
|
|
}
|
|
|
|
export type Customer = typeof customers.$inferSelect;
|
|
export type NewCustomer = typeof customers.$inferInsert;
|
|
|
|
export type Invoice = typeof invoices.$inferSelect;
|
|
export type NewInvoice = typeof invoices.$inferInsert;
|
|
|
|
export type Expense = typeof expenses.$inferSelect;
|
|
export type NewExpense = typeof expenses.$inferInsert;
|
|
|
|
export type Account = typeof accounts.$inferSelect;
|
|
export type Transaction = typeof transactions.$inferSelect;
|
|
|
|
export type Widget = typeof widgets.$inferSelect;
|
|
export type NewWidget = typeof widgets.$inferInsert;
|