# rn-json-schema-form URL: /docs/native/docyrus/json-schema-form Render a JSON Schema as a native form — create, edit and read-only view modes, nested objects, arrays and a root array, with the web schema-to-field mapping. ## Installation ```bash pnpm dlx @docyrus/cli add @docyrus/rn-json-schema-form ``` **Dependencies:** - [tailwind-variants](https://www.npmjs.com/package/tailwind-variants) ## Usage ```tsx import { JsonSchemaForm } from '@/components/docyrus-native/json-schema-form'; import { type JsonSchema } from '@/hooks/docyrus-native/use-docyrus-data-source-json-schema'; const schema: JsonSchema = { type: 'object', title: 'Customer', required: ['name', 'email'], properties: { name: { type: 'string', title: 'Name' }, email: { type: 'string', format: 'email' }, tier: { type: 'string', enum: ['free', 'pro', 'enterprise'] }, address: { type: 'object', properties: { city: { type: 'string' }, zip: { type: 'string' } } }, tags: { type: 'array', items: { type: 'string' } } } }; export function CustomerForm() { return ( console.log(value)} onSubmit={async value => save(value)} /> ); } ``` Pair it with [`useDocyrusDataSourceJsonSchema`](/docs/native/hooks/use-docyrus-data-source-json-schema) to build the schema from a data source's fields. ### Schema → field mapping | Schema | Field | |--------|-------| | `enum` with ≤ 4 values | `field-radioGroup` (labels from `x-enumNames` / `enumNames` / `x-enum-labels` / `x-enumLabels`, else humanized) | | `enum` with > 4 values | `field-select` | | `boolean` | `field-switch` | | `number` / `integer` | `field-number` | | `string` + `contentMediaType: application/json` | Monospace code input with JSON parse validation (value stays a string) | | `format: email` / `uri` / `url` | `field-email` / `field-url` | | `format: date` / `date-time` / `datetime` / `time` | `field-date` / `field-dateTime` / `field-time` | | `format: password` / `color` / `hex-color` | `field-password` / `field-color` | | `format: textarea` / `multiline`, or `maxLength > 160` | `field-textarea` | | other `string` | `field-text` | | `object` | Outlined `Card` group (root object renders flat) | | `array` | `SchemaRepeater` (`minItems` / `maxItems` honoured); tuple `items` supported | Inputs render through `DocyFieldDynamic`; `mode="view"` renders values through `DocyValueDynamic`. Enum values keep their original JSON type (strings, numbers, booleans, `null`). Empty strings / nulls are dropped from the emitted value, and empty nested objects / arrays are omitted (the root is always emitted). ## API Reference | Prop | Type | Default | Description | |------|------|---------|-------------| | `schema` | `JsonSchema` | — | **Required.** Root object or root array schema | | `data` | `Record \| unknown[] \| null` | — | Initial / external value. External changes re-seed the form unless they echo the last emitted value | | `mode` | `'create' \| 'edit' \| 'view'` | `'create'` | `view` renders read-only values | | `disabled` | `boolean` | — | Disable every input and the submit button | | `submitLabel` | `string` | `'Save'` | Full-width submit button label (rendered only with `onSubmit`) | | `onChange` | `(value: JsonSchemaFormData) => void` | — | Called with the denormalized value on every change | | `onSubmit` | `(value: JsonSchemaFormData) => void \| Promise` | — | Called on submit after `required` + JSON validation pass; the button shows a spinner while it resolves | | `emptyState` | `ReactNode` | — | Rendered for an object without properties or an empty array (view mode) | | `className` | `string` | — | Container className | ## Components | Component | Description | |-----------|-------------| | `JsonSchemaForm` | Schema-driven form (create / edit / view) | ## Type Exports | Type | Description | |------|-------------| | `JsonSchemaFormProps` | Props for `JsonSchemaForm` | | `JsonSchemaFormMode` | `'create' \| 'edit' \| 'view'` | | `JsonSchemaFormData` | `Record \| Array` | `JsonSchema` itself is exported by `use-docyrus-data-source-json-schema`. ## Differences from web - No `@tanstack/react-form` — state is a plain immutable value tree inside the component. - Always a single column; `ref` and HTML div attributes are dropped (`className` is kept). - On submit, `required` properties and JSON inputs are validated and errors are shown inline (web submits without schema validation). ## Translation keys `ui.jsonSchemaForm.submit`, `ui.jsonSchemaForm.form`, `ui.jsonSchemaForm.group`, `ui.jsonSchemaForm.item`, `ui.jsonSchemaForm.add`, `ui.jsonSchemaForm.noFields`, `ui.jsonSchemaForm.noItems`, `ui.jsonSchemaForm.required`, `ui.jsonSchemaForm.invalidJson` (English fallbacks; the web component hardcodes this copy).