Experiment: Redux aus der OOP-Welt

Im Internet wird seit langem ein heiliger Krieg zwischen Anhängern von Functional Programming und OOP, Redux und MobX, React und Angular geführt. Ich habe sie viele Jahre gemieden, aber jetzt hat mich dieses Thema berührt.



Jetzt, wo Redux in Hunderttausenden von Projekten eingesetzt wird, wird die Community allmählich weniger flexibel. Wenn Sie zu einem Unternehmen kommen, in dem beispielsweise React aktiv verwendet wird, wird Redux höchstwahrscheinlich im Kit verwendet. Es hat sich ziemlich viel Hass auf diese Bibliothek angesammelt, aber etwas anderes zu benutzen ist aus vielen Gründen bereits schwieriger. Warum Redux so schlecht ist und warum es ohne es noch schlimmer ist, wird in vielen Artikeln gut ausgedrückt, aber in der Regel sind Autoren emotional gezwungen, etwas zu verwenden, das sie selbst mehr mögen. Die vielleicht objektivste schriftliche Übersetzung ist " Redux reduzieren ". Aber ich möchte besonders ein Zitat hervorheben:


Redux, , . , Redux, , , « , jQuery».

, .


: .

React , , . , , , MobX, , ...



… ?


, ( Redux) — . , Redux.


, Vuex, , , . vuex @, , , . ,  . — , , , .


Store


, , , :


import {Store, state, Mutation, Action} from "@disorrder/storm";

export default class Account extends Store {
    @state amount = 0

    @Mutation setAmount(val = 0) {
        return {amount: val};
    }

    @Action async updateAmount() {
        let {data} = await api.get("/user/account");
        //  1
        this.setAmount(data);
        //  2
        this.amount = data;
        //  3
        this.mutate({amount: data}); // ,     .
        //  3      ,     .
    }
}

, , () Redux. vuex , .


Store state, . mutate(),   state, .


 @state ( ) state.


Mutation — , reducer Redux, state. , "" . Redux, - action , . Redux ,  action.type . Mutation  .


Action — . API, , action. , , , , .


vuex  action action, .   , , . , .



, React Vue. connect ( Redux).   !


// src/store/index.js
import User from "./User"
export const user = new User()
  . . .

// src/store/User.js
export default class User extends Store {
  // ...
}

// src/App.js
import user from "./store";

class App extends Component {
    componentDidMount() {
        user.subscribe((mutation, oldState) => {
            this.setState({});
        });
    }
}

. subscribe user, mutation , .


Collection pattern


, , . , . , . , , CRUD. . (, , )


export default class Collection extends Store {
    url = "/"
    pk = "id" // Primary key

    @state items = {}
    @state indices = [] // itemIds

    // -         .       .
    @Mutation __add(item) {
        const id = item[this.pk];
        this.items = {...this.items, [id]: item};
        this.indices = [...this.indices, id];
    }

    // - 
    @Mutation add(item) {
        const id = item[this.pk];
        const items = {...this.items, [id]: item};
        let mutation = {items};

        const rewrite = id in this.items;
        if (!rewrite) {
            mutation.indices = [...this.indices, id];
        }

        return mutation;
    }

    @Action async create(data) {
        let item = await api.post(this.url, data);
        this.add(item);
    }

    @Action async getById(id) {
        let item = await api.get(`${this.url}/${id}`);
        this.add(item);
    }

    @Action async getList(id, params) {
        let items = await api.get(this.url, {params});
        items.forEach(this.add.bind(this));
    }
}

, :


export default class Users extends Collection {
    url = "/users"
}

. . : , SOLID, DRY, KISS — , .



  • 150 . , , . , "Redux , ". !
  • . Redux reducers actions .
  • switch-case


  • , . Babel. createStore, .
  • subscribe, watcher
  • , ,

PS: Ich gebe nicht vor, eine bahnbrechende Bibliothek zu sein, sondern habe mit dem Code selbst begonnen, der mir am bequemsten erscheint. Dies ist mein persönliches Experiment und die Gedanken, die ich teilen möchte. Jede Kritik wird akzeptiert, bleiben Sie einfach in Kontakt.



All Articles