npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2024 – Pkg Stats / Ryan Hefner

@blogcode/next-form

v0.0.9

Published

A flexible and powerful form management library for Next.js applications with support for SSR, CSR, and integration with popular validation libraries.

Downloads

19

Readme

@blogcode/next-form

@blogcode/next-form is a flexible and powerful form management library for Next.js applications. It provides an easy-to-use API for handling form state, validation, and submission in both client-side and server-side rendering scenarios.

CHANGE LOG

  • 0.0.9:

    • Restruct output build
  • 0.0.8:

    • Add exports for package.json to alias import.
  • 0.0.7:

    • Export Form and Controller components to support CSR.
    • Clean dist and rebuild
  • 0.0.6

    • createFormData function support fully type.
  • 0.0.5:

    • Add action function for error Warning: Extra attributes from the server: action;
      • If using as CSR, set action as a void function.
    • throw new Error('React form unexpectedly submitted.').
      • Cannot using import via exported to index.tsx of package.
      • Import directly to file contain Form will fix this.
      • Removed exported to index.tsx. If using Form and Controller, let's import directly to file.
        • import { Form } from "@blogcode/next-form/Form";
        • import { Controller } from "@blogcode/next-form/Controller";
    • javascript:throw new Error('A React form was unexpectedly submitted. If you called form.submit() manually, consider using form.requestSubmit() instead. If you\'re trying to use event.stopPropagation() in a submit event handler, consider also calling event.preventDefault().')
      • This error is caused by hot reload so it will not appear in production environment. Therefore we will not try to fix it.
    • The logic handler from server action (action) to client (onAfterSubmit) removed.
      • Although it has been tested in a real project and it works fine, in order to fix the Server Action errors listed here, it is temporarily removed.
      • It may reappear in the future if it does not cause errors. We are still working around it.
    • Removed props.ssr. Because server and client threads will be used independently, this flag has no effect anymore.
    • Some types have been redefined to better accommodate the new treatment.
  • 0.0.4:

    • Fix Controller component does not required props.form.
    • That mean when using without Form Component wrapped it, you must be passed form for Controller.
  • 0.0.3:

    • Fix typeof value of ControllerRenderField from unknown to string.
  • 0.0.2:

    • Fix export value as set default as empty string for getInputProps.
    • Change type of value from unknown to string.

Installation

To install @blogcode/next-form, run the following command in your project directory:

npm i @blogcode/next-form

Or if you're using yarn:

yarn add @blogcode/next-form

Check demo code at here

Features

  • Easy form state management with useForm hook
  • Built-in form validation
  • Support for both client-side and server-side rendering
  • Flexible form submission handling
  • Integration with popular validation libraries (Zod, Yup, Joi)
  • Customizable input props
  • Controlled and uncontrolled component support

useForm hook

The useForm hook is the core of @blogcode/next-form. It provides form state management, validation, and submission handling.

Basic usage

import { useForm } from '@blogcode/next-form';

function MyForm() {
  const { form, formProps } = useForm({
    values: { name: '', email: '' },
    onSubmit: (e, data) => {
      console.log(data);
    },
  });

  return (
    <form {...formProps}>
      <input {...form.getInputProps('name')} />
      <input {...form.getInputProps('email')} />
      <button type="submit">Submit</button>
    </form>
  );
}

UseFormProps

The useForm hook accepts the following props:

  • action?: FormAction<unknown>: A function to handle form submission on the server-side.
  • onSubmit?(data: FormData): void: A function to handle form submission on the client-side.
  • onAfterSubmit?(data: unknown): void: A function called after successful form submission.
  • onError?(error: Record<string, FormError>): void: A function to handle validation or submission errors.
  • enhanceGetInputProps?(form: FormInstance): Partial<InputHTMLAttributes<HTMLInputElement>>: A function to customize input props.
  • resolver?: FormResolver: A custom validation resolver function.
  • values?: FormValues: Initial form values.
  • schema?: FormSchema: A schema object for built-in validation.
  • ssr?: boolean: Enable server-side rendering support.
  • mode?: FormMode: Validation mode ('change', 'blur', or 'submit').

Using with built-in schema

@blogcode/next-form provides a built-in validation system using a schema object:

const { form, formProps } = useForm({
  values: { name: '', email: '' },
  schema: {
    name: { required: true, minLength: 2 },
    email: { required: true, pattern: /^[^\s@]+@[^\s@]+\.[^\s@]+$/ },
  },
  onSubmit: (e, data) => {
    console.log(data);
  },
});

Using with SSR

For server-side rendering support, use the ssr prop and provide an action function:

const { form, formProps } = useForm({
  ssr: true,
  action: async (formData) => {
    // Handle server-side form submission
    const result = await submitToServer(formData);
    return result;
  },
  onAfterSubmit: (result) => {
    console.log('Server response:', result);
  },
  onError: (errors) => {
    console.error('Submission errors:', errors);
  },
});

Using with CSR

For client-side rendering, use the onSubmit prop:

const { form, formProps } = useForm({
  onSubmit: (e, formData) => {
    // Handle client-side form submission
    console.log('Form data:', formData);
  },
  onError: (errors) => {
    console.error('Validation errors:', errors);
  },
});

Form component

The Form component is a wrapper that simplifies form creation and management.

Using with children as ReactElement

import { Form } from '@blogcode/next-form';

function MyForm() {
  return (
    <Form
      values={{ name: '', email: '' }}
      onSubmit={(e, data) => console.log(data)}
    >
      <input name="name" />
      <input name="email" type="email" />
      <button type="submit">Submit</button>
    </Form>
  );
}

Using with children as function

import { Form } from '@blogcode/next-form';

function MyForm() {
  return (
    <Form
      values={{ name: '', email: '' }}
      onSubmit={(e, data) => console.log(data)}
    >
      {(form) => (
        <>
          <input {...form.getInputProps('name')} />
          <input {...form.getInputProps('email')} type="email" />
          <button type="submit">Submit</button>
        </>
      )}
    </Form>
  );
}

Controller component

The Controller component allows you to create controlled inputs with ease:

import { Form, Controller } from '@blogcode/next-form';

function MyForm() {
  return (
    <Form
      values={{ name: '', email: '' }}
      onSubmit={(e, data) => console.log(data)}
    >
      <Controller
        name="name"
        render={({ field, fieldState }) => (
          <input
            {...field}
            placeholder="Name"
            style={{ borderColor: fieldState.error ? 'red' : 'initial' }}
          />
        )}
      />
      <Controller
        name="email"
        render={({ field, fieldState }) => (
          <input
            {...field}
            type="email"
            placeholder="Email"
            style={{ borderColor: fieldState.error ? 'red' : 'initial' }}
          />
        )}
      />
      <button type="submit">Submit</button>
    </Form>
  );
}

Using with Validation Libraries

@blogcode/next-form can be integrated with popular validation libraries for more advanced validation scenarios.

Zod

import { z } from 'zod';
import { useForm } from '@blogcode/next-form';
import { zodResolver } from '@blogcode/next-form/zod';

const schema = z.object({
  name: z.string().min(2),
  email: z.string().email(),
});

function MyForm() {
  const { form, formProps } = useForm({
    resolver: zodResolver(schema),
    onSubmit: (data) => console.log(data),
  });

  // ... rest of the component
}

Yup

import * as yup from 'yup';
import { useForm } from '@blogcode/next-form';
import { yupResolver } from '@blogcode/next-form/yup';

const schema = yup.object().shape({
  name: yup.string().required().min(2),
  email: yup.string().required().email(),
});

function MyForm() {
  const { form, formProps } = useForm({
    resolver: yupResolver(schema),
    onSubmit: (data) => console.log(data),
  });

  // ... rest of the component
}

Joi

import Joi from 'joi';
import { useForm } from '@blogcode/next-form';
import { joiResolver } from '@blogcode/next-form/joi';

const schema = Joi.object({
  name: Joi.string().required().min(2),
  email: Joi.string().required().email(),
});

function MyForm() {
  const { form, formProps } = useForm({
    resolver: joiResolver(schema),
    onSubmit: (data) => console.log(data),
  });

  // ... rest of the component
}

Known issues

  • When using the Controller component, the onChange and onBlur handlers may not behave correctly in all scenarios. We are working on resolving this issue in future updates.