why do we need container component in react-redux - reactjs

I understand why we want to extract data logic from component into somewhere else, but why do we have to put this logic in a container component, rather than a controller-like javascript object which is connected to the component. This object will subscribe to the store and force the view to update itself when data changes. This way it does not has to be part of view structure and only handle data.
Thanks for help.

In Redux, connect replaces the need to use an explicit separate container component. So, essentially, you're completely right, you don't need to literally create another component that just renders the dumb component.
I create a dumb component and then I have a separate file where I connect the component, but there's no JSX or separate component in this file.
const DumbComponent = (props) => <div>{props.name}</div>;
const ContainerComponent = connect(mapStateToProps)(DumbComponent);

Related

should I pass the imported components as props or can I just import it directly in the subcomponent - React JS

I am making a project with different pages, and each pages/main component of the page contains many subcomponents. I have been passing data as props, which is for the single source of truth as I learned it, but I think I misunderstood that concept, or not(?), because I also have passed the imported components from the parent component as props to the subcomponents to use them.
example:
import ReusableComponent from ../path
import SubComponent from ../differentpath
export default function MainComponent() {
<SubComponent Comp={ReusableComponent} />
}
is this wrong and I can just import the component directly to the subcomponent while maintaining one source of truth using props? The one source of truth idea threw me off. Thank you! I just do not want to proceed yet because the refactoring would be too many.
Having a single "source of truth" is useful for values that could possibly change, that you need to synchronize. For example, if you want to keep track of how many times the user has clicked anywhere, you might initialize a state for that in the root component and pass it down as a prop wherever it's needed.
But static reusable components don't change (at least, not if they're designed sanely). Whether the component is imported directly in the module it's used, or whether it's imported in a different module and passed down as a prop, doesn't make a difference; it'll work the same either way. As a result, it'd usually make sense to import the component only where it's going to be used.
import ReusableComponent from ../path
export default function SubComponent() {
// ...
return (
<div>
<ReusableComponent />
// ...
You can pass components down as props if you want, but that technique is usually useful when the component is dynamic; if the component to use in the descendant is completely static, it'd make more sense to import it directly in the descendant.

How can I communicate between two react sibling component directly without using parent component?

I have a parent component C and it's two children A and B. Suppose I got some data after calculating in B component I want to pass directly to A component without using parent component C.
How can I do that and how many ways to do that?
Does it help here redux or Context API ?
If you don't want to lift your state up to the parent then, both redux or Context API is a good option, however, if you're not using redux already in your project then I would suggest trying to use Context API,
redux comes with a lot of boilerplate code, using redux for just two component is overkill.
redux store is global to your project if you want to share data between just two siblings with Context API you can just wrap those with a Context Provider
Yes, you can use redux here to communicate with component A without using the parent component. Pass the data from component B to an action creator which will then, dispatch an action to a reducer. The reducer will return the state(which now holds the data) that you can access from component A. You will need to connect both A & B to the redux store.
Suppose you want "data" that you have in component A to also be accessible in component B.
class A extends React.Component{
//call this.props.actionCreator and pass it the data
}
export default connect(null, actionCreators)(A)
The action creator recieves the data, wraps it in an action and dispatches to the reducer. The reducer returns the data, which becomes part of the state.
class B extends React.Component{
//We can access data as this.props.data here
}
function mapDispatchToProps(state) {
return {data: state.LoginReducer.data};
}
export default connect(mapDispatchToProps, actionCreators)(B)
We then specify what piece of state we want inside mapDispatchToProps and pass it to the connect helper. The connect helper makes the data available as this.props.data inside component B.
I hope I explained it well enough.

React - Where is the best place to fetch data?

It is a conceptual question about a better way of fetching data using react and react with redux.
I have a component called UsersSelect which is a select component that displays the user information. Currently I'm fetching the user data inside this component to make it more reusable.
I also have an UsersTable component which does kind of the same as UsersSelect and, sometimes, I have them both rendered on the same screen which causes two identical fetches. To avoid this, I'm using redux-saga with takeLatest.
So my questions are:
Is it ok to use this?
Should I put the fetch logic on the parent component? Like an UsersPage component?
Is there another better option to simplify this?
I agree with Miro J.'s comment.
Since you're using the same data into two different components, it'd be better to fetch the data in the parent and pass it down as props to the children.
In your case, (it seems) both your components are very closely related.
In cases in which the components are not so close, but you'd still need the data, you could also load the data when setting up the root App component.
For react architecture, without redux , fetch data is working in parent, and yes UsersPage component should has data for the child components for work, but with redux you has some options, like to create a presentational components , or implement a factory pattern but this requiere that backend architecture couple
const factoryComponent = (FactoryComponent, DefaultComponent, props) => ({
Component: FactoryComponent || props.component || DefaultComponent,
props: { ...props, component: FactoryComponent ? props.component : fetch(url).then(data=>console.log(data)); },
})

How to use Redux store in one component without Provider but with connect, because children aren't necessary?

I want to use connect for its performance optimizations and ease of use with mapStateToProps. I don't think I need to pass the store to the component from a <Provider> wrapper component to any child components, because I don't have any child components that will need the store; I want the store to be in one component, which is "Header.jsx". Mainly, I don't have any other components, other than the default React, and Material-UI, ones, that I want to use the store with.
How would I go about it? I tried to pass the store through defaultProps and used export default connect(mapStateToProps)(Header) but it keeps saying Uncaught Invariant Violation: Could not find "store" in the context of "Connect(Header)". I read that context is what's used to get props passed down the tree using the provider.
I'm new to Redux and React so if I'm going about this completely the wrong way, please let me know.
If using connect can't be done without a provider, how would I go about wrapping my class from the inside?
Example:
class componentName extends Component {
constructor(props) {
super(props);
};
render() {
return (
<h1>Hello World!</h1>
);
}
}
export default connect(mapStateToProps)(<Provider store={storeName}>componentName</Provider>); // Maybe something like this?
I think you simply cannot use connect() without the <Provider/> - it depends on that pattern being followed. If you want to use connect(), the connected component must be a descendant of the provider. The example you have suggested of including the <Provider/> in the call to connect() will not work, as:
a) That method takes a react component class, not an already instantiated react element, and
b) Even then, it creates a component class that, upon being instantiated/mounted, checks the context for a store, and this happens both above (in terms of DOM-hierarchy) the Provider that would create the context and before it is mounted and has a chance to create that context.
What's the reason you are against using the <Provider/>? Are you trying to prematurely optimize because you think including the provider at the root of your app will have some performance impact? If so, I think you may find there is no appreciable impact from including it, or if you are experiencing one, I would suggest that the problem may be in the setup of your reducers, not simply in the use of <Provider/>.
If you are absolutely set on not using the reducer, you could take your Store object (returned from wherever you are calling createStore()), and, in the componentDidMount() of your one component that needs it you could store.subscribe() to listen to state changes, then use store.getState() to get those changes and load them into state. But eventually, you'll find you are just reimplementing <Provider/>, although maybe without the context part.
TL;DR: Sounds like an XY problem

React props states and Redux

What is the different between states and props?
How can you pass a value of let's say CompomentA to ComponentB if we have have for example ComponentA which takes an input then ComponentB is suppose to output(to print it on the screen) that same value if we have a third component called CompomentContainer which is a container of both A and B?
What is Redux? the definition of redux on the main website does not make sense to me. How does it work exactly? How is it useful to react?
Please bear with me, I hope my questions make sense. Thank you.
Those are very valid questions. I've been there and I know how frustrating it is to read about redux and not understanding anything. For some reason people like to use fancy words, which sounds complicated but in reality things are very simple and easy.
What is Redux?
Redux is a Flux architecture. In simple words it will help you to manage the global state of your app.
How does it work exactly?
Redux will create a single "store", this store will have all the data that you need to render in your components, you can update the data using "actions", you will call the actions from your components, these actions will transfer the new data to the "reducers", inside of a reducer you will basically copy the data from the components to the global state (reducers should be pure functions).
How is it useful to react?
It's very useful! Mainly because you will be able to share data across components. Also by having a global state you could save it to the local storage (or a database) to add offline support.
What is the different between states and props?
You can define props to describe the properties that the component will receive when creating instances, you can think of props like parameters, for example:
<MyComponent name="Crysfel" lastname="Villa" />
The previous component is receiving two props, name and lastname. Props will allow you to send data from ComponentA to ComponentB, assuming ComponentB is a child of ComponentA. Props will also help you to receive data from redux. As a rule of thumb, you should never modify the value of the props, these values are just to receive data.
State on the other hand is an object that might contain configurations for your component, the idea is to handle the state of the component, for example a collapsible container, you could have a toggle property in the component's state and toggle the value when user clicks a button. However when using redux you will rarely use the component's state, because Redux is managing the state of your app.
For your second question about sending data between component, you would use redux for that, ComponentA should call an action and send the new data to the global state, then redux will update your component with the new data and then you can render the new data into ComponentB (using props).
What is the different between states and props?
State is data that is tied directly to the React component in which it is set. Props is data that is passed into a child component from the parent component. Unlike state, props are immutable and never "set" directly.
How can you pass a value of let's say CompomentA to ComponentB if we have have for example ComponentA which takes an input then ComponentB is suppose to output(to print it on the screen) that same value if we have a third component called CompomentContainer which is a container of both A and B?
To pass value from Component A to ComponentB you would provide the value as props, passed in via the ComponentA render function. Something like this:
class ComponentA extends React.component {
render() {
return <ComponentB myvalue={value} />
}
}
In ComponentB the value can be accessed: this.props.myvalue
What is Redux? the definition of redux on the main website does not make sense to me. How does it work exactly? How is it useful to react?
Redux is an implementation of the ideas of Flux with a few architectural differences. You can think of it as a library that helps you create a central data store that passes data one-way into React components. It allows you to maintain global state outside of the components themselves.
A top-level container component typically listens to the store and re-renders whenever the store data changes (see the connect function). The data is then passed from the container component into the children components that need that data so they can render properly.

Resources