Mbox是react中的状态管理,通过透明式的函数响应式编程使得状态管理变得简单和可扩展

  1. 下载mobx
npm install mobx mobx-react

  1. 在src下新建store目录 modules 为子store模块

alt

  1. index.js 入口文件
// 子store
import Study from './modules/study'
import User from './modules/user'

class Store{
    constructor(){
        // 集成 子store 放在store上
        this.study = new Study()
        this.user = new User()
    }
}

export default  new Store()

子store例子:

// v6 写法
import { makeObservable, observable, action, computed, flow } from 'mobx'
import { getlist } from '@/api/getCnode'
class Study{
    constructor(){
        makeObservable(this,{
            msg:observable,
            num:observable,
            params:observable,
            list:observable,
            addNum:computed,
            changeParams:action,
            getCnodeList:action,
            setList:action
        })
    }
    msg = 'GP7'
    num = 1
    get addNum(){
        return this.num+1
    }

    params = {page:1,limit:5,tab:''}
    
    changeParams(params){
        this.params = params
    }

    setList(v){
        this.list = v
    }

    list = []
    getCnodeList(params){
        getlist(params).then(res=>{
            console.log(res);
            // 异步action中修改也是不允许的
            this.setList(this.params.page===1?res:[...this.list,...res])
        })
    }

}

export default Study


// v5 写法
// 【mobx(v5)写法】
// import { observable, action, computed } from 'mobx'
// class StudyStore {
//   @observable
//   num = 0
//
//   @action
//   changeNum(payload) {
//     this.num += payload
//   }
//
//   @computed
//   get num2() {
//     return this.num * 2
//   }
// }
  1. 在整个项目的index.js文件中使用Provider 注入数据
import { Provider } from 'mobx-react';
import store from '@/store';


export default ()=>{  
    return( 
        <HashRouter>
            <Provider {...store}>
                <Layout />
            </Provider>
        </HashRouter>
    )   
}    
            
  1. 使用store
// cnode案例
import { inject,observer } from "mobx-react";
// 注入数据
export default inject('study')(
    observer(
        ({study})=>{
        const [params,setParams] = useState({page:1,limit:5,tab:''})
        const h = useHistory()
        const list = study.list
        useEffect(()=>{
            study.changeParams(params)
            study.getCnodeList(params)
        },[params])

        const handleTab = (v)=>{
            switch (v){
                case 'good': return '精华';
                case 'ask': return '问答';
                case 'share': return '分享';
                case 'job': return '招聘';
            }
        }
        const skipToDetail = ele =>{
            h.push('/detail/'+ele.id)
        }
        return (
            <div className='alllist'>
                <div className='list'>
                    <ul className='uls'>
                    {
                        [
                            { tab:'', label:'全部'},
                            { tab:'good', label:'精华'},
                            { tab:'ask', label:'问答'},
                            { tab:'share', label:'分享'},
                            { tab:'job', label:'招聘'}
                        ].map(ele=>{
                            return(
                                <li 
                                    className='lis'
                                    key={ele.tab}
                                    onClick={()=>setParams({...params,tab:ele.tab,page:1})}
                                    style={{backgroundColor:ele.tab === params.tab?'#80BD01':''}}
                                >
                                    {ele.label}
                                </li>
                            )
                        })
                    }
                    </ul>
                </div>
                <div>
                    {
                        list.map(ele=>{
                            return(
                                <div className='lists' onClick={()=>skipToDetail(ele)} key={ele.id+Math.random()}>
                                    <img src={ele.author.avatar_url}/>
                                    {/* {(ele.tab === 'job' && ele.top) &&  
                                            <span 
                                                className='top' 
                                                style={{backgroundColor:ele.top||ele.good?'#80BD01':'#E5E5E5',color:ele.top||ele.good?'#fff':'#aaa'}}
                                            >
                                            置顶
                                            </span>
                                    } */}
                                    {
                                        // && (ele.tab !== 'job')
                                        ((ele.tab !== 'ask'))
                                            ?
                                            <span 
                                                className='top' 
                                                style={{backgroundColor:ele.top||ele.good?'#80BD01':'#E5E5E5',color:ele.top||ele.good?'#fff':'#aaa'}}
                                            >
                                                {ele.top
                                                    ?
                                                    '置顶'
                                                    : ele.good
                                                        ?'精华'
                                                        :handleTab(ele.tab)
                                                }
                                            </span>
                                            :''
                                        
                                    }
                                
                                
                                    <span className='content'>
                                        <span className='title'>{ele.title}</span><br/>
                                        <span className='visit'>{ele.reply_count}/{ele.visit_count}</span>
                                    </span>
                                    <span className='time'>{time(ele.last_reply_at)}</span>
                                </div>
                            )
                        })
                    }
                </div>
                <button onClick={()=>setParams({...params,page:params.page+1})}>加载更多</button>
            </div>
        )
    }
))

注意:以上是mobx/mobx-react(v6/v7)ES6 版本写法