Agree for the most part. I will take a 500 line component over a code base that has too many abstractions tbh. It's easier to search one file than to trace a spiderweb back and forth.
@Dom-zy1qy9 ай бұрын
I guess, but If someone is that bad at writing abstractions that 500 lines of code is preferable, they prob have more important things needing work. I was that guy though when I started in react. For some reason the idea of applying proper design patterns to front end JavaScript code just didn't click.
@FabuBrik9 ай бұрын
@@Dom-zy1qy 500 lines isn’t even that much. Much of that could even be imports. All depends on the situation of course but anecdotally I’ve spent far more time and brain power switching between files than scrolling up and down.
@radulaski9 ай бұрын
@@FabuBrik 500 lines defeats the most important benefits of components and that is reusability and readability.
@FabuBrik9 ай бұрын
@@radulaski like I said sometimes it’s more readable in a single file than abstractions would be. It depends of course.
@radulaski9 ай бұрын
@@FabuBrik allowing hundreds of lines of code is a certain road to spagetti and doom. It may be your preference but in general it is a very bad idea. You'll be hard pressed to find a CS professor that would agree with you.
@shakapaker8 ай бұрын
1. Use useEffect Carefully to Prevent Infinite Loops 2. Use Redux Appropriately for Global State, Not for Local State 3. Standardize CSS Practices in Your Project 4. Break Down Large Components into Smaller, Manageable Pieces 5. Rationalize the Use of Libraries in Your Application
@СергейМихеев-е8я9 ай бұрын
One of the cases where I find it appropriate to have a big component (>= 250 lines) is when you use recharts library while building complex charts - they can easily get out of hand quickly and due to their limitation, you can't properly make custom components, only by using some hacky-wacky workaround which is not good :(
@dave6012Ай бұрын
Where I work they’ve established this pattern defining components inside components, but hiding it as a useMemo that returns JSX, and you’re right they’re trying to share state and props with the parent. It’s maddening to come across this 1200 line behemoth with layers of nested JSX returns.
@jasper2virtual9 ай бұрын
I am a new react developer, I jump from vue because I feel react is much more flexible and creative for developers. It’s more fun to construct things in your own way. I will take this video seriously and try a new exercise in frontend mentor
@dealloc9 ай бұрын
Anti-pattern: Using context as a solution for state management or to "avoid prop drilling". While you can use it for that, you probably shouldn't. Make your global/shared state live outside React and subscribe to updates where needed. Deep prop drilling is a sign of too much abstraction going on. Instead of reaching for Context, try to simplify your component structure. If some state is updated across components (i.e. shared state), move that state into global state outside of React instead. Context can result some decremental effects, especially as you move it higher up the tree to allow more components to subscribe to it. Contexts are useful for dependency injection within a small and specialized scope, like for example within compound components where each component can read from its parent scope and update attributes or change behavior based on it and it's not trivial to pass props between them (and by non-trivial I don't mean in depth of a tree but in usage)
@majorhumbert6769 ай бұрын
I would just recommend against using context altogether. A rule with exceptions is just going to be broken all the time. It's better to be black and white and keep it simple. While Context might result in some boilerplate, you can draw a lot of benefits from having pure code.
@dealloc9 ай бұрын
@@majorhumbert676 As I explained above, it depends on what API you're trying to provide. Sure you could just export hooks and have someone setup components by passing props manually, like React Aria. But compound components (like Radix) are a useful pattern where Context is the only mechanism that allows you to pass state between the components in the tree, without leaking internal API details and doesn't require the user to wire up everything themselves, just styling. This makes sense when you want to provide sane defaults as a component library. There are uses for it, but it's mostly related to passing dependencies within a well-defined scope.
@크로로-l3r9 ай бұрын
Understanding and appropriately using the Context API is also important. The Context API is not a state management API, but it is a good solution if there is excessive props drilling. Additionally, the Context provider does not necessarily have to operate at the very top; it is better to place it as close as possible to the components that need to share state.
@rafaelrocha39919 ай бұрын
Now that’s something I’ve been using Context API for and has turned a few heads - as a DI container for features to decouple user value from toolchain (which in this ecosystem just changes way too often)
@dealloc9 ай бұрын
@@rafaelrocha3991 It depends what you are injecting and how much. It makes sense as an enhancement to existing pieces, which is what I assume you use it for-like providing features that components can use conditionally. But using context purely to make your code "easier to test" just to avoid props or use of mocks makes it difficult to convey which components require which providers since you are introducing implicit constraints that cannot be easily linted or type checked. That's also why I recommend our team to always provide sane default context values for contexts, and otherwise rethink their approach if they can't.
@landsman7379 ай бұрын
thanks for the tip about Knip, it's great!
@irfanmohammad72699 ай бұрын
I respect you so much sir, this kind of content we required 😄
@jakubsalanyk88309 ай бұрын
Good you mentioned these barrel index files. Seems like lots of people use it and recommend for defining clear interfaces to communicate with a particular feature, and it makes sense. Until you try code splitting and notice it doesn't work as expected.
@privateanon76238 ай бұрын
But it does work if you configure it properly. Vite through Rollup config, Webpack, Rspack, esbuild and parcel all support the SideEffects tree-shaking config, which lets you configure which exports have side effects via a string or an array of glob patterns
@nazarshvets75018 ай бұрын
@@privateanon7623 Yes and no. You can do that, but I never saw anyone sucessfully implemented such optimization for an _app_ Of course u can do that for a library, as it just smaller, easier to manage, and have backed-in isolation I would really like some content/resources to learn, on how to properly manage barrels, without manually adding those into package.json(and bursting cache for your monorepo tasks) and/or without posibility of shoting yourself into the foot by accident if you would have side-effect(and how to manage those situations)
@ibrahimblahblahyapyap9 ай бұрын
I remember seeing really weird behaviour from a forwardref component that seemed deeply entangled within an app. It returned an array of fields and some fields re-rendered more times than others. Managing state was way too complex for my skills. The entire form state was deeply nested in global state somewhere and local state was difficult to manage because of how the fields are reused - either a field would go missing or had stale state and showed the wrong properties. Ended up easier to write logic directly in the return rather than bringing it out to simplify things.
@kikevanegazz3259 ай бұрын
This video was interesting from start to end. The one thing I can't wrap my mind around is the 50-lines-long component. I measure my components in terms of complexity and responsibility and have never reached 50. Experience may show me how.
@danielkeefer19019 ай бұрын
Hey Jack, could you do a deep dive on barrel files. They are so convenient, i know it's not really something important but i hate seeing many lines of massive import strings. I'd love to hear your thoughts on the barrel file pattern, more on why it's bad and if there is any other patterns that are better for grouping related code.
@RockyTheDog7569 ай бұрын
Agree, barrel files hides your module implementation details, which helps a lot, during future refactoring. For example if you have changed file name or module files structure you need to change imports only in one barrel file, otherwise you have to change import across whole project and its very annoying in big projects with different codeowners per folder, and get messy on code review.
@RockyTheDog7569 ай бұрын
And I’ve never heard that it creates some problems for bundlers, but even if it’s do. It’s better to have problems for bundler then for developers!
@privateanon76238 ай бұрын
Bundlers also solved this a long time ago. You can define a sideEffects prop that's supported by all the existing bundlers, where you specify - via a string or an array of glob patterns - which files have side effects, so others can be pruned when not used in imports, via tree-shaking.
@samithafernando64329 ай бұрын
Spot on! throwing all in to a big Redux store probably the worst !
@DioArsya9 ай бұрын
hmmm I do that barrel files pattern, but only for small files like global constant, global config, global endpoint, essentially anything that global. I didn't know that it is named barrel, but I want to explore more of that to rethink my decision on our projects. Thank you, sir! 🚀
@jherr9 ай бұрын
When you say globals do you just mean cosntants. If so, that's probably ok. The problem is really when the barrel file in turn makes a lot of imports and re-exports those. Those don't get pruned in development mode so they significantly slow down the DX if you use them.
@privateanon76238 ай бұрын
check out sideEffects config prop in webpack/rspack/parcel or through rollup in vite. It's specifically made to solve the tree shaking problem in barrel files that you were discussing in the video @@jherr
@Stevie1derson9 ай бұрын
The kitchen junk drawer! (Totally on my list to clean tomorrow)
@presida39279 ай бұрын
Thank you, Uncle Jack!. And please make a video regarding Tanstack Router.
@Blue-bb9ro8 ай бұрын
Thank you for the great videos!
@kevinbatdorf9 ай бұрын
With objects, the dependency array looks at the reference id values, not a reference itself. Too many devs incorrectly think objects are passed by reference but they are always passed by value (which is a copy of the reference id, not the reference - big difference).
@alexeyzhabin7 ай бұрын
TanStack Query - one love
@codefinity9 ай бұрын
Thanks!
@Geuni6209 ай бұрын
Hello. I'm enjoying the video :) I accidentally opened the explanation and found the last 10:36 min 1. Library overload missing
@dealloc9 ай бұрын
On your point about using a single state managers. It depends what those state managers are used for. Most state management libraries are general purpose and great for custom business logic, but others also provide specific state management, like react-stately for ARIA compliant components, React Query for caching async results, or form-specific state management. It's OK to use multiple state management libraries, but for each their purpose.
@jellyfish17729 ай бұрын
Redux is beautiful. Its people's fault if they dont know how to use it
@gransmistad3239 ай бұрын
Couldn't agree more. So many people seem to prefer using the same tool for everything.
@antoniocestari57759 ай бұрын
I’m not sure I agree with the hard limit on LOC for comps. Like in some cases the JSX is long but the actual functionality isn’t or even what’s being done in the component is just calling hooks with a bunch of params which is still easy to read but long. So I think it depends but if I see a long component doing a lot of stuff with 600+ lines yeah I’d be mad
@tasin55419 ай бұрын
How would you refactor a component that only has a form and several input components which makes it >300 LOC?
@richardflosi9 ай бұрын
Where does the store (redux store) keep its data? Where do other store providers keep their data?
@Kwuala9 ай бұрын
In memory, but it can be persisted in localStorage / sessionStorage
@dealloc9 ай бұрын
Outside of React*. Components subscribe to the state and re-render when state is updated. It can be as granular as needed.
@popuguytheparrot_9 ай бұрын
Go next top of anti-patterns
@radulaski9 ай бұрын
I believe that barrel files are fine as long as you take care that their scope does not blow up.
@jherr9 ай бұрын
All things in moderation.
@semyaza5559 ай бұрын
This is unintentionally a Vue advertisement.
@grugbrain9 ай бұрын
Haha. For Vue developers, they pick Pinia and it's sweet. No need to dig among Redux, Recoil, Zustand, Jotai, Hookstate, MobX, etc; sometimes maybe immer, valtio 🤣
@vetrivendhan61228 ай бұрын
Jotai's atom is very simple to store and access data like useState. 😊
@codeChuck9 ай бұрын
I have been to one React project for experience after finishing the GoIT courses. The reality of that project was that people are making 500 to 700 lines components and don't want to refactor them into smaller once because they are lazy and they don't care about your opinion at all. As long as their code works, the Project Manager is satisfied. The complains of developers with more "refined" taste for code are being ignored. So, basically, as long as devs make features, and everything works, nobody actually cares. Once your code start to be a cause of problem, then PM may ask you to rework it to something better. The decision maker of the project is in charge of the assigning people to do the refactor job. If you just tell someone to refactor, and you do not controll these people, it means your best intentions are in vain. People listen to their leader only, the one who is in charge and possibly may pay in the future, whom they depend on.
@webcoderspeed9 ай бұрын
Hi Jack, can you make video on how to build two different microfrontend app in typescript react and deploy them on aws s3 bucket and consume them.
@elliotyoung12919 ай бұрын
I support the continued use of Redux and don't understand the urge to re-implement it using hooks for every app that we write. Most application developers don't have the time or know-how to create hooks code that rivals redux in maintainability and performance.
@gercius9 ай бұрын
0:41 That naming 💀
@jovincebrillantes10425 ай бұрын
+1 for zustand
@nikhilpsathyanathan9 ай бұрын
Knip is great for cleanup
@docmars9 ай бұрын
Hating long components as an arbitrary limitation is silly to me. Sometimes you may have a larger context provider pulling together several bits of data and doing derived data transforms in useMemo hooks, or sometimes you just want to reduce indirection during your dev flow and work in 1 file. Splitting into many files for the sake of organization seems like a premature optimization to me. If scrolling is annoying, use your IDE's symbol lookup shortcuts to navigate quickly!
@rand0mtv6609 ай бұрын
Yeah, abstracting things based on lines of code is really silly. Of course don't create 1k+ line components all the time, but splitting things into 50 components that are each 20 lines of code doesn't make it magically better or more readable/comprehensible. It might make that single component easier to understand, but how all these 50 components integrate together might be super hard to wrap your head around. Regarding larger components, I think it also helps if you are consistent with your component structure. I usually order things the same way so all components that I write have basically the same shape: - static values outside the component. I might have some value being used in multiple places to configure the component, but that value doesn't depend on state or props, so I put it outside the component. Best if I have an object with some values so I don't put it inside the component body where it would get re-defined on each render - inside the component function body, basic state goes first (useState/useReducer) - 3rd party hooks or custom hooks (useRouter, useMyQuery, useWhatever) - useEffect - useMemo - simpler computed variables (e.g. "const isSearchViewActive = !searchInput.isEmpty && whatever.length > 0") or something like that. useMemo just isn't required here, it's not an expensive computation. Those are named variables that I then use in JSX to render things conditionally or pass as a value to other components - JSX
@developersteve16589 ай бұрын
I agree with this wholeheartedly. Refactoring after you have it done so maintenance is easier, sure. Starting with 15 files? That's a sure-fire way to get confused.
@majorhumbert6769 ай бұрын
You'd be surprised of how many programmers are okay with components with thousands of lines. Where I work, even the programmers who do acknowledge that our 5000 lines components are problematic refuse to do anything about it. Kill me.
@nazarshvets75018 ай бұрын
50 lines for component is Clean Code take(L) Can't wrap my head my would you guess how such component will evolve to not have a refactoring mess for every change. Over-abstraction and/or over-decomposition can create situations where you would have to many pieces to compose, making it hard to maintain (kinda rxjs amount of operators problem, with an exception, what you don't have time to refine all of components on every change to any of such component). Such desicion can age poorly
@nazarshvets75018 ай бұрын
just write it in, if you spot several layers of abtractions intervined within such component, you can extract lower level implementation and abtract it out If there is no clear way to split it, and it doesn't make your life miserable just leave it there for the next change request. For me anything that less than 500 lines its ok, as long as its comply with previous points. Should point out, that I have hard-divide rule for a component - if it have more than 20 lines of none-jsx stuff in it, I will extract all of that in coresponding separate file(s) to deal at one complexity at the time (separation of logic and view as jsx)
@nazarshvets75018 ай бұрын
also, I often work with comboboxes and datagrids, which are highly tailored for each usecase (no clear way to generalize it, at least while we at rapid development cycle), so 100 lines in components its basic boilerplace that I copy-paste before I start to customize it
@Mo.Faried9 ай бұрын
Awesome, I can't agree more. These anti-patterns are very important to be aware of.
@jaminroberts23339 ай бұрын
You think 250 lines is crazy? I work in codebases with components over 3,000 lines... Debug city
@JoonasKarp9 ай бұрын
Could you possibly create a tutorial video on how to set up and configure testing in Reactjs + Vite (vitest + react testing library)? Because create react app came with jest and it was easy but Vite does not come with jest…
@nazarshvets75018 ай бұрын
but it comes with vitest, share same config for testing, so you pretty much setuped from get-go (if you don't need coverage, e2e, or any specific framework for testing) Just write a test, and run it ☺
@Infinitay9 ай бұрын
My issue is always googling to see how to organize my files, components and types 😭
@rmltsn9 ай бұрын
thx for article
@fedoskamcha37688 ай бұрын
💯
@KorhalKk7 ай бұрын
Aren't they discontinuing or leaving the maintenance for Redux?
@jherr7 ай бұрын
Not that I know of. Redux is still under active development. But there are lots of other state managers out there now (Zustand, MobX, Jotai, Recoil, XState (sort of), etc.)
@vetrivendhan61229 ай бұрын
I feel Redux reducers are anti-patterns, business logic must be separated with creational patterns for unit testing. Also complex conditions in the component are hard to read, they must be moved out of the component.
@varandz9 ай бұрын
zustand forever
@DioArsya9 ай бұрын
-+2000 lines of a single component, with a hundred of them. And all of that is a hand over projects, so yeah, this is real life, dude. Real life.
@charlie64x29 ай бұрын
These are some of the reasons I’m moving away from React. So many rules and caveats it’s just crazy. I’ve used Angular and Vue for years and never thought I was stupid. React made me feel stupid af. I went back to Vue and it’s heaven.
@DeffQ9 ай бұрын
Worth mentioning here in comments about Jotai and Nanostores for state management and DaisyUI as great TailwindCSS Component library (IMO better than Shadcn) 👨💻
@tomfancode9 ай бұрын
Fun fact. Leetcode lighthouse score is only 53 points😂. Too much libraries.
@ericmackrodt94412 ай бұрын
There's only one way to do CSS in React and it's styled components with your styles built from scratch. It's more readable, you don't have as much css lost in a sea of css, you don't have piles of classes in html elements. Fight me
@Cahnisama9 ай бұрын
People keep telling me that using react-query as state management is an anti-pattern, but it just works and solves my problems. Am I crazy?
@rand0mtv6609 ай бұрын
Do you really use it for "state" or do you just use it to "sync with the server"? Pulling data from an API using react-query is not state management, at least not to me. Most apps are CRUD apps anyway and you don't really need state management, you just pull data from the server and do POST/PUT/DELETE requests when needed.
@Cahnisama9 ай бұрын
@@rand0mtv660 I use it for both server-state (sync with the server, AKA fetching and caching data), and also for storing client-state (aka, global state) and using it to inject the data into the components
@PeterThomsen-fg4mv9 ай бұрын
Hooks.
@helleye3119 ай бұрын
I hate long components, I put a lint rule for 300 lines for component files. That I then proceeded to turn off because some of my component files were 350+ lines. I still feel like ~100-150 lines is a relatively simple component though. One monster I've seen was 800 lines of super complicated nested conditional logic with just one component, I managed to split that at least. But a few remained. And I absolutely agree, redux needs to die. There are so many better alternatives. Tanstack query + zustand cover basically every use case while being way less complicated. And althrough you could argue "two state management libraries, that's worse", I think getting two smaller libraries that are specifically built to handle their respective side of the state is a better option.
@majorhumbert6769 ай бұрын
That's nothing: where I work, we have countless components with over 1000 lines, and many components with over 5000. Last week in a code review, I proposed that we simply extract some inline SVG markup into a component, but that got shut down.
@abel0907139 ай бұрын
Big components in many cases are fine. I'd rather see more at once than have to dive into 20 components to understand whats going on. Also a big component for me is >= 1000 loc
@Marasma1019 ай бұрын
Too many. My max is 500
@siya.abc1239 ай бұрын
I can't wait till the KZbin influencers realize that the double GET hack is a HACK and was never necessary. Don't get me wrong I reach for react before anything
@matttamal83329 ай бұрын
Redux-saga is so good for unit/integration testing. Shame I can't use it outside of redux
@jherr9 ай бұрын
Why can't you? Redux isn't bound to React. Is Redux Saga?
@dmytroportianka38429 ай бұрын
1. antipattern use of react. you might dont need it, also you might make it worse with react.
@wswebus9229 ай бұрын
The key takeaway from the video is to Stop Using React. This framework doesn't help you write good code; it only complicates and confuses, forcing you to seek auxiliary tools and jump from one to another.
@wishmeheaven7 ай бұрын
To be honest, I like when people (usually they also happen to be positive people) say what they do recommend according to their experience rather than exclusively what not... This is why this video was great.. (in contrast to this comment) - For every "how not to do something" there was always the correct way to do so. Cheers!
@wswebus9227 ай бұрын
@@wishmeheaven you’re right. You can use Vue, Svelte, Solid, Astro, Alpinejs and all these frameworks don’t have so much pain that you’ll have using React
@RachidBoudjelida9 ай бұрын
It's been more than a year now I do not recommend react to my clients, because I think react is the anti-pattern here.
@joshuagalit69369 ай бұрын
Can you collaborate with @theo-t3? I love to hear both of you arguing 🤣