DEV Community

Zach
Zach

Posted on

Creating a Users component

In this post:

  1. The Goal
  2. The Problem
  3. The Options
  4. The Decision
  5. The Plan

The Goal

Add a users list to the two feed pages.

One of the things that I enjoy most about software engineering is working out the interactions between the many moving parts of a web application, and identifying efficiencies, inefficiencies, and opportunities, and then either building or re-factoring code to execute on those good ideas.

That's what I'm thinking about as I look at the following code which renders an html page which I'll also paste below:


const Feed = (props) => {

  const [postData, setPostData] = useState([]);
  const [feedView, setFeedView] = useState(null);

  const path = props.match.path;

  useEffect(() => {

    if (path === "/all"){
      httpHandler.getFeedAllUsers((err, data)=>{
      setPostData(data)
      setFeedView(path)
      })
    } else if (path === "/:user/feed"){
        const user = props.match.params.user
        httpHandler.getFeedOneUser(user, (err, data)=>{
        setPostData(data)
        setFeedView(path)
      })

    }
  }, [props.feedView])

    if (postData){

      return(
        <div id='feed'>
          {postData.map(post=>
            <div className='post' >
              <>
              <h3 className='post-title'>{post.title}</h3>
              <div className='post-content'>
                <Link to={`/${post.author.userName}/feed`}>
                  <div><strong>{post.author.userName}</strong></div>
                </Link>
                <div>{post.text}</div>
               </div>
              </>
            </div>
          )}
        </div>
      )
    } else {
      return <div>No posts</div>
    }
}
Enter fullscreen mode Exit fullscreen mode

What it looks like:
Alt Text

The Problem

Right now, I'm 100% feed. That is, I've managed to render two different feeds with one component - one for all users and one for a specific user. So the feed component is all I've got and it's doing two jobs

  1. Serving all content
  2. Fetching its own data

But now, I want to add a users list that uses a sub-set of the feed data (Since I have a non-normalized schema, all authors are attached to posts. To get all authors, I need to pull all posts).

The Options

I have two options.

  1. 'Quick and Easy': ties the post feed and users into the same component, and requires little new code.
  2. 'Slow and Hard': refactor and create a custom hook that makes data calls and feeds separate user and feed components.

Quick and Easy:

As I mentioned above, the user data is bound inside of the post data. I have two options, then, for getting all distinct users:

  1. Making a separate call to the database using Model.distinct()
  2. Filtering the post data either server- or client-side to extract user names.

Pros:

  • Quick and Easy!

Cons:

  • Extra request and extra database query.
  • Possibly delaying the inevitable (the custom-data-hook-refactor), and creating work that I'll need to unwind.

Slow and Hard

Instead of building users into feed, (or putting them both into a parent-component that is based on feed), I would build a new separate component.

Why? It's likely that I'll end up using this list separately from feeds elsewhere on the site).

How? I'd make a new custom hook that makes its own data queries and feeds that to both user list (a proto-friend list) and to feed.

Pros:

  • Flexibility/modularity/DRY
  • Good, no GREAT, practice with hooks.

Cons:

  • Time-expensive refactoring
  • I don't know what I don't know.
  • This might end up not being the end-solution. I'd hate to end up refactoring this refactor.

The Decision

I'm going to need to sit with this and figure out which direction to travel...

Twenty minutes later...

I've come to a decision. I'm not totally happy with it, but I believe it's the right move.

I'm glad I took the time to step back, because I realized that I needed to think about my real goal. It's not to build a blog platform. My goal is to build enough to attract a team. And my most expensive resource right now is time.

So I decided to go with the first option. Because it better aligns with my business objectives.

The Plan

I'm going to roll the list of users into the feed. Now the lazy way to do this is to just write a few more divs in the return statement.

But I'm not doing this to be lazy, I'm doing this to be efficient, so I'll create separate feed and user components and embed those in a parent component.

Again, I ask myself: does it meet business objectives? My objectives are: speed and solid engineering practices. I believe this is the correct solution.

There's very little overhead to doing this new thing. It's almost free, and does not make things unreasonably complicated if I want to unwind it.

I'm good to go.

Top comments (0)