I call the function 'booksRefresh()' from the parent in the child component, but I get the error:
TypeError: booksRefresh is not a function
I don't know why, because 'booksRefresh' is a function. Can someone help me explain why this error occurs?
Here is my code:
import React, {useState} from "react";
import {Redirect} from "react-router";
import {addBook} from "../api/api";
import {Button} from "react-bootstrap";
const AddBookForm = (booksRefresh) => {
const [title, setTitle] = useState();
const [description, setDescription] = useState();
const [submitted, setSubmitted] = useState(false);
const postRequestHandler = () => {
addBook(title, description);
booksRefresh();
}
...
return (
...
<Button type="submit" onClick={postRequestHandler} variant="outline-success">Add</Button>
</div>
)
Parent:
function App({history}) {
...
const [changeInBooks, setChangeInBooks] = useState(0)
const booksRefresh = () => {
let incrementChangeInBook = changeInBooks + 1;
setChangeInBooks(incrementChangeInBook)
}
return (
<div className="App">
<header className="App-header">
...
<Button variant="outline-success" onClick={() => history.push("/new-book")}>
{ADD_BOOK}</Button>
...
</header>
<Switch>
...
<Route path="/new-book" exact render={() =>
<AddBookForm
booksRefresh={booksRefresh}/>
}/>
...
</Switch>
</div>
);
}
export default withRouter(App);
The TypeError: "x" is not a function can be fixed using the following suggestions: Paying attention to detail in code and minimizing typos. Importing the correct and relevant script libraries used in code. Making sure the called property of an object is actually a function.
This is a standard JavaScript error when trying to call a function before it is defined. This error occurs if you try to execute a function that is not initialized or is not initialized correctly. This means that the expression did not return a function object.
While there is no direct way to pass data from the child to the parent component, there are workarounds. The most common one is to pass a handler function from the parent to the child component that accepts an argument which is the data from the child component. This can be better illustrated with an example.
Define the function in the parent component. Pass it as a prop to the child component, e.g. <Child handleClick={handleClick} /> . Use the function in the child component.
The argument a React function component receives is its props, which is an object with named properties for each of the properties. So your AddBookForm
's parameter shouldn't be booksRefresh
, but (by convention) props
, and then you use it via props.booksRefresh()
:
const AddBookForm = (props) => {
// −−−−−−−−−−−−−−−−−−^^^^^
const [title, setTitle] = useState();
const [description, setDescription] = useState();
const [submitted, setSubmitted] = useState(false);
const postRequestHandler = () => {
addBook(title, description);
props.booksRefresh();
// −−−−−^^^^^^
}
// ...
Or if it's the only prop, you can use destructuring as adiga shows:
const AddBookForm = ({booksRefresh}) => {
const AddBookForm = ({booksRefresh}) => {
const [title, setTitle] = useState();
const [description, setDescription] = useState();
const [submitted, setSubmitted] = useState(false);
const postRequestHandler = () => {
addBook(title, description);
booksRefresh();
}
try this i hope it works
because of props.booksRefresh is a function
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With