mobx react动作绑定

IT技术 reactjs mobx mobx-react
2021-05-22 17:43:38

对于那些使用mobx+编写应用程序的人react,我想知道在带有&的 react 组件中使用事件处理程序是否有更好的方法来处理上下文问题(例如,商店中this.返回undefinedmobxonClickinjectobserver

我一直在编写处理程序onClick={actionFromStore.bind(this.props.theStore)}来解决这个问题,但似乎应该有更简洁的方法来做到这一点,我不知道。

我不是 mobx 专家,任何建议将不胜感激!

这里的操作是异步获取请求

3个回答

您可以使用@action.bound装饰器:

@action.bound
doSomething(){

    // logic

}

或使用将保留上下文的 labmda 函数:

@action
doSomething = ()=> {

    // logic

}

自 2018 年以来,React 应用程序开发的最佳实践是使用 lambda 函数作为类属性而不是类方法。

作为类属性的 lambda 函数解决了上下文中可能发生的所有问题。如果使用它,您不必将方法绑定到特定的上下文。

例如,您this在某些类方法中使用:

export default class SomeClass {
    myProp = "kappa"

    myMethod() {
        console.log(this.myProp)
    }
}

在这种情况下,如果您将使用它,例如,像某些事件侦听器一样,this将会意外地(实际上,超出预期)从SomeClass实例更改为其他值。所以,如果你使用类方法,你应该像这样修改你的代码:

export default class SomeClass {
    constructor() {
        this.myMethod = this.myMethod.bind(this)
    }

    myProp = "kappa"

    myMethod() {
        console.log(this.myProp)
    }
}

在构造函数中,您将类方法绑定到SomeClass实例上下文

避免这种不必要的代码的最好方法(想象一下,你有 10 多个这种类型的方法 - 你应该绑定它们中的每一个),就是简单地使用 lambda 函数:

export default class SomeClass {
    myProp = "kappa"

    myMethod = () => {
        console.log(this.myProp)
    }
}

而已!Lambda 函数没有上下文,因此this将始终指向SomeClass实例。所以,现在您可以根据需要装饰您的类属性:

export default class SomeClass {
    myProp = "kappa"

    @action
    myMethod = () => {
        console.log(this.myProp)
    }
}

请注意,如果您使用 Babel,则必须使用transform-class-properties插件。

这个问题更多地与JavaScript的核心有关,所以我建议你阅读这篇MDN文章以获取更多关于this行为的信息

希望,这很有帮助!

在 Mobx 6 中,装饰器变得越来越不鼓励使用并且使用起来很麻烦(要求在构造函数中仔细调用 makeObservable(this),即使在子类中也是如此。)

因此,我现在发现使用起来更干净

doStuff = action(() => {
    //  stuff logic
})

而不是

@action.bound
doStuff() { ...

或者

@action
doStuff = () => { ...

这种没有装饰器的模式也适用于旧的 Mobx 版本。