После введения запроса в поле поиска, осуществляется переход на новую страницу с названиями видео под этот запрос React
Есть компонента Feed, в ней лежит список видосов с базы данных, как реализовать то, чтоб после нажатия кнопки поиск я переходил на новую страницу с нужными видео по названию?
Часть кода feed:
<form name="publish">
<input id="search" type="text" name="message" placeholder="Поиск" />
<button id="searchButton" type="submit"></button>
</form>
Код Страницы результатов поиска:
import React, { useContext, useState, useEffect } from 'react';
import { Row, Col,} from 'react-bootstrap';
import {Redirect} from 'react-router-dom';
import './SearchDisplay.scss';
import { MyContext } from '../../MyContext'
import Navigation from '../../layout/navigation/navigation';
import Header from '../../layout/header/Header';
// const CabinetContext = React.createContext()
const SearchDisplay = () => {
let [videos, setVideos] = useState([]);
let [error, setError] = useState(null);
const { isAuthorized, isFetching } = useContext(MyContext)
useEffect(() => {
fetch('/api/user/my/favorites')
.then(response => response.json())
.then(result =>{
console.log(result)
setVideos(videos= result )
})
.catch(e => {
console.log(e);
setError(isFetching, error = e );
});
console.log('!!!',videos);
}, [])
if (isFetching) {
return <div>Loading...</div>
}
if (!isAuthorized) {
return <Redirect to="/logreg1" />;
}
else
return (
<>
<Header />
<div className="Max">
<Row>
<Col sm={2}>
<Navigation key="navigation"/>
</Col>
<Col>
<div className="Box">
<div className="VideoList">
{Object.keys(videos).map(key => (
<div className="VideoContainer">
<a href={"./watch" + videos[key]._id}>
<div key={key} className="container">
<div className="thumbnail">
<img className="previmg" src=
{videos[key].coverURL}
alt="PreviewImg"
/>
</div>
<div className="body">
<div className="body__img"></div>
<div className="body__txt">
<div className="title1">
<p>{videos[key].videoname}</p>
</div>
<div className="title2">
<p>{videos[key].channelName}</p>
</div>
</div>
</div>
</div>
</a>
</div>
))}
</div>
</div>
</Col>
</Row>
</div>
</>
)
}
export default SearchDisplay;
Ответы (2 шт):
Вот рабочий вариант раутинга по вашему примеру. Немного упростил код, но принцип такой. Добавил переход на фильтрованный список.
import React from "react";
import { BrowserRouter, Route, Link } from "react-router-dom";
const linkStyle = {
border: "1px solid black",
padding: "1rem",
margin: "1rem",
display: "block",
};
const fakeServerData = [
{ id: "1", label: "Ocean1", description: "Ocean1-Description1" },
{ id: "2", label: "Ocean2", description: "Ocean2-Description2" },
{ id: "3", label: "Video1", description: "Video1-Description1" },
{ id: "4", label: "Video2", description: "Video2-Description2" },
];
const App = () => {
return (
<BrowserRouter>
<Route exact path="/" component={SearchDisplay} />
<Route exact path="/search" component={SearchResults} />
<Route path="/search/:id" component={Video} />
</BrowserRouter>
);
};
export default App;
const SearchDisplay = ({ history }) => {
const [filter, setFilter] = React.useState("");
const searchButtonHandler = () => {
const filteredData = fakeServerData.filter((item) =>
item.label.toLowerCase().includes(filter.toLowerCase())
);
history.push("/search", filteredData);
};
return (
<div>
SearchDisplay
<input
type="text"
onChange={({ target: { value } }) => setFilter(value)}
value={filter}
/>
<button onClick={searchButtonHandler}>Search</button>
</div>
);
};
const SearchResults = ({ location, history }) => {
const data = location.state;
return (
<div>
<h3>SearchResults</h3>
{data.map(({ id, label }) => (
<Link key={id} to={`/search/${id}`} style={linkStyle}>
Video: {label}
</Link>
))}
<button onClick={() => history.goBack()}>Go back</button>
</div>
);
};
const Video = ({ match, history }) => {
// здесь обычно загружаем данные с сервера по id
const currentVideo = fakeServerData.find(({ id }) => id === match.params.id);
const { id, label, description } = currentVideo;
return (
<div>
<h3>This Video is {label}</h3>
<h4>id: {id}</h4>
<p>Description: {description}</p>
<button onClick={() => history.goBack()}>Go back</button>
</div>
);
};
Снова возникли вопросы, пытаюсь код внедрить в проект, на данный момент выдает ошибку 
Коды следующие: В компоненте Header, который подключен к App и в котором осуществляется поиск:
import React, { useContext } from 'react';
import { Navbar } from 'react-bootstrap';
import { BrowserRouter, Route, Link } from "react-router-dom";
import './Header.scss';
import { MyContext } from '../../MyContext'
import { FeedContext } from '../../Pages/Feed/FeedContext'
import SearchDisplay from '../../Pages/SearchDisplay/SearchDisplay';
const SearchComp = ({ history }) => {
const { videos1 } = useContext(FeedContext)
console.log(videos1)
const [filter, setFilter] = React.useState("");
const searchButtonHandler = () => {
const filteredData = videos1.filter((item) =>
item.videoname.toLowerCase().includes(filter.toLowerCase())
);
history.push("/searchDisplay", filteredData);
};
return (
<div>
SearchDisplay
<input
type="text"
onChange={({ target: { value } }) => setFilter(value)}
value={filter}
/>
<button onClick={searchButtonHandler}>Search</button>
</div>
);
};
const Header = () => {
return (
<>
<Navbar fixed="top">
<Navbar.Brand href="/" >
<div className="LaT">
</div>
</Navbar.Brand>
<Navbar.Collapse id="responsive-navbar-nav">
<BrowserRouter>
<div className="search">
<SearchComp/>
</div>
</BrowserRouter>
</Navbar.Collapse>
</Navbar>
</>
)
}
export default Header;
Сама компонента SearchDisplay, где должен происходить вывод
import React, { useContext, useState, useEffect } from 'react';
import { Row, Col,} from 'react-bootstrap';
import {Redirect, Link} from 'react-router-dom';
import './SearchDisplay.scss';
import { MyContext } from '../../MyContext'
import Navigation from '../../layout/navigation/navigation';
import Header from '../../layout/header/Header';
const linkStyle = {
border: "1px solid black",
padding: "1rem",
margin: "1rem",
display: "block",
};
// const CabinetContext = React.createContext()
const SearchDisplay = ({ location, history }) => {
const data = location.state;
let [videos, setVideos] = useState([]);
let [error, setError] = useState(null);
const { isFetching } = useContext(MyContext)
useEffect(() => {
fetch('/api/user/my/favorites')
.then(response => response.json())
.then(result =>{
// console.log(result)
setVideos( result )
})
.catch(e => {
console.log(e);
setError(isFetching, e );
});
console.log('!!!',videos);
}, [])
if (error) return <div>{`Error: ${error.message}`}</div>;
if (isFetching) {
return <div>Loading...</div>
}
else
return (
<>
<Header />
<div className="Max">
<Row>
<Col sm={2}>
<Navigation key="navigation"/>
</Col>
<Col>
<div className="Box">
<div className="VideoList">
<h3>SearchResults</h3>
{data.map(({ _id, videoname }) => (
<Link key={_id} to={`/search/${_id}`} style={linkStyle}>
Video: {videoname}
</Link>
))}
</div>
</div>
</Col>
</Row>
</div>
</>
)
}
export default SearchDisplay;
Также в Header приходит массив из Видео, со страницы с общим списоком Роликов:

Пока не могу понять, в чем проблема, а их определенно несколько