# formio.js: JSON form builder and renderer for plain JavaScript

> formio.js is a plain JavaScript library that renders JSON form schemas as interactive HTML forms and includes a visual form builder that produces those schemas. It has no jQuery, Angular or React dependency in its core, installs as @formio/js on npm, and is tightly coupled to the Form.io platform API for submission and data management.

**formio/formio.js** — JavaScript powered Forms with JSON Form Builder

- Repository: https://github.com/formio/formio.js
- Website: https://formio.github.io/formio.js
- Stars: 2,085 · Forks: 1,109
- Language: JavaScript
- License: MIT
- Published: 2026-10-11 · Updated: 2026-10-11 · Language: en
- Canonical page: https://hysenlabs.com/projects/formio-formio-js

## Form.io as platform, formio.js as the open-source rendering layer

Form.io is a form management platform with its own API server. formio.js is the open-source JavaScript library that renders the JSON schemas that platform produces and provides an SDK for communicating with its API. Using the renderer to display forms built locally is possible without a Form.io account. Using the SDK to submit form data, however, routes through the Form.io API.

The library describes itself as using plain JavaScript with ES6 and modern practices, carrying no dependency on jQuery, Angular, React or any other framework. Its npm package name is @formio/js, and the current version in package.json is 5.6.0. Three distinct capabilities ship together: a form renderer that converts a JSON schema into interactive HTML, a visual form builder that produces those schemas, and an API SDK for authentication and submission.

Repository topics list angular, react, vue, vanilla-js and vanillajs, indicating that framework-specific integrations exist alongside the core. The README describes the core as framework-independent but does not document the framework integration paths in its main text. Official documentation lives at https://help.form.io, not in the repository itself.

The library handles nested components, layouts, Date/Time, Select and Input Masks, as listed in the README. Each of those is a built-in component type, but the README does not show their schema shapes in the text, pointing instead to https://help.form.io/dev/form-development/form-renderer for the complete documentation.

## How the JSON schema describes components, their fields, and the wizard display property

A form schema is a JavaScript object. Its top-level shape includes a components array, and each entry in that array describes one form element with a type property, a key property that names the data field it populates, and a label property for display. Additional properties such as placeholder, input, action and theme appear depending on the component type. The README example shows two text fields and a submit button:

```js
Formio.createForm(document.getElementById('formio'), {
  components: [
    {
      type: 'textfield',
      key: 'firstName',
      label: 'First Name',
      placeholder: 'Enter your first name.',
      input: true,
    },
    {
      type: 'textfield',
      key: 'lastName',
      label: 'Last Name',
      placeholder: 'Enter your last name',
      input: true,
    },
    {
      type: 'button',
      action: 'submit',
      label: 'Submit',
      theme: 'primary',
    },
  ],
});
```

For multi-step forms, the schema carries a display property. Setting that property to wizard switches the rendering from a single page to a paginated wizard. The README states that the same method call handles both modes; the display value on the schema governs the output. A form stored on the Form.io platform can switch rendering modes without changing any client-side code, as long as the schema's display value changes.

The README's wizard section contains the word 'determiniation' where 'determination' was intended, a typo in the documentation text. The schema property name and code path remain functional.

## Installing @formio/js and rendering a form from a URL or an inline schema

To install the library in a project:

```
npm install --save @formio/js
```

For HTML-only use, the README shows loading from a CDN. Rendering a form from a Form.io URL requires the embed script and Bootstrap for styling:

```html
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons/font/bootstrap-icons.css" />
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap/dist/css/bootstrap.min.css" />
<script src="https://cdn.form.io/js/formio.embed.js"></script>
```

With those loaded, a single call renders the form into any container element by passing a Form.io form URL as the second argument. For self-contained use without a Form.io URL, pass an inline schema object instead. The form renders in the browser, though any submission data still needs a target endpoint unless the SDK is configured separately.

For a single-line embed, the inline embed script accepts the form URL and a libs flag as query parameters:

```html
<script src="https://cdn.form.io/js/formio.embed.min.js?src=https://examples.form.io/example&libs=true"></script>
```

This is the minimum footprint for rendering a Form.io-hosted form on any page. The libs=true flag tells the embed script to load supporting libraries automatically. All rendering paths, whether via npm or CDN, depend on Bootstrap being available for the form to display correctly.

## The visual form builder: what Formio.builder produces and where documentation lives

The form builder runs in a browser and produces the JSON schema that the renderer consumes. Embedding the builder requires the full script bundle and Bootstrap:

```html
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap-icons/font/bootstrap-icons.css" />
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap/dist/css/bootstrap.min.css" />
<link rel="stylesheet" href="https://cdn.form.io/js/formio.full.min.css" />
<script src="https://cdn.form.io/js/formio.full.min.js"></script>
```

With those loaded, the call `Formio.builder(document.getElementById('builder'), {}, {})` renders an interactive drag-and-drop builder into the target element. A live demo sits at https://formio.github.io/formio.js/app/builder.

The builder and the renderer share the same JSON schema format, so a schema designed in the builder is immediately usable by the renderer without conversion. The third argument to the builder call accepts options, though the README gives no list of valid option keys in the text it contains. Documentation for the builder lives at https://help.form.io/dev/form-development/form-builder.

This tight coupling between builder output and renderer input is the main practical benefit of using them together. Teams that build forms outside formio.js, using a different form schema format, cannot feed those schemas directly into the renderer without converting them to the JSON structure the library expects.

## The JavaScript SDK: loadForm and saveSubmission against the Form.io API

Beyond rendering, the library provides a JavaScript SDK for interacting with the Form.io API directly. Instantiating the Formio class with a form URL creates a client bound to that endpoint. From there, the README shows loading a form and saving a submission:

```html
<script src="https://cdn.form.io/js/formio.min.js"></script>
<script type="text/javascript">
  var formio = new Formio('https://examples.form.io/example');
  formio.loadForm().then(function (form) {
    console.log(form);
    formio
      .saveSubmission({
        data: {
          firstName: 'Joe',
          lastName: 'Smith',
          email: 'joe@example.com',
        },
      })
      .then(function (submission) {
        console.log(submission);
      });
  });
</script>
```

This SDK path requires a live Form.io endpoint. The example uses examples.form.io, which is Form.io's public demonstration server. A team running its own Form.io instance would replace that host. The saveSubmission method posts data to the bound endpoint and returns a promise that resolves to the full submission object.

For projects that want form rendering without any external API dependency, the SDK section is not relevant. The renderer can display a form from an inline JSON schema with no network call, but once a user submits, the submission handling falls outside what the renderer provides on its own.

## What the package.json exports field exposes and a gap in the sub-paths

The package.json exports field maps five named paths: the dot key for the main entry, plus ./sdk, ./form, ./embed and ./utils. The primary export at the dot key lists both an import condition and a require condition. Both resolve to the same file: `./lib/cjs/index.js`. The build scripts in package.json run both tsconfig.cjs.json and tsconfig.mjs.json, meaning a separate MJS compilation does execute, but its output does not appear in the exports map. A bundler looking at the import condition will receive the file from the cjs directory rather than any mjs output.

The ./sdk, ./form, ./embed and ./utils sub-paths also resolve to files under ./lib/cjs/. The ./dist/* and ./lib/* paths serve pre-built distribution files and raw library files without specific type differentiation. The file fields in package.json list the dist, lib, embed.d.ts, form.d.ts, sdk.d.ts and utils.d.ts entries that ship with the package.

For teams using a modern bundler that relies on package exports to distinguish module types, testing the specific bundler behavior with @formio/js before committing to the dependency is a concrete step. The MJS compilation runs during the build but is not addressed in the exports field, so its output is available only through the ./lib/* wildcard, not through named sub-path conditions.

## Bootstrap as a required styling dependency and what the build scripts produce

Every rendering and building example in the README loads Bootstrap icons and Bootstrap CSS from a CDN. The npm package does not bundle them, so any project using formio.js must include these stylesheets. The README examples load from cdn.jsdelivr.net/npm/bootstrap-icons and cdn.jsdelivr.net/npm/bootstrap, without specifying which Bootstrap version to use. A version mismatch between what the form expects and what Bootstrap provides can affect layout and icon rendering.

The full CDN build also loads a formio-specific stylesheet from cdn.form.io/js/formio.full.min.css. That file is not in the npm package and serves from Form.io's CDN. A project that needs a fully offline or self-hosted setup must account for this dependency explicitly.

The build scripts in package.json show that the project uses Webpack (both webpack.config.js and webpack.prod.js), Gulp and TypeScript. The build command runs documentation generation with typedoc, the library compile step, and the dist step. TypeScript type definitions ship for the main entry, SDK, form and utils sub-paths.

The package is MIT-licensed per LICENSE.txt at the repository root, and the last push was on 2026-09-30. The repository has no GitHub releases; CHANGELOG.md at the root tracks changes instead.

## Conclusion

formio.js suits projects that already use Form.io as a form management platform, or teams that want a visual form builder and a matching renderer without committing to a front-end framework. It is a poor fit for applications that need self-contained form submission without an external API, since the SDK routes data through Form.io's server. Before adopting, check that Bootstrap is acceptable as a runtime dependency for your styling requirements, and verify that the package exports map works correctly with your bundler, since both the import and require conditions in the exports field resolve to the file under the cjs directory.

## FAQ

### What is formio.js and what does it do?

formio.js is a plain JavaScript library that renders JSON form schemas as interactive HTML forms and includes a visual form builder for creating those schemas. It also provides a JavaScript SDK for communicating with the Form.io API to load forms and save submissions.

### How do I install formio.js?

Run `npm install --save @formio/js` to add it to a project. For HTML-only use, the README gives CDN links to formio.full.min.js and formio.embed.js from cdn.form.io.

### Does formio.js require React or Angular?

The core library uses plain JavaScript with no framework dependency on jQuery, Angular or React, as stated in the README. The repository topics include angular, react and vue, indicating that framework-specific integrations exist alongside the core.

### Does formio.js require Bootstrap?

Every rendering and building example in the README loads Bootstrap icons and Bootstrap CSS from a CDN. The npm package does not bundle them, so they must be included separately in any project that uses formio.js.

### How does the wizard rendering work in formio.js?

Setting the display property of the form schema to wizard switches the rendering from a single page to a paginated wizard. The README states that the same rendering method handles both standard and wizard display modes.

## Sources

- [formio/formio.js on GitHub](https://github.com/formio/formio.js)
- [Issues](https://github.com/formio/formio.js/issues)
- [License: MIT](https://github.com/formio/formio.js/blob/main/LICENSE)
- [Project website](https://formio.github.io/formio.js)
- [README](https://github.com/formio/formio.js/blob/main/README.md)

---

Hysen Labs editorial analysis, written from the project's own repository and release notes. Cite the canonical page: https://hysenlabs.com/projects/formio-formio-js
