Formify Docs

API Reference

Complete reference for useForm, components, hooks, HOCs, and utilities

API Reference

Complete reference for everything Formify exports.

useForm(options)

The core hook. Returns the full form bag (see below).

const form = useForm<Values>({
  initialValues,
  onSubmit,
  validate?,          // (values) => errors | Promise<errors>
  validationSchema?,  // config schema | function | yup-like object
  validateOnChange?,  // default true
  validateOnBlur?,    // default true
  validateOnMount?,   // default false
  validateOnSubmit?,  // default true — set false to skip validation on submit
  enableReinitialize?,// default false — reset state when initialValues change
  focusFirstError?,   // default true — focus the first invalid field on submit
  validateDebounce?,  // global debounce (ms) for async validation
  messages?,          // global message overrides, keyed by rule name
  plugins?,           // FormPlugin[]
  onError?,           // (errors) => void — called when submit fails validation
});

Options

OptionTypeDefaultDescription
initialValuesValues—Initial form values.
onSubmit(values, helpers) => void | Promise—Called with valid values. Async functions drive isSubmitting.
validate(values) => errors | Promise<errors>—Form-level validator.
validationSchemaconfig | fn | yup-like—See validation styles.
validateOnChangebooleantrueValidate fields on change.
validateOnBlurbooleantrueValidate fields on blur.
validateOnMountbooleanfalseRun validation once on mount.
validateOnSubmitbooleantruefalse skips validation entirely on submit.
enableReinitializebooleanfalseWhen initialValues change, reset values/errors/touched.
focusFirstErrorbooleantrueFocus the first invalid [name] field after a failed submit.
validateDebouncenumber0Global debounce for async validation (per-field options win).
messagesRecord<string, string>—Global error messages, e.g. { required: "Füll mich aus" }.
pluginsFormPlugin[]—See plugins.
onError(errors) => void—Fired when submit fails validation.

The form bag

useForm returns everything Formik's useFormik returns, plus extras:

State

  • values, errors, touched, initialValues, isSubmitting, isValidating, submitCount, status, dirty, isValid
  • validating (extra: per-field async flags, e.g. form.validating.username)
  • messages (extra: the resolved message dictionary — defaults + overrides)

Handlers

  • handleChange(event) or handleChange("field")(eventOrValue)
  • handleBlur(event) or handleBlur("field")(eventOrTouched)
  • handleSubmit(event?) — prevents default, validates, submits
  • handleReset() — resets to initial values

Imperative helpers

  • setFieldValue(field, value, shouldValidate?)
  • setFieldTouched(field, touched?, shouldValidate?)
  • setFieldError(field, error?)
  • setValues(values, shouldValidate?)
  • setErrors(errors)
  • setTouched(touched, shouldValidate?)
  • setStatus(status?)
  • setSubmitting(bool)
  • setFormifyState(state | (prev) => state)
  • resetForm(nextState?)
  • submitForm() — Promise; throws nothing; blocks while submitting
  • validateForm() — Promise of the errors object
  • validateField(field) — Promise of the field error (or undefined)

Field accessors

  • getFieldProps(name) → { name, value, onChange, onBlur } — spread onto any input
  • getFieldMeta(name) → { value, error, touched, initialValue, isValidating }
  • getFieldHelpers(name) → { setValue, setTouched, setError }
  • registerField(name, { validate }) / unregisterField(name)

Validation styles

// 1. Config schema (recommended) — plain data, zero boilerplate
validationSchema: {
  email: { required: true, email: true, minLength: [5, "Too short"] },
}

// 2. Validation function
validate: (values) => {
  const errors = {};
  if (values.password !== values.confirm) {
    errors.confirm = "Passwords do not match";
  }
  return errors;
}

// 3. Yup-like schema (duck-typed — works without installing yup)
import * as yup from "yup";
validationSchema: yup.object({
  email: yup.string().email().required(),
})

Components

<Formify>

Render-prop wrapper over useForm:

<Formify initialValues={...} onSubmit={...} validationSchema={...}>
  {(form) => <MyForm form={form} />}
</Formify>

Also supports render and component props.

<Form>

A <form> pre-wired to the nearest form context. Optional onSubmit override.

<Field>

Binds one field to the context:

<Field name="email" type="email" placeholder="you@example.com" />
<Field name="country" as="select">
  <option value="">Select…</option>
  <option value="in">India</option>
</Field>
<Field name="bio">
  {({ field, meta }) => (
    <div>
      <textarea {...field} />
      {meta.touched && meta.error && <p>{meta.error}</p>}
    </div>
  )}
</Field>

Supports as, component, children (fn), render and validate (field-level validator).

<FastField>

Memoized <Field> for large forms.

<ErrorMessage>

<ErrorMessage name="email" component="p" className="error" />
// or
<ErrorMessage name="email">{(msg) => <span>⚠ {msg}</span>}</ErrorMessage>

Only renders when the field is touched and has an error.

<FieldArray>

Helpers for array fields: push, pop, swap, move, insert, remove, replace, unshift, plus form and name.

<FieldArray name="emails">
  {({ push, remove, form }) => (
    <>
      {form.values.emails.map((email, i) => (
        <div key={i}>
          <Field name={`emails.${i}`} />
          <button type="button" onClick={() => remove(i)}>Remove</button>
        </div>
      ))}
      <button type="button" onClick={() => push("")}>Add email</button>
    </>
  )}
</FieldArray>

Context

  • <FormifyProvider value={form}> — provide a bag manually
  • <FormifyConsumer> — render-prop consumer
  • useFormifyContext() — access the nearest bag

Hooks

useField(propsOrName)

const [field, meta, helpers] = useField("email");
const [field, meta, helpers] = useField({
  name: "email",
  validate: (value) => (value === "x" ? "No" : undefined),
});

<input {...field} />
{meta.touched && meta.error && <p>{meta.error}</p>}

useFormValidator (v1 alias)

Backward-compatible alias — see migration.

HOCs

  • withFormify(config)(Component) — injects formify prop
  • connect(Component) — injects formify prop from context

Formatters

Format field values as the user types (onChange) or on blur (onBlur), controlled per field via the format config — see Formatters.

validationSchema: {
  ssn:   { format: "ssn" },                          // 123-45-6789 as you type
  ein:   { format: "ein" },                          // 12-3456789
  tin:   { format: { type: "tin", options: { mask: "XX-XXXXXXX" } } },
  phone: {
    format: { type: "phone", options: { country: "US", ext: true } },
    phone: true,
  },
  name:  { format: [{ type: "trim", trigger: "onBlur", options: { mode: "both" } }, "upperCase"] },
}

Normalization

Normalize values as the user types — see Plugins for the normalize field config:

validationSchema: {
  username: { required: true, normalize: "trim" },
  code:     { normalize: "uppercase" },
  phone:    { normalize: (v) => String(v).replace(/[^\d+]/g, "") },
}

Utilities

getIn, setIn, removeIn, toPath, isEmptyObject, isEmptyValue, isPromise, isObject, isString, isEvent, deepEqual, interpolate, hasErrors, touchAll, validateYupSchema, validateYupSchemaSync, yupToFormErrors, plus formatter helpers (applyMask, trim, ssn, ein, itin, tin, mask, phone, zip, creditCard, currency, date, time, upperCase, lowerCase, digitsOnly) and the registerFormatter / FORMATTERS registry.

On this page