React Redux

Install redux

npm install react-redux

Add redux to index.js file

React Redux provides <Provider/>, which makes the Redux store available to the rest of your app

import React from 'react'
import ReactDOM from 'react-dom'
import thunk from 'redux-thunk'
import {createStore, applyMiddleware} from 'redux'
import { Provider } from 'react-redux'
import store from './store'
import allReducers from './redux/reducers/allReducer.js'
import App from './App'

const rootElement = document.getElementById('root')

ReactDOM.render(
  <Provider store={createStore(allReducers, applyMiddleware(thunk))}>
    <App />
  </Provider>,
  rootElement
)

Connect Component to store

React Redux provides a connect function for you to connect your component to the store.

import React, { Component } from 'react';
import { connect } from 'react-redux';
import LandingPage from './landing_page';
import Header from './header/header';
import Posts from './post/posts';
import LeftPanel from './left_panel';
import RightPanel from './right_panel';

class Home extends Component {

    constructor(props) {
        super(props);
        this.state = {
            userAuthenticated: localStorage.getItem('userUuid') ? true : false
        }
    }

    componentDidMount() {
    }

    render() {

        return (
            <div>
                <Header />
                <main>
                    <div className="main-wrapper pt-80">
                        <div className="container">
                            <div className="row">
                                <LeftPanel page="HOME"/>
                                <Posts page="HOME"/>
                                <RightPanel/>
                            </div>
                        </div>
                    </div>
                </main>
            </div>
        )
    }
}

const mapStateToProps = (state) => {
    return state;
}

export default connect(mapStateToProps, {
})(Home);

Access data from the store

import React, { Component } from 'react';
import {connect} from 'react-redux';
import { loadNotifications } from '../redux/actions/NotificationAction';

class RecentNotifications extends Component {

    constructor(props) {
        super(props);
        console.log("RecentNotifications constructor()");
        this.state = {
        }
    }

    componentDidMount(){
        
    }

    render() {
        console.log("RecentNotifications render()");

        console.log(this.props.ntcsState.notificationInfo.content);

        let listOfNotifications = {};
        
        if(this.props.ntcsState.notificationInfo.content!==undefined && this.props.ntcsState.notificationInfo.content!==null){
            listOfNotifications = this.props.ntcsState.notificationInfo.content.map((notification) =>

                <li key={notification.uuid} className="unorder-list">
                    {/* profile picture end */}
                    <div className="profile-thumb">
                        <a href="/">
                            <div className="profile-thumb-small">
                                <img src={notification.createdBy.profileImageUrl} alt="profile" />
                            </div>
                        </a>
                    </div>
                    {/* profile picture end */}

                    <div className="unorder-list-info">
                        <h3 className="list-title"><a href="/">Any one can join with us if you want</a></h3>
                        <p className="list-subtitle">5 min ago</p>
                    </div>
                </li>
            );
        }else{
            listOfNotifications = <li className="unorder-list"></li>
        }

        return (
            <div className="card widget-item">
                <h4 className="widget-title">Recent Notifications</h4>
                <div className="widget-body">
                    <ul className="like-page-list-wrapper">
                        {listOfNotifications} 
                    </ul>
                </div>
            </div>
        )
    }
}

const mapStateToProps = (state) => {
    return state;
}

export default connect(mapStateToProps,{
    loadNotifications: loadNotifications
})(RecentNotifications);

You can access data from the store by connecting to the store and using props like this.props.ntcsState.

NotificationReducer.js

const notificationInitialState = {
    notificationInfo: {}
};

let notificationInfo;

export const NotificationStateReducer = (state = notificationInitialState, action) => {

    switch (action.type) {
        case 'LOAD_NOTIFICATIONS':

            notificationInfo = action.payload;

            //console.log("LOAD_NOTIFICATIONS");
            //console.log(notificationInfo.data);

            return Object.assign({}, state, {
                notificationInfo: notificationInfo.data
            });

        default:
            return state;
    }
}

NotificationAction.js

import NotificationAPI from '../../api/notification';

export const loadNotifications = () => {

    let userUuid = localStorage.getItem("userUuid");
    let pageSize = 10;
    let pageNumber = 0;

    //console.log("LOAD_NOTIFICATIONS");

    return async function(dispatch, getState) {
        const response = await NotificationAPI.getNotifications(userUuid, pageSize, pageNumber);
        dispatch({ type: "LOAD_NOTIFICATIONS", payload: response });
    };
};

 

Trigger actions in the store

import React, { Component } from 'react';
import Avatar from '../images/avatar.png';
import UserAPI from '../api/user';
import { connect } from 'react-redux';
import { setUserSession } from '../redux/actions/UserAction';

class ProfileUpdate extends Component {

    constructor(props) {
        super(props);
        this.state = {
            profile: {
                firstName: "",
                lastName: "",
                email:"",
                phoneNumber:"",
                gender: "",
                maritalStatus: "",
                profileImageUrl: props.userState.userProfileImageUrl!== null ? props.userState.userProfileImageUrl : Avatar,
                coverImageUrl: props.userState.userCoverImageUrl!== null ? props.userState.userCoverImageUrl : Avatar,
                uploadImage:""
            }
        }

        this.loadProfile = this.loadProfile.bind(this);
        this.handleInputChange = this.handleInputChange.bind(this);
        this.updateProfile = this.updateProfile.bind(this);
    }

    componentDidMount() {
    }

    handleInputChange(event) {
        console.log("handleInputChange");
        const target = event.target;
        const value = target.type === 'checkbox' ? target.checked : target.value;
        const name = target.name;

        if(name==="profileImageFile"){
            console.log("upload profile image");

            const formData = new FormData(); 
            formData.append( 
                "file", 
                event.target.files[0], 
                event.target.files[0].name 
            ); 

            let uuid = localStorage.getItem("userUuid");

            UserAPI.uploadProfileImage(uuid, formData)
            .then(response => {
                console.log("response");
                console.log(response.data);

                let user = response.data;

                this.setState({profile:user},()=>{});

                this.props.setUserSession(user);

            }).catch(error => {
                console.log("error");
                console.log(error.response.data);
            });
            return;
        }

        if(name==="coverImageFile"){
            console.log("upload cover image");

            const formData = new FormData(); 
            formData.append( 
                "file", 
                event.target.files[0], 
                event.target.files[0].name 
            ); 

            let uuid = localStorage.getItem("userUuid");

            UserAPI.uploadCoverImage(uuid, formData)
            .then(response => {
                console.log("response");
                console.log(response.data);

                let user = response.data;

                this.setState({profile:user},()=>{});

                this.props.setUserSession(user);

            }).catch(error => {
                console.log("error");
                console.log(error.response.data);
            });
            return;
        }

        let updatedState = {
            profile: this.state.profile
        }

        updatedState['profile'][name] = value;

        console.log("updated state");
        console.log(updatedState);

        this.setState(updatedState, function () {
            //console.log(this.state);
        });
    }

    loadProfile(event){

        let uuid = localStorage.getItem("userUuid");

        UserAPI.getProfile(uuid)
        .then(response => {
        console.log("response");
        console.log(response.data);

        let user = response.data;

        this.setState({profile: user});

        this.props.setUserSession(user);

        }).catch(error => {
            console.log("error");
            console.log(error.response.data);
        });
    }

    updateProfile(event){
        
        console.log(this.state.profile);

        UserAPI.updateProfile(this.state.profile)
        .then(response => {
            console.log("response");
            console.log(response.data);

            let user = response.data;

            this.setState({profile: user});

            this.props.setUserSession(user);

        }).catch(error => {
            console.log("error");
            console.log(error.response.data);
        });
    }

    render() {
        return (
            <div className="col-lg-2 col-md-3 d-none d-md-block">
                <div className="profile-edit-panel">
                    <button onClick={this.loadProfile} className="btn-adda edit-btn" data-toggle="modal" data-target="#profileUpdateModal" >edit profile</button>
                </div>
                <div className="modal fade in" id="profileUpdateModal" aria-labelledby="profileUpdateModal">
                    <div className="modal-dialog">
                        <div className="modal-content">
                            <div className="modal-header">
                                <h5 className="modal-title">Update Profile</h5>
                                <button type="button" className="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">×</span></button>
                            </div>
                            <div className="modal-body custom-scroll">
                                <div className="row">
                                    <div className="col-sm-12 text-center">
                                        <img src={this.state.profile.profileImageUrl} className="rounded" alt="..."/>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-6 offset-sm-3">
                                        <div className="form-group text-center">
                                            <input type="file" className="form-control-file"
                                             name="profileImageFile"
                                             onChange={this.handleInputChange}
                                             />
                                        </div>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-12 text-center">
                                        <img src={this.state.profile.coverImageUrl} className="rounded" alt="..."/>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-6 offset-sm-3">
                                        <div className="form-group text-center">
                                            <input type="file" className="form-control-file"
                                             name="coverImageFile"
                                             onChange={this.handleInputChange}
                                             />
                                        </div>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>First Name</label>
                                            <input type="text" className="form-control" aria-describedby="firstNameHelp" placeholder="Enter first name"
                                            name="firstName"
                                            onChange={this.handleInputChange}
                                            value={this.state.profile.firstName}/>
                                        </div>
                                    </div>
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>Last Name</label>
                                            <input type="text" className="form-control" aria-describedby="lastNameHelp" placeholder="Enter last name"
                                            name="lastName"
                                            onChange={this.handleInputChange}
                                            value={this.state.profile.lastName}
                                            />
                                        </div>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>Email</label>
                                            <input type="email" className="form-control" aria-describedby="emailHelp" placeholder="Enter email"
                                            name="email"
                                            onChange={this.handleInputChange}
                                            value={this.state.profile.email}
                                            />
                                        </div>
                                    </div>
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>Phone</label>
                                            <input type="tel" className="form-control" aria-describedby="phoneNumberHelp" placeholder="Enter phone number"
                                            name="phoneNumber"
                                            onChange={this.handleInputChange}
                                            value={this.state.profile.phoneNumber}
                                            />
                                        </div>
                                    </div>
                                </div>
                                <div className="row">
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>Gender</label>
                                            <select className="form-control"
                                                name="gender"
                                                onChange={this.handleInputChange} 
                                                value={this.state.profile.gender}>
                                                <option value="MALE">Male</option>
                                                <option value="FEMALE">Female</option>
                                                <option value="TRANGENDER">Transgender</option>
                                            </select>
                                        </div>
                                    </div>
                                    <div className="col-sm-6">
                                        <div className="form-group">
                                            <label>Marital Status</label>
                                            <select className="form-control"
                                                name="maritalStatus"
                                                onChange={this.handleInputChange} 
                                                value={this.state.profile.maritalStatus}>
                                                <option value="SINGLE">Single</option>
                                                <option value="MARRIED">Married</option>
                                                
                                                
                                            </select>
                                        </div>
                                    </div>
                                </div>
                            </div>
                            
                            <div className="modal-footer">
                                <button type="button" className="btn-adda post-share-btn" data-dismiss="modal">cancel</button>
                                <button onClick={this.updateProfile} type="button" data-dismiss="modal" className="btn-adda post-share-btn">Update</button>
                            </div>
                        </div>
                    </div>
                </div>
            </div>
        )
    }
}

const mapStateToProps = (state) => {
    //console.log("home all states", state)
    return state;
}

export default connect(mapStateToProps, {
    setUserSession: setUserSession
})(ProfileUpdate);

You use props to call actions like this 

this.props.setUserSession(user);

 

 




Subscribe To Our Newsletter
You will receive our latest post and tutorial.
Thank you for subscribing!

required
required


Leave a Reply

Your email address will not be published. Required fields are marked *