nuxt / ui

A UI Library for Modern Web Apps, powered by Vue & Tailwind CSS.
https://ui.nuxt.com
MIT License
3.62k stars 423 forks source link

Dynamic Form Generation from JSON Schema #786

Closed bryantgillespie closed 3 months ago

bryantgillespie commented 9 months ago

Description

Would be awesome if you could pass a JSON schema for the <Form> component and dynamically generate and render the form.

Why?

When working with a Nuxt project that's connected to a headless CMS or other backend - non-dev users often have a need to create and render forms on the frontend. Implementing a new form either requires:

A) developer to code it up which obviously takes a lot of time and needs to happen for each new form added to the site / app

or

B) the non-dev to build it in a third party tool like Typeform, Jotform, and others - and then embed it in the page / content. This could break the layout or function of the app / site and also requires adding another dependency / tool to the project.

Neither of these is really ideal for basic form use cases (contact information, lead generation, client intake)

Must haves

Here's an example schema for a form.

[
    {
        "name": "first_name",
        "type": "text",
        "label": "First Name",
        "placeholder": "John",
        "help": null,
        "width": "50"
    },
    {
        "name": "last_name",
        "type": "text",
        "label": "Last Name",
        "width": "50"
    },
    {
        "name": "email",
        "type": "text",
        "label": "Email",
        "placeholder": "john@example.com",
        "validation": "required",
        "width": "50"
    },
    {
        "name": "phone",
        "type": "text",
        "label": "Phone Number",
        "width": "50"
    },
    {
        "name": "company",
        "type": "text",
        "label": "Company",
        "help": "What's the name of your company / organization?",
        "width": "100"
    },
    {
        "name": "message",
        "type": "textarea",
        "label": "Message",
        "placeholder": "How can we help?",
        "width": "100"
    },
    {
        "name": "consent",
        "type": "checkbox",
        "label": "I agree with terms of service",
        "width": "100"
    }
]

Nice To Haves

Gotchas

Notes

I'm using dynamic form generation in this project https://github.com/directus-community/agency-os/blob/main/components/base/VForm.vue

But currently through another library.

Example

@benjamincanac put together a quick example of how this might be possible here. https://stackblitz.com/edit/nuxt-ui-zjzjmm?file=components%2FFormCustom.ts

Additional context

Examples of Editing Forms with a Headless CMS (Directus in this case)

ScreenShot 2023-10-06 at 10 36 42@2x

ScreenShot 2023-10-06 at 10 37 19@2x

luksak commented 4 months ago

Here is a very good implementation in vue: https://jsonforms.io/

Sandros94 commented 3 months ago

@romhml could I ask your opinion on this?

romhml commented 3 months ago

Implementing a form builder / custom json validation rules falls out of the scope of a component library like nuxt/ui. However, you can achieve these functionalities using Nuxt UI components. Here's a basic example to get you started: https://stackblitz.com/edit/nuxt-ui-apnozj

State management (especially for nested structures)

Managing nested form state can be tricky, but the next Nuxt UI version will include built-in nested forms for easier handling. See a preview here: https://github.com/benjamincanac/ui3/blob/dev/playground/components/FormNestedExample.vue