nicromium1988
nicromium1988

Reputation: 23

filter data retrieved by redux

as you can see from my code I have some props({allRecipes}) fetched by Redux, I can display them with const mapRecipe =(), but I would like to filter them by a search bar, I think the solution would be the hook useEffect, but I can't go on,

useEffect(() =>{
      
    const res = allRecipies.filter(el => el.name.toLowerCase().includes(searchTerm))
    setSearchResults(res)},[searchTerm])

give to me error: allRecipies is null.

hope someone can point me on the right direction. here the code:

    const [searchTerm, setSearchTerm] = useState("");
    const [searchResults, setSearchResults] = useState([]);
    const handleChange = event => {
        console.log("search bar",event.target.value)

        setSearchTerm(event.target.value);
    }
    useEffect(() =>{
      
    const res = allRecipies.filter(el => el.name.toLowerCase().includes(searchTerm))
    setSearchResults(res)
},[searchTerm])
 const mapRecipe =() =>{
     if(!allRecipies){return<li>no fish</li>}
     else{return allRecipies.map(el =>{
     return (<div className="col s12 l4" key={el._id}  >
   
            
                
                
                    <div className="card ">
                      <div style={{backgroundImage:`url(${staticImage})`,height:"200px",backgroundSize:"cover"}} className="card-image ">
                     
                      <a className="btn-floating halfway-fab waves-effect waves-light btn-large lime darken-2"><i className="material-icons">clear</i></a>
                      </div>
                     
                       
                            <span className="card-title">{el.name}</span>
                            
                            
                        
                        <div className="card-content">
                            <p>{el.listOfStages[0]}</p>
                        </div>
                    </div>
              
            

    
     </div>)
     })}
 
} 
 return (
    <div>
        <input type="text"
         placeholder="search"
         value={searchTerm}
         onChange={handleChange}/>
    <div className="row" >
        {mapRecipe()}
          
    </div>
   
    </div>
  
      
 )
 
    
 }
function mapStateToProps(state){
    console.log(state);
    return state
}
export default connect(mapStateToProps)(Landing) 

Upvotes: 0

Views: 53

Answers (2)

lala
lala

Reputation: 1439

I would do this:-

  1. detect incoming allRecipies with useEffect & apply default searchTerm:-
  2. another useEffect for filtering searchTerm:-
// do search
const seacrh = (allRecipies, searchTerm) => {
  return allRecipies.filter(el => el.name.toLowerCase().includes(searchTerm))
}

// run when 'allRecipies' present
useEffect(() => {
  (() => {
    if(allRecipes) {
      setSearchResult(() => search(allRecipies, ''))
    }
  })()
}, [allRecipies])

// run when there's changes on 'searchTerm'
useEffect(() => {
  (() => {
    if(searchTerm) {
      setSearchResult(() => search(allRecipies, searchTerm))
    }
  })()
}, [searchTerm])

Upvotes: 0

Ketan Ramteke
Ketan Ramteke

Reputation: 10675

Use null propogation to get rid of that error:

useEffect(() =>{
    const res = allRecipies?.filter(el => el.name.toLowerCase().includes(searchTerm))
    setSearchResults(res)
},[searchTerm])

You can read more about it here : Null Propagation Operator in JavaScript

Upvotes: 1

Related Questions