J'essaie de configurer un écouteur d'historique au niveau le plus élevé afin qu'à chaque fois que l'emplacement change, du code soit exécuté (suivi de Google Analytics dans mon cas).
Actuellement, mon App.js ressemble à ceci :
render() { return ( <BrowserRouter> <Switch> <Route path="/" exact component={Home}/> <Route path="/" component={MainLayout}/> </Switch> </BrowserRouter> ); }
D'après ce que je comprends, je ne peux utiliser history
que dans BrowserRouter
, mais il ne peut avoir qu'un seul enfant, donc je ne peux le mettre que dans Switch
, mais ensuite je devrai le mettre dans chaque composant sous Switch, ce que je ne peux pas faire car je veux qu'il ne s'exécute qu'une seule fois. Si j'ajoute simplement un composant personnalisé sous Switch
sans l'envelopper dans un Router
, il n'y a pas d'historique.
Que dois-je changer pour le faire fonctionner? Est-il possible d'obtenir une instance de historique
dans le code App.js
? Est-il possible de réaliser en utilisant un composant personnalisé ou un HOC?
4 Réponses :
Il est possible d'utiliser le package history
, au lieu de se fier sur celui par défaut créé par react router.
Par exemple, en utilisant history.listen
:
history.listen((location) => { ReactGA.pageview(location.pathname + window.location.search); });
Dans mon exemple, j'utilise react-ga
, afin de standardiser notre instrumentation GA sur projets.
C'est le problème principal - où puis-je obtenir l ' historique
en dehors du composant Router
?
Si vous configurez le routeur au niveau supérieur, qu'y a-t-il en dehors de cela?
@ulu, vous pouvez le créer à l'aide du package history
, au lieu de en s'appuyant sur celui par défaut créé par le routeur de réaction.
J'ai essayé ce package. Je ne me souviens pas quel était le problème exact, mais je pense que le gestionnaire listen
ne se déclenchera pas, car le routeur a créé sa propre histoire
@ulu vous pouvez transmettre l'historique pour utiliser un historique différent de celui par défaut. C'est dans la doc
Vous devez ajouter une Route
qui sera rendue sans condition.
Essayez quelque chose comme ceci:
render() { return ( <BrowserRouter> <React.Fragment> <Route component={HistoryListenerComponent}/> <Switch> <Route path="/" exact component={Home}/> <Route path="/" component={MainLayout}/> </Switch> </React.Fragment> </BrowserRouter> ); }
Ainsi, HistoryListenerComponent
est toujours rendu et vous pouvez écouter
depuis son componentDidMount
.
Ce n'est pas une bonne recommandation. Il existe un historique
conçu pour cela, et un composant de routeur pour chaque cas d'utilisation.
HistoryListenerComponent
obtient un objet history
fourni par React Router via props.history
. Et cet objet doit être utilisé pour l'écoute.
HistoryListenerComponent
obtient un objet history
qui est vrai. Mais vous avez oublié que cela n'est nécessaire que dans l'application react-router, alors que Google Analytics n'a pas besoin d'utiliser react-router, historique
est suffisant et c'est aussi pourquoi vous pouvez le fournir via accessoires
.
Nous avons découvert que l'option la plus simple est le composant Update - https : //github.com/pshrmn/rrc/blob/master/docs/OnUpdate.md
Voici ce qui a fonctionné pour moi:
componentDidMount=()=>{ ReactGa.initialize('00000'); //enter id ReactGa.pageview(window.location.pathname + window.location.search); this.props.history.listen(location => { ReactGa.set({ page: location.pathname }); // Update the user's current page ReactGa.pageview(location.pathname); // Record a pageview for the given page }); } render (){ return ( <Switch> <Route ....> ..... <Switch> ); } export default withRouter(ComponentName)
Maintenant, enveloppez simplement le composant où vous utilisez React-ga avec withRouter comme ceci:
import {withRouter} from 'react-router-dom';N'oubliez pas que sans encapsuler avec Routeur, vous ne pouvez pas utiliser la propriété this.props.history. Vous ne pouvez pas utiliser l'écouteur d'historique personnalisé pour le composant BrowserRouter. Il a un accessoire d'historique intégré (c'est-à-dire this.props.history).