简体   繁体   English

使用MobX存储循环引用进行设置测试

[英]Setup testing with MobX store circular references

I am trying to figure out testing with Jest for my MobX stores. 我正在尝试为我的MobX商店使用Jest进行测试。

I am using Mobx, React, and Jest. 我正在使用Mobx,React和Jest。

class ConfigStore {
    constructor(RootStore) {
        this.rootStore = RootStore;
        this.config = {};
    }
}
class DataStore {
    constructor(RootStore) {
        this.config = RootStore.config;
    }
}
class UIStore {
    constructor(RootStore) {
        this.config = RootStore.config;
        this.data = RootStore.data;
    }
}
class RootStore {
    constructor() {
        this.config = new ConfigStore(this);
        this.ui = new UIStore(this);
        this.data = new DataStore(this);
    }
}

Did I set my stores up correctly? 我是否正确设置了商店?

If so, what is the best way to test the stores before they get passed to Provider? 如果是这样,在将商店传递给提供者之前对其进行测试的最佳方法是什么?

Your question is very unclear. 您的问题还不清楚。 What exactly do you want to test about these stores in unit tests? 您到底想在单元测试中对这些商店进行什么测试? You can't really test data itself. 您无法真正测试数据本身。

My suggestions: 我的建议:

link to stores 链接到商店

instead of using setting a single property just keep the whole store: 不用设置单个属性,只需保留整个商店即可:

class DataStore {
    constructor(RootStore) {
        this.configStore = RootStore;
    }
}

this way you can besure properties are always properly updated and observed. 这样,您可以确保始终正确更新和观察属性。

if you want you can always have property on your lower level stores: 如果您希望始终可以在较低级别的商店中拥有财产:

class DataStore {
    constructor(RootStore) {
        this.configStore = RootStore;
    }
    get config() {
       return this.configStore.config;
    }
}

Abstract 抽象

if you use typescript abstract your stores with interfaces so the stores are way easilier tested: 如果您使用打字稿抽象您的商店与接口,以便商店更容易测试:

class DataStore {
    constructor(store: IConfigStore) {
        this.configStore = store;
    }
}
interface IConfigStore {
     config: Config;
}

Use a repository pattern 使用存储库模式

For every store make a repository injectable so that all api calls done by the store are actually done in this repository: 对于每个商店,使存储库可注入,以便由商店完成的所有api调用实际上都在此存储库中完成:

class RootStore {
    constructor(repository) {
        this.repostiory = repository;
        this.config = new ConfigStore(this);
        this.ui = new UIStore(this);
        this.data = new DataStore(this);
        this.initializeData();
    }
    async initializeData(){
         this.config = await this.repository.getConfig();
    }
}

This way you can easily mock the repository to give static date so you dont need to do any api calls. 这样,您可以轻松模拟存储库以提供静态日期,因此您无需执行任何api调用。

Keep your react components pure 保持反应成分纯净

The react components that you really want to unit test. 您真正要进行单元测试的react组件。 make sure they dont use mobx stores directly but you use the inject() function instead to make a second class: https://github.com/mobxjs/mobx-react#inject-as-function 确保他们不直接使用mobx存储,但是您可以使用inject()函数来创建第二个类: https : //github.com/mobxjs/mobx-react#inject-as-function

this way your components are way easilier testable and useable stand alone: 这样,您的组件可以更轻松地进行测试和独立使用:

const PureReactComponent = ({ name }) => <h1>{name}</h1>

const SimpleMobxComponent = inject(stores => ({
    name: stores.userStore.name
}))(PureReactComponent)

// usage:
render() {
  return <SimpleMobxComponent/>
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM