Ad

How To Implement Search Function In React-GraphQL Using React-Hooks And Apollo Client?

I try to implement the Search function into my management system using React-Hooks and GraphQL-Apollo Client. While the interface is shown successfully, when I press the 'Search' button it came out an error which named:

Invalid hook call. Hooks can only be called inside of the body of a function component.

I'm pretty sure the useQuery is being called inside a function, so I do not understand what will cause this. The other function such as display all users and add new users are working fine.

I have tried a couple of ways to implement the search function and search around online while still couldn't get it solve. This is my first time encounters React-Hooks too.

Here is my current code in the searchUser component

import React from 'react'
import {useQuery} from 'react-apollo-hooks';
import {searchUserQ} from '../queries/queries';

const SearchUserForm = () => {
    let name = '';
    let content;

return (
    <div id="edit-user">
        <div className="field">
            <label htmlFor="name">Search UserName</label>
            <input type="text" id="name" onChange={ (event) => {
                name = event.target.value }}/>
            <button onClick={(event) => {
                event.preventDefault();
                const { data, loading, error } = useQuery(searchUserQ, {
                    variables: { name: name },
                    suspend: false
                });

                if (loading) {
                    content = <p>Loading User...</p>
                }

                if (error){
                    console.log(`Error Occur: ${ error }`);
                    content = <p>Error Occur!</p>
                }

                content = data.users.map(user => (
                    <p key={user.id}>Username: {user.name}    ID: {user.id}</p>
                ));
            }}>
                Submit
            </button>
            <p>{ content }</p>
        </div>
    </div>
)
}

export default SearchUserForm;

Can anyone help with this?

One more question is that my data seems to return undefined everytime I execute the query. Is there something wrong with my query? Here are the query:

const searchUserQ = gql`
query User($name: String!){
    user(name: $name){
        id
        name
        email
    }
 }
`;

Thanks and appreciate on the help!

Ad

Answer

According to the Rules of Hooks:

Don’t call Hooks from regular JavaScript functions. Instead, you can:

✅ Call Hooks from React function components.

✅ Call Hooks from custom Hooks (we’ll learn about them on the next page).

If you need to manually call a query manually ins response to an event, use the Apollo client directly. You can use useApolloClient to get an instance of the client inside your component:

const SearchUserForm = () => {
  const client = useApolloClient();
  ...
    return (
      ...
      <button onClick={async (event) => {
        try {
          const { data } = client.query({
            query: searchUserQ,
            variables: { name: event.target.value },
          });
          // Do something with data, like set state
        catch (e) {
          // Handle errors
        }
      }} />

You can also still use useQuery, like this:

const SearchUserForm = () => {
  const [name, setName] = useState('')
  const { data, loading, error } = useQuery(searchUserQ, {
    variables: { name },       
  });
  ...
    return (
      ...
      <button onClick={async (event) => {
        setName(event.target.value)
        ...
      }} />
Ad
source: stackoverflow.com
Ad