You are not logged in. Please login at www.codechef.com to post your questions!

×

How to Divide React Components into Presentational and Container Components

I am new to reactjs and redux and have been working on a MERN user registration application which I got working now.

I only struggle in grasping the concept and rewriting the code in such a way:

Here is an example of a post component, I written using to display user created comments. It is receiving the data from the post in a higher-level component passed down as props. In the return, I have all my markup with bootstrap styling applied. I am subscribing to redux actions I imported and using by creating event handlers.

import React, { Component } from 'react'; import PropTypes from 'prop-types'; import { connect } from 'react-redux'; import classnames from 'classnames'; import { Link } from 'react-router-dom'; import { deletePost, addLike, removeLike } from '../../actions/postActions';

class PostItem extends Component {
onDeleteClick(id) { this.props.deletePost(id); }

onLikeClick(id) { this.props.addLike(id); }

onUnlikeClick(id) { this.props.removeLike(id); }

findUserLike(likes) { const { auth } = this.props; if (likes.filter(like => like.user === auth.user.id).length > 0) { return true; } else { return false; } }

render() { const { post, auth, showActions } = this.props;

return (
  <div className="card card-body mb-3">
    <div className="row">
      <div className="col-md-2">
        <a href="profile.html">
          <img
            className="rounded-circle d-none

d-md-block" src={post.avatar} alt="" />

{post.name}

{post.text}

{showActions ? ( <button onclick="{this.onLikeClick.bind(this," post._id)}="" type="button" classname="btn btn-light mr-1"> {post.likes.length} </button> <button onclick="{this.onUnlikeClick.bind(this," post._id)}="" type="button" classname="btn btn-light mr-1"> </button> <link to="{&lt;code">/post/${post._id}} className="btn btn-info mr-1"> Comments </link> {post.user === auth.user.id ? ( <button onclick="{this.onDeleteClick.bind(this," post._id)}="" type="button" classname="btn btn-danger mr-1"> </button> ) : null} ) : null}
); } }

PostItem.defaultProps = {
showActions: true, };

PostItem.propTypes = { deletePost: PropTypes.func.isRequired, addLike: PropTypes.func.isRequired,
removeLike: PropTypes.func.isRequired, post: PropTypes.object.isRequired,
auth: PropTypes.object.isRequired, };

const mapStateToProps = state => ({
auth: state.auth, });

export default connect(mapStateToProps, { deletePost, addLike, removeLike })(PostItem);

As you can see is the code not as neat and compact as I would like. My goal is to make the presentational component unaware of redux, and do all styling and bootstrap stuff here, while the container component have the redux and connect functionalities. Does anyone know how I should approach this?

I saw people using connect to link these types components together:

const PostItemContainer = connect( mapStateToProps, { deletePost, addLike, removeLike } )(PostItem);

export default PostItemContainer;

But I have no idea how to achieve this. If you could help me explain and provide some example code that would be amazing.

Thanks in advance!

asked 20 Aug '18, 18:00

kimberly_071's gravatar image

0★kimberly_071
-1
accept rate: 0%


const PostItemContainer = connect( mapStateToProps, { deletePost, addLike, removeLike } )(PostItem);

export default PostItemContainer; 192.168.0.1

link

answered 09 Oct '18, 18:22

thelightning's gravatar image

0★thelightning
1
accept rate: 0%

toggle preview
Preview

Follow this question

By Email:

Once you sign in you will be able to subscribe for any updates here

By RSS:

Answers

Answers and Comments

Markdown Basics

  • *italic* or _italic_
  • **bold** or __bold__
  • link:[text](http://url.com/ "title")
  • image?![alt text](/path/img.jpg "title")
  • numbered list: 1. Foo 2. Bar
  • to add a line break simply add two spaces to where you would like the new line to be.
  • basic HTML tags are also supported
  • mathemetical formulas in Latex between $ symbol

Question tags:

×58

question asked: 20 Aug '18, 18:00

question was seen: 186 times

last updated: 09 Oct '18, 18:22