【问题标题】:Ajax call in MobX: MobX observer: Store is not available! Make sure it is provided by some ProviderMobX 中的 Ajax 调用:MobX 观察者:商店不可用!确保它是由某个 Provider 提供的
【发布时间】:2017-10-07 18:28:03
【问题描述】:

我正在从具有树结构的传统 React 应用程序迁移到具有 MobX 的状态管理结构。

目前,我的各个组件从父/祖父进行的 Ajax 调用向下传播数据,这工作正常。

现在我希望改变这一点,由于并行孙/子的复杂性和依赖性的变化,我不再在树结构中工作。

假设我在 componentDidMount<Parent1/> React 类中做了一个 axios.get。然后如何使用MobX 访问数据?

到目前为止我已经尝试过:

创建一个看起来像这样的store.jsx

import { observable } from 'mobx';
const axios = require('axios');

class Store {
    @observable parentdata;
    loadParent = () => {
        let that = this;
        axios.get("/api/parent").then(function(response){
            that.parentdata = response.parentdata;
        }).catch(function(error){
         // Error handling
        })
    };
}

export default Store;

我的ReactDOM 呈现在包含所有父母的container.jsx 中,也意味着<Parent1/>。在container.jsx 中,我们执行以下操作:

import { Provider } from 'mobx-react';

import Store from './store/store.jsx';
let store = new Store();

ReactDOM.render(
    <Provider store={store}>
        <Main />
    </Provider>,
    document.getElementById('content')
);

.. 最后。

container.jsx 的渲染方法中,我没有对&lt;Parent1/&gt; 做任何事情——它只是将组件渲染为正常(这就是这里的想法,对吧?)

parent1.jsx 中,我删除了之前的axios.get 并添加了这些:

import { inject, observer } from 'mobx-react';


@inject('store') @observer
export default class Parent1 extends React.Component {
// ..... 

 componentDidMount () {
        this.props.store.loadParent();

之后,提供错误:MobX observer: Store 'parentdata' is not available! Make sure it is provided by some Provider

我这里绑定数据哪里出错了?

编辑:删除 @inject 并仅使用 @observer 会导致:TypeError: Cannot read property 'loadParent' of undefined

【问题讨论】:

  • 这一行:that.parentdata = response.parentdata 是可疑的。 response.parentData 是否存在?据我所知,Axios 响应数据在 res.data 中。
  • 您提供的代码中没有错误。仅当您尝试在某处使用@inject('parentdata') 并且parentdata 未由Provider 提供时,才会出现您显示的错误消息。您是否出于本示例的目的更改了一些代码,或者您是否有一些其他代码试图注入 parentdata
  • @cbll 我会返回并将所有参考更改为您的商店以匹配大写字母。在我看来,您的商店是用大写字母声明并注入小写字母的。你能验证一下吗?

标签: ajax reactjs axios mobx


【解决方案1】:

有几件事需要解决:

假设您将 parentData 商店命名为 'store' 而不是 'Store' 像类名那样,则 Provider 看起来配置正确

我将如何更改商店本身:


import { observable } from 'mobx';
const axios = require('axios');

class Store {
    @observable parentdata;
    loadParent = () => {
        // There's no need to clone this if you're using arrow functions
        axios.get("/api/parent").then((response) => {
            this.parentdata = response.parentdata;
        }).catch(function(error){
         // Error handling
        })
    };
}

export default Store;

在组件中,我可能会这样做:


import { inject, observer } from 'mobx-react';


@inject('store') @observer
export default class Parent1 extends React.Component {
  // ... //
  componentDidMount () {
      this.props.store.loadParent();
  }

  render() {
    if (!this.props.store.parentData) { return (<div>Loading...</div>) }

    const { parentData } = this.props.store
    return (<pre>{JSON.stringify(parentData, null, 4)}</pre>)

  }

}

我怀疑您的商店区分大小写且名称错误。

调试的一个绝妙技巧是console.log 重要变量或将它们附加到窗口对象以进行测试。

例如:

class Parent1 {

  componentDidMount() {
    window.Parent1 = this
    window.Parent1Props = this.props
    window.Store = this.props.store // or `this.props.Store` check case sensitivity!
  }


  // Open browser console and try to access your now global variables

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-08-24
    • 1970-01-01
    相关资源
    最近更新 更多