myTest532 myTest532
myTest532 myTest532

Reputation: 2381

react-hooks-form conflict with reactstrap

I'm trying to add react-hook-form to my reactstrap form and inputs, but looks like it has a conflict between the packages.

import React, { useState, useEffect } from 'react';
import { useForm } from "react-hook-form";
import {
    Button,
    Form,
    Label,
    Input
} from 'reactstrap';
import { FormControlLabel, Checkbox, FormGroup } from '@material-ui/core';

...

const { register, handleSubmit, errors } = useForm();

...

const updDetails = (data) => {
   console.log(data);    
}

return (
   <Form onSubmit={handleSubmit(updDetails)}>
      <FormGroup className="mr-10 mb-10">
         <Label for="compName" className="mr-sm-10">Company Name</Label>
         <Input type="text" name="compName" id="compName" placeholder="Company Name"
            ref={register({ required: true })} aria-invalid={errors.name ? "true" : "false"}
            value={compDetails.compName} onChange={(e) => setCompDetails({...compDetails, compName: e.target.value})}
         />
         {errors.name && errors.name.type === "required" && (
            <span role="alert">This is required</span>
         )} 
      </FormGroup>
      <Button type="submit" className="col-sm-3" color="primary">Update Details</Button>
   </Form>
)
...

When I load the page, I can see in the browser console warnings for all my inputs: Field is missing `name` attribute . However, I am adding the name to every input as in the code above. Also, when I click on Update Details with an empty value for the compName it submits and the data is empty object. Can't I use react-hook-form with reactstrap?

Thanks

Upvotes: 2

Views: 3889

Answers (3)

Anna T
Anna T

Reputation: 955

If you're trying to do this in 2023 and with Typescript, then you'll get a TS error when trying to assign a bunch of properties output by register(...) to innerRef that only expects one element of one of the 3 types, so you'll see something like this: Type 'UseFormRegisterReturn<"compName">' is not assignable to type 'Ref<HTMLInputElement | HTMLTextAreaElement> | undefined'

Replacing the ref part of the register(...) output with innerRef solved it for me:

const {
        register,
        handleSubmit,
        formState: { errors }
    } = useForm();

const registerRs = (fieldName: string, options = {}) => {
        const registeredField: Partial<UseFormRegisterReturn> = register(fieldName, options);
        const ref = registeredField.ref;
        delete registeredField.ref;
        return {...registeredField, innerRef: ref};
    }

...

<Input
  type="text"
  id="compName"
  placeholder="Company Name"
  {...registerRs("compName", { required: true })}
  aria-invalid={errors.compName ? "true" : "false"}
/>

Upvotes: 1

Herku
Herku

Reputation: 7666

You probably have to use innerRef instead of ref on the Input component. i found this in the source here.

<Input
  type="text"
  name="compName"
  id="compName"
  placeholder="Company Name"
  innerRef={register({ required: true })}
  aria-invalid={errors.compName ? "true" : "false"}
/>

Upvotes: 6

Dori Lahav Waisberg
Dori Lahav Waisberg

Reputation: 970

I am not familiar with the reactstrap code, but a thing you could do is pass the name to the register function, use it this way:

ref={register({name: 'input-name', /* rest of options*/})}

Hope I could help :D

Upvotes: 1

Related Questions