#reactjs #components #observer-pattern
#reactjs #Компоненты #наблюдатель-шаблон
Вопрос:
Может ли кто-нибудь предоставить глупо-простой пример наблюдаемого в ReactJS?
По сути, я хочу передать сообщение от одного компонента к другому.
Поисковые запросы Google отправили меня в кроличьи норы с RxJS, Redux, хуками, разделяемой памятью, компонентами на основе классов и другими вовлеченными темами.
Возьмем, к примеру, следующую структуру:
A
/
B C
/
D E
Мне просто нужно отправить сообщение true / false из компонента D в C.
Является ли это изначально сложным в React? tyvm, Кит :^)
Комментарии:
1. digitalocean.com/community/tutorials/react-usecontext
Ответ №1:
RxJS
Redux-observable использует ReactiveX observables, но я не думаю, что это наиболее часто используемый метод для приложений React.
Состояние реакции
Состояние реакции (this.state или useState) передается только от родительского элемента к дочерним элементам, поэтому, когда D и C нуждаются в состоянии, им нужно управлять в общем предке, которым является A. Это означает, что A необходимо передать B реквизиты, которые B не нужны, только для того, чтобы B мог передать их C. Это называется детализацией реквизита и считается плохим, поэтому не лучшим вариантом.
Redux и react-redux
Хранилище Redux — это хранилище событий, вы можете отправлять действия (events), а редукторы или промежуточное программное обеспечение будут реагировать на эти действия для обновления состояния (reducers) или вызывать побочные эффекты (обычно это делается с помощью промежуточного программного обеспечения). Компонент (ы) может использовать селекторы для получения данных из состояния с помощью useSelector(selectorFunction)
, ранее использовался HOC connect
, но перехват намного проще.
Когда отправляется действие, которое вызывает изменение состояния, все selectorFunction
функции вызываются react-redux, и если их возвращаемое значение отличается от последнего запуска, он повторно отобразит компонент, в котором useSelector
использовался.
Redux — хороший кандидат, если вам нужно реализовать сложные требования, поскольку шаблон CQRS / event store позволяет легко отделять действия (указать, что произошло) от редукторов (что делать, когда что-то произойдет), и вы можете запросить хранилище с помощью селекторов (обычно используетсяповторный выбор).
Контекст
Для приложений, у которых нет сложных требований, вам может сойти с рук использование контекста, всякий раз, когда вы меняете контекст, компонент, который имеет useContext
, будет повторно отображаться. Ниже приведен простой пример.
const BoolContext = React.createContext();
const BoolProvider = ({ children }) => {
//set bool message to true
const [bool, setBool] = React.useState(true);
const toggle = React.useCallback(
() => setBool((b) => !b),
[]
);
return (
// set value of context to {bool, toggle}
<BoolContext.Provider value={{ bool, toggle }}>
{children}
</BoolContext.Provider>
);
};
const D = () => {
const { bool, toggle } = React.useContext(BoolContext);
return <button onClick={toggle}>D:{String(bool)}</button>;
};
const C = () => {
const { bool, toggle } = React.useContext(BoolContext);
return <button onClick={toggle}>C:{String(bool)}</button>;
};
//removed E as it does not do anything to demonstrate context
const B = () => ( <D /> )
const A = () => {
return (
<BoolProvider>
<B />
<C />
</BoolProvider>
);
};
ReactDOM.render(<A />, document.getElementById('root'));
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script>
<div id="root"></div>
Комментарии:
1. Отлично, спасибо. Пожалуйста, объясните
{children}
, что это единственная часть, которая неясна. ty2. @kmiklas В этом случае дочерние элементы (props.children)
BoolProvider
являются<B /><C />