Brian Guan
Brian Guan

Reputation: 323

consistently return objects instead of promises useEffect()

I'm trying to get the "isSeller: true" field from document "user" in firestore, but kept getting undefined. Eventually I realized the user object inside useEffect is often returning a promise (__proto__: object) instead of the actual object.

function StorefrontPage(props) {
  const auth = useAuth();
  const router = useRouter();
  const [user, setUser] = useState({});

  const uid = auth.user && auth.user.uid;


  useEffect(() => {
    uid && getUser(uid).then(currentUser => {
      setUser(currentUser);
    })
    console.log(user);
  }, [])

  console.log(user);

The first time I run this, it returns the objects I want, but subsequent refreshes and page changes will turn the console.log into a __proto__ object/promise. I thought wrapping it inside of the useEffect hook would solve this issue, but it is not. How do I make sure it always returns the user object instead of a promise?

For reference, the getUser function is:

export function getUser(uid) {
  return firestore.collection('users').doc(uid).get().then(user => {
    return user.data();
  })
}

Upvotes: 2

Views: 133

Answers (1)

Hagai Harari
Hagai Harari

Reputation: 2877

From the effect you can just lunch the function that will set state

useEffect(() => { uid && getUser(uid, setUser)}, [])

And add .catch after using .then

export function getUser(uid, setUser) {
  return firestore.collection('users')
                 .doc(uid).get()
                 .then(user => setUser(user))
                 .catch(err => console.log(err))
}

Upvotes: 1

Related Questions