Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

React Redux toolkit how to implement search

Redux newbie here. I'm trying to implement search functionality in my React App. I'm fetching data using the thunk middleware. Here is my slice code:

export const fetchAllJobs = createAsyncThunk(
    'job/fetchJobs',
    async () => {
        const response = await fetch('some-api/availableJobs')
            .then(res => res.json())
        return response;
    }
)
export const jobSlice = createSlice({
    name: 'job',
    initialState: {
        jobs: [],
        searchedJobs: [],
        isLoading: true
    },
    reducers: {
        handleSearchJobs: (state, action) => {
            state.searchedJobs = [];
            state.searchedJobs.push(action.payload)
        },
    },
    extraReducers: (builder) => {
        builder.addCase(fetchAllJobs.fulfilled, (state, action) => {
            state.jobs = action.payload;
            state.searchedJobs = action.payload;
            state.isLoading = false;
        })
        builder.addCase(fetchAllJobs.pending, (state, action) => {
            state.isLoading = true;
        })
    },
});
export const { handleSearchJobs } = jobSlice.actions;
export default jobSlice.reducer;

I am populating the DOM from the fetched data on my Jobs page.

const [jobId, setJobId] = useState('');
// products to be rendered on the UI
const [displayJobs, setDisplayJobs] = useState(useSelector((state) => state.jobs.jobs));
const dispatch = useDispatch();
const jobs = useSelector((state) => state.jobs.jobs);

useEffect(() => {
    dispatch(fetchAllJobs()) 
}, [dispatch, jobs]);

// handle search job 
const handleSearch = event => {
    if (event.target.value) {
        const searchText = event.target.value;
        const matchedJobs = jobs.filter(job => job.jobTitle
        .toLowerCase().includes(searchText.toLowerCase()));
        dispatch(handleSearchJobs(matchedJobs));
    }
}
return (
    <>
        <div className="search-container">
                <TextField
                    sx={{ width: "50%" }}
                    onChange={handleSearch}
                    placeholder="Search Jobs" />
         </div>
         <div className="jobsContainer">
             <div className="jobs-container-left">
                  {
                      displayJobs.map(job => <Job key={job._id}
                              handleSetJob={handleSetJob}
                              job={job}>
                          </Job>)
                    }
              </div>
          </div>
       </>
    );
};

Jobs are loading perfectly fine. But what I want to do is whenever a user types something in the search box, I want to filter jobs that have titles similar to the search text. And then, display only those jobs on the page. I understand there is a filter mechanism that should be implemented on the slice, but after many attempts, I'm just exhausted. Could use some help. TIA.

like image 787
Tajmin Avatar asked Aug 31 '26 22:08

Tajmin


1 Answers

If you have all jobs client-side and just want to search within those, that searching would be done either in a memoized selector (see the computing derived data docs page) or just within a useMemo in your component - I would probably prefer the latter.

const [filter, setFilter] = useState("")
const allJobs = useSelector(state => state.jobs)
const filteredJobs = useMemo(() => allJobs.filter(job => job.startsWith(filter), [filter])

Either way, you would not change your Redux state all the time.

like image 59
phry Avatar answered Sep 04 '26 09:09

phry



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!