Socket
Socket
Sign inDemoInstall

use-form-input

Package Overview
Dependencies
Maintainers
1
Versions
5
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

use-form-input - npm Package Compare versions

Comparing version 1.1.1 to 1.2.0

dist/compareObjectKeys.d.ts

23

dist/index.d.ts
import * as React from 'react';
declare type ErrorType<T> = {
[key in keyof T]: {
error: boolean;
messages: Array<string>;
};
};
declare type ValueType = object | [] | string | boolean | number;
declare type ValidatorConfigType = {
condition: boolean;
message?: string;
onMatch?: (messages?: string) => void;
};
declare type ValidatorType<T> = (errors: any) => (name: keyof T, config: ValidatorConfigType) => void;
export declare function useFormInput<T>(fields: T): [
import { ErrorType, ValidatorType, ValueType } from './types';
export declare function useFormInput<T>(fields: T, handleSubmit?: (data: T) => void, validation?: (data: T) => any): [
T,
{
onChange: (name: keyof T, value?: ValueType | ((previousValue: ValueType) => any)) => (event?: React.ChangeEvent<any>) => void;
setValue: (name?: keyof T, value?: ValueType | ((previousValue: ValueType) => any)) => void;
onChange: (event?: React.ChangeEvent<any>) => void;
onSubmit: (e: React.FormEvent) => void;
validator: ValidatorType<T>;

@@ -23,4 +13,5 @@ isValid: (errors: ErrorType<T> | {}) => boolean;

setErrors: React.Dispatch<React.SetStateAction<{}>>;
clear: () => void;
modified: T;
}
];
export {};

@@ -25,38 +25,66 @@ Object.defineProperty(exports, '__esModule', { value: true });

function useFormInput(fields) {
// compares two object and returns new object comparing two
function compareObjectKeys(object1, object2) {
const result = {};
Object.keys(object1).forEach((k) => {
if (String(object1[k]) !== String(object2[k])) {
result[k] = true;
}
});
return result;
}
function useFormInput(fields, handleSubmit, validation) {
const [data, setData] = React__namespace.useState(Object.assign({}, fields));
const [errors, setErrors] = React__namespace.useState({});
const onChange = (name, value) => {
return function (event) {
event === null || event === void 0 ? void 0 : event.persist();
setData((prev) => {
var _a;
if (value === undefined || value === null) {
return Object.assign(Object.assign({}, prev), { [name]: (_a = event === null || event === void 0 ? void 0 : event.target) === null || _a === void 0 ? void 0 : _a.value });
}
else {
if (typeof value === 'function') {
const functionReturnValue = value(prev[name]);
return Object.assign(Object.assign({}, prev), { [name]: functionReturnValue });
}
else {
return Object.assign(Object.assign({}, prev), { [name]: value });
}
}
});
};
const [modified, setModified] = React__namespace.useState({});
// called every time data is changed
React__namespace.useEffect(() => {
if (validation) {
const catchedErrors = validation(data);
setErrors(catchedErrors);
}
}, [data]);
// checks whether the data is modified or not
React__namespace.useEffect(() => {
const compared = compareObjectKeys(fields, data);
const newlyModified = Object.assign(Object.assign({}, modified), compared);
setModified(newlyModified);
}, [data]);
// setValue to set the individual items
const setValue = (name, value) => {
setData((prev) => {
if (typeof value === 'function') {
const functionReturnValue = value(prev[name]);
return Object.assign(Object.assign({}, prev), { [name]: functionReturnValue });
}
else {
return Object.assign(Object.assign({}, prev), { [name]: value });
}
});
};
// onChange for `named` form fields
const onChange = function (event) {
// for previous version of react ( pooling )
event === null || event === void 0 ? void 0 : event.persist();
const fieldName = event === null || event === void 0 ? void 0 : event.target.name;
if (!fieldName) {
throw new Error(`'name' attribute is missing in props`);
}
setData((prev) => {
var _a;
return Object.assign(Object.assign({}, prev), { [fieldName]: (_a = event === null || event === void 0 ? void 0 : event.target) === null || _a === void 0 ? void 0 : _a.value });
});
};
// validator
const validator = (errors) => {
return function (name, config) {
var _a, _b;
var _a;
const { condition, message, onMatch } = config;
if (condition) {
errors[name] = {
error: true,
messages: (_b = (_a = errors[name]) === null || _a === void 0 ? void 0 : _a.messages) !== null && _b !== void 0 ? _b : [],
};
errors[name] = (_a = errors[name]) !== null && _a !== void 0 ? _a : [];
const hasErrorMessage = message !== null && message !== undefined;
if (Object.prototype.hasOwnProperty.call(errors, name)) {
if (hasErrorMessage) {
errors[name].messages = [...errors[name].messages, message];
errors[name] = [...errors[name], message];
}

@@ -66,3 +94,3 @@ }

if (hasErrorMessage) {
errors[name].messages = [message];
errors[name] = [message];
}

@@ -79,8 +107,55 @@ }

};
// checks whether the errors is empty or not
const isValid = (errors) => {
return Object.keys(errors).length === 0;
};
// clears the form
const clear = () => {
const formData = Object.keys(data).map((val) => {
const field = data[val];
return {
key: val,
value: field,
valueType: typeof field,
};
});
const emptyData = formData.reduce((acc, curr) => {
let resetValue;
if (curr.valueType === 'boolean') {
resetValue = false;
}
else {
resetValue = '';
}
return Object.assign(Object.assign({}, acc), { [curr.key]: resetValue });
}, Object.assign({}, data));
setData(emptyData);
};
// handle the submit
const onSubmit = (e) => {
e.preventDefault();
const modifiedData = Object.keys(fields).reduce((acc, curr) => {
return Object.assign(Object.assign({}, acc), { [curr]: true });
}, {});
setModified(modifiedData);
if (!isValid(errors)) {
return;
}
if (handleSubmit) {
handleSubmit(data);
}
};
return [
data,
React__namespace.useMemo(() => ({ onChange, validator, isValid, errors, setErrors }), [errors]),
React__namespace.useMemo(() => ({
setValue,
onChange,
validator,
isValid,
errors,
setErrors,
clear,
modified,
onSubmit,
}), [errors, modified]),
];

@@ -87,0 +162,0 @@ }

{
"name": "use-form-input",
"version": "1.1.1",
"version": "1.2.0",
"description": "Simple hook to provide form validation in react",

@@ -5,0 +5,0 @@ "main": "dist/index.js",

@@ -8,8 +8,8 @@ # USE-FORM-INPUT

- Small size and no dependencies
- Easy to use APIs
- Fully customizable form handling and validations
- Easy to use
### Install
### Installation
Install with npm:
Install:

@@ -22,32 +22,154 @@ ```sh

#### 1. Basic form handling
Form handling can be done with `useFormInput`.
Example:
```jsx
// Basic form handling
import { useFormInput } from 'use-form-input';
export default function App() {
const [data, { onChange, validator, isValid, errors, setErrors }] =
export default function BasicFormHandling() {
const [data, { onChange, onSubmit }] = useFormInput(
{
firstName: '',
lastName: '',
},
(data) => {
console.log('FINAL DATA', data);
}
);
return (
<>
<form onSubmit={onSubmit} style={{ marginLeft: 10 }}>
<input
type="text"
name="firstName"
value={data.firstName}
onChange={onChange}
/>
<br />
<input
type="text"
name="lastName"
value={data.lastName}
onChange={onChange}
/>
<br />
<input value="Submit" type="submit" />
</form>
</>
);
}
```
Note: The form element must have `name` prop available to use `onChange`.
#### 2. Form Validation
Form validation can be done by passing third parameter ( function ) which should return an error object.
The function is called with the data.
Example:
```jsx
import { useFormInput } from 'use-form-input';
export default function FormValidation() {
const [data, { onChange, onSubmit, errors, modified }] = useFormInput(
{
firstName: '',
lastName: '',
},
(data) => {
console.log('FINAL DATA', data);
},
(data) => {
const errors = {};
if (data.firstName.length === 0) {
errors.firstName = 'Empty first name';
}
if (data.lastName.length === 0) {
errors.lastName = 'Empty last name';
}
return errors;
}
);
return (
<>
<form onSubmit={onSubmit} style={{ marginLeft: 10 }}>
<input
type="text"
name="firstName"
value={data.firstName}
onChange={onChange}
/>
{modified.firstName && errors.firstName && (
<span style={{ color: 'red' }}>{errors.firstName}</span>
)}
<br />
<input
type="text"
name="lastName"
value={data.lastName}
onChange={onChange}
/>
{modified.lastName && errors.lastName && (
<span style={{ color: 'red' }}>{errors.lastName}</span>
)}
<br />
<input value="Submit" type="submit" />
</form>
</>
);
}
```
Note: `modified` object is used so that, the error is not shown by default. The form should either be submitted or certain fields must change before it should show error. `modified` object has the property same as fields passed to `useFormInput` hook.
#### 3. Manual Validation
Form can be manually validated by using `validator`, `setErrors` and `isValid` methods.
Example:
```jsx
import { useFormInput } from 'use-form-input';
export default function ManualValidation() {
const [data, { onChange, errors, setErrors, isValid, validator }] =
useFormInput({
name: 'John Doe',
firstName: '',
lastName: '',
});
const onSubmit = (e: React.FormEvent) => {
const onSubmit = (e) => {
e.preventDefault();
const cachedErrors = {};
const validate = validator(cachedErrors);
const catchedErrors = {};
const validate = validator(catchedErrors);
const { name } = data;
validate('firstName', {
condition: data.firstName.length === 0,
message: 'Empty first name',
});
validate('name', {
condition: name.length === 0,
message: 'Empty name',
onMatch: function (message) {
if (message) {
console.error(message);
}
},
validate('lastName', {
condition: data.lastName.length === 0,
message: 'Emptry last name',
});
setErrors(cachedErrors);
setErrors(catchedErrors);
if (!isValid(cachedErrors)) {
if (!isValid(catchedErrors)) {
return;

@@ -64,11 +186,22 @@ }

type="text"
placeholder="name"
value={data.name}
onChange={onChange('name')}
name="firstName"
value={data.firstName}
onChange={onChange}
/>
<p style={{ color: 'red' }}>
{errors.name &&
errors.name.messages.length > 0 &&
errors.name.messages[0]}
</p>
{errors.firstName && (
<span style={{ color: 'red' }}>{errors.firstName}</span>
)}
<br />
<input
type="text"
name="lastName"
value={data.lastName}
onChange={onChange}
/>
{errors.lastName && (
<span style={{ color: 'red' }}>{errors.lastName}</span>
)}
<br />
<input value="Submit" type="submit" />

@@ -81,4 +214,63 @@ </form>

#### 4. Manually Setting Values
We need a method to manually set the values of certain fields. We can do it by using `setValue` method.
Example:
```jsx
const [data, { setValue }] = useFormInput({ firstName: '' });
...
<input
type="text"
name="firstName"
value={data.firstName}
onChange={e => setValue('firstName', e.target.value)}
/>
```
`setValue` accepts two parameters:
1. Field Name
2. Value
#### 5. Modifiying previous values
We can modify the previous values using `setValue` method. For example, we can use it in checkbox.
Example:
```jsx
const [data, { setValue }] = useFormInput({ married: false });
...
<input
type="text"
name="married"
checked={data.married}
onChange={e => setValue('married', (previousValue) => !previousValue)}
/>
```
It works like a `setState` function, getting previous value and returning modified one.
#### 6. Clearing form
We can clear the from by using `clear` method which sets all the modified fields to its initial one.
Example:
```jsx
const [data, { clear }] = useFormInput({ firstName: '', lastName: '' });
...
<button onClick={() => clear()}>Clear</button>
```
## License
MIT

Sorry, the diff of this file is not supported yet

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc