简体   繁体   中英

React Native AsyncStorage async function return

I have a helper function:

export async function isFavorite(id) {
  try {
    let favorites = await AsyncStorage.getItem("@rn-food-app:favorites");
    if (favorites) {
      return JSON.parse(favorites).includes(id);
    }
    return false;
  } catch (error) {
    return false;
  }
}

which I'm calling like this:

class DetailScreen extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      recipe: null,
      isFavorite: false,
    };
  }

  componentDidMount() {
    const { route } = this.props;

    if (route.params && route.params.recipeId) {
      const recipe = getRecipe(route.params.recipeId);
      this.setState(
        {
          recipe,
        },
        () => {
          this.checkIfFavorite();
        }
      );
    }
  }

  checkIfFavorite() {
    const { recipe } = this.state;

    console.log(isFavorite(recipe.id));
  }

... ... ...

but the console.log() returns something like this

Promise {
  "_U": 0,
  "_V": 0,
  "_W": null,
  "_X": null,
}

instead of a bool .

I can make it work like this:

export async function isFavorite(id) {
  try {
    return await AsyncStorage.getItem("@rn-food-app:favorites");
  } catch (error) {
    return false;
  }
}

and then in the DetailScreen component

  checkIfFavorite() {
    const { recipe } = this.state;

    isFavorite(recipe.id)
      .then((res) => {
        const favorite = JSON.parse(res).includes(recipe.id);
        console.log(favorite);
      })
      .catch((err) => console.log(err));
  }

This works but why doesn't the approach above work? I wanted to extract all this logic into a helper function so I can simply call isFavorite: bool inside my components without extra logic.

It seems like you are not resolving your promise correctly thats why you get that weird looking console.log

Take a look at this example and change it to your needs - when getting the item from AsyncStorage I am calling 2x .then() calls and 1x .catch() call.

You can store and retrieve your data like this with AsyncStorage:

  const storeData = async (key, value) => {
    try {
      await AsyncStorage.setItem(key, value); 
    } catch (error) {
      console.log(error);
    }
  };

  const getData = async key => {
    try {
      const data = await AsyncStorage.getItem(key);
      if (data !== null) {
        console.log(data);
        return data;
      }
    } catch (error) {
      console.log(error);
    }
  };

then call getData with the key name like you stored your value wherever you want and set the key to a state value.

Store the value:

storeData("@rn-food-app:favorites", the value);

get the value:

  await getData"@rn-food-app:favorites") 
    .then((data) => data)
    .then((value) => this.setState({ isFavorite: value }))
    .catch((err) => console.log("AsyncStorageErr: " + err));

You are logging out Promise instead of an actual result of a Promise, something like this would:

 async checkIfFavorite() {
    const { recipe } = this.state;
    const isFav = await isFavorite(recipe.id) 

    console.log(isFav);
  }

or something along those lines would work

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM