Comment mettre à jour le composant ReactJS basé sur URL / path avec React-Router

Comment puis-je mettre à jour un composant ReactJS basé sur URL / path en utilisant React-Router?

Le code ci-dessous fonctionne, mais est-ce la bonne façon de le faire? Semble comme beaucoup de code pour faire une simple mise à jour. J'espérais qu'il y aurait un appel D'API stateful dans le routeur pour prendre automatiquement en charge ce scénario.

var MyHomeView = React.createClass({
   componentDidMount: function() {
        this.props.updateHeader(); 
   },

   render: function() {
      return (
         <div>
            <h2>Home</h2>
         </div>
      );
  } 
}); 


var MyAboutView = React.createClass({
   componentDidMount: function() {
        this.props.updateHeader(); 
   },

  render: function() {
    return (
      <div className="my-page-text">
        <h2>About</h2>
      </div>
    );
  }
});


var MyHeader = React.createClass({
  mixins: [ CurrentPath ],

  getInitialState: function() {
    return {
       myPath: "about",
       classes: "ion-ios7-information"
    };
  },   

   updateHeader: function() {    
      // Classnames refer to www.ionicons.com
     if (this.getCurrentPath() === "/") {
        this.setState( {myPath: "about" } );
        this.setState( {classes: "ion-ios7-information" } );
     } else {
        this.setState( {myPath: "/" } );
        this.setState( {classes: "ion-ios7-rewind" } );
     }      
   }, 

  render: function() {
    return (
       <Link to={this.state.myPath}>
          <i className={this.state.classes} />
       </Link>
    );
  }
});


var App = React.createClass({
   updateHeader: function() {
      this.refs.header.updateHeader();
   },

   render: function() {
      return (
         <div>
            <MyHeader ref="header" />

         <this.props.activeRouteHandler updateHeader={this.updateHeader} />
         </div>
      );
  } 
}); 


React.renderComponent((
  <Routes> 
    <Route path="/" handler={App}>
      <DefaultRoute handler={MyHomeView} />
      <Route name="about" handler={MyAboutView} />
    </Route>
  </Routes>
), document.body);
19
demandé sur Giant Elk 2014-10-14 02:48:33

3 réponses

Dans réagissent-routeur 2.0.0 vous pouvez utiliser le hashHistory ou browerhistory:

browserHistory.listen(function(ev) {
  console.log('listen', ev.pathname);
});

<Router history={browserHistory}>{routes}</Router>
9
répondu Dherik 2016-03-21 12:02:22

ceci a été mis à jour si vous travaillez avec le routeur react > v11.0.

Vous pouvez lire ici

TLDR:

 // v0.11.x
 var Something = React.createClass({
   mixins: [ Router.State ],
   render: function () {
      var path = this.getPath();
   }
 });

Pour les State API:https://github.com/rackt/react-router/blob/master/doc/04%20Mixins/State.md

6
répondu cooncesean 2015-12-04 17:44:04

cette question est ouverte depuis longtemps, et il semble qu'il devrait y avoir une solution plus simple, mais je vais tenter ma chance et partager ce que nous faisons dans notre application.

nous utilisons L'architecture Flux, qui a la notion de magasins qui informent les composants lorsque leur état est mis à jour. react-router, ils ont un PathStore cela s'intègre parfaitement dans ce modèle, puisque lorsque L'URL change, il peut alors notifier les composants qui se soucient et ont besoin d'être mis à jour.

le StoreListener nous utilisons dans notre application est publiquement disponible ici: https://github.com/odysseyscience/react-flux-suppprt. Je devrais avoir publié à la NGP, mais n'ont pas encore. Je le ferai bientôt si vous pensez que ça pourrait être utile.

Voici comment nous utilisons notre StoreListener pour écouter les changements sur le PathStorereact-router, et comment vous pouvez l'utiliser dans votre MyHeader:

var StoreListener = require('path/to/StoreListener');
var PathStore = require ('react-router/modules/stores/PathStore');

var MyHeader = React.createClass({
  mixins: [
    StoreListener(PathStore)
  ],

  getStateFromStores: function() {
    return {
        path: PathStore.getCurrentPath()
    };
  },

  render: function() {
    var path = this.state.path;
    var myPath;
    var classes;

    if (this.state.path === "/") {
      myPath = 'about';
      classes = 'ion-ios7-information';
    } else {
      myPath = '/';
      classes = 'ion-ios7-rewind';
    } 

    return (
      <Link to={myPath}>
        <i className={classes} />
      </Link>
    );
  }
});

Cela commence par un mixin cela dit "je me soucie des changements à la PathStore". Chaque fois que ce magasin (ou n'importe quel magasin écouté) change, getStateFromStores() est appelé sur votre component afin de récupérer les données du magasin sur this.state. Si/Lorsque que des modifications de données, render() est appelé à nouveau, et vous relisez this.state, et appliquer vos modifications.

c'est exactement notre modèle pour appliquer certaines classes CSS "actives" sur les onglets d'en-tête, ou n'importe où dans l'application qui dépend de l'URL courante.

Notez que nous utilisez webpack pour regrouper nos modules communs JS, de sorte qu'il peut y avoir certaines hypothèses sur l'environnement qui peuvent/peuvent ne pas fonctionner pour vous.

Je n'ai pas répondu à cette question il y a un mois quand je l'ai vue pour la première fois parce que j'ai supposé qu'il y avait une meilleure façon, mais peut-être que notre solution peut aider d'autres avec la même question.

3
répondu Sean Adkinson 2014-11-27 07:43:19