Za react-router
pomocą tego Link
elementu mogę tworzyć linki, które są natywnie obsługiwane przez router reagujący.
Widzę, że to wewnętrzne połączenia this.context.transitionTo(...)
.
Chcę zrobić nawigację. Nie z linku, ale z rozwijanego wyboru (jako przykład). Jak mogę to zrobić w kodzie? Co to jest this.context
?
Widziałem Navigation
mixin, ale czy mogę to zrobić bez mixins
?
reactjs
react-router
George Mauer
źródło
źródło
Odpowiedzi:
W
useHistory
React Router> 5.1.0 pojawi się nowy haczyk, jeśli używasz React> 16.8.0 i komponentów funkcjonalnych.W wersji 4 React Router istnieją trzy podejścia do zautomatyzowanego routingu w ramach komponentów.
withRouter
komponentu wyższego rzędu.<Route>
context
.React Router to głównie opakowanie wokół
history
biblioteki.history
obsługuje interakcje z przeglądarkamiwindow.history
za pomocą przeglądarki i historii skrótów. Zapewnia również historię pamięci, która jest przydatna w środowiskach, które nie mają historii globalnej. Jest to szczególnie przydatne w tworzeniu aplikacji mobilnych (react-native
) i testowaniu jednostkowym za pomocą Node.history
Przykład dwie metody nawigacji:push
ireplace
. Jeśli uważasz, żehistory
jest to tablica odwiedzanych lokalizacji,push
doda nową lokalizację do tablicy ireplace
zastąpi bieżącą lokalizację w tablicy nową. Zazwyczaj będziesz chciał użyć tejpush
metody podczas nawigacji.We wcześniejszych wersjach React routera, trzeba było stworzyć własną
history
instancję, ale w V4<BrowserRouter>
,<HashRouter>
i<MemoryRouter>
składniki będą tworzyć przeglądarce, ziemniaczane i instancje pamięci dla ciebie. React Router udostępnia właściwości i metodyhistory
instancji powiązanej z routerem za pośrednictwem kontekstu, podrouter
obiektem.1. Użyj
withRouter
komponentu wyższego rzęduwithRouter
Składnika wyższego rzędu wstrzykniehistory
obiekt jako podpora elementu. Umożliwia to dostęp do metodpush
ireplace
bez konieczności zajmowania się nimicontext
.2. Użyj kompozycji i renderuj
<Route>
<Route>
Składnikiem jest nie tylko dla miejsc dopasowywania. Możesz wyrenderować trasę bez ścieżki , która zawsze będzie pasować do bieżącej lokalizacji .<Route>
Komponent przechodzi te same rekwizyty jakwithRouter
, dzięki czemu będą mogli uzyskać dostęp dohistory
metod przezhistory
podpory.3. Użyj kontekstu *
Ale prawdopodobnie nie powinieneś
Ostatnią opcją jest ta, z której powinieneś korzystać tylko wtedy, gdy czujesz się komfortowo pracując z modelem kontekstowym React (Context API React jest stabilny od wersji 16).
1 i 2 to najprostsze opcje do wdrożenia, więc w większości przypadków są to najlepsze zakłady.
źródło
withRouter
zamiast przejśćhistory
przez wszystkie moje komponenty? Gahh Muszę spędzać więcej czasu na czytaniu dokumentów ...history.push('/new-location')
bez dołączania tego zachowania do przycisku lub innego elementu DOM?Unexpected use of 'history' no-restricted-globals
context
nie jest już eksperymentalny od reakcji 16.Możesz użyć nowego
useHistory
zaczepu w elementach funkcjonalnych i programowo nawigować:W wersji 4.0 i nowszych użyj historii jako rekwizytu swojego komponentu.
UWAGA: this.props.history nie istnieje w przypadku, gdy twój komponent nie był renderowany
<Route>
. Powinieneś użyć,<Route path="..." component={YourComponent}/>
aby mieć this.props.history w YourComponentW wersji 3.0 i nowszej użyj routera jako rekwizytu swojego komponentu.
W wersji 2.4 i nowszej użyj komponentu wyższego rzędu, aby uzyskać router jako rekwizyt komponentu.
Ta wersja jest wstecznie kompatybilna z wersją 1.x, więc nie ma potrzeby Przewodnika aktualizacji. Samo przejrzenie przykładów powinno wystarczyć.
To powiedziawszy, jeśli chcesz przełączyć się na nowy wzorzec, w routerze znajduje się moduł browserHistory, do którego masz dostęp
import { browserHistory } from 'react-router'
Teraz masz dostęp do historii przeglądarki, dzięki czemu możesz wykonywać takie czynności, jak wypychanie, zastępowanie itp. Jak:
browserHistory.push('/some/path')
Dalsza lektura: Historie i nawigacja
Nie będę wchodził w szczegóły aktualizacji. Możesz o tym przeczytać w Przewodniku aktualizacji
Główną zmianą w tym pytaniu jest zmiana z Mixinu nawigacji na Historię. Teraz używa interfejsu API historii przeglądarki do zmiany trasy, więc będziemy używać
pushState()
odtąd.Oto przykład użycia Mixin:
Zauważ, że
History
pochodzi to z projektu rack / history . Nie z samego React-Routera.Jeśli z jakiegoś powodu nie chcesz używać Mixin (być może z powodu klasy ES6), możesz uzyskać dostęp do historii, którą otrzymujesz z routera
this.props.history
. Będzie dostępny tylko dla komponentów renderowanych przez router. Tak więc, jeśli chcesz go używać w komponentach potomnych, musisz przekazać go jako atrybut przezprops
.Możesz przeczytać więcej o nowej wersji w dokumentacji 1.0.x.
Oto strona pomocy dotycząca nawigacji poza komponentem
Zaleca złapanie referencji
history = createHistory()
i wywołaniereplaceState
tego.Wpadłem w ten sam problem i mogłem znaleźć rozwiązanie tylko dzięki mixinowi Nawigacji, który jest dostarczany z routerem reagującym.
Oto jak to zrobiłem
Mogłem zadzwonić
transitionTo()
bez potrzeby dostępu.context
Lub możesz wypróbować fantazyjny ES6
class
React-Router-Redux ma kilka dostępnych metod, które pozwalają na łatwą nawigację z poziomu kreatorów akcji wewnętrznych. Mogą być one szczególnie przydatne dla osób, które mają istniejącą architekturę w React Native i chcą korzystać z tych samych wzorców w React Web przy minimalnym nakładzie pracy.
Poznaj następujące metody:
push(location)
replace(location)
go(number)
goBack()
goForward()
Oto przykład użycia z Redux-Thunk :
./actioncreators.js
./viewcomponent.js
źródło
v2.4.0
ale wspomniane podejście nie działa dla mnie, moja aplikacja w ogóle się nie wyświetla, a wyniki konsoli:Uncaught TypeError: (0 , _reactRouter.withRouter) is not a function
oto link do mojego postu SO: stackoverflow.com/questions/37306166/…2.6.0
.3.0.x
? Wydaje się, że wiele osób korzysta z tejcontext
drogi.this.props.history
nie istnieje w przypadku, gdy twój komponent nie był renderowany<Route>
. Należy użyć<Route path="..." component={YourComponent}/>
, abythis.props.history
wYourComponent
.W najnowszej wersji (
v2.0.0-rc5
) zalecaną metodą nawigacji jest bezpośrednie przejście do singletonu historii. Możesz to zobaczyć w akcji w dokumencie Nawigowanie poza dokumentem Składniki .Odpowiedni fragment:
W przypadku korzystania z nowszej reagować-Router API, należy skorzystać z poniższych
history
odthis.props
kiedy wewnątrz elementów tak:Oferuje również,
pushState
ale jest to przestarzałe dla zarejestrowanych ostrzeżeń.Jeśli używasz
react-router-redux
, oferujepush
funkcję, którą możesz wysłać w następujący sposób:Można to jednak wykorzystać tylko do zmiany adresu URL, a nie do nawigacji na stronie.
źródło
import { browserHistory } from './react-router'
ale zamiast tego tworzy historięimport createBrowserHistory from 'history/lib/createBrowserHistory'
. Później można uzyskać dostęphistory
z rekwizytów komponentów:this.props.history('/some/path')
var browserHistory = require('react-router').browserHistory; browserHistory.goBack();
push
zmienia tylko adres URL, w rzeczywistości nie zmienia strony. Aby to zrobić, zaimportujbrowserHistory
zireact-router
użyjbrowserHistory.push('/my-cool-path')
. Niestety nie jest to bardzo łatwe do znalezienia. github.com/reactjs/react-router/blob/master/docs/guides/…react-router
wersji v4Oto jak to zrobić za
react-router v2.0.0
pomocą ES6 .react-router
odszedł od mixinów.źródło
history
singletonu, jak stwierdził @Bobby. Państwo mogli używaćcontext.router
, ale robisz to naprawdę trudne do badanej jednostki te elementy jako instancji tylko , że komponent nie będzie mieć to w kontekście.Z mojej strony lubię mieć pojedynczy obiekt historii, który mogę przenosić nawet poza komponentami. Lubię robić jeden plik history.js, który importuję na żądanie i po prostu nim manipuluję.
Musisz tylko zmienić
BrowserRouter
na Router i podać propozycję historii. Nie zmienia to dla ciebie niczego poza tym, że masz swój własny obiekt historii, którym możesz manipulować, jak chcesz.Musisz zainstalować historię , bibliotekę używaną przez
react-router
.Przykładowe użycie, notacja ES6:
history.js
BasicComponent.js
Jeśli musisz nawigować z komponentu, który jest faktycznie renderowany z
Route
komponentu, możesz również uzyskać dostęp do historii z rekwizytów, w ten sposób:BasicComponent.js
źródło
Router
zamiastBrowserRouter
.BrowserRouter
tworzy i utrzymujehistory
obiekt dla Ciebie. Nie powinieneś domyślnie tworzyć własnych, tylko jeśli [„potrzebujesz głębokiej integracji z narzędziami do zarządzania stanem, takimi jak Redux.”] Reagtraining.com/react-router/web/api/Routerthis.props.history
, nie znalazłem jeszcze rozwiązania, które mogłoby mi pomóc zrobić coś takiego w klasie, która nie jest komponentem, ani żadnym innym narzędziem, które nie zostało zbudowane jako komponent React, do którego możesz przekazywać rekwizyty. Dziękujemy za opinię :)Dla tego, który nie kontroluje strony serwera i dlatego korzysta z routera mieszającego v2:
Umieść swoją historię w osobnym pliku (np. App_history.js ES6):
I używaj go wszędzie!
Twój punkt wejścia do routera reagującego (app.js ES6):
Twoja nawigacja wewnątrz dowolnego komponentu (ES6):
źródło
history
obu tych metodtl: dr;
Prosta i deklaratywna odpowiedź brzmi: musisz używać
<Redirect to={URL} push={boolean} />
w połączeniu zsetState()
Pełny przykład tutaj . Przeczytaj więcej tutaj .
PS. W przykładzie użyto inicjalizatorów właściwości ES7 + do inicjalizacji stanu. Zajrzyj tutaj , jeśli jesteś zainteresowany.
źródło
withRouter
nie działało, gdy znajduje się na przeładowywanej trasie. W naszym przypadku musieliśmy selektywnie zrobićsetState
(powodującreturn <Redirect>
), jeśli już jesteś na trasie lubhistory.push()
z innego miejsca.Możesz to zrobić również bez miksów.
Gotcha z kontekstami polega na tym, że nie jest dostępna, dopóki nie zdefiniujesz
contextTypes
klasy.Jeśli chodzi o kontekst, jest to obiekt, podobnie jak rekwizyty, przekazywany z rodzica na dziecko, ale przekazywany jest w sposób dorozumiany, bez konieczności każdorazowego zmieniania rekwizytów. Zobacz https://www.tildedave.com/2014/11/15/introduction-to-contexts-in-react-js.html
źródło
Próbowałem co najmniej 10 sposobów na zrobienie tego, zanim coś zadziałało!
Odpowiedź @Felipe Skinner
withRouter
była dla mnie nieco przytłaczająca i nie byłem pewien, czy chcę utworzyć nowe nazwy klas „ExportedWithRouter”.Oto najprostszy i najczystszy sposób, aby to zrobić, około obecnych React-Router 3.0.0 i ES6:
lub, jeśli nie jest to domyślna klasa, wyeksportuj:
Zauważ, że w 3.xx
<Link>
sam komponent używarouter.push
, więc możesz przekazać mu wszystko, co przekażesz<Link to=
tag, na przykład:źródło
200 OK
zamiast30x
kodu. Jak mogę rozwiązać ten problem?Aby nawigować programowo, musisz przesłać nową historię do props.history w swoim
component
, aby coś takiego mogło dla ciebie wykonać:źródło
W przypadku komponentów ES6 + React następujące rozwiązanie działało dla mnie.
Śledziłem Felippe Skinner, ale dodałem kompleksowe rozwiązanie, aby pomóc początkującym, takim jak ja.
Poniżej są używane wersje:
Poniżej znajduje się mój komponent reagujący, w którym korzystałem z nawigacji programowej za pomocą routera reagującego:
Poniżej znajduje się konfiguracja mojego routera:
źródło
To może nie być najlepsze podejście, ale ... Używając React-Router v4, poniższy Typescript może dać pomysł na niektóre.
W wydanego składnika poniżej, np
LoginPage
,router
obiekt jest dostępny i po prostu zadzwońrouter.transitionTo('/homepage')
do nawigacji.Kod nawigacji został pobrany z .
"react-router": "^4.0.0-2",
"react": "^15.3.1",
źródło
Możesz użyć
withRouter
ithis.props.history.push
.źródło
Aby używać
withRouter
z komponentem opartym na klasach, spróbuj czegoś takiego poniżej. Nie zapomnij zmienić instrukcji eksportu, aby użyćwithRouter
:import { withRouter } from 'react-router-dom'
źródło
na podstawie poprzedniej odpowiedzi
José Antonio Postigo i Bena Wheelera
nowość? ma być napisany pismem maszynowym
i użyciem dekoratorów
LUB właściwości / pola statycznego
z jakimkolwiek zainstalowanym dzisiaj npm. „reaguj-router”: „^ 3.0.0” i
„@ typy / reaguj-router”: „^ 2.0.41”
źródło
z React-Router v4 na horyzoncie istnieje teraz nowy sposób na zrobienie tego.
React-Lego to przykładowa aplikacja, która pokazuje, jak używać / aktualizować React-Router i zawiera przykładowe testy funkcjonalne, które poruszają się po aplikacji.
źródło
W reakcji router v4. Podążam tą drogą w dwóch kierunkach, aby programować trasy.
Numer dwa
Aby uzyskać historię w rekwizytach, być może będziesz musiał owinąć swój komponent
źródło
Jeśli używasz historii skrótów lub przeglądarki, możesz to zrobić
źródło
hashHistory.push
, nie można odczytać właściwości „push” niezdefiniowanej. Skąd je importujesz?W obecnej wersji React (15.3)
this.props.history.push('/location');
działało dla mnie, ale wyświetlało następujące ostrzeżenie:i rozwiązałem to w
context.router
następujący sposób:źródło
React-Router V4
jeśli używasz wersji 4, możesz użyć mojej biblioteki (wtyczka Shameless), w której po prostu wywołujesz akcję i wszystko po prostu działa!
trippler
źródło
Ci, którzy mają problemy z implementacją tego na React-Router v4.
Oto działające rozwiązanie do poruszania się po aplikacji React od działań redux.
history.js
App.js / Route.jsx
inny_plik.js LUB plik redux
Wszystko dzięki temu komentarzowi: komentarz dotyczący problemów ReactTraining
źródło
Jeśli zdarzy się sparowanie RR4 w / redux poprzez React -Router-Redux , skorzystaj z opcji tworzenia akcji routingu od
react-router-redux
również.Jeśli używasz redux thunk / saga do zarządzania przepływem asynchronicznym, zaimportuj powyższych twórców akcji w działaniach redux i podpnij się, aby zareagować na komponenty za pomocą mapDispatchToProps.
źródło
react-router-redux
był przestarzały / archiwizowany przez długi czasMożesz także użyć
useHistory
haka w komponencie bezstanowym. Przykład z dokumentów.źródło
Właściwa odpowiedź była dla mnie w momencie pisania
Ale musisz dodać PropTypes do swojego komponentu
Nie zapomnij zaimportować PropTypes
źródło
Może nie jest to najlepsze rozwiązanie, ale wykonuje zadanie:
Zasadniczo logika powiązana z jedną akcją (w tym przypadku po usunięciu) spowoduje wywołanie wyzwalacza przekierowania. Nie jest to idealne, ponieważ dodasz „wyzwalacz” węzła DOM do swojego znacznika, aby móc wygodnie wywoływać go w razie potrzeby. Będziesz także bezpośrednio wchodził w interakcje z DOM, co w komponencie React może nie być pożądane.
Jednak ten typ przekierowań nie jest tak często wymagany. Tak więc jedno lub dwa dodatkowe, ukryte łącza w znacznikach komponentów nie zaszkodziłyby tak bardzo, szczególnie jeśli nadasz im sensowne nazwy.
źródło
To działało dla mnie, nie potrzebowałem specjalnego importu:
źródło
history
dodanyprops
sam. Pochodzi z HoC, który musisz zaimportować, aby użyć (komponenty wysłane bezpośrednio przezRoute
są automatycznie pakowane przez ten HoC, ale potem potrzebujesz importu dlaRoute
...)zamiast tego użyj hookroutera, nowoczesnej alternatywy dla routera reagującego
https://www.npmjs.com/package/hookrouter
aby odpowiedzieć na pytanie OP dotyczące łączenia poprzez pole wyboru, możesz to zrobić:
źródło
Zakładając, że nie będziesz musiał nawigować podczas samego renderowania (do którego możesz użyć
<Redirect>
komponentu), to właśnie robimy w naszej aplikacji.Zdefiniuj pustą trasę, która zwraca null, pozwoli to uzyskać dostęp do obiektu historii. Musisz to zrobić na najwyższym poziomie, na którym
Router
jest zdefiniowany.Teraz można zrobić wszystkie rzeczy, które można zrobić na historii jak
history.push()
,history.replace()
,history.go(-1)
itp!źródło
React-router-dom: 5.1.2
Ta strona ma 3 strony, z których wszystkie są renderowane dynamicznie w przeglądarce.
Chociaż strona nigdy się nie odświeża, zauważ, jak React Router aktualizuje adres URL podczas przeglądania witryny. Pozwala to zachować historię przeglądarki, upewniając się, że przycisk Wstecz i zakładki działają poprawnie
Przełącznik przegląda wszystkich swoich dzieci i elementów sprawia, że pierwszy z nich, którego ścieżka odpowiada aktualny adres URL. Korzystaj z niego, gdy masz wiele tras, ale chcesz, aby renderowała tylko jedna z nich na raz
źródło
Tak więc w mojej odpowiedzi istnieją 3 różne sposoby programowego przekierowania na trasę. Niektóre rozwiązania zostały już zaprezentowane, ale następne koncentrują się wyłącznie na elementach funkcjonalnych z dodatkową aplikacją demonstracyjną.
Korzystanie z następujących wersji:
Konfiguracja:
Przede wszystkim rozwiązanie używa
HashRouter
, skonfigurowane w następujący sposób:Z dokumentacji dotyczącej
<HashRouter>
:Rozwiązania:
<Redirect>
pomocą push za pomocąuseState
:Używając funkcjonalnego komponentu (
RedirectPushAction
komponentu z mojego repozytorium) możemy użyćuseState
do obsługi przekierowania. Trudna część polega na tym, że po przekierowaniu musimyredirect
przywrócić stanfalse
. KorzystającsetTimeOut
z0
opóźnieniem, czekamy na potwierdzenie ReactRedirect
przejdzie do DOM, a następnie zwróci przycisk, aby użyć go następnym razem.Mój przykład poniżej:
Z
<Redirect>
dokumentacji:useHistory
haka:W moim rozwiązaniu istnieje komponent o nazwie,
UseHistoryAction
który reprezentuje następujące elementy:withRouter
uzyskajhistory
odprops
:Utworzono jeden komponent o nazwie
WithRouterAction
, wyświetla się jak poniżej:Czytanie z
withRouter
dokumentacji:Próbny:
Dla lepszej reprezentacji zbudowałem repozytorium GitHub z tymi przykładami, znajdź go poniżej:
https://github.com/norbitrial/react-router-programmatically-redirect-examples
Mam nadzieję, że to pomoże!
źródło