web-dev-qa-db-fra.com

Comment accéder à l'état du magasin dans React Redux?

Je suis en train de créer une application simple pour apprendre async avec Redux. J'ai tout fait fonctionner, maintenant je veux juste afficher l'état actuel sur la page Web. Maintenant, comment puis-je accéder à l'état du magasin dans la méthode de rendu?

Voici mon code (tout est dans une page parce que je viens d'apprendre):

const initialState = {
        fetching: false,
        fetched: false,
        items: [],
        error: null
    }

const reducer = (state=initialState, action) => {
    switch (action.type) {
        case "REQUEST_PENDING": {
            return {...state, fetching: true};
        }
        case "REQUEST_FULFILLED": {
            return {
                ...state,
                fetching: false,
                fetched: true,
                items: action.payload
            }
        }
        case "REQUEST_REJECTED": {
            return {...state, fetching: false, error: action.payload}   
        }
        default: 
            return state;
    }
};

const middleware = applyMiddleware(promise(), thunk, logger());
const store = createStore(reducer, middleware);

store.dispatch({
    type: "REQUEST",
    payload: fetch('http://localhost:8000/list').then((res)=>res.json())
});

store.dispatch({
    type: "REQUEST",
    payload: fetch('http://localhost:8000/list').then((res)=>res.json())
});

render(
    <Provider store={store}>
        <div>
            { this.props.items.map((item) => <p> {item.title} </p> )}
        </div>
    </Provider>,
    document.getElementById('app')
);

Donc, dans la méthode de rendu de l'état, je veux lister tous les item.title du magasin.

Merci

60
Parkicism

Vous devez créer un composant distinct, qui écoutera les changements d'état et se mettra à jour à chaque changement d'état:

class Items extends Component {
  constructor(props) {
    super(props);

    this.state = {
      items: [],
    };

    store.subscribe(() => {
      // When state will be updated(in our case, when items will be fetched), 
      // we will update local component state and force component to rerender 
      // with new data.

      this.setState({
        items: store.getState().items;
      });
    });
  }

  render() {
    return (
      <div>
        {this.state.items.map((item) => <p> {item.title} </p> )}
      </div>
    );
  }
};

render(<Items />, document.getElementById('app'));
43
1ven

Importez connect à partir de react-redux et utilisez-le pour connecter le composant à l'état connect(mapStates,mapDispatch)(component)

import React from "react";
import { connect } from "react-redux";


const MyComponent = (props) => {
    return (
      <div>
        <h1>{props.title}</h1>
      </div>
    );
  }
}

Enfin, vous devez mapper les états sur les accessoires pour y accéder avec this.props

const mapStateToProps = state => {
  return {
    title: state.title
  };
};
export default connect(mapStateToProps)(MyComponent);

Seuls les états que vous mappez seront accessibles via props

Découvrez cette réponse: https://stackoverflow.com/a/36214059/404056

Pour en savoir plus: https://medium.com/@atomarranger/redux-mapstatetoprops-and-mapdispatchtoprops-shorthand-67d6cd78f132

36
Zakher Masri

Vous devez utiliser Store.getState() pour obtenir l'état actuel de votre magasin.

Pour plus d'informations sur getState() regardez this courte vidéo.

11
semanser

Vous voulez faire plus que simplement getState. Vous voulez réagir aux changements dans le magasin.

Si vous n'utilisez pas react-redux, vous pouvez faire ceci:

function rerender() {
    const state = store.getState();
    render(
        <div>
            { state.items.map((item) => <p> {item.title} </p> )}
        </div>,
        document.getElementById('app')
    );
}

// subscribe to store
store.subscribe(rerender);

// do initial render
rerender();

// dispatch more actions and view will update

Mais mieux vaut utiliser react-redux. Dans ce cas, vous utilisez le fournisseur comme vous l'avez mentionné, mais utilisez ensuite connectez-vous pour connecter votre composant au magasin.

5
Brandon

Si vous souhaitez effectuer un débogage puissant, vous pouvez vous abonner à chaque changement d'état et mettre l'application en pause pour voir ce qui se passe en détail, comme suit.

store.subscribe( () => {
  console.log('state\n', store.getState());
  debugger;
});

Placez cela dans le fichier où vous faites createStore.

Pour copier l'objet state de la console dans le Presse-papiers, procédez comme suit:

  1. Cliquez avec le bouton droit de la souris sur un objet dans la console de Chrome et sélectionnez Stocker en tant que variable globale dans le menu contextuel. Il retournera quelque chose comme temp1 en tant que nom de variable.

  2. Chrome dispose également d'une méthode copy(). Par conséquent, copy(temp1) dans la console doit copier cet objet dans votre presse-papiers.

https://stackoverflow.com/a/25140576

https://scottwhittaker.net/chrome-devtools/2016/02/29/chrome-devtools-copy-object.html

Vous pouvez voir l'objet dans un visualiseur JSON comme celui-ci: http://jsonviewer.stack.hu/

Vous pouvez comparer deux objets JSON ici: http://www.jsondiff.com/

3
Mowzer