-1

I've set up a search Bar to fetch the data from the backend and return it.

CODE:

const App = () => {

const[datas,setDatas] = useState([])   //NOthing to do with this.

const [space,setSpace] = useState(null)
const [print, setPrint] = useState(false)


function getData(val){
  console.log(val.target.value)
  setSpace(val.target.value);
  setPrint(false)
}

console.log(space)  //Returning inputted text in console. Works well

  useEffect(() => {
    const fecthPosts = async () => {
      let initial_url = `http://localhost:4000/search` 
      let url = initial_url + "?text=" + space  
       
       const res = await fetch(url);
       const {result} = await res.json();

     setDatas(result);
    fecthPosts();
  },[space]);

return(
<div className="App">
     {                  //Displaying on search
        print?
         <>
        <h2>{space}</h2>  //submited text
        <div> 
       {results.map((field) => 
       <p>{field.title}</p> 
       <p>{field.author}</p> 
       )}
        </div>
        </>
        :null
      }
   <input type="text" onChange={getData} />
 <button onClick={() => setSpace(true)}>search</button>
</div>
  )
 }
};

export default App;

Now, this code works perfectly fine. But when I click on Network Tab then,

It's fetching data from every text I'm typing. Problems with onChange

search?text=s
search?text=sa  
search?text=sam 
search?text=sams
search?text=samsu   
search?text=samsun
search?text=samsung

I don't want this to be happen because I've got limited No. of requests to send.

Anyone plz help to solve this issue.I've tried several things but nothing working...

NOTE: I can't use Timeout and any other method which works... only search or fetch data if user press enter or click the button.

  • You can add a timeout to achieve this. Please check this link https://stackoverflow.com/questions/51855807/how-to-set-timeout-on-event-onchange – Rukshán Dikovita Jul 29 '21 at 03:09
  • Does this answer your question? [How to use throttle or debounce with React Hook?](https://stackoverflow.com/questions/54666401/how-to-use-throttle-or-debounce-with-react-hook) – Emile Bergeron Jul 29 '21 at 03:13
  • No, I can't use `TImeout` bcz uses can also redirected on this page `http://localhost:3000/search?query=Samsung` –  Jul 29 '21 at 03:26

3 Answers3

1

You can fetch inside a short timeout (say, after 2 seconds of inactivity after typing) with a ref.

Don't ignore possible errors either - unhandled rejections should always be avoided.

const timeoutRef = useRef();
useEffect(() => {
    const doFetch = () => {
        const url = 'http://localhost:4000/search?text=' + space
        fetch(url)
            .then(res => res.json())
            .then(({ result }) => setDatas(result))
            .catch(handleErrors); // don't forget this
    };
    clearTimeout(timeoutRef.current);
    timeoutRef.current = setTimeout(doFetch, 2000);
}, [space]);
CertainPerformance
  • 356,069
  • 52
  • 309
  • 320
  • I believe the ref could be removed and the timeout could be cleared in the cleanup function of the effect, leaving everything local to the effect. – Emile Bergeron Jul 29 '21 at 03:15
  • **PLEASE** any other ways? which directly searches for it? without using `onChage`. I really need help with this. –  Jul 29 '21 at 03:16
  • Hey i can't use `Timeout` , because users can also directly searches for `http://localhost:3000/search?text=Samsung` –  Jul 29 '21 at 03:23
  • 1
    @VanrajMishra If you mean the user can type it directly into the address bar, or programatically make such requests themselves without being subject to the limiter, that's not something you'll be able to solve on the client-side - you'll have to change your server-side logic for that. – CertainPerformance Jul 29 '21 at 03:25
  • 1
    What do you mean, `without using onChage`? Do you mean `onChange`? But how would it even work without `onChange`? – CertainPerformance Jul 29 '21 at 03:26
  • Ok, only shows result on user click on `searchButton` or `press ENter` ? that makes sense? –  Jul 29 '21 at 03:29
  • 1
    Ok, then implement a button or listen for enter keypresses? – CertainPerformance Jul 29 '21 at 03:42
  • @CertainPerformance Examples of codes with this will be helpful.. :) –  Jul 29 '21 at 03:44
  • @CertainPerformance Please Help me with this Question https://stackoverflow.com/questions/68640515/how-to-get-query-parameter-from-url-in-react-js –  Aug 03 '21 at 18:01
0

I think there are some issues with the code, for example when showing the search result, if I understand correctly:

{results.map((field) => 

should be

{datas.map((field) => 

right?

For your current problem,

  1. You're calling the search API every time when the input text is changed.
  2. Only show the search result when the search button is clicked.

So why not only trigger the API call when the search button is clicked?

Grace Han
  • 26
  • 4
  • Please checkout this https://stackoverflow.com/questions/68640515/how-to-get-query-parameter-from-url-in-react-js –  Aug 03 '21 at 18:02
-1

You can use denounce, to call search API after only n seconds.

  • can't possible that only `search` or `fetch API` if users hits the search button or Enter key?? –  Jul 29 '21 at 03:35
  • In that case you can search for libraries for API call other than **fetch**, which might provide a way to make API call after some time. As far as I know **fetch** does not provide such a feature. If nothing works, it's best to use debounce. – krupa Panchal Jul 29 '21 at 04:14
  • Please help me with this question https://stackoverflow.com/questions/68640515/how-to-get-query-parameter-from-url-in-react-js ? –  Aug 03 '21 at 18:00