efnan
efnan

Reputation: 58

How do I use search in react?

I want to search by holiday name on the holiday list coming from the API. The user should be able to select the line with the name of the holiday s/he is looking for by clicking on it after seeing it in the crud table list. I want the user to find the holiday s/he is looking for simply by name in the entire list and access its details. How can I do this with react hook? The code is as I shared below.


const AddHolidayDateForm = () => {

    let history = useHistory();
    const [holidays, setHolidays] = useState([])
   const [searchTerm, setSearchTerm] = React.useState("");

    useEffect(() => {
        loadHoliday();
    }, []);

    const loadHoliday = async () => {     
        const res = await axios.post(`..`, {   });  
        
        setHolidays(res.data.reverse());
    };

    const [page, setPage] = React.useState(0);
    const [rowsPerPage, setRowsPerPage] = React.useState(10);
    const handleChangePage = (event, newPage) => {
        setPage(newPage);
    };

    const handleChangeRowsPerPage = event => {
        setRowsPerPage(parseInt(event.target.value, 10));
        setPage(0);
    };
   
     const handleChangeSearch = event => {
        setSearchTerm(event.target.value);
    };

    const results = !searchTerm
        ? holidays
        : holidays.filter(
            holiday => holiday && holiday.toLowerCase && holiday.toLowerCase().includes(searchTerm.toLocaleLowerCase())
        );


    return (
        <div className="container">
            <div className="py-4">
                <div className="ui search">
                    <div className="float-left mb-3">
                        <input type="text"
                            placeholder="search"
                            className="mr-sm-2"
                            value={searchTerm}
                            onChange={handleChangeSearch}
                        />
                        <FaSearch />
                    </div>
                </div>            
                <Table responsive>
                    <thead class="thead-dark">
                        <tr>
                            <th scope="col">#</th>
                           
                            <th scope="col">Name</th>
                            <th scope="col">Start Time</th>
                            <th scope="col">End Time</th>
                        </tr>
                    </thead>
                    <tbody>
                        {results
                                .slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage)
                                .map((holiday, index) => {
                                    return (
                                        <tr>
                                            <th scope="row">{index + 1}</th>                                         
                                            <td>{holiday.name}</td>
                                            <td>{holiday.startTime}</td>
                                            <td>{holiday.endTime}</td>
                                        </tr>                                    )
                                })                         
                        }

                    </tbody>
                </Table>             
            </div>
            <div className="col-sm-6">
               </div>
            <div className="d-flex justify-content-center">
                <TablePagination
                    rowsPerPageOptions={[5, 10, 25]}
                    component="div"
                    count={holidays.length}
                    rowsPerPage={rowsPerPage}
                    page={page}
                    onChangePage={handleChangePage}
                    onChangeRowsPerPage={handleChangeRowsPerPage}
                />
            </div>
        </div>
    );
}
export default AddHolidayDateForm;

Upvotes: 2

Views: 414

Answers (1)

Giovanni Esposito
Giovanni Esposito

Reputation: 11156

The first thing I see is that results is not a state variable. In react if you want to render a variable you have to manage it as a state variable.

So, change your code in this way:

const AddHolidayDateForm = () => {

    let history = useHistory();
    const [holidays, setHolidays] = useState([])
   const [searchTerm, setSearchTerm] = React.useState("");
   const [res, setRes] = useState([]);  //<-- state to render

    useEffect(() => {
        loadHoliday();
    }, []);

    useEffect(() => {  //<-- every time holidays or searchTerm change, filter results
       const results = !searchTerm
        ? holidays
        : holidays.filter(
            holiday => holiday && holiday.toLowerCase && holiday.toLowerCase().includes(searchTerm.toLocaleLowerCase())
        );
        setRes(results);
    }, [holidays, searchTerm]);

    const loadHoliday = async () => {     
        const res = await axios.post(`..`, {   });  
        
        setHolidays(res.data.reverse());
    };

    const [page, setPage] = React.useState(0);
    const [rowsPerPage, setRowsPerPage] = React.useState(10);
    const handleChangePage = (event, newPage) => {
        setPage(newPage);
    };

    const handleChangeRowsPerPage = event => {
        setRowsPerPage(parseInt(event.target.value, 10));
        setPage(0);
    };
   
     const handleChangeSearch = event => {
        setSearchTerm(event.target.value);
    };


    return (
        <div className="container">
            <div className="py-4">
                <div className="ui search">
                    <div className="float-left mb-3">
                        <input type="text"
                            placeholder="search"
                            className="mr-sm-2"
                            value={searchTerm}
                            onChange={handleChangeSearch}
                        />
                        <FaSearch />
                    </div>
                </div>            
                <Table responsive>
                    <thead class="thead-dark">
                        <tr>
                            <th scope="col">#</th>
                           
                            <th scope="col">Name</th>
                            <th scope="col">Start Time</th>
                            <th scope="col">End Time</th>
                        </tr>
                    </thead>
                    <tbody>
                        {res   //<-- here use res state and not results
                                .slice(page * rowsPerPage, page * rowsPerPage + rowsPerPage)
                                .map((holiday, index) => {
                                    return (
                                        <tr>
                                            <th scope="row">{index + 1}</th>                                         
                                            <td>{holiday.name}</td>
                                            <td>{holiday.startTime}</td>
                                            <td>{holiday.endTime}</td>
                                        </tr>                                    )
                                })                         
                        }

                    </tbody>
                </Table>             
            </div>
            <div className="col-sm-6">
               </div>
            <div className="d-flex justify-content-center">
                <TablePagination
                    rowsPerPageOptions={[5, 10, 25]}
                    component="div"
                    count={holidays.length}
                    rowsPerPage={rowsPerPage}
                    page={page}
                    onChangePage={handleChangePage}
                    onChangeRowsPerPage={handleChangeRowsPerPage}
                />
            </div>
        </div>
    );
}
export default AddHolidayDateForm;

Upvotes: 1

Related Questions