Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Best ways/patterns to split app into components #399

Closed
glaszczyk opened this Issue May 18, 2018 · 1 comment

Comments

Projects
None yet
2 participants
@glaszczyk
Copy link

glaszczyk commented May 18, 2018

Hello,
I would like to ask what is best approach when splitting app into components. I always struggle with this part. How specialized/universal should components be?

Thank you.

@kentcdodds

This comment has been minimized.

Copy link
Owner

kentcdodds commented Jul 2, 2018

Hi @glaszczyk!

I answered this question in my newsletter today: https://buttondown.email/kentcdodds/archive/ebc5ac2c-07bf-4e07-8a2b-fe131fe573e0

Here's a copy/paste of the whole thing:


When to break up a component into multiple components

At what point does it make sense to break a single component into multiple components?

Advanced React Component Patterns Course in Portland next week!

Hey friends, one quick thing before this newsletter, I'm giving a live and in person workshop in Portland next week right before ChainReact. Ask your boss if they'll pay for you to go get better at React. They probably would love for you to attend this workshop :) We'll be going over:

  • Use the Compound Components Pattern to write React components that implicitly share state while giving rendering flexibility to the user
  • Share code and enhance your components with the Higher Order Components Pattern
  • Give full rendering power to users with the Render Props Pattern
  • Improve the render prop API with the Prop Collections and Prop Getters Patterns
  • Provide total logic control with the Controlled Props and State Reducer Patterns
  • Take advantage of React’s Context API to share state throughout the application with the Provider Pattern

Ok, now on to our newsletter!


Did you know that you could write any React Application as a single React Component? There's absolutely nothing technically stopping React from putting your entire application into one giant component. You'd have a HUGE render method, a TON of instance methods, a LOT of state, and you'd probably need every lifecycle hook (with the exception of shouldComponentUpdate (it should always update!) and componentWillMount (it will never unmount!)).

If you tried this though you'd face a few problems:

  1. Performance would probably suffer: Every state change results in a re-render of the entire application.
  2. Code sharing/reusability would be... not easy.
  3. State would be a challenge: Knowing which pieces of state and event handlers went with what parts of JSX would make your head hurt 😬 and lead to some hard to track down bugs 🐜
  4. Testing would be 100% integration: Not necessarily an altogether bad thing, but it would be pretty tough to test edge cases and keep things isolated to the parts that you're trying to test, so maintaining those tests would be a challenge.
  5. Working together on the codebase with multiple engineers would just be terrible. Can you imagine the git diffs and merge conflicts?!
  6. Using third party component libraries would be..... ummm... impossible? If we're writing everything as a single component third party libraries is at odds with that goal! And even if we allowed using third party components, what about HOCs like react-emotion? Not allowed!
  7. Encapsulating imperative abstractions/APIs in a more declarative component API wouldn't be allowed either meaning that the imperative API would be littered throughout the lifecycle hooks of our one giant component, leading to harder to follow code.

These are the reasons that we write custom components. It allows us to solve these problems.

I've had a question on my AMA for a while: Best ways/patterns to split app into components. And this is my answer: "When you experience one of the problems above, that's when you break your component into multiple smaller components. NOT BEFORE." Breaking a single component into multiple components is what's called "abstraction." Abstraction is awesome, but every abstraction comes with a cost, and you have to be aware of that cost and the benefits before you take the plunge

"Duplication is far cheaper than the wrong abstraction." - Sandi Metz.

So I don't mind if my component's render method gets really long. Remember that JSX is just a bunch of JavaScript expressions using the declarative APIs given by components. Not a whole lot can go wrong with code like that and it's much easier to keep that render method as it is than breaking out things into a bunch of smaller components and start Prop Drilling everywhere.

Conclusion

So feel free to break up your components into smaller ones, but don't be afraid of a growing component until you start experiencing real problems. It's WAY easier to maintain it until it needs to be broken up than maintain a pre-mature abstraction. Good luck!

Looking for a job? Looking for a developer? Check out my job board: kcd.im/jobs


Learn more about React from me:

  • Workshop.me - I'm giving my Advanced Component Patterns workshop in person in Portland next week!!!!
  • egghead.io (beginners) - My Beginner's Guide to React absolutely free on egghead.io.
  • egghead.io (advanced) - My Advanced React Component Patterns course available on egghead.io!
  • Frontend Masters - My Advanced React Patterns course in the form of a Workshop.
  • Workshop.me - I'm giving my Intro to React workshop in person in Salt Lake City in August!

Things to not miss:

Some tweets from this last week:

This is just so freaking cool: facebook/jest#6380

Mad props to @lucasazzola27 Jun 2018

screenshot of the tweet

Friends, I'm telling you @fbjest is an incredible testing framework. Seriously so good. Give it a try if you haven't 💗 🃏25 Jun 2018

Font: http://Dank.sh by @_philpl
Theme: http://aka.ms/nightowl by @sarah_edo

Shortening this tweet to http://kcd.im/mft (my font/theme)

+ other @code things: http://kcd.im/vscode 👌27 Jun 2018

screenshot of the tweet

Phew, got 24 branches ready for my course on Configuring Jest in modern JavaScript web applications. 😌

Now time to get recording! 😬 😆30 Jun 2018


This week's blog post is "Test Isolation with React". It's the published version of my newsletter from 2 weeks ago. If you thought it was good, go ahead and give it some claps (👏x50) and a retweet:

screenshot of the tweet

Special thanks to my sponsor Patreons: Hashnode

P.S. If you like this, make sure to subscribe, follow me on twitter, buy me lunch, support me on patreon, and share this with your friends 😀


👋 Hi! I’m Kent C. Dodds. I work at PayPal as a full stack JavaScript engineer. I represent PayPal on the TC39. I’m actively involved in the open source community. I’m an instructor on egghead.io, Frontend Masters, and Workshop.me. I’m also a Google Developer Expert. I’m happily married and the father of four kids. I like my family, code, JavaScript, and React.

@kentcdodds kentcdodds closed this Jul 2, 2018

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
You can’t perform that action at this time.