0

I'm new to react and I'm trying to build a basic Shopify app using React and the Polaris React suite.

TL:DR;

How can I prevent a React component from rendering until data has been fetched asynchronously from the server? OR What is the correct method to get a Polaris app to connect to the shopify service?

Full Explanation

The problem is the render function should add the store domain to an attribute on the <AppProvider/> element. Ie. <AppProvider shopOrigin="https://user-store.myshopify.com"/> However, the domain differs depending on the store using the app.

Given that React is rendered on the client side, I need to send a request to the server to retrieve the current store domain. But this happens after the app has rendered:

render() {

    return (
      <AppProvider
        shopOrigin={this.state.shop} {/* Null when first rendered  */}
        debug={true}
      > ... </AppProvider>

This results in the Polaris app atempting to connect to Shopify with a Null value for the shop domain and everything breaks.

I've been able to prevent this by having the render function return Null on the first render but this feels kind of hacky

 render() {   

    if (typeof this.state.shop === 'undefined') {/* true on first render */}
      return null; { /* prevent rendering at this stage */ }

    return (
      <AppProvider
        shopOrigin={this.state.shop}
        debug={true}
      > 

Here is the async function that I'm using to get the domain from the server

 constructor() {
    super();

    this.state = {};
  }

  componentDidMount() {
    this.callApi()
      .then(res => this.setState(res))
      .catch(err => console.log(err));
  }

  callApi = async () => {
    const response = await fetch('/shopify/config');
    const body = await response.json();

    if (response.status !== 200) throw Error(body.message);

    return body;
  };
4

1 回答 1

3

一个简单的方法是保持'isLoading'组件状态中的属性,该状态最初设置为true.

一旦您的组件完成获取所需的任何数据,请调用this.setState({isLoading: false}).

然后你的组件的渲染方法应该是这样的:

render() {
    const { isLoading } = this.state;

    if (isLoading) {
        return <span>loading...</span>
    }

    return <AppProvider {...props}/>
}

这样,您的应用在完成获取数据之前不会尝试连接到 Shopify 服务。

当然,您可以设置render任何您喜欢的返回值,可以在其中放一个加载图标/动画,或者只返回一个空的<div>.

于 2018-08-12T01:36:04.067 回答