@sanity/form-toolkit
3.0.173.0.18
~
Modified (7 files)
Index: package/package.json
===================================================================
--- package/package.json
+++ package/package.json
@@ -1,7 +1,7 @@
{
"name": "@sanity/form-toolkit",
- "version": "3.0.17",
+ "version": "3.0.18",
"description": "Tool kit for integrating forms with a Sanity Studio",
"keywords": [
"sanity",
"sanity-plugin"
@@ -31,26 +31,26 @@
},
"dependencies": {
"@formium/client": "^0.1.4",
"@mailchimp/mailchimp_marketing": "^3.0.80",
- "@sanity/ui": "^4.0.4",
+ "@sanity/sanity-plugin-async-list": "^3.0.5",
+ "@sanity/ui": "^4.2.7",
"h3": "^1.15.11",
- "react-icons": "^5.7.0",
- "@sanity/sanity-plugin-async-list": "^3.0.4"
+ "react-icons": "^5.7.0"
},
"devDependencies": {
"@sanity/tsconfig": "^2.2.1",
- "@sanity/tsdown-config": "^0.26.0",
- "@testing-library/react": "^16.3.2",
+ "@sanity/tsdown-config": "^0.27.1",
+ "@testing-library/react": "^16.3.3",
"@types/mailchimp__mailchimp_marketing": "^3.0.22",
"@types/node": "^24.13.3",
- "@types/react": "^19.2.18",
- "@types/react-dom": "^19.2.4",
+ "@types/react": "^19.3.0",
+ "@types/react-dom": "^19.3.0",
"jsdom": "^29.1.1",
- "oxc-transform-react": "^0.145.0",
- "react": "^19.2.8",
- "react-dom": "^19.2.8",
- "sanity": "^6.10.1",
+ "oxc-transform-react": "^0.147.0",
+ "react": "^19.3.0",
+ "react-dom": "^19.3.0",
+ "sanity": "^6.16.0",
"tsdown": "^0.22.14"
},
"peerDependencies": {
"react": "^19.2", Index: package/dist/create-handler-2pX-bzeN.js.map
===================================================================
--- package/dist/create-handler-2pX-bzeN.js.map
+++ package/dist/create-handler-2pX-bzeN.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"create-handler-2pX-bzeN.js","names":[],"sources":["../src/shared/create-handler.ts"],"sourcesContent":["import type {IncomingMessage, ServerResponse} from 'node:http'\n\nimport {defineEventHandler, type H3Event} from 'h3' // For Nuxt.js/Nitro\n\n// Utility function to detect the framework at runtime\nconst detectFramework = (): string => {\n if (process.env['NEXT_RUNTIME']) {\n return 'nextjs'\n } else if (process.env['NUXT_ENV']) {\n return 'nuxt'\n } else if (process.env['SVELTEKIT_ENV']) {\n return 'sveltekit'\n } else if (process.env['REMIX_ENV']) {\n return 'remix'\n } else if (process.env['ASTRO_ENV']) {\n return 'astro'\n }\n // Default to the Next.js-compatible handler. The framework env vars above\n // aren't always set (e.g. Next.js API routes where NEXT_RUNTIME is absent),\n // and throwing here would break the most common setup.\n return 'nextjs'\n}\n\n// Create a generic handler with predefined logic\nconst createHandler = (handlerFunc: () => Promise<unknown>) => {\n const framework = detectFramework()\n\n // Handler logic to fetch Mailchimp data\n const handlerLogic = async ({\n res,\n }: {\n req: IncomingMessage | Request\n res?: ServerResponse\n }): Promise<unknown> => {\n try {\n const data = await handlerFunc()\n\n if (res) {\n // Send response directly for frameworks like Next.js and Nuxt.js\n res.writeHead(200, {'Content-Type': 'application/json'})\n res.end(JSON.stringify(data))\n }\n\n // Return the response for frameworks like SvelteKit, Remix, and Astro\n return data\n } catch (error) {\n if (error instanceof Error) {\n if (res) {\n res.writeHead(500, {'Content-Type': 'application/json'})\n res.end(JSON.stringify({error: error.message}))\n }\n return {error: error.message}\n }\n // Handle non-Error types (e.g., strings, objects)\n if (res) {\n res.writeHead(500, {'Content-Type': 'application/json'})\n res.end(JSON.stringify({error: 'An unexpected error occurred'}))\n }\n return {error: 'An unexpected error occurred'}\n }\n }\n\n // Framework-specific implementations\n if (framework === 'nextjs') {\n return async (req: IncomingMessage, res: ServerResponse) => {\n // Set CORS headers\n res.setHeader('Access-Control-Allow-Origin', '*') // Allow all origins\n res.setHeader('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS') // Allowed HTTP methods\n res.setHeader('Access-Control-Allow-Headers', 'Content-Type, Authorization') // Allowed headers\n\n // Short-circuit CORS preflight requests so we don't hit the upstream API\n if (req.method === 'OPTIONS') {\n res.writeHead(204)\n res.end()\n return\n }\n\n await handlerLogic({req, res})\n }\n } else if (framework === 'nuxt') {\n return defineEventHandler(async (event: H3Event) => {\n const req = event.node.req\n const res = event.node.res\n return handlerLogic({req, res})\n })\n } else if (framework === 'sveltekit') {\n return {\n GET: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return new Response(JSON.stringify(result), {\n headers: {'Content-Type': 'application/json'},\n })\n },\n }\n } else if (framework === 'remix') {\n return {\n loader: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return new Response(JSON.stringify(result), {\n headers: {'Content-Type': 'application/json'},\n })\n },\n }\n } else if (framework === 'astro') {\n return {\n get: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return {\n body: JSON.stringify(result),\n headers: {'Content-Type': 'application/json'},\n }\n },\n }\n }\n throw new Error(`Unsupported framework: ${framework}`)\n}\n\nexport default createHandler\n"],"mappings":";AAKA,MAAM,wBACA,QAAQ,IAAI,eACP,WACE,QAAQ,IAAI,WACd,SACE,QAAQ,IAAI,gBACd,cACE,QAAQ,IAAI,YACd,UACE,QAAQ,IAAI,YACd,UAKF,UAIH,iBAAiB,gBAAwC;CAC7D,IAAM,YAAY,gBAAgB,GAG5B,eAAe,OAAO,EAC1B,UAIsB;EACtB,IAAI;GACF,IAAM,OAAO,MAAM,YAAY;GAS/B,OAPI,QAEF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,IAAI,CAAC,IAIvB;EACT,SAAS,OAAO;GAad,OAZI,iBAAiB,SACf,QACF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,EAAC,OAAO,MAAM,QAAO,CAAC,CAAC,IAEzC,EAAC,OAAO,MAAM,QAAO,MAG1B,QACF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,EAAC,OAAO,+BAA8B,CAAC,CAAC,IAE1D,EAAC,OAAO,+BAA8B;EAC/C;CACF;CAGA,IAAI,cAAc,UAChB,OAAO,OAAO,KAAsB,QAAwB;EAO1D,IALA,IAAI,UAAU,+BAA+B,GAAG,GAChD,IAAI,UAAU,gCAAgC,iCAAiC,GAC/E,IAAI,UAAU,gCAAgC,6BAA6B,GAGvE,IAAI,WAAW,WAAW;GAE5B,AADA,IAAI,UAAU,GAAG,GACjB,IAAI,IAAI;GACR;EACF;EAEA,MAAM,aAAa;GAAC;GAAK;EAAG,CAAC;CAC/B;CACK,IAAI,cAAc,QACvB,OAAO,mBAAmB,OAAO,UAAmB;EAClD,IAAM,MAAM,MAAM,KAAK,KACjB,MAAM,MAAM,KAAK;EACvB,OAAO,aAAa;GAAC;GAAK;EAAG,CAAC;CAChC,CAAC;CACI,IAAI,cAAc,aACvB,OAAO,EACL,KAAK,OAAO,EAAC,cAAiC;EAC5C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO,IAAI,SAAS,KAAK,UAAU,MAAM,GAAG,EAC1C,SAAS,EAAC,gBAAgB,mBAAkB,EAC9C,CAAC;CACH,EACF;CACK,IAAI,cAAc,SACvB,OAAO,EACL,QAAQ,OAAO,EAAC,cAAiC;EAC/C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO,IAAI,SAAS,KAAK,UAAU,MAAM,GAAG,EAC1C,SAAS,EAAC,gBAAgB,mBAAkB,EAC9C,CAAC;CACH,EACF;CACK,IAAI,cAAc,SACvB,OAAO,EACL,KAAK,OAAO,EAAC,cAAiC;EAC5C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO;GACL,MAAM,KAAK,UAAU,MAAM;GAC3B,SAAS,EAAC,gBAAgB,mBAAkB;EAC9C;CACF,EACF;CAEF,MAAU,MAAM,0BAA0B,WAAW;AACvD"}
\ No newline at end of file
+{"version":3,"file":"create-handler-2pX-bzeN.js","names":["\"NEXT_RUNTIME\"","\"NUXT_ENV\"","\"SVELTEKIT_ENV\"","\"REMIX_ENV\"","\"ASTRO_ENV\""],"sources":["../src/shared/create-handler.ts"],"sourcesContent":["import type {IncomingMessage, ServerResponse} from 'node:http'\n\nimport {defineEventHandler, type H3Event} from 'h3' // For Nuxt.js/Nitro\n\n// Utility function to detect the framework at runtime\nconst detectFramework = (): string => {\n if (process.env['NEXT_RUNTIME']) {\n return 'nextjs'\n } else if (process.env['NUXT_ENV']) {\n return 'nuxt'\n } else if (process.env['SVELTEKIT_ENV']) {\n return 'sveltekit'\n } else if (process.env['REMIX_ENV']) {\n return 'remix'\n } else if (process.env['ASTRO_ENV']) {\n return 'astro'\n }\n // Default to the Next.js-compatible handler. The framework env vars above\n // aren't always set (e.g. Next.js API routes where NEXT_RUNTIME is absent),\n // and throwing here would break the most common setup.\n return 'nextjs'\n}\n\n// Create a generic handler with predefined logic\nconst createHandler = (handlerFunc: () => Promise<unknown>) => {\n const framework = detectFramework()\n\n // Handler logic to fetch Mailchimp data\n const handlerLogic = async ({\n res,\n }: {\n req: IncomingMessage | Request\n res?: ServerResponse\n }): Promise<unknown> => {\n try {\n const data = await handlerFunc()\n\n if (res) {\n // Send response directly for frameworks like Next.js and Nuxt.js\n res.writeHead(200, {'Content-Type': 'application/json'})\n res.end(JSON.stringify(data))\n }\n\n // Return the response for frameworks like SvelteKit, Remix, and Astro\n return data\n } catch (error) {\n if (error instanceof Error) {\n if (res) {\n res.writeHead(500, {'Content-Type': 'application/json'})\n res.end(JSON.stringify({error: error.message}))\n }\n return {error: error.message}\n }\n // Handle non-Error types (e.g., strings, objects)\n if (res) {\n res.writeHead(500, {'Content-Type': 'application/json'})\n res.end(JSON.stringify({error: 'An unexpected error occurred'}))\n }\n return {error: 'An unexpected error occurred'}\n }\n }\n\n // Framework-specific implementations\n if (framework === 'nextjs') {\n return async (req: IncomingMessage, res: ServerResponse) => {\n // Set CORS headers\n res.setHeader('Access-Control-Allow-Origin', '*') // Allow all origins\n res.setHeader('Access-Control-Allow-Methods', 'GET, POST, PUT, DELETE, OPTIONS') // Allowed HTTP methods\n res.setHeader('Access-Control-Allow-Headers', 'Content-Type, Authorization') // Allowed headers\n\n // Short-circuit CORS preflight requests so we don't hit the upstream API\n if (req.method === 'OPTIONS') {\n res.writeHead(204)\n res.end()\n return\n }\n\n await handlerLogic({req, res})\n }\n } else if (framework === 'nuxt') {\n return defineEventHandler(async (event: H3Event) => {\n const req = event.node.req\n const res = event.node.res\n return handlerLogic({req, res})\n })\n } else if (framework === 'sveltekit') {\n return {\n GET: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return new Response(JSON.stringify(result), {\n headers: {'Content-Type': 'application/json'},\n })\n },\n }\n } else if (framework === 'remix') {\n return {\n loader: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return new Response(JSON.stringify(result), {\n headers: {'Content-Type': 'application/json'},\n })\n },\n }\n } else if (framework === 'astro') {\n return {\n get: async ({request}: {request: Request}) => {\n const result = await handlerLogic({req: request})\n return {\n body: JSON.stringify(result),\n headers: {'Content-Type': 'application/json'},\n }\n },\n }\n }\n throw new Error(`Unsupported framework: ${framework}`)\n}\n\nexport default createHandler\n"],"mappings":";AAKA,MAAM,wBACA,QAAQ,IAAIA,eACP,WACE,QAAQ,IAAIC,WACd,SACE,QAAQ,IAAIC,gBACd,cACE,QAAQ,IAAIC,YACd,UACE,QAAQ,IAAIC,YACd,UAKF,UAIH,iBAAiB,gBAAwC;CAC7D,IAAM,YAAY,gBAAgB,GAG5B,eAAe,OAAO,EAC1B,UAIsB;EACtB,IAAI;GACF,IAAM,OAAO,MAAM,YAAY;GAS/B,OAPI,QAEF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,IAAI,CAAC,IAIvB;EACT,SAAS,OAAO;GAad,OAZI,iBAAiB,SACf,QACF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,EAAC,OAAO,MAAM,QAAO,CAAC,CAAC,IAEzC,EAAC,OAAO,MAAM,QAAO,MAG1B,QACF,IAAI,UAAU,KAAK,EAAC,gBAAgB,mBAAkB,CAAC,GACvD,IAAI,IAAI,KAAK,UAAU,EAAC,OAAO,+BAA8B,CAAC,CAAC,IAE1D,EAAC,OAAO,+BAA8B;EAC/C;CACF;CAGA,IAAI,cAAc,UAChB,OAAO,OAAO,KAAsB,QAAwB;EAO1D,IALA,IAAI,UAAU,+BAA+B,GAAG,GAChD,IAAI,UAAU,gCAAgC,iCAAiC,GAC/E,IAAI,UAAU,gCAAgC,6BAA6B,GAGvE,IAAI,WAAW,WAAW;GAE5B,AADA,IAAI,UAAU,GAAG,GACjB,IAAI,IAAI;GACR;EACF;EAEA,MAAM,aAAa;GAAC;GAAK;EAAG,CAAC;CAC/B;CACK,IAAI,cAAc,QACvB,OAAO,mBAAmB,OAAO,UAAmB;EAClD,IAAM,MAAM,MAAM,KAAK,KACjB,MAAM,MAAM,KAAK;EACvB,OAAO,aAAa;GAAC;GAAK;EAAG,CAAC;CAChC,CAAC;CACI,IAAI,cAAc,aACvB,OAAO,EACL,KAAK,OAAO,EAAC,cAAiC;EAC5C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO,IAAI,SAAS,KAAK,UAAU,MAAM,GAAG,EAC1C,SAAS,EAAC,gBAAgB,mBAAkB,EAC9C,CAAC;CACH,EACF;CACK,IAAI,cAAc,SACvB,OAAO,EACL,QAAQ,OAAO,EAAC,cAAiC;EAC/C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO,IAAI,SAAS,KAAK,UAAU,MAAM,GAAG,EAC1C,SAAS,EAAC,gBAAgB,mBAAkB,EAC9C,CAAC;CACH,EACF;CACK,IAAI,cAAc,SACvB,OAAO,EACL,KAAK,OAAO,EAAC,cAAiC;EAC5C,IAAM,SAAS,MAAM,aAAa,EAAC,KAAK,QAAO,CAAC;EAChD,OAAO;GACL,MAAM,KAAK,UAAU,MAAM;GAC3B,SAAS,EAAC,gBAAgB,mBAAkB;EAC9C;CACF,EACF;CAEF,MAAU,MAAM,0BAA0B,WAAW;AACvD"}
\ No newline at end of file Index: package/dist/form-renderer/index.js.map
===================================================================
--- package/dist/form-renderer/index.js.map
+++ package/dist/form-renderer/index.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"index.js","names":["{field, fieldState, error}","options = {}","choices = []","validation = []","validation.reduce((acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }, {})","(acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }","(\n e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>,\n ) => {\n onChange?.(e.target.value)\n }","(e: ChangeEvent<HTMLInputElement>, choiceValue: string) => {\n if (Array.isArray(value)) {\n const newValue = e.target.checked\n ? [...value, choiceValue]\n : value.filter((v: string) => v !== choiceValue)\n onChange?.(newValue)\n } else {\n onChange?.(e.target.checked ? choiceValue : '')\n }\n }","e","v","(fallback?: string) =>\n isControlled ? {value: value ?? '', onChange: handleChange} : {defaultValue: fallback}","() => {\n switch (type) {\n case 'submit':\n return <button type=\"submit\">{label || 'Submit'}</button>\n case 'textarea':\n return (\n <textarea\n ref={toRef<HTMLTextAreaElement>(ref)}\n name={name}\n onBlur={onBlur}\n placeholder={options.placeholder}\n {...validationRules}\n {...textValueProps(options.defaultValue)}\n />\n )\n\n case 'select':\n return (\n <select\n ref={toRef<HTMLSelectElement>(ref)}\n name={name}\n {...textValueProps()}\n {...validationRules}\n onBlur={onBlur}\n >\n {choices?.map((choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n ))}\n </select>\n )\n\n case 'radio':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"radio\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled ? {checked: value === choice.value, onChange: handleChange} : {})}\n />\n {choice.label}\n </label>\n ))\n\n case 'checkbox':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"checkbox\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled\n ? {\n checked: Array.isArray(value)\n ? value.includes(choice.value)\n : value === choice.value,\n onChange: (e: ChangeEvent<HTMLInputElement>) =>\n handleCheckboxChange(e, choice.value),\n }\n : {})}\n />\n {choice.label}\n </label>\n ))\n\n default:\n return (\n <input\n type={type}\n ref={toRef<HTMLInputElement>(ref)}\n name={name}\n {...textValueProps(options.defaultValue)}\n {...validationRules}\n onBlur={onBlur}\n placeholder={options.placeholder}\n />\n )\n }\n }","choices?.map","options.defaultValue","(choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n )","choice","label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>","renderInput()","error && <span className=\"error\">{error}</span>","<>\n {label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>}\n {renderInput()}\n {error && <span className=\"error\">{error}</span>}\n </>","getFieldState = defaultGetFieldState","fieldComponents = defaultFieldComponents","(field: FormField) => {\n const CustomComponent = fieldComponents[field.type]\n const fieldState = getFieldState(field.name)\n const error = getFieldError?.(field.name)\n\n if (CustomComponent) {\n return <CustomComponent field={field} fieldState={fieldState} error={error} />\n }\n\n return <DefaultField field={field} fieldState={fieldState} error={error} />\n }","formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))","fields","field","renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })","formData?.submitButton?.text || 'Submit'","<form {...elProps} id={elProps.id ?? formData?.id?.current}>\n {formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))}\n\n {children}\n\n {renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })}\n </form>","elProps.id ?? formData?.id?.current"],"sources":["../../src/form-renderer/components/default-field.tsx","../../src/form-renderer/components/form-renderer.tsx"],"sourcesContent":["import type {ChangeEvent, FC, Ref} from 'react'\n\nimport type {FieldComponentProps} from './types'\n\n// oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- FieldState.ref is loosely typed so refs from any form library can be passed through\nconst toRef = <T extends HTMLElement>(ref: unknown) => ref as Ref<T> | undefined\n\nexport const DefaultField: FC<FieldComponentProps> = ({field, fieldState, error}) => {\n const {type, label, name, options = {}, choices = [], validation = []} = field\n if (!type || !name) return null\n const validationRules = validation.reduce((acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }, {})\n const {value, onChange, onBlur, ref} = fieldState\n // Without an onChange handler the fields render as uncontrolled inputs, so the\n // browser keeps them interactive (e.g. the default native-form usage). When a\n // handler is provided (react-hook-form, TanStack Form, etc.) they're controlled.\n const isControlled = typeof onChange === 'function'\n\n const handleChange = (\n e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>,\n ) => {\n onChange?.(e.target.value)\n }\n\n const handleCheckboxChange = (e: ChangeEvent<HTMLInputElement>, choiceValue: string) => {\n if (Array.isArray(value)) {\n const newValue = e.target.checked\n ? [...value, choiceValue]\n : value.filter((v: string) => v !== choiceValue)\n onChange?.(newValue)\n } else {\n onChange?.(e.target.checked ? choiceValue : '')\n }\n }\n\n // Controlled inputs bind `value`/`onChange` from form state only — never the\n // schema default, which would desync the UI from what the form library submits.\n // Uncontrolled (native) inputs use `defaultValue` so the browser owns state.\n const textValueProps = (fallback?: string) =>\n isControlled ? {value: value ?? '', onChange: handleChange} : {defaultValue: fallback}\n\n const renderInput = () => {\n switch (type) {\n case 'submit':\n return <button type=\"submit\">{label || 'Submit'}</button>\n case 'textarea':\n return (\n <textarea\n ref={toRef<HTMLTextAreaElement>(ref)}\n name={name}\n onBlur={onBlur}\n placeholder={options.placeholder}\n {...validationRules}\n {...textValueProps(options.defaultValue)}\n />\n )\n\n case 'select':\n return (\n <select\n ref={toRef<HTMLSelectElement>(ref)}\n name={name}\n {...textValueProps()}\n {...validationRules}\n onBlur={onBlur}\n >\n {choices?.map((choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n ))}\n </select>\n )\n\n case 'radio':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"radio\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled ? {checked: value === choice.value, onChange: handleChange} : {})}\n />\n {choice.label}\n </label>\n ))\n\n case 'checkbox':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"checkbox\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled\n ? {\n checked: Array.isArray(value)\n ? value.includes(choice.value)\n : value === choice.value,\n onChange: (e: ChangeEvent<HTMLInputElement>) =>\n handleCheckboxChange(e, choice.value),\n }\n : {})}\n />\n {choice.label}\n </label>\n ))\n\n default:\n return (\n <input\n type={type}\n ref={toRef<HTMLInputElement>(ref)}\n name={name}\n {...textValueProps(options.defaultValue)}\n {...validationRules}\n onBlur={onBlur}\n placeholder={options.placeholder}\n />\n )\n }\n }\n\n return (\n <>\n {label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>}\n {renderInput()}\n {error && <span className=\"error\">{error}</span>}\n </>\n )\n}\n","import type {ComponentType, FC, HTMLProps} from 'react'\n\nimport {DefaultField} from './default-field'\nimport type {FieldComponentProps, FieldState, FormDataProps, FormField} from './types'\n\ninterface FormRendererProps extends HTMLProps<HTMLFormElement> {\n formData?: FormDataProps\n // Function to get field state for a given field name\n getFieldState?: (fieldName: string) => FieldState\n // Function to get field error for a given field name\n getFieldError?: (fieldName: string) => string | undefined\n // Override default field components\n fieldComponents?: Record<string, ComponentType<FieldComponentProps>>\n}\n\n// No field state by default: fields render as uncontrolled, interactive inputs\n// so the form works out of the box (e.g. as a native HTML form). Consumers can\n// pass `getFieldState` to make the fields controlled.\nconst EMPTY_FIELD_STATE: FieldState = {}\nconst defaultGetFieldState = (): FieldState => EMPTY_FIELD_STATE\n\nconst defaultFieldComponents: Record<string, ComponentType<FieldComponentProps>> = {}\n\nexport const FormRenderer: FC<FormRendererProps> = (props) => {\n const {\n formData,\n getFieldState = defaultGetFieldState,\n getFieldError,\n fieldComponents = defaultFieldComponents,\n children,\n } = props\n const renderField = (field: FormField) => {\n const CustomComponent = fieldComponents[field.type]\n const fieldState = getFieldState(field.name)\n const error = getFieldError?.(field.name)\n\n if (CustomComponent) {\n return <CustomComponent field={field} fieldState={fieldState} error={error} />\n }\n\n return <DefaultField field={field} fieldState={fieldState} error={error} />\n }\n const elProps = Object.assign({}, props)\n delete elProps.formData\n delete elProps.getFieldState\n delete elProps.getFieldError\n delete elProps.fieldComponents\n\n return (\n <form {...elProps} id={elProps.id ?? formData?.id?.current}>\n {formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))}\n\n {children}\n\n {renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })}\n </form>\n )\n}\n"],"mappings":"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"}
\ No newline at end of file
+{"version":3,"file":"index.js","names":["{field, fieldState, error}","options = {}","choices = []","validation = []","validation.reduce((acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }, {})","(acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }","(\n e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>,\n ) => {\n onChange?.(e.target.value)\n }","(e: ChangeEvent<HTMLInputElement>, choiceValue: string) => {\n if (Array.isArray(value)) {\n const newValue = e.target.checked\n ? [...value, choiceValue]\n : value.filter((v: string) => v !== choiceValue)\n onChange?.(newValue)\n } else {\n onChange?.(e.target.checked ? choiceValue : '')\n }\n }","e","v","(fallback?: string) =>\n isControlled ? {value: value ?? '', onChange: handleChange} : {defaultValue: fallback}","() => {\n switch (type) {\n case 'submit':\n return <button type=\"submit\">{label || 'Submit'}</button>\n case 'textarea':\n return (\n <textarea\n ref={toRef<HTMLTextAreaElement>(ref)}\n name={name}\n onBlur={onBlur}\n placeholder={options.placeholder}\n {...validationRules}\n {...textValueProps(options.defaultValue)}\n />\n )\n\n case 'select':\n return (\n <select\n ref={toRef<HTMLSelectElement>(ref)}\n name={name}\n {...textValueProps()}\n {...validationRules}\n onBlur={onBlur}\n >\n {choices?.map((choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n ))}\n </select>\n )\n\n case 'radio':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"radio\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled ? {checked: value === choice.value, onChange: handleChange} : {})}\n />\n {choice.label}\n </label>\n ))\n\n case 'checkbox':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"checkbox\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled\n ? {\n checked: Array.isArray(value)\n ? value.includes(choice.value)\n : value === choice.value,\n onChange: (e: ChangeEvent<HTMLInputElement>) =>\n handleCheckboxChange(e, choice.value),\n }\n : {})}\n />\n {choice.label}\n </label>\n ))\n\n default:\n return (\n <input\n type={type}\n ref={toRef<HTMLInputElement>(ref)}\n name={name}\n {...textValueProps(options.defaultValue)}\n {...validationRules}\n onBlur={onBlur}\n placeholder={options.placeholder}\n />\n )\n }\n }","choices?.map","options.defaultValue","(choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n )","choice","label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>","renderInput()","error && <span className=\"error\">{error}</span>","<>\n {label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>}\n {renderInput()}\n {error && <span className=\"error\">{error}</span>}\n </>","_c","_Fragment","getFieldState = defaultGetFieldState","fieldComponents = defaultFieldComponents","(field: FormField) => {\n const CustomComponent = fieldComponents[field.type]\n const fieldState = getFieldState(field.name)\n const error = getFieldError?.(field.name)\n\n if (CustomComponent) {\n return <CustomComponent field={field} fieldState={fieldState} error={error} />\n }\n\n return <DefaultField field={field} fieldState={fieldState} error={error} />\n }","formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))","fields","field","renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })","formData?.submitButton?.text || 'Submit'","<form {...elProps} id={elProps.id ?? formData?.id?.current}>\n {formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))}\n\n {children}\n\n {renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })}\n </form>","elProps.id ?? formData?.id?.current","_c"],"sources":["../../src/form-renderer/components/default-field.tsx","../../src/form-renderer/components/form-renderer.tsx"],"sourcesContent":["import type {ChangeEvent, FC, Ref} from 'react'\n\nimport type {FieldComponentProps} from './types'\n\n// oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- FieldState.ref is loosely typed so refs from any form library can be passed through\nconst toRef = <T extends HTMLElement>(ref: unknown) => ref as Ref<T> | undefined\n\nexport const DefaultField: FC<FieldComponentProps> = ({field, fieldState, error}) => {\n const {type, label, name, options = {}, choices = [], validation = []} = field\n if (!type || !name) return null\n const validationRules = validation.reduce((acc: Record<string, string>, v) => {\n acc[v.type] = v.value\n return acc\n }, {})\n const {value, onChange, onBlur, ref} = fieldState\n // Without an onChange handler the fields render as uncontrolled inputs, so the\n // browser keeps them interactive (e.g. the default native-form usage). When a\n // handler is provided (react-hook-form, TanStack Form, etc.) they're controlled.\n const isControlled = typeof onChange === 'function'\n\n const handleChange = (\n e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>,\n ) => {\n onChange?.(e.target.value)\n }\n\n const handleCheckboxChange = (e: ChangeEvent<HTMLInputElement>, choiceValue: string) => {\n if (Array.isArray(value)) {\n const newValue = e.target.checked\n ? [...value, choiceValue]\n : value.filter((v: string) => v !== choiceValue)\n onChange?.(newValue)\n } else {\n onChange?.(e.target.checked ? choiceValue : '')\n }\n }\n\n // Controlled inputs bind `value`/`onChange` from form state only — never the\n // schema default, which would desync the UI from what the form library submits.\n // Uncontrolled (native) inputs use `defaultValue` so the browser owns state.\n const textValueProps = (fallback?: string) =>\n isControlled ? {value: value ?? '', onChange: handleChange} : {defaultValue: fallback}\n\n const renderInput = () => {\n switch (type) {\n case 'submit':\n return <button type=\"submit\">{label || 'Submit'}</button>\n case 'textarea':\n return (\n <textarea\n ref={toRef<HTMLTextAreaElement>(ref)}\n name={name}\n onBlur={onBlur}\n placeholder={options.placeholder}\n {...validationRules}\n {...textValueProps(options.defaultValue)}\n />\n )\n\n case 'select':\n return (\n <select\n ref={toRef<HTMLSelectElement>(ref)}\n name={name}\n {...textValueProps()}\n {...validationRules}\n onBlur={onBlur}\n >\n {choices?.map((choice) => (\n <option key={choice.value} value={choice.value}>\n {choice.label}\n </option>\n ))}\n </select>\n )\n\n case 'radio':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"radio\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled ? {checked: value === choice.value, onChange: handleChange} : {})}\n />\n {choice.label}\n </label>\n ))\n\n case 'checkbox':\n return choices?.map((choice) => (\n <label key={choice.value}>\n <input\n type=\"checkbox\"\n name={name}\n ref={toRef<HTMLInputElement>(ref)}\n value={choice.value}\n onBlur={onBlur}\n {...validationRules}\n {...(isControlled\n ? {\n checked: Array.isArray(value)\n ? value.includes(choice.value)\n : value === choice.value,\n onChange: (e: ChangeEvent<HTMLInputElement>) =>\n handleCheckboxChange(e, choice.value),\n }\n : {})}\n />\n {choice.label}\n </label>\n ))\n\n default:\n return (\n <input\n type={type}\n ref={toRef<HTMLInputElement>(ref)}\n name={name}\n {...textValueProps(options.defaultValue)}\n {...validationRules}\n onBlur={onBlur}\n placeholder={options.placeholder}\n />\n )\n }\n }\n\n return (\n <>\n {label && !['hidden', 'submit'].includes(type) && <label htmlFor={name}>{label}</label>}\n {renderInput()}\n {error && <span className=\"error\">{error}</span>}\n </>\n )\n}\n","import type {ComponentType, FC, HTMLProps} from 'react'\n\nimport {DefaultField} from './default-field'\nimport type {FieldComponentProps, FieldState, FormDataProps, FormField} from './types'\n\ninterface FormRendererProps extends HTMLProps<HTMLFormElement> {\n formData?: FormDataProps\n // Function to get field state for a given field name\n getFieldState?: (fieldName: string) => FieldState\n // Function to get field error for a given field name\n getFieldError?: (fieldName: string) => string | undefined\n // Override default field components\n fieldComponents?: Record<string, ComponentType<FieldComponentProps>>\n}\n\n// No field state by default: fields render as uncontrolled, interactive inputs\n// so the form works out of the box (e.g. as a native HTML form). Consumers can\n// pass `getFieldState` to make the fields controlled.\nconst EMPTY_FIELD_STATE: FieldState = {}\nconst defaultGetFieldState = (): FieldState => EMPTY_FIELD_STATE\n\nconst defaultFieldComponents: Record<string, ComponentType<FieldComponentProps>> = {}\n\nexport const FormRenderer: FC<FormRendererProps> = (props) => {\n const {\n formData,\n getFieldState = defaultGetFieldState,\n getFieldError,\n fieldComponents = defaultFieldComponents,\n children,\n } = props\n const renderField = (field: FormField) => {\n const CustomComponent = fieldComponents[field.type]\n const fieldState = getFieldState(field.name)\n const error = getFieldError?.(field.name)\n\n if (CustomComponent) {\n return <CustomComponent field={field} fieldState={fieldState} error={error} />\n }\n\n return <DefaultField field={field} fieldState={fieldState} error={error} />\n }\n const elProps = Object.assign({}, props)\n delete elProps.formData\n delete elProps.getFieldState\n delete elProps.getFieldError\n delete elProps.fieldComponents\n\n return (\n <form {...elProps} id={elProps.id ?? formData?.id?.current}>\n {formData?.fields?.map((field) => (\n <div key={field._key ?? field.name} className=\"form-field\">\n {renderField(field)}\n </div>\n ))}\n\n {children}\n\n {renderField({\n type: 'submit',\n name: 'submit',\n label: formData?.submitButton?.text || 'Submit',\n })}\n </form>\n )\n}\n"],"mappings":"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"}
\ No newline at end of file Index: package/dist/form-schema/index.js.map
===================================================================
--- package/dist/form-schema/index.js.map
+++ package/dist/form-schema/index.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"index.js","names":["props.path.slice(0, 2)","path","props.renderDefault(props)","props.renderDefault","props.renderDefault({\n ...props,\n schemaType: {\n ...props.schemaType,\n options: {...props.schemaType.options, list: validationTypesByFieldType[type]},\n },\n })","props.schemaType.options","validationTypesByFieldType[type]"],"sources":["../../src/form-schema/schema-types/form.ts","../../src/form-schema/components/validation-type.tsx","../../src/form-schema/schema-types/form-field.ts","../../src/form-schema/schema-types/index.ts","../../src/form-schema/index.ts"],"sourcesContent":["import {FaWpforms} from 'react-icons/fa'\nimport {defineField, defineType, type SchemaTypeDefinition} from 'sanity'\n\nimport type {FieldsOption} from '..'\n\nexport const formType = (fields: FieldsOption): SchemaTypeDefinition => {\n // const fieldsOf =\n // fields && fields.length ? [{type: 'formField'}, ...fields] : [{type: 'formField'}]\n return defineType({\n name: 'form',\n title: 'Form',\n type: 'document',\n icon: FaWpforms,\n fields: [\n defineField({\n name: 'title',\n title: 'Form Title',\n type: 'string',\n description: 'Internal title for the form',\n validation: (Rule) => Rule.required(),\n }),\n defineField({\n name: 'id',\n title: 'Form ID',\n type: 'slug',\n options: {\n source: 'title',\n },\n // validation: (Rule) => Rule.required(),\n }),\n defineField({\n name: 'fields',\n title: 'Form Fields',\n type: 'array',\n of: [{type: 'formField'}, ...fields],\n }),\n defineField({\n name: 'submitButton',\n title: 'Submit Button',\n type: 'object',\n fields: [\n defineField({\n name: 'text',\n title: 'Button Text',\n type: 'string',\n initialValue: 'Submit',\n }),\n ],\n }),\n ],\n })\n}\n","import type {StringInputProps} from 'sanity'\nimport {useFormValue} from 'sanity'\n\nimport type {FormField} from '../../form-renderer/components/types'\nimport {validationTypesByFieldType} from '../schema-types/form-field'\n\nexport const ValidationType = (props: StringInputProps) => {\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- parent value shape is defined by the formField schema type\n const {type} = useFormValue(props.path.slice(0, 2)) as FormField\n if (!type || !props.schemaType?.options) return props.renderDefault(props)\n return props.renderDefault({\n ...props,\n schemaType: {\n ...props.schemaType,\n options: {...props.schemaType.options, list: validationTypesByFieldType[type]},\n },\n })\n}\n","import {LuTextCursorInput} from 'react-icons/lu'\nimport {defineField, defineType} from 'sanity'\n\nimport {ValidationType} from '../components/validation-type'\ninterface ValidationContextDocument {\n fields?: Array<{\n name: string\n type?: string\n }>\n}\n\n// Validation options by field type\nexport const validationTypesByFieldType: Record<string, string[]> = {\n 'checkbox': ['minSelectedCount', 'maxSelectedCount'],\n 'color': [],\n 'date': ['minDate', 'maxDate'],\n 'datetime-local': ['minDate', 'maxDate'],\n 'email': ['pattern'],\n 'file': ['maxSize', 'fileType'],\n 'hidden': [],\n 'number': ['min', 'max'],\n // password: ['minLength', 'pattern'],\n 'radio': [],\n 'range': ['min', 'max', 'step'],\n 'select': [],\n 'tel': ['pattern'],\n 'text': ['minLength', 'maxLength', 'pattern'],\n 'textarea': ['minLength', 'maxLength'],\n 'time': [],\n 'url': ['pattern'],\n}\nconst fieldTypeTitle = (fieldType: string): string => {\n switch (fieldType) {\n case 'datetime-local':\n return 'Date & Time'\n case 'textarea':\n return 'Text Area'\n case 'tel':\n return 'Phone Number'\n default:\n return fieldType.charAt(0).toUpperCase() + fieldType.slice(1)\n }\n}\n\nexport const formFieldType = defineType({\n name: 'formField',\n title: 'Form Field',\n type: 'object',\n icon: LuTextCursorInput,\n fields: [\n defineField({\n name: 'type',\n title: 'Field Type',\n type: 'string',\n options: {\n list: Object.keys(validationTypesByFieldType).map((type) => {\n return {title: fieldTypeTitle(type), value: type}\n }),\n },\n }),\n defineField({\n name: 'label',\n title: 'Field Label',\n type: 'string',\n }),\n defineField({\n name: 'name',\n title: 'Field Name',\n type: 'string',\n description:\n 'Must start with a letter and contain only letters, numbers, underscores, or hyphens. Must be unique within the form.',\n validation: (Rule) =>\n Rule.required().custom((name, context) => {\n if (!name) {\n return 'Required'\n }\n // Check format (HTML ID/name rules)\n if (!/^[a-zA-Z][a-zA-Z0-9_-]*$/.test(name)) {\n return 'Field name must start with a letter and contain only letters, numbers, underscores, or hyphens'\n }\n\n // Check uniqueness across all fields\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- document shape is defined by the form schema type\n const doc = context.document as ValidationContextDocument\n const allFieldNames = doc?.fields?.map((field) => field.name) || []\n\n // Count occurrences of this name\n const nameCount = allFieldNames.filter((n) => n === name).length\n\n // If we find more than one occurrence (including current field), it's not unique\n if (nameCount > 1) {\n return 'Field name must be unique across all form fields'\n }\n\n // Check for reserved HTML form attributes\n const reservedNames = [\n 'action',\n 'method',\n 'target',\n 'enctype',\n 'accept-charset',\n 'autocomplete',\n 'novalidate',\n 'rel',\n 'submit',\n 'reset',\n ]\n if (reservedNames.includes(name.toLowerCase())) {\n return 'This name is reserved for HTML form attributes. Please choose a different name.'\n }\n\n return true\n }),\n }),\n defineField({\n name: 'required',\n title: 'Required',\n type: 'boolean',\n initialValue: false,\n }),\n defineField({\n name: 'validation',\n title: 'Validation Rules',\n type: 'array',\n hidden: ({parent}) => {\n if (!parent?.type) return true\n const validationTypes = validationTypesByFieldType[parent.type]\n return !validationTypes || validationTypes.length === 0\n },\n of: [\n {\n type: 'object',\n fields: [\n defineField({\n name: 'type',\n title: 'Validation Type',\n type: 'string',\n options: {\n // TODO: I think this needs to be a custom input component?\n // list: ({parent}) => (parent?.type ? validationTypesByFieldType[parent.type] : []),\n list: [],\n },\n components: {\n input: ValidationType,\n },\n }),\n defineField({\n name: 'value',\n title: 'Value',\n type: 'string',\n }),\n defineField({\n name: 'message',\n title: 'Error Message',\n type: 'string',\n }),\n ],\n preview: {\n select: {\n title: 'type',\n subtitle: 'value',\n },\n },\n },\n ],\n }),\n defineField({\n name: 'choices',\n title: 'Choices',\n type: 'array',\n hidden: ({parent}) => {\n return !['select', 'radio', 'checkbox'].includes(parent?.type)\n },\n of: [\n {\n type: 'object',\n fields: [\n defineField({\n name: 'label',\n title: 'Label',\n type: 'string',\n }),\n defineField({\n name: 'value',\n title: 'Value',\n type: 'string',\n }),\n ],\n },\n ],\n }),\n defineField({\n name: 'options',\n title: 'Field Options',\n type: 'object',\n hidden: ({parent}) => {\n return ['select', 'radio', 'checkbox', 'file'].includes(parent?.type)\n },\n fields: [\n defineField({\n name: 'placeholder',\n title: 'Placeholder',\n type: 'string',\n }),\n defineField({\n name: 'defaultValue',\n title: 'Default Value',\n type: 'string',\n }),\n ],\n }),\n ],\n preview: {\n select: {\n label: 'label',\n name: 'name',\n type: 'type',\n },\n prepare({label, name, type}) {\n return {\n title: label || name,\n subtitle: type,\n }\n },\n },\n})\n","import type {SchemaTypeDefinition} from 'sanity'\n\nimport type {FieldsOption} from '..'\nimport {formType} from './form'\nimport {formFieldType} from './form-field'\n\nexport const schema = (fields: FieldsOption): {types: SchemaTypeDefinition[]} => {\n return {types: [formType(fields), formFieldType]}\n}\n","import {definePlugin, type FieldDefinition} from 'sanity'\n\n// import {structureTool} from 'sanity/structure'\n// import {FormRenderer} from './components/form-renderer'\nimport {schema} from './schema-types'\n// import {defaultDocumentNode} from './structure'\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {formSchema} from '@sanity/form-toolkit/form-schema'\n *\n * export default defineConfig({\n * // ...\n * plugins: [formSchema()],\n * })\n * ```\n */\nexport type FieldsOption = Array<FieldDefinition>\ninterface FormSchemaPluginOptions {\n /**\n * Array of field definitions to be used in the form schema.\n */\n fields?: FieldsOption\n}\n\nexport const formSchema = definePlugin<FormSchemaPluginOptions | void>((options) => {\n return {\n name: 'form-toolkit_form-schema',\n schema: schema(options?.fields ?? []),\n // plugins: [structureTool({defaultDocumentNode})],\n }\n})\n"],"mappings":"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"}
\ No newline at end of file
+{"version":3,"file":"index.js","names":["props.path.slice(0, 2)","path","props.renderDefault(props)","props.renderDefault","props.renderDefault({\n ...props,\n schemaType: {\n ...props.schemaType,\n options: {...props.schemaType.options, list: validationTypesByFieldType[type]},\n },\n })","props.schemaType.options","validationTypesByFieldType[type]","_c","\"checkbox\"","\"color\"","\"date\"","\"email\"","\"file\"","\"hidden\"","\"number\"","\"radio\"","\"range\"","\"select\"","\"tel\"","\"text\"","\"textarea\"","\"time\"","\"url\""],"sources":["../../src/form-schema/schema-types/form.ts","../../src/form-schema/components/validation-type.tsx","../../src/form-schema/schema-types/form-field.ts","../../src/form-schema/schema-types/index.ts","../../src/form-schema/index.ts"],"sourcesContent":["import {FaWpforms} from 'react-icons/fa'\nimport {defineField, defineType, type SchemaTypeDefinition} from 'sanity'\n\nimport type {FieldsOption} from '..'\n\nexport const formType = (fields: FieldsOption): SchemaTypeDefinition => {\n // const fieldsOf =\n // fields && fields.length ? [{type: 'formField'}, ...fields] : [{type: 'formField'}]\n return defineType({\n name: 'form',\n title: 'Form',\n type: 'document',\n icon: FaWpforms,\n fields: [\n defineField({\n name: 'title',\n title: 'Form Title',\n type: 'string',\n description: 'Internal title for the form',\n validation: (Rule) => Rule.required(),\n }),\n defineField({\n name: 'id',\n title: 'Form ID',\n type: 'slug',\n options: {\n source: 'title',\n },\n // validation: (Rule) => Rule.required(),\n }),\n defineField({\n name: 'fields',\n title: 'Form Fields',\n type: 'array',\n of: [{type: 'formField'}, ...fields],\n }),\n defineField({\n name: 'submitButton',\n title: 'Submit Button',\n type: 'object',\n fields: [\n defineField({\n name: 'text',\n title: 'Button Text',\n type: 'string',\n initialValue: 'Submit',\n }),\n ],\n }),\n ],\n })\n}\n","import type {StringInputProps} from 'sanity'\nimport {useFormValue} from 'sanity'\n\nimport type {FormField} from '../../form-renderer/components/types'\nimport {validationTypesByFieldType} from '../schema-types/form-field'\n\nexport const ValidationType = (props: StringInputProps) => {\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- parent value shape is defined by the formField schema type\n const {type} = useFormValue(props.path.slice(0, 2)) as FormField\n if (!type || !props.schemaType?.options) return props.renderDefault(props)\n return props.renderDefault({\n ...props,\n schemaType: {\n ...props.schemaType,\n options: {...props.schemaType.options, list: validationTypesByFieldType[type]},\n },\n })\n}\n","import {LuTextCursorInput} from 'react-icons/lu'\nimport {defineField, defineType} from 'sanity'\n\nimport {ValidationType} from '../components/validation-type'\ninterface ValidationContextDocument {\n fields?: Array<{\n name: string\n type?: string\n }>\n}\n\n// Validation options by field type\nexport const validationTypesByFieldType: Record<string, string[]> = {\n 'checkbox': ['minSelectedCount', 'maxSelectedCount'],\n 'color': [],\n 'date': ['minDate', 'maxDate'],\n 'datetime-local': ['minDate', 'maxDate'],\n 'email': ['pattern'],\n 'file': ['maxSize', 'fileType'],\n 'hidden': [],\n 'number': ['min', 'max'],\n // password: ['minLength', 'pattern'],\n 'radio': [],\n 'range': ['min', 'max', 'step'],\n 'select': [],\n 'tel': ['pattern'],\n 'text': ['minLength', 'maxLength', 'pattern'],\n 'textarea': ['minLength', 'maxLength'],\n 'time': [],\n 'url': ['pattern'],\n}\nconst fieldTypeTitle = (fieldType: string): string => {\n switch (fieldType) {\n case 'datetime-local':\n return 'Date & Time'\n case 'textarea':\n return 'Text Area'\n case 'tel':\n return 'Phone Number'\n default:\n return fieldType.charAt(0).toUpperCase() + fieldType.slice(1)\n }\n}\n\nexport const formFieldType = defineType({\n name: 'formField',\n title: 'Form Field',\n type: 'object',\n icon: LuTextCursorInput,\n fields: [\n defineField({\n name: 'type',\n title: 'Field Type',\n type: 'string',\n options: {\n list: Object.keys(validationTypesByFieldType).map((type) => {\n return {title: fieldTypeTitle(type), value: type}\n }),\n },\n }),\n defineField({\n name: 'label',\n title: 'Field Label',\n type: 'string',\n }),\n defineField({\n name: 'name',\n title: 'Field Name',\n type: 'string',\n description:\n 'Must start with a letter and contain only letters, numbers, underscores, or hyphens. Must be unique within the form.',\n validation: (Rule) =>\n Rule.required().custom((name, context) => {\n if (!name) {\n return 'Required'\n }\n // Check format (HTML ID/name rules)\n if (!/^[a-zA-Z][a-zA-Z0-9_-]*$/.test(name)) {\n return 'Field name must start with a letter and contain only letters, numbers, underscores, or hyphens'\n }\n\n // Check uniqueness across all fields\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- document shape is defined by the form schema type\n const doc = context.document as ValidationContextDocument\n const allFieldNames = doc?.fields?.map((field) => field.name) || []\n\n // Count occurrences of this name\n const nameCount = allFieldNames.filter((n) => n === name).length\n\n // If we find more than one occurrence (including current field), it's not unique\n if (nameCount > 1) {\n return 'Field name must be unique across all form fields'\n }\n\n // Check for reserved HTML form attributes\n const reservedNames = [\n 'action',\n 'method',\n 'target',\n 'enctype',\n 'accept-charset',\n 'autocomplete',\n 'novalidate',\n 'rel',\n 'submit',\n 'reset',\n ]\n if (reservedNames.includes(name.toLowerCase())) {\n return 'This name is reserved for HTML form attributes. Please choose a different name.'\n }\n\n return true\n }),\n }),\n defineField({\n name: 'required',\n title: 'Required',\n type: 'boolean',\n initialValue: false,\n }),\n defineField({\n name: 'validation',\n title: 'Validation Rules',\n type: 'array',\n hidden: ({parent}) => {\n if (!parent?.type) return true\n const validationTypes = validationTypesByFieldType[parent.type]\n return !validationTypes || validationTypes.length === 0\n },\n of: [\n {\n type: 'object',\n fields: [\n defineField({\n name: 'type',\n title: 'Validation Type',\n type: 'string',\n options: {\n // TODO: I think this needs to be a custom input component?\n // list: ({parent}) => (parent?.type ? validationTypesByFieldType[parent.type] : []),\n list: [],\n },\n components: {\n input: ValidationType,\n },\n }),\n defineField({\n name: 'value',\n title: 'Value',\n type: 'string',\n }),\n defineField({\n name: 'message',\n title: 'Error Message',\n type: 'string',\n }),\n ],\n preview: {\n select: {\n title: 'type',\n subtitle: 'value',\n },\n },\n },\n ],\n }),\n defineField({\n name: 'choices',\n title: 'Choices',\n type: 'array',\n hidden: ({parent}) => {\n return !['select', 'radio', 'checkbox'].includes(parent?.type)\n },\n of: [\n {\n type: 'object',\n fields: [\n defineField({\n name: 'label',\n title: 'Label',\n type: 'string',\n }),\n defineField({\n name: 'value',\n title: 'Value',\n type: 'string',\n }),\n ],\n },\n ],\n }),\n defineField({\n name: 'options',\n title: 'Field Options',\n type: 'object',\n hidden: ({parent}) => {\n return ['select', 'radio', 'checkbox', 'file'].includes(parent?.type)\n },\n fields: [\n defineField({\n name: 'placeholder',\n title: 'Placeholder',\n type: 'string',\n }),\n defineField({\n name: 'defaultValue',\n title: 'Default Value',\n type: 'string',\n }),\n ],\n }),\n ],\n preview: {\n select: {\n label: 'label',\n name: 'name',\n type: 'type',\n },\n prepare({label, name, type}) {\n return {\n title: label || name,\n subtitle: type,\n }\n },\n },\n})\n","import type {SchemaTypeDefinition} from 'sanity'\n\nimport type {FieldsOption} from '..'\nimport {formType} from './form'\nimport {formFieldType} from './form-field'\n\nexport const schema = (fields: FieldsOption): {types: SchemaTypeDefinition[]} => {\n return {types: [formType(fields), formFieldType]}\n}\n","import {definePlugin, type FieldDefinition} from 'sanity'\n\n// import {structureTool} from 'sanity/structure'\n// import {FormRenderer} from './components/form-renderer'\nimport {schema} from './schema-types'\n// import {defaultDocumentNode} from './structure'\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {formSchema} from '@sanity/form-toolkit/form-schema'\n *\n * export default defineConfig({\n * // ...\n * plugins: [formSchema()],\n * })\n * ```\n */\nexport type FieldsOption = Array<FieldDefinition>\ninterface FormSchemaPluginOptions {\n /**\n * Array of field definitions to be used in the form schema.\n */\n fields?: FieldsOption\n}\n\nexport const formSchema = definePlugin<FormSchemaPluginOptions | void>((options) => {\n return {\n name: 'form-toolkit_form-schema',\n schema: schema(options?.fields ?? []),\n // plugins: [structureTool({defaultDocumentNode})],\n }\n})\n"],"mappings":"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"}
\ No newline at end of file Index: package/dist/formium/index.js.map
===================================================================
--- package/dist/formium/index.js.map
+++ package/dist/formium/index.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"index.js","names":[],"sources":["../../src/formium/index.ts"],"sourcesContent":["import {createClient, type Form} from '@formium/client'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\ninterface FormiumInputConfig {\n /* nothing here yet */\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {formiumInput} from '@sanity/form-toolkit/formium'\n *\n * export default defineConfig({\n * // ...\n * plugins: [formiumInput()],\n * })\n * ```\n */\n// Is Formium dead? All attempts to use the API come back with an expired cert https://github.com/formium/formium/issues/77\nexport const formiumInput = definePlugin<FormiumInputConfig | void>(() => {\n return {\n name: 'sanity-plugin-form-toolkit_formium-input',\n plugins: [\n asyncList({\n schemaType: 'formiumInput',\n secrets: {\n keys: [\n {key: 'projectId', title: 'Project ID'},\n {key: 'token', title: 'Token'},\n ],\n },\n loader: async ({secrets}) => {\n const formium = createClient(secrets?.['projectId'] || '', {\n apiToken: secrets?.['token'],\n })\n const {data}: {data: Form[]} = await formium.findForms()\n return data && data.length\n ? data.map(({name, id}) => {\n return {\n title: name,\n value: id,\n }\n })\n : []\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;;;;;;;;;;AAsBA,MAAa,eAAe,oBACnB;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,SAAS,EACP,MAAM,CACJ;GAAC,KAAK;GAAa,OAAO;EAAY,GACtC;GAAC,KAAK;GAAS,OAAO;EAAO,CAC/B,EACF;EACA,QAAQ,OAAO,EAAC,cAAa;GAI3B,IAAM,EAAC,SAAwB,MAHf,aAAa,SAAU,aAAgB,IAAI,EACzD,UAAU,SAAU,MACtB,CACqC,CAAA,CAAQ,UAAU;GACvD,OAAO,QAAQ,KAAK,SAChB,KAAK,KAAK,EAAC,MAAM,UACR;IACL,OAAO;IACP,OAAO;GACT,EACD,IACD,CAAC;EACP;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file
+{"version":3,"file":"index.js","names":["\"projectId\"","\"token\""],"sources":["../../src/formium/index.ts"],"sourcesContent":["import {createClient, type Form} from '@formium/client'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\ninterface FormiumInputConfig {\n /* nothing here yet */\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {formiumInput} from '@sanity/form-toolkit/formium'\n *\n * export default defineConfig({\n * // ...\n * plugins: [formiumInput()],\n * })\n * ```\n */\n// Is Formium dead? All attempts to use the API come back with an expired cert https://github.com/formium/formium/issues/77\nexport const formiumInput = definePlugin<FormiumInputConfig | void>(() => {\n return {\n name: 'sanity-plugin-form-toolkit_formium-input',\n plugins: [\n asyncList({\n schemaType: 'formiumInput',\n secrets: {\n keys: [\n {key: 'projectId', title: 'Project ID'},\n {key: 'token', title: 'Token'},\n ],\n },\n loader: async ({secrets}) => {\n const formium = createClient(secrets?.['projectId'] || '', {\n apiToken: secrets?.['token'],\n })\n const {data}: {data: Form[]} = await formium.findForms()\n return data && data.length\n ? data.map(({name, id}) => {\n return {\n title: name,\n value: id,\n }\n })\n : []\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;;;;;;;;;;AAsBA,MAAa,eAAe,oBACnB;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,SAAS,EACP,MAAM,CACJ;GAAC,KAAK;GAAa,OAAO;EAAY,GACtC;GAAC,KAAK;GAAS,OAAO;EAAO,CAC/B,EACF;EACA,QAAQ,OAAO,EAAC,cAAa;GAI3B,IAAM,EAAC,SAAwB,MAHf,aAAa,SAAUA,aAAgB,IAAI,EACzD,UAAU,SAAUC,MACtB,CACqC,CAAA,CAAQ,UAAU;GACvD,OAAO,QAAQ,KAAK,SAChB,KAAK,KAAK,EAAC,MAAM,UACR;IACL,OAAO;IACP,OAAO;GACT,EACD,IACD,CAAC;EACP;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file Index: package/dist/hubspot/index.js.map
===================================================================
--- package/dist/hubspot/index.js.map
+++ package/dist/hubspot/index.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"index.js","names":["<Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>","name","{background: 'inherit'}","<Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>","`ID: ${option.value}`","<Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>\n </Card>"],"sources":["../../src/hubspot/components/option.tsx","../../src/hubspot/fetch-hubspot-data.ts","../../src/hubspot/create-handler.ts","../../src/hubspot/index.ts"],"sourcesContent":["import {Card, Text} from '@sanity/ui'\nimport type {ReactElement} from 'react'\n\nexport const Option = (option: {value: string; name: string}): ReactElement => {\n return (\n <Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>\n </Card>\n )\n}\n","type HubSpotForm = {\n id: string\n name: string\n [key: string]: unknown // Additional properties from the API response\n}\n\ntype MappedResult = HubSpotForm & {\n value: string\n}\nexport async function fetchHubSpotData({token}: {token: string}): Promise<MappedResult[] | null> {\n try {\n const apiResponse = await fetch('https://api.hubapi.com/marketing/v3/forms/?limit=9999', {\n headers: {\n Authorization: `Bearer ${token}`,\n },\n })\n\n if (!apiResponse.ok) {\n console.error(`Failed to fetch data: ${apiResponse.statusText}`)\n return null\n }\n\n const {results}: {results: HubSpotForm[]} = await apiResponse.json()\n\n return results.map((result) => Object.assign(result, {value: result.id}))\n } catch (e: unknown) {\n console.error(e)\n return null // Explicitly return null on error\n }\n}\n","import createHandler from '../shared/create-handler'\nimport {fetchHubSpotData} from './fetch-hubspot-data'\n\nexport const hubSpotHandler = ({token}: {token: string}) => {\n return createHandler(() => fetchHubSpotData({token}))\n}\n","import '@sanity/ui/styles.css'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\nimport {Option} from './components/option'\nimport {hubSpotHandler} from './create-handler'\nimport {fetchHubSpotData} from './fetch-hubspot-data'\ninterface HubSpotInputConfig {\n url: string | URL\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {hubSpotInput} from '@sanity/form-toolkit/hubspot'\n *\n * export default defineConfig({\n * // ...\n * plugins: [\n * hubSpotInput({\n * url: 'http://localhost:3000/api/hubspot'\n * })\n * ],\n * })\n * ```\n */\n\ntype ExtendedOption = {value: string; name: string}\nexport {fetchHubSpotData, hubSpotHandler}\nexport const hubSpotInput = definePlugin<HubSpotInputConfig>((options) => {\n return {\n name: 'sanity-plugin-form-toolkit_hubspot-input',\n plugins: [\n asyncList({\n schemaType: 'hubSpotForm',\n loader: async () => {\n const data = await fetch(options.url)\n const body = await data.json()\n return body\n },\n autocompleteProps: {\n renderOption: (option) =>\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- HubSpot loader returns options with a name property\n Option(option as ExtendedOption),\n renderValue(value, option) {\n // @ts-expect-error can't extend default type?\n return option?.name ?? value\n },\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;AAGA,MAAa,UAAU,WAAwD;eAGzEA;CACUC,AAAAA,EAAAA,OAAAA,OAAAA,oBADV,KAAA,oBAAC,MAAD;EAAM,MAAM;EAAG,cAAa;EACzB,UAAA,OAAO;CACJ,CAAA,GADIA,EAAAA,KAAAA,OAAAA;CAEiCC,IAAAA;qDAAC,KAAA,EAAA,YAAY,UAAS;CAE5D,IAAA,KAAA,OAAO,OAAO,SAFnBC;CAEKC,AAAAA,EAAAA,OAAAA,kBAFL,KAAA,oBAAC,MAAD;EAAM,YAAY;EAAG,MAAK;EAAU,OAAOF;EACzC,UAAA,oBAAC,MAAD;GAAM,MAAM;GAAG,cAAa;GACzBE,UAAAA;EACG,CAAA;CACF,CAAA,GAFDA,EAAAA,KAAAA;CANPC,IAAAA;CADF,OAEIL,EAAAA,OAAAA,MAAAA,EAAAA,OAGAG,MAJF,KAAA,qBAAC,MAAD;EAAM,WAAQ;EAAS,SAAS;EAAG,QAAQ;EAAG,MAAK;EAAnD,UAAA,CACEH,IAGAG,EAKI;KARJH,EAAAA,KAAAA,IAGAG,EAAAA,KAAAA,4BAJFE;AAWJ;ACPA,eAAsB,iBAAiB,EAAC,SAAyD;CAC/F,IAAI;EACF,IAAM,cAAc,MAAM,MAAM,yDAAyD,EACvF,SAAS,EACP,eAAe,UAAU,QAC3B,EACF,CAAC;EAED,IAAI,CAAC,YAAY,IAEf,OADA,QAAQ,MAAM,yBAAyB,YAAY,YAAY,GACxD;EAGT,IAAM,EAAC,YAAqC,MAAM,YAAY,KAAK;EAEnE,OAAO,QAAQ,KAAK,WAAW,OAAO,OAAO,QAAQ,EAAC,OAAO,OAAO,GAAE,CAAC,CAAC;CAC1E,SAAS,GAAY;EAEnB,OADA,QAAQ,MAAM,CAAC,GACR;CACT;AACF;AC1BA,MAAa,kBAAkB,EAAC,YACvB,oBAAoB,iBAAiB,EAAC,MAAK,CAAC,CAAC,GC2BzC,eAAe,cAAkC,aACrD;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,QAAQ,YAGC,OADY,MADA,MAAM,QAAQ,GAAG,EAAA,CACZ,KAAK;EAG/B,mBAAmB;GACjB,eAAe,WAEb,OAAO,MAAwB;GACjC,YAAY,OAAO,QAAQ;IAEzB,OAAO,QAAQ,QAAQ;GACzB;EACF;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file
+{"version":3,"file":"index.js","names":["<Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>","name","{background: 'inherit'}","<Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>","`ID: ${option.value}`","<Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>\n </Card>","_c"],"sources":["../../src/hubspot/components/option.tsx","../../src/hubspot/fetch-hubspot-data.ts","../../src/hubspot/create-handler.ts","../../src/hubspot/index.ts"],"sourcesContent":["import {Card, Text} from '@sanity/ui'\nimport type {ReactElement} from 'react'\n\nexport const Option = (option: {value: string; name: string}): ReactElement => {\n return (\n <Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {option.name}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`ID: ${option.value}`}\n </Text>\n </Card>\n </Card>\n )\n}\n","type HubSpotForm = {\n id: string\n name: string\n [key: string]: unknown // Additional properties from the API response\n}\n\ntype MappedResult = HubSpotForm & {\n value: string\n}\nexport async function fetchHubSpotData({token}: {token: string}): Promise<MappedResult[] | null> {\n try {\n const apiResponse = await fetch('https://api.hubapi.com/marketing/v3/forms/?limit=9999', {\n headers: {\n Authorization: `Bearer ${token}`,\n },\n })\n\n if (!apiResponse.ok) {\n console.error(`Failed to fetch data: ${apiResponse.statusText}`)\n return null\n }\n\n const {results}: {results: HubSpotForm[]} = await apiResponse.json()\n\n return results.map((result) => Object.assign(result, {value: result.id}))\n } catch (e: unknown) {\n console.error(e)\n return null // Explicitly return null on error\n }\n}\n","import createHandler from '../shared/create-handler'\nimport {fetchHubSpotData} from './fetch-hubspot-data'\n\nexport const hubSpotHandler = ({token}: {token: string}) => {\n return createHandler(() => fetchHubSpotData({token}))\n}\n","import '@sanity/ui/styles.css'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\nimport {Option} from './components/option'\nimport {hubSpotHandler} from './create-handler'\nimport {fetchHubSpotData} from './fetch-hubspot-data'\ninterface HubSpotInputConfig {\n url: string | URL\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {hubSpotInput} from '@sanity/form-toolkit/hubspot'\n *\n * export default defineConfig({\n * // ...\n * plugins: [\n * hubSpotInput({\n * url: 'http://localhost:3000/api/hubspot'\n * })\n * ],\n * })\n * ```\n */\n\ntype ExtendedOption = {value: string; name: string}\nexport {fetchHubSpotData, hubSpotHandler}\nexport const hubSpotInput = definePlugin<HubSpotInputConfig>((options) => {\n return {\n name: 'sanity-plugin-form-toolkit_hubspot-input',\n plugins: [\n asyncList({\n schemaType: 'hubSpotForm',\n loader: async () => {\n const data = await fetch(options.url)\n const body = await data.json()\n return body\n },\n autocompleteProps: {\n renderOption: (option) =>\n // oxlint-disable-next-line typescript-eslint/no-unsafe-type-assertion -- HubSpot loader returns options with a name property\n Option(option as ExtendedOption),\n renderValue(value, option) {\n // @ts-expect-error can't extend default type?\n return option?.name ?? value\n },\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;AAGA,MAAa,UAAU,WAAwD;eAGzEA;CACUC,AAAAA,EAAAA,OAAAA,OAAAA,oBADV,KAAA,oBAAC,MAAD;EAAM,MAAM;EAAG,cAAa;EACzB,UAAA,OAAO;CACJ,CAAA,GADIA,EAAAA,KAAAA,OAAAA;CAEiCC,IAAAA;qDAAC,KAAA,EAAA,YAAY,UAAS;CAE5D,IAAA,KAAA,OAAO,OAAO,SAFnBC;CAEKC,AAAAA,EAAAA,OAAAA,kBAFL,KAAA,oBAAC,MAAD;EAAM,YAAY;EAAG,MAAK;EAAU,OAAOF;EACzC,UAAA,oBAAC,MAAD;GAAM,MAAM;GAAG,cAAa;GACzBE,UAAAA;EACG,CAAA;CACF,CAAA,GAFDA,EAAAA,KAAAA;CANPC,IAAAA;CADF,OAEIL,EAAAA,OAAAA,MAAAA,EAAAA,OAGAG,MAJF,KAAA,qBAAC,MAAD;EAAM,WAAQ;EAAS,SAAS;EAAG,QAAQ;EAAG,MAAK;EAAnD,UAAA,CACEH,IAGAG,EAKI;KARJH,EAAAA,KAAAA,IAGAG,EAAAA,KAAAA,4BAJFE;AAWJ;ACPA,eAAsB,iBAAiB,EAAC,SAAyD;CAC/F,IAAI;EACF,IAAM,cAAc,MAAM,MAAM,yDAAyD,EACvF,SAAS,EACP,eAAe,UAAU,QAC3B,EACF,CAAC;EAED,IAAI,CAAC,YAAY,IAEf,OADA,QAAQ,MAAM,yBAAyB,YAAY,YAAY,GACxD;EAGT,IAAM,EAAC,YAAqC,MAAM,YAAY,KAAK;EAEnE,OAAO,QAAQ,KAAK,WAAW,OAAO,OAAO,QAAQ,EAAC,OAAO,OAAO,GAAE,CAAC,CAAC;CAC1E,SAAS,GAAY;EAEnB,OADA,QAAQ,MAAM,CAAC,GACR;CACT;AACF;AC1BA,MAAa,kBAAkB,EAAC,YACvB,oBAAoB,iBAAiB,EAAC,MAAK,CAAC,CAAC,GC2BzC,eAAe,cAAkC,aACrD;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,QAAQ,YAGC,OADY,MADA,MAAM,QAAQ,GAAG,EAAA,CACZ,KAAK;EAG/B,mBAAmB;GACjB,eAAe,WAEb,OAAO,MAAwB;GACjC,YAAY,OAAO,QAAQ;IAEzB,OAAO,QAAQ,QAAQ;GACzB;EACF;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file Index: package/dist/mailchimp/index.js.map
===================================================================
--- package/dist/mailchimp/index.js.map
+++ package/dist/mailchimp/index.js.map
@@ -1,1 +1,1 @@
-{"version":3,"file":"index.js","names":["<Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>","`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`","{background: 'inherit'}","<Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>","`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`","<Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>\n </Card>"],"sources":["../../src/mailchimp/components/option.tsx","../../src/mailchimp/create-handler.ts","../../src/mailchimp/index.ts"],"sourcesContent":["import {Card, Text} from '@sanity/ui'\nimport type {ReactElement} from 'react'\n\nexport const Option = (option: {\n value: string\n form: {\n header: {\n text?: string\n }\n }\n list: {\n name: string\n stats: {\n member_count: number\n }\n }\n}): ReactElement => {\n return (\n <Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>\n </Card>\n )\n}\n","import mailchimp from '@mailchimp/mailchimp_marketing'\n\nimport createHandler from '../shared/create-handler'\n\ninterface MailchimpSignupForm {\n signup_form_url: string\n [key: string]: unknown\n}\n\n// Fetch from Mailchimp's API\nexport async function fetchMailchimpData({\n key,\n server,\n}: {\n key: string\n server: string\n}): Promise<unknown> {\n mailchimp.setConfig({\n apiKey: key,\n server: server,\n })\n const response = await mailchimp.lists.getAllLists()\n if (!('lists' in response)) {\n throw new Error('Failed to fetch Mailchimp lists')\n }\n const signupFormsPerList = await Promise.all(\n response.lists.map(async (list) => {\n const {signup_forms: signupForms}: {signup_forms: MailchimpSignupForm[]} =\n // @ts-expect-error getListSignupForms is missing from the mailchimp typings\n await mailchimp.lists.getListSignupForms(list.id)\n return signupForms.map((form) => ({\n list,\n form,\n value: form.signup_form_url,\n }))\n }),\n )\n return signupFormsPerList.flat()\n}\n\n// Create the Mailchimp handler for a specific key and server\nexport const mailchimpHandler = (keys: {key: string; server: string}) => {\n return createHandler(() => fetchMailchimpData(keys))\n}\n","import '@sanity/ui/styles.css'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\nimport {Option} from './components/option'\nimport {mailchimpHandler} from './create-handler'\nimport {fetchMailchimpData} from './create-handler'\ninterface MailchimpInputConfig {\n url: string | URL\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {mailchimpInput} from '@sanity/form-toolkit/mailchimp'\n *\n * export default defineConfig({\n * // ...\n * plugins: [\n * mailchimpInput({\n * url: 'http://localhost:3000/api/mailchimp'\n * })\n * ],\n * })\n * ```\n */\nexport {fetchMailchimpData, mailchimpHandler}\nexport const mailchimpInput = definePlugin<MailchimpInputConfig>((options) => {\n return {\n name: 'sanity-plugin-form-toolkit_mailchimp-input',\n plugins: [\n asyncList({\n schemaType: 'mailchimpForm',\n loader: async () => {\n const data = await fetch(options.url)\n const body = await data.json()\n return body\n },\n autocompleteProps: {\n //@ts-expect-error incorrect typing on props?\n renderOption: (option) => Option(option),\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;;AAGA,MAAa,UAAU,WAaH;eAIX,KAAA,GAAG,OAAO,KAAK,OAAO,OAAO,GAAG,OAAO,KAAK,OAAO,KAAK,OAAO,KAAK,OAAO,SAD9EA;CACGC,AAAAA,EAAAA,OAAAA,kBADH,KAAA,oBAAC,MAAD;EAAM,MAAM;EAAG,cAAa;EACzBA,UAAAA;CACG,CAAA,GADHA,EAAAA,KAAAA;CAEwCC,IAAAA;qDAAC,KAAA,EAAA,YAAY,UAAS;CAE5D,IAAA,KAAA,GAAG,OAAO,KAAK,KAAK,KAAK,OAAO,KAAK,MAAM,aAAa,SAAS,OAAO,KAAK,MAAM,gBAAgB,IAAI,KAAK,OAFjHC;CAEKC,AAAAA,EAAAA,OAAAA,kBAFL,KAAA,oBAAC,MAAD;EAAM,YAAY;EAAG,MAAK;EAAU,OAAOF;EACzC,UAAA,oBAAC,MAAD;GAAM,MAAM;GAAG,cAAa;GACzBE,UAAAA;EACG,CAAA;CACF,CAAA,GAFDA,EAAAA,KAAAA;CANPC,IAAAA;CADF,OAEIL,EAAAA,OAAAA,MAAAA,EAAAA,OAGAG,MAJF,KAAA,qBAAC,MAAD;EAAM,WAAQ;EAAS,SAAS;EAAG,QAAQ;EAAG,MAAK;EAAnD,UAAA,CACEH,IAGAG,EAKI;KARJH,EAAAA,KAAAA,IAGAG,EAAAA,KAAAA,4BAJFE;AAWJ;ACnBA,eAAsB,mBAAmB,EACvC,KACA,UAImB;CACnB,UAAU,UAAU;EAClB,QAAQ;EACA;CACV,CAAC;CACD,IAAM,WAAW,MAAM,UAAU,MAAM,YAAY;CACnD,IAAI,EAAE,WAAW,WACf,MAAU,MAAM,iCAAiC;CAcnD,QAAO,MAZ0B,QAAQ,IACvC,SAAS,MAAM,IAAI,OAAO,SAAS;EACjC,IAAM,EAAC,cAAc,gBAEnB,MAAM,UAAU,MAAM,mBAAmB,KAAK,EAAE;EAClD,OAAO,YAAY,KAAK,UAAU;GAChC;GACA;GACA,OAAO,KAAK;EACd,EAAE;CACJ,CAAC,CACH,EAAA,CAC0B,KAAK;AACjC;AAGA,MAAa,oBAAoB,SACxB,oBAAoB,mBAAmB,IAAI,CAAC,GCbxC,iBAAiB,cAAoC,aACzD;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,QAAQ,YAGC,OADY,MADA,MAAM,QAAQ,GAAG,EAAA,CACZ,KAAK;EAG/B,mBAAmB,EAEjB,eAAe,WAAW,OAAO,MAAM,EACzC;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file
+{"version":3,"file":"index.js","names":["<Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>","`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`","{background: 'inherit'}","<Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>","`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`","<Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>\n </Card>","_c"],"sources":["../../src/mailchimp/components/option.tsx","../../src/mailchimp/create-handler.ts","../../src/mailchimp/index.ts"],"sourcesContent":["import {Card, Text} from '@sanity/ui'\nimport type {ReactElement} from 'react'\n\nexport const Option = (option: {\n value: string\n form: {\n header: {\n text?: string\n }\n }\n list: {\n name: string\n stats: {\n member_count: number\n }\n }\n}): ReactElement => {\n return (\n <Card data-as=\"button\" padding={3} radius={2} tone=\"inherit\">\n <Text size={2} textOverflow=\"ellipsis\">\n {`${option.form.header.text ? `${option.form.header.text} - ` : ``}${option.value}`}\n </Text>\n <Card paddingTop={2} tone=\"inherit\" style={{background: 'inherit'}}>\n <Text size={1} textOverflow=\"ellipsis\">\n {`${option.list.name} - ${option.list.stats.member_count} member${option.list.stats.member_count == 1 ? '' : 's'}`}\n </Text>\n </Card>\n </Card>\n )\n}\n","import mailchimp from '@mailchimp/mailchimp_marketing'\n\nimport createHandler from '../shared/create-handler'\n\ninterface MailchimpSignupForm {\n signup_form_url: string\n [key: string]: unknown\n}\n\n// Fetch from Mailchimp's API\nexport async function fetchMailchimpData({\n key,\n server,\n}: {\n key: string\n server: string\n}): Promise<unknown> {\n mailchimp.setConfig({\n apiKey: key,\n server: server,\n })\n const response = await mailchimp.lists.getAllLists()\n if (!('lists' in response)) {\n throw new Error('Failed to fetch Mailchimp lists')\n }\n const signupFormsPerList = await Promise.all(\n response.lists.map(async (list) => {\n const {signup_forms: signupForms}: {signup_forms: MailchimpSignupForm[]} =\n // @ts-expect-error getListSignupForms is missing from the mailchimp typings\n await mailchimp.lists.getListSignupForms(list.id)\n return signupForms.map((form) => ({\n list,\n form,\n value: form.signup_form_url,\n }))\n }),\n )\n return signupFormsPerList.flat()\n}\n\n// Create the Mailchimp handler for a specific key and server\nexport const mailchimpHandler = (keys: {key: string; server: string}) => {\n return createHandler(() => fetchMailchimpData(keys))\n}\n","import '@sanity/ui/styles.css'\nimport {asyncList} from '@sanity/sanity-plugin-async-list'\nimport {definePlugin} from 'sanity'\n\nimport {Option} from './components/option'\nimport {mailchimpHandler} from './create-handler'\nimport {fetchMailchimpData} from './create-handler'\ninterface MailchimpInputConfig {\n url: string | URL\n}\n\n/**\n * Usage in `sanity.config.ts` (or .js)\n *\n * ```ts\n * import {defineConfig} from 'sanity'\n * import {mailchimpInput} from '@sanity/form-toolkit/mailchimp'\n *\n * export default defineConfig({\n * // ...\n * plugins: [\n * mailchimpInput({\n * url: 'http://localhost:3000/api/mailchimp'\n * })\n * ],\n * })\n * ```\n */\nexport {fetchMailchimpData, mailchimpHandler}\nexport const mailchimpInput = definePlugin<MailchimpInputConfig>((options) => {\n return {\n name: 'sanity-plugin-form-toolkit_mailchimp-input',\n plugins: [\n asyncList({\n schemaType: 'mailchimpForm',\n loader: async () => {\n const data = await fetch(options.url)\n const body = await data.json()\n return body\n },\n autocompleteProps: {\n //@ts-expect-error incorrect typing on props?\n renderOption: (option) => Option(option),\n },\n }),\n ],\n }\n})\n"],"mappings":";;;;;;;;AAGA,MAAa,UAAU,WAaH;eAIX,KAAA,GAAG,OAAO,KAAK,OAAO,OAAO,GAAG,OAAO,KAAK,OAAO,KAAK,OAAO,KAAK,OAAO,SAD9EA;CACGC,AAAAA,EAAAA,OAAAA,kBADH,KAAA,oBAAC,MAAD;EAAM,MAAM;EAAG,cAAa;EACzBA,UAAAA;CACG,CAAA,GADHA,EAAAA,KAAAA;CAEwCC,IAAAA;qDAAC,KAAA,EAAA,YAAY,UAAS;CAE5D,IAAA,KAAA,GAAG,OAAO,KAAK,KAAK,KAAK,OAAO,KAAK,MAAM,aAAa,SAAS,OAAO,KAAK,MAAM,gBAAgB,IAAI,KAAK,OAFjHC;CAEKC,AAAAA,EAAAA,OAAAA,kBAFL,KAAA,oBAAC,MAAD;EAAM,YAAY;EAAG,MAAK;EAAU,OAAOF;EACzC,UAAA,oBAAC,MAAD;GAAM,MAAM;GAAG,cAAa;GACzBE,UAAAA;EACG,CAAA;CACF,CAAA,GAFDA,EAAAA,KAAAA;CANPC,IAAAA;CADF,OAEIL,EAAAA,OAAAA,MAAAA,EAAAA,OAGAG,MAJF,KAAA,qBAAC,MAAD;EAAM,WAAQ;EAAS,SAAS;EAAG,QAAQ;EAAG,MAAK;EAAnD,UAAA,CACEH,IAGAG,EAKI;KARJH,EAAAA,KAAAA,IAGAG,EAAAA,KAAAA,4BAJFE;AAWJ;ACnBA,eAAsB,mBAAmB,EACvC,KACA,UAImB;CACnB,UAAU,UAAU;EAClB,QAAQ;EACA;CACV,CAAC;CACD,IAAM,WAAW,MAAM,UAAU,MAAM,YAAY;CACnD,IAAI,EAAE,WAAW,WACf,MAAU,MAAM,iCAAiC;CAcnD,QAAO,MAZ0B,QAAQ,IACvC,SAAS,MAAM,IAAI,OAAO,SAAS;EACjC,IAAM,EAAC,cAAc,gBAEnB,MAAM,UAAU,MAAM,mBAAmB,KAAK,EAAE;EAClD,OAAO,YAAY,KAAK,UAAU;GAChC;GACA;GACA,OAAO,KAAK;EACd,EAAE;CACJ,CAAC,CACH,EAAA,CAC0B,KAAK;AACjC;AAGA,MAAa,oBAAoB,SACxB,oBAAoB,mBAAmB,IAAI,CAAC,GCbxC,iBAAiB,cAAoC,aACzD;CACL,MAAM;CACN,SAAS,CACP,UAAU;EACR,YAAY;EACZ,QAAQ,YAGC,OADY,MADA,MAAM,QAAQ,GAAG,EAAA,CACZ,KAAK;EAG/B,mBAAmB,EAEjB,eAAe,WAAW,OAAO,MAAM,EACzC;CACF,CAAC,CACH;AACF,EACD"}
\ No newline at end of file