mobx与反应存储没有反映在观察员

mobx与反应存储没有反映在观察员

问题描述:

与所有事情反应我试图做一些简单的,我猜我缺少一些明显的配置明智所有我想要做的是采取一个REDX应用程序和实施mobx。mobx与反应存储没有反映在观察员

我的问题是,我试图去的路线/用户/ 12345

这家店是被称为 - 我正在从API获取数据回来,但我发现除少数例外,首先是从mobx

An uncaught exception occurred while calculation your computed value, autorun or tranformer. Or inside the render().... In 'User#.render()' 

然后如有些预期null值的主持人,因为RET的炸毁因为店里还没有在店里装

Uncaught TypeError: Cannot read property 'name' of null 

然后本身之前 - 在我的用户正在设置我已经加入到@Action被调用API,所以我不知道我已经有了搞砸商店功能的mobx例外

Uncaught(in promise) Error: [mobx] Invariant failed: It is not allowed to create or change state outside an `action` 

urned API /承诺我泡泡糖和大量的修复我宁愿有一些反馈如何正确地做到这一点。谢谢。

UserStore.js

import userApi from '../api/userApi'; 
import {action, observable} from 'mobx'; 

class UserStore{ 
    @observable User = null; 

    @action getUser(userId){ 
     userApi.getUser(userId).then((data) => { 
     this.User = data; 
     }); 
    } 
} 

const userStore = new UserStore(); 
export default userStore; 
export{UserStore}; 

index.js

import {Router, browserHistory} from 'react-router; 
import {useStrict} from 'mobx'; 
import routes from './routes-mob'; 

useStrict(true); 
ReactDOM.render(
    <Router history={browserHistory} routes={routes}></Router>, 
    document.getElementById('app') 
); 

路由-mob.js

import React from 'react'; 
import {Route,IndexRoute} from 'react-router'; 
import App from './components/MobApp'; 
import UserDetail from './components/userdetail; 

export default(
    <Route name="root" path="/" component={App}> 
     <Route name="user" path="user/:id" component={UserDetail} /> 
    </Route> 
); 

MobApp.js

import React,{ Component } from 'react'; 
import UserStore from '../mob-stores/UserStore'; 

export default class App extends Component{ 
    static contextTypes = { 
     router: React.PropTypes.object.isRequired 
    }; 

    static childContextTypes = { 
     store: React.PropTypes.object 
    }; 

    getChildContext(){ 
     return { 
     store: { 
      user: UserStore 
     } 
     } 
    } 

    render(){ 
     return this.props.children; 
    } 

} 

.component/userdetail/index.js(容器?)

import React, {Component} from 'react'; 
import userStore from '../../mob-stores/UserStore'; 
import User from './presenter'; 

class UserContainer extends Component{ 
    static childContextTypes = { 
     store: React.PropTypes.object 
    }; 

    getChildContext(){ 
     return {store: {user: userStore}} 
    } 

    componentWillMount(){ 
     if(this.props.params.id){ 
     userStore.getUser(this.props.params.id); 
     } 
    } 

    render(){ 
     return(<User />) 
    } 
} 

export default UserContainer; 

.component/userdetail/presenter.js

import React, {Component} from 'react'; 
import {observer} from 'mobx-react'; 

@observer 
class User extends Component{ 
    static contextTypes = { 
     store: React.PropTypes.object.isRequired 
    } 

    render(){ 
     const {user} = this.context.store; 
     return(
      <div>{user.User.name}</div> 
    ) 
    } 
} 

原谅我,如果它的有点乱了我所拼凑如何从各种博客文章实现mobx以及文档和堆栈溢出问题。我有一个很难找到汤到坚果的例子,不只是标准todoapp

UPDATE

基本上解决方法是@mweststrate答案的下面添加行动的承诺相结合响应

@action getUser(userId){ 
    userApi.getUser(userId).then(action("optional name", (data) => { 
    // not in action 
    this.User = data; 
    })); 

}

,它包括在主持人的检查,我们其实有一些显示

<div>{this.context.store.user.User ? this.context.store.user.User.name : 'nada' }</div> 
+0

第一个错误是由于第二个错误(缺少'name')而引发的,但是当我(错误地)在'render'(它被'@ observable'包裹)修改了一个observable时,我只碰到了第三个错误。 ,这不是你的代码在做什么。 – robertklep

+0

我正确地处理上下文吗? – maehue

+0

tbh,我使用['mobx-connect'](https://github.com/nightwolfz/mobx-connect),所以我不能肯定地说。但是,它应该很容易通过初始化用户可观察对象并注释掉提取用户数据的代码来测试。 – robertklep

注意,下面的代码不被动作保护:

@action getUser(userId){ 
     userApi.getUser(userId).then((data) => { 
     // not in action 
     this.User = data; 
     }); 
    } 

action只有装饰当前函数,但回调是一种反璞归真的功能,所以改用:

@action getUser(userId){ 
     userApi.getUser(userId).then(action("optional name", (data) => { 
     // not in action 
     this.User = data; 
     })); 
    } 
+0

我试过了,它是一样的 - 是否应该在我尝试使用它之前检查.component/userdetail/presenter.js中的值?如果我将演示者渲染方法更改为

{this.context.store.user.User ? this.context.store.user.User.name : 'nada' }
- 这最初会闪烁'nada',然后在更新存储后(api调用完成后)显示正确的值,我只能使其工作。 – maehue
+0

听起来像正确的行为,您的承诺将需要花费不确定的时间来完成,所以你应该在没有完成的承诺的情况下定义你的UI。否则,您的用户界面需要“冻结”,直到您的承诺满足,MobX和React都不想鼓励的情景:) – mweststrate