-1

I have a variable I wanna be reactive. Example is simple: user types in an email's input, value reactively renders on the page. But it doesn't happens :( Variable's value changed, but doesn't rendered. Example on codesandbox. Thank you!

MegaBomber
  • 345
  • 2
  • 3
  • 11
  • 1
    please produce https://stackoverflow.com/help/minimal-reproducible-example – Sırrı Kırımlıoğlu May 15 '21 at 17:02
  • This comment doesn't help, but I **abhor** mobx with react. React, at it's core, requires data to be immutable. Mobx, at it's core, forces devs to become comfortable with mutations. [Look how easy this is **without mobx**](https://codesandbox.io/s/mobx-reactive-var-doesnt-updates-forked-00mcz?file=/src/UserProfileForm.js) – Adam Jenkins May 15 '21 at 17:11
  • Does this help? [component not re-rendering when updating the state in mobx](https://stackoverflow.com/q/67034998/2873538) – Ajeet Shah May 15 '21 at 17:12

1 Answers1

0

Started from MobX 6 you need to use makeObservable despite of decorators. Full example:

UserProfileStore:

import { action, makeObservable, observable } from "mobx"

class UserProfileStore
{
    @observable email = 'initial@email.com'

    constructor()
    {
        makeObservable( this ) // REQUIRED
        console.log( 'Store :: constructor initialized' )
    }

    get getEmail()
    {
        console.log( 'Store :: email requested' )
        return this.email
    }

    @action saveEmail( value )
    {
        this.email = value
        console.log( 'Store :: email saved: ' + value )
    }
}

export default UserProfileStore

UserProfileForm:

import React, { Component } from "react"
import { Col, FormGroup, Input, Label } from "reactstrap"
import { observer } from "mobx-react"
import UserProfileStore from "./UserProfileStore";

@observer
class UserProfileForm extends Component
{
    /**
     * @type {UserProfileStore}
     */
    store = null;

    constructor( props )
    {
        super( props );

        this.store = new UserProfileStore()
        this.saveEmail = this.saveEmail.bind( this )

        console.log( 'Form :: constructor initialized' )
    };

    saveEmail( { target: { value } } )
    {
        console.log( 'Form :: saving email value: ' + value )
        this.store.saveEmail( value )
    }

    render()
    {
        return (
            <div>
                <FormGroup row>
                    <Label htmlFor="email" md={2}>Email</Label>
                    <Col md={10}>
                        <Input type="text" id="email" name="email" placeholder="Email" onChange={this.saveEmail}/>
                    </Col>
                </FormGroup>
                <div>New email: {this.store.getEmail}</div>
            </div>
        );
    }
}

export default UserProfileForm
MegaBomber
  • 345
  • 2
  • 3
  • 11