Reputation: 81
I am doing my first steps with React-Redux together. I am having troubles with the state managing.
Everything is working as expected. I have a button that onClick
triggers the action dispatcher (FetchUserAction). This action does an HTTP request. Reducer consumes the data and modifies the store.
I was debugging and saw that on connect function the state (with the data) is coming well.
My understanding is when the state is modified, the component is going to call the render method. That is happening! The real problem is that I expect that as I pass the new data through prop to the child component I will see it, but that is not occurring. What am I doing wrong?
class Home extends Component {
constructor(props) {
super(props);
this.state = {
users: []
};
this.onButtonUserClick = this.onButtonUserClick.bind(this);
}
onButtonUserClick(){
this.props.fetchUser();
}
render() {
return (
<div className={styles.home}>
<FetchUsersButton
fetchUsers={this.onButtonUserClick}/>
<UsersTable
users={this.props.users}/>
</div>
);
}
}
function mapDispatchToProps(dispatch) {
return bindActionCreators({ fetchUser }, dispatch);
}
const mapStateToProps = (state) => {
return {
users: state.users
};
};
export default connect(mapStateToProps, mapDispatchToProps)(Home);
import React, {Component} from 'react';
import {Table, Thead, TBody, Td, Th, Tr} from 'reactable';
import styles from './index.css';
export default class UsersTable extends Component{
constructor(props){
super(props);
this.state = {
users: props.users
};
this.renderUsersTable = this.renderUsersTable.bind(this);
}
renderUsersTable() {
return this.state.users.map(user => {
return (
<Tr key={user}>
<Td column="steamId">
{user.steam_id_64}
</Td>
<Td column="invited">
Yes
</Td>
</Tr>
);
});
}
render(){
return(
<Table className={`table ${styles.usersTable}`}>
<Thead>
<Th column="steamId">
<strong className="name-header">SteamID</strong>
</Th>
<Th column="invited">
<strong>Invited</strong>
</Th>
</Thead>
{ this.state.users.length > 0 ? this.renderUsersTable() : null}
</Table>
);
}
}
import { FETCH_USERS } from "../actions/index";
export default function(state = [], action) {
switch (action.type) {
case FETCH_USERS:
return [action.payload.data, ...state];
}
return state;
}
Upvotes: 0
Views: 753
Reputation: 5645
Your <UserList />
rendering is looking to it's internal state for what to render. You will need it to look at props for this to work.
renderUsersTable() {
// change this.state to this.props
return this.state.users.map(user => {
return (
<Tr key={user}>
<Td column="steamId">
{user.steam_id_64}
</Td>
<Td column="invited">
Yes
</Td>
</Tr>
);
});
}
Fix this line to reference props
as well { this.state.users.length > 0 ? this.renderUsersTable() : null}
Side note: You could turn <UserList />
into a stateless functional component and get rid of the class overhead.
Upvotes: 2