[HN Gopher] The new wave of React state management
       ___________________________________________________________________
        
       The new wave of React state management
        
       Author : remrem
       Score  : 170 points
       Date   : 2022-07-02 14:31 UTC (8 hours ago)
        
 (HTM) web link (frontendmastery.com)
 (TXT) w3m dump (frontendmastery.com)
        
       | m_ke wrote:
       | Mobx solved all of the state problems properly a long time ago.
        
         | jetako wrote:
         | Shoutout to MobX-state-tree
        
           | speedgoose wrote:
           | It is a lot slower though, I had to migrate from it to normal
           | mobx to come back to descent performance when having a few
           | thousand objects.
        
             | tomduncalf wrote:
             | Seconded, I looked at using MST a few years ago for a React
             | Native app with frequent (30hz maybe) state updates and the
             | CPU hit compared to plain MobX was too much
        
         | phaedryx wrote:
         | That's actually what converted me to Vue. I did all of the
         | Redux stuff, but then found Mobx and enjoyed that so much more.
         | A friend of my told me "if you like React + Mobx you'd probably
         | like Vue" (I think he was quoting from the Vue website). He was
         | right.
        
         | pweissbrod wrote:
         | Agreed! I'm surprised at the comprehensive work going into
         | researching the history of state management in this article
         | while completely missing MobX.
         | 
         | What problem does MobX not already solve?
        
           | Chris_Newton wrote:
           | _What problem does MobX not already solve?_
           | 
           | I'd say the two biggest hazards with the reactive/declarative
           | style are cyclic dependencies in the data model and
           | remembering history.
           | 
           | Tools like MobX let you write quite elegant code in the right
           | circumstances but they are less helpful if, for example, you
           | have a complicated set of constraints and the effects of
           | changing one value in your state can propagate in different
           | directions depending on what first changed to start the
           | cascade.
           | 
           | This style also tends to emphasise observing the current
           | state of the system, so if you need a history as well (for
           | undo, syncing with other user actions via a server, etc.)
           | then you probably have to write a whole extra layer on top,
           | which is more work with this kind of architecture than for
           | example if you are using a persistent data structure and
           | reducer-style updates (as popularised by Redux within the
           | React ecosystem).
        
             | tomduncalf wrote:
             | This is a really great explanation - I love MobX in many
             | ways but the "observing the current state of the system"
             | definitely has its downsides, which you've expressed very
             | clearly!
        
           | jitl wrote:
           | All cited frameworks solve the problems. Article is more of a
           | survey. It's a pity to miss Mobx while discussing
           | proxy/mutation API in Valtio.
        
           | tommoor wrote:
           | came here to say the same thing.
        
         | kabes wrote:
         | Mobx has made me finally appreciate frontend programming again.
         | It's like people want to deal with the insanity that is redux
         | only because it's a more pure functional style which react
         | seems to promote.
        
           | Rapzid wrote:
           | Something I like to point out to teams when it's the case,
           | and it's often the case, is "When is the last time anyone on
           | the team has used time travel debugging? Never?".
        
             | acemarke wrote:
             | Depends on what you mean here specifically :)
             | 
             | I'll agree that the Redux DevTools "skip action" and "jump
             | back to action" features are not all that commonly used in
             | practice. I _maintain_ Redux, and I don't even use them
             | that often.
             | 
             | On the other hand, the ability to see a written list of all
             | dispatched action type names is valuable by itself. So is
             | the ability to click one of the listed actions and see the
             | action contents, state diff, and final state. _That_ is
             | very powerful.
             | 
             | Beyond that... I now work at a company called Replay (
             | https://replay.io ), and we're building a true "time
             | traveling debugger" for JS. Our app is meant to help
             | simplify debugging scenarios by making it easy to record,
             | reproduce and investigate your code.
             | 
             | The basic idea of Replay: Use our special browser to make a
             | recording of your app, load the recording in our debugger,
             | and you can pause at any point in the recording. In fact,
             | you can add print statements to any line of code, and it
             | will show you what it would have printed every time that
             | line of code ran!
             | 
             | From there, you can jump to any of those print statement
             | hits, and do typical step debugging and inspection of
             | variables. So, it's the best of both worlds - you can use
             | print statements and step debugging, together, at any point
             | in time in the recording.
             | 
             | Additionally, because Replay records the browser's OS
             | calls, it captures _everything_ that happens in the page.
             | That means you can debug _any_ website or JS app, no matter
             | what framework it uses - React, Vue, Angular, Svelte,
             | jQuery, or vanilla JS.
             | 
             | I actually recently implemented a POC version of support
             | for the Redux DevTools in our Replay debugging app, so that
             | if you do record a Redux app (or Jotai, or Zustand, or
             | NgRx), you can use that same Redux DevTools UI to see the
             | action history.
             | 
             | So, yes, time travel debugging _is_ an amazingly powerful
             | concept. It's just ironic that that particular aspect of
             | Redux didn't end up getting used that much... but the Redux
             | DevTools themselves are still valuable, and Replay is
             | actually a far superior "time travel debugger" overall.
        
               | Rapzid wrote:
               | Time travel debugging is fantastic and it's a shame
               | Chakra was shelved and we have no great OSS alternatives
               | in the works at the VM level.
               | 
               | What I meant though, was that people get hung up on the
               | some ideal of how Redux is and will work for them while
               | the reality is often quite different.
        
       | DonHopkins wrote:
       | >For example with local UI state, prop drilling both data and
       | methods to update that data often becomes a probably relatively
       | quickly as things grow.
       | 
       | Can anyone parse that sentence please? Was this article written
       | by GPT-3?
        
         | andrewljohnson wrote:
         | probably->problem is a typo, and prop drilling is lingo for
         | digging down a large chain of components I think.
        
           | rpeden wrote:
           | Prop drilling in this context is just passing both state and
           | update function(s) for that state into a component via its
           | props.
        
       | hellohowareu wrote:
        
         | arcturus17 wrote:
         | > never heard of tools
         | 
         | These libs are at 4.7k, 8.9k and 17.1k stars on GitHub...
         | 
         | > discuss the deep inner workings of things
         | 
         | The article is a few thousand words and there are a few
         | interesting reflections...
         | 
         | > of things that already exist
         | 
         | The point of the article is to actually talk about "new wave
         | stuff"...
         | 
         | You are arguably incorrect on many fronts, but more
         | importantly, did you have to spend this many words being an
         | utter dick to the author?
        
       | nwh5jg56df wrote:
       | Just what the world needed
        
       | [deleted]
        
       | shroompasta wrote:
       | Zustand is a lot more popular than the comments or the article
       | implies. I see it quite heavily used amongst Netflix engineers.
       | 
       | That being said, prop drilling was made more of an issue than it
       | really is, especially considering the boilerplate needed for
       | state management libraries like Redux.
       | 
       | But if there does need to be a global store, I usually reach for
       | zustand as the API is probably the easiest out of the ones
       | mentioned.
        
       | UmbertoNoEco wrote:
       | Or you just manage state in the server. With
       | https://inertiajs.com/ you can even afford to not to declare an
       | API and still manage the state back there.
        
         | ramesh31 wrote:
         | >Or you just manage state in the server. With
         | https://inertiajs.com/ you can even afford to not to declare an
         | API and still manage the state back there.
         | 
         | Then we can party like it's 1999!
        
           | UmbertoNoEco wrote:
           | As God has always intended
        
       | ramesh31 wrote:
       | I'm just tired of the redundant reinvention of new "terms" for
       | literally everything in JS. I don't want to know what an "atom"
       | or a "proxy" or a "thunk" is. These are meaningless abstractions
       | that simplify down to a store and a callback. Stop inventing
       | terms to make yourself feel smart.
        
         | acemarke wrote:
         | FWIW, the term "thunk" is a long-standing CS term that long
         | predates Redux [0] [1] [2].
         | 
         | In fact, my first job back in 2008 involved a C++-based
         | emulator/VM framework, and the devs used "thunk" to refer to
         | jumping from the original program binary out to
         | altered/replacement code written as C++ to add additional
         | behavior or replace functionality.
         | 
         | "Proxy" is also a long-standing term as well that describes
         | wrapping or replacing functionality of a system, which is why
         | it's used for HTTP servers and why it got used for a new JS
         | capability in the ES2015 language spec.
         | 
         | [0] https://en.wikipedia.org/wiki/Thunk
         | 
         | [1] https://stackoverflow.com/questions/2641489/what-is-a-thunk
         | 
         | [2]
         | https://devblogs.microsoft.com/oldnewthing/20081020-00/?p=20...
        
           | mechanicum wrote:
           | And "atom" comes from Clojure's atomically updatable state.
           | [0] [1]
           | 
           | [0] https://clojure.org/reference/atoms
           | 
           | [1] https://news.ycombinator.com/item?id=23183385
        
       | petilon wrote:
       | The "state management problem" appears to be an invention of
       | React. This didn't use to be a problem with MVC. The state lives
       | on the server. When state changes it should be persisted on the
       | server immediately (in case the user unexpectedly closes the
       | browser). On the client all you need is a cache.
       | 
       | With MVC, each page is more or less independent. Each page gets
       | the data it needs from the server (through a client-side cache),
       | then updates the server when something changes. No "state
       | management problem". In contrast, ReactRouter sees the entire
       | application as one humungous component. Therein lies the problem.
        
         | bcherny wrote:
         | Your causation is reversed.
         | 
         | People demanded more interactive web apps, which led to more
         | stateful UI, which led to React.
         | 
         | In the case of Facebook, the motivating app was Ads Manager --
         | an enormous, highly interactive single page app for
         | advertisers. You couldn't build something like it with HTML +
         | server endpoints; in the pre-web days, apps with this kind of
         | complexity would be desktop apps.
         | 
         | Google Docs, Google Sheets, Maps, Spotify -- these all have a
         | huge amount of client-side state. You can't represent that
         | state on the server without making the UI unusably slow. The
         | need to build these kinds of apps in a portable way led to
         | complex state, which React tried to address (so did Angular,
         | Ember, Backbone, etc.).
        
           | petilon wrote:
           | > _You can't represent that state on the server without
           | making the UI unusably slow._
           | 
           | And that's why you use a client-side cache.
        
             | xeromal wrote:
             | And once that cache is sufficiently complex, it's just a
             | state store like redux.
        
               | petilon wrote:
               | Cache stays simple even for large applications. It never
               | gets "sufficiently complex".
        
               | xeromal wrote:
               | Theoretically, but not practically.
        
               | ekidd wrote:
               | As the joke goes, there are two hard problems in
               | software:
               | 
               | 1. Naming things.
               | 
               | 2. Cache invalidation.
               | 
               | 3. Off-by-one errors.
               | 
               | Caches are tricky beasts. First, you need to update them
               | when the server-side state changes (for example, two
               | people editing a single Google doc). Second, writing
               | state changes to the server and waiting for confirmation
               | is too slow for many kinds of interactions. In these
               | cases, it's typical to optimistically write local changes
               | to a local store, and then try to sync those changes with
               | server asynchronously. But if synchronization fails, then
               | the client needs to report that.
               | 
               | And finally, there's the problem of partially loaded
               | state, where the rest is loaded asynchronously on demand.
               | That _should_ be simple, but without some kind of
               | framework, it also tends to have lots of subtle state-
               | machine and null-reference bugs.
               | 
               | So, no, cache does not always stay simple in large
               | applications. (Unless the app is read only, and you're OK
               | showing stale data.)
        
               | petilon wrote:
               | If you are building Google doc editor by all means,
               | design a complex state management system, it is worth it.
               | But then don't bring that complexity into typical
               | business applications.
        
             | kaoD wrote:
             | And that's why you need state management. Cache is state.
        
         | pweissbrod wrote:
         | I used to think the same thing until I considered that single
         | page app development is really just a reinvention of thick
         | clients.
         | 
         | When you look at an SPA as a thick client state management is a
         | natural thing as it was in Java swing and WPF and Windows forms
         | and other stacks beyond my knowledge
        
         | jitl wrote:
         | I came to understand MVC (model-view-controller) from writing
         | Objective-C desktop software (https://developer.apple.com/libra
         | ry/archive/documentation/Ge...).
         | 
         | The "M" in that MVC is "Model", which is the same idea as
         | "state management". It's an object that stores state and
         | notifies listeners when it changes. You can think of these
         | libraries as ways to implement the "Model" concern in the
         | application.
         | 
         | But from your use of MVC, I think you are referring to server-
         | side MVC, where the "V" is a rendered HTML template? I'm not
         | sure how to square the desktop software version of MVC with
         | your assertion that state should only exist on the server.
         | 
         | My Cocoa desktop apps ran fine 10 years ago without a server.
         | The React application I work on today has many bits of local
         | state it needs to track like "what is selected?", "how wide is
         | the sidebar?", and "should this menu be open?". I don't think
         | the server should be involved in such matters.
        
           | petilon wrote:
           | I am talking about client-side MVC. Models should be POJO
           | [1], no library needed.
           | 
           | [1] https://en.wikipedia.org/wiki/Plain_old_Java_object
        
         | s-lambert wrote:
         | React wasn't the first complex frontend framework, arguably
         | people were having these state management problems ever since
         | people started doing more stuff like jQuery UI. It's not tied
         | to SPAs either, you can have state management problems for a
         | single URL as long as it has any form of state change (like
         | opening a modal).
        
         | wilde wrote:
         | This is true until your customers complain that your UI is
         | super slow. You realize they're trying to use your app from a
         | cell phone with poor service. So you have the genius idea to
         | add optimistic updates in JS. Now you have all the problems
         | from the article since you need to update all the components
         | everywhere on screen that share state.
        
           | pcthrowaway wrote:
           | > Now you have all the problems from the article since you
           | need to update all the components everywhere on screen that
           | share state.
           | 
           | If anyone can field a question about react-query here, this
           | seems like one of the exact problems I thought it solved when
           | I started using it.
           | 
           | I _do_ enjoy using it, but requesting the same data with the
           | same key+queryFn from multiple, unrelated components still
           | generates regular requests at the configured interval (even
           | if I 'd want/expect those components to share the response
           | and only make that request at whatever rate satisfies the
           | shortest configured interval)
           | 
           | Am I missing something in my configuration here?
        
             | frosted-flakes wrote:
             | React-Query is very aggressive about refreshing the cache
             | by default, including whenever the browser receives focus,
             | on a set schedule, and automatically retrying failed
             | queries multiple times, these can all be disabled. If any
             | queries use the same key they _should_ share data, but I
             | haven 't experimented with it enough to learn all its
             | intricacies.
        
           | petilon wrote:
           | All you need is a client-side cache.
        
             | wilde wrote:
             | How do changes to that cache get displayed? Your cache
             | emits events that each UI element has to listen to?
             | Congrats you're using redux!
             | 
             | (It would perhaps be more accurate to say that React folks
             | had to reinvent these patterns, but the problems were
             | definitely present in the postback era)
        
               | petilon wrote:
               | > _Your cache emits events that each UI element has to
               | listen to?_
               | 
               | It doesn't. How often do you have the same information
               | redundantly displayed in multiple places, on the same
               | screen?
        
               | ativzzz wrote:
               | It's not even necessarily the same information, but small
               | pieces of one bigger piece that need to be updated once
               | some of the other smaller pieces change
        
               | wilde wrote:
               | Yeah this. The classic is unread state in a mail app.
               | Unread state is usually displayed both as bold state per
               | message in a message list, and as a count in the folder
               | list. These need to stay in sync as the user reads mail
               | (and sometimes marks read state explicitly). Two views of
               | the same underlying state.
        
               | petilon wrote:
               | Sure, you can come up with an example where some
               | synchronization is needed, but how often do you have this
               | requirement? In most apps it is rare, which means that it
               | can be solved by using a couple of extra lines of code to
               | update the screen, as opposed to adopting a complex state
               | management system with events firing and so on. Simple
               | solutions for simple problems.
        
             | lhnz wrote:
             | That is exactly what the React state management solutions
             | all are...
        
       | monkaiju wrote:
       | Really surprised there was no mention on MobX. I've used int for
       | lots of projects and loved it.
        
       | glenjamin wrote:
       | I find it very disappointing that this article does not attempt
       | to draw a distinction between state management for complex local
       | states (imagine an image editor), or state management for
       | fetching and updating data via APIs
       | 
       | I think the shape of solution needed for these two problems are
       | quite different.
        
         | lloydatkinson wrote:
         | Same here. Local state and server state are not always the
         | same. I see a lot of people saying how replacing redux with
         | react query worked well and that's great but there's definitely
         | times when you have a lot of state in a client side heavy SPA.
         | The distinction should really be highlighted more.
        
         | gloryjulio wrote:
         | Exactly. I think people who complains about complexity of some
         | of the tools, just have not worked on the complex webapp(not
         | the webpage) before. Unfortunately these 2 always get
         | conflated.
        
       | ashishb wrote:
       | Afaik, Vue ships with batteries included.
        
       | fabian2k wrote:
       | For me the issue of state management mostly went away after
       | starting to use React Query. It turned out that the most
       | problematic state was server-side state for me, which is handled
       | very well by libraries built for that purpose.
       | 
       | The state that remains is often simple enough that plain old
       | React state management with useState/useReducer is sufficient. A
       | lot of state can be local, and local state is easy to handle with
       | the built-in tools of React. And global state is only really an
       | issue if it changes often. For mostly static state like
       | information about the current user, theme or UI settings and
       | similar kinds of state using React Context works perfectly fine.
       | 
       | Of course this depends heavily on the kind of web application you
       | write, if your application is closer to Photoshop in the browser
       | than a simple CRUD app you probably can make good use of more
       | complex state management libraries.
        
         | bernawil wrote:
         | The state that remains is often simple enough that plain old
         | React state management with useState/useReducer is sufficient
         | 
         | hah this is an understatement. For hooks, the React runtime
         | already does a ton of non-standard-js things under the hood.
         | useState gives a method to update and "subscribes" a component
         | to updates on the hook's value. Put that code in a custom hook,
         | export it and you re-invented Redux. In fact, exporting a
         | single big useReducer for all your state gives you something
         | almost identical to old style Redux.
        
           | acemarke wrote:
           | FWIW, there _are_ a number of technical and conceptual
           | differences between Context+`useReducer` and Redux. I wrote
           | an extensive post describing those differences and potential
           | use cases for each:
           | 
           | https://blog.isquaredsoftware.com/2021/01/context-redux-
           | diff...
        
         | ggregoire wrote:
         | Exact same experience here. We were using Redux to manage
         | server-side data and switching to React Query massively
         | simplified everything. It appears that managing server-side
         | data in an efficient way is an insanely complicated topic and
         | React Query just solved everything about it that I can think
         | of.
        
           | acemarke wrote:
           | Yeah, both the React Query and Redux maintainers agree that
           | you shouldn't be writing data fetching and caching logic
           | yourself. That's why we recently added a new "RTK Query" data
           | fetching and caching API to Redux Toolkit, so that if you're
           | using Redux it handles that work for you:
           | 
           | - https://redux.js.org/tutorials/essentials/part-7-rtk-
           | query-b...
           | 
           | - https://redux-toolkit.js.org/rtk-query/overview
           | 
           | and if you're just using React, definitely look at React
           | Query.
        
             | ggregoire wrote:
             | Yes we chose Redux 6 years ago for data fetching and
             | caching when there wasn't as many alternatives as today!
        
               | acemarke wrote:
               | Hah, yeah, the ecosystem landscape has definitely changed
               | over the last few years :)
        
         | likortera wrote:
         | I've only used SWR. How does it compare? I
        
           | krall12 wrote:
           | SWR does basically the same core thing (query, cache and
           | mutation help) with less features.
        
         | cercatrova wrote:
         | Redux now has its own query solution as well, it's pretty
         | useful [0].
         | 
         | [0] https://redux-toolkit.js.org/rtk-query/overview
        
         | kasane wrote:
         | This matches my experience as well. Additionally, React Query
         | has support for features like retries and caching.
        
         | cehrlich wrote:
         | Agree completely, React Query has made it so much easier to
         | build any kind of app that deals with server state, stuff that
         | would have been extremely challenging to write in the past is
         | now just a couple of lines and works better than before.
         | 
         | I personally like using Jotai (if I just want a better version
         | of React Context) or Zustand (if I need a bit more than that)
         | for "client state" alongside React Query, but I've also built
         | projects where I didn't need a client state management solution
         | at all.
        
         | celim307 wrote:
         | React query is one of the highest quality react libraries I've
         | ever used
        
       | weeksie wrote:
       | The problem with redux is that it's a simple, extremely powerful
       | tool for creating a CQRS architecture on the front end but very
       | few people treat it that way. Instead they bolt on things like
       | rtk and add yet another layer of abstraction over their project.
       | In those cases it's almost always better to just use something
       | small and simple like Zustand, which the article called out.
       | 
       | For bigger projects, custom middleware is where the magic is. If
       | you don't understand redux well enough to write your own
       | middleware (it's not very complex, it's just under documented for
       | some reason) then it's better to use one of the other, simpler
       | abstractions instead of adding one abstraction (redux) then
       | piling on more abstractions to make it usable.
        
         | acemarke wrote:
         | Pretty sure you and I debated "vanilla Redux" vs RTK in a
         | thread a couple years ago, but I'll link my most recent
         | explanations of why RTK is the right way to use Redux today:
         | 
         | - https://redux.js.org/introduction/why-rtk-is-redux-today
         | 
         | - https://blog.isquaredsoftware.com/2022/06/presentations-
         | mode...
         | 
         | Also, note that RTK has a new "listener" middleware that
         | simplifies the process of "run this code when some action is
         | dispatched". You can certainly still write a completely custom
         | middleware if you _want_ to, but the listener middleware
         | handles that work for you.
        
           | weeksie wrote:
           | I get it, you're _really_ invested in RTK but man, I just
           | find it to be the right answer to the wrong question.
           | 
           | Since we last talked I have worked on projects where rtk was
           | used because the devs didn't really grok redux and so far
           | that's the best use case I've run across. That said, now when
           | I run across situations like that I tend to guide clients to
           | simpler state management solutions instead of piling on
           | another layer of abstraction.
        
       | civilized wrote:
       | Curious layman here (no web dev experience). I thought the main
       | selling point of reactive programming was that it abstracted away
       | the need to manage state. What problems, then, does a state
       | management library solve in a reactive framework?
        
         | chrisco255 wrote:
         | As we know from computer science, there are two difficult
         | problems: naming things and cache invalidation. State
         | management is inherently difficult in web apps (I think it's
         | inherently difficult for any complex application). They are
         | effectively distributed systems with local caches and remote
         | server data that need to be synced correctly in order to manage
         | a user application at scale. That all has to align with how the
         | presentation logic is built. It has to deal with the
         | constraints of the web platform, etc.
        
         | tadfisher wrote:
         | Reactive programming provides the capability to _react_ to
         | changes in state. You still need to hold that state somewhere,
         | mutate the state from your reactive code, and control the
         | lifetime /scope of that state. Managing state becomes _more_ of
         | a concern with reactive programming, but it also becomes very
         | explicit; this is something that traditional MVC approaches try
         | to hide, to the detriment of anyone trying to understand the
         | data path of your application.
        
         | ksbrooksjr wrote:
         | Most state management libraries help you deal with the problem
         | of sharing state between multiple components. In modern React,
         | most components are just functions, so this boils down to
         | passing state through deep call stacks.
         | 
         | If you have a component A, which renders component B, which in
         | turn renders component C, without a state management library
         | you'd have to pass state from A to B to C (this is often called
         | prop drilling). The longer the call stack, the more irritating
         | this becomes.
         | 
         | State management libraries allow component C and component A to
         | modify, and subscribe to a shared state store. Redux et al. are
         | effectively the reactive version of global variables.
        
       | bayesian_horse wrote:
       | I didn't get the memo apparently. I still think
       | Redux+Thunks+Selectors+Sagas is great and that combination solves
       | all my problems. Boilerplate isn't negligible but relatively
       | tame. There's a straightforward way how to model state, and I
       | don't have to put too much logic (especially async) into
       | components.
       | 
       | But that's just me...
        
         | chrisco255 wrote:
         | Yeah I've always thought the complaints about boilerplate were
         | misguided. Whatever the cost in boilerplate implementation was
         | more than made up for by having predictable, deterministic UI
         | output. That being said, I think hooks did open up the state
         | management design space quite a bit and classic redux style
         | state management doesn't quite line up with it. Still totally
         | valid as an architecture, though, in my opinion.
        
       | ezekiel11 wrote:
       | I ditched React/Redux for Vue 3 & Pinia and my god, what a world
       | of a difference. Everything is intuitive and I am not googling
       | days to fix tooling issues, or having to do it the React/Redux
       | way which was honestly overly engineered and non-productive.
       | 
       | Frontend shouldn't be complicated and we've been lied to, you are
       | not Facebook, you don't have billions to throw at engineering,
       | you must pick the path of list resistance
        
         | MentallyRetired wrote:
         | Bingo. React is great for insane amounts of fine grained
         | control.
         | 
         | But I don't want that. I want to build interfaces and not
         | "manually shift" my local state management.
        
         | 42e6e8c8-f7b8-4 wrote:
         | I believe the worst part is redux. React is mostly reasonable.
         | Redux is massive boilerplate.
        
       | kizer wrote:
       | "Prop drilling". So many buzzwords. SSR, Hydration, Tree shaking,
       | Hot module reload.
       | 
       | How has web development gotten here? It just seems to have
       | evolved so much needless complexity to me.
       | 
       | Don't forget about web components! Integrated into the platform.
        
         | cercatrova wrote:
         | I've often found those that complain about these buzzwords are
         | the people who do not actually do any frontend engineering.
         | There are buzzwords in every language and every library. It's
         | not an indictment of complexity (which exists outside of any
         | one language or library), it is simply the terms of the trade
         | of that particular technology.
        
           | kizer wrote:
           | I don't know why but front-end terminology always makes me
           | cringe. I know it's useful jargon. I don't know why I have a
           | visceral distaste for them. Maybe because it feels like
           | taking a small, simple thing and making it seem like it's
           | something more.
           | 
           | But you're right. I haven't done much front-end at large
           | scales. Only at one employer for a short while.
        
             | cercatrova wrote:
             | > _Maybe because it feels like taking a small, simple thing
             | and making it seem like it 's something more._
             | 
             | Perhaps it makes more sense to treat frontend engineering
             | as thick client desktop development of yore. Websites are
             | no longer small, simple things, they are now the primary
             | apps that many people use (through the broswer and
             | especially through Electron), so there needs to be
             | sufficient tooling around managing that complexity.
        
               | kizer wrote:
               | You're right. That makes sense. I've been out of web dev
               | for about 4 years so I'm just reactionary now I guess.
        
             | dboreham wrote:
             | You're experiencing the cognitive dissonance from trying to
             | understand unnecessary complexity.
        
       | nikodunk wrote:
       | For anyone struggling with the complexity and boilerplate of
       | Redux, at my day job we added Redux Toolkit (the newly
       | recommended add-on by the Redux project itself!) and it solves
       | most of the verbosity issues! We use it to share all our state
       | logic over mobile and web and it works excellently now. I'd
       | actually recommend Redux w/ Redux-Toolkit, for the first time
       | ever.
        
         | phreack wrote:
         | There's a library called rematch that's been implementing most
         | of these ideas for a long time, but sadly it didn't get popular
         | enough and it seems to be somewhat lacking maintenance. It was
         | such a pleasure to use (in comparison) that I just can't
         | believe how people ever work with those massive switch
         | statements.
        
           | acemarke wrote:
           | One of the reasons we created Redux Toolkit was to eliminate
           | the need to write those switch statements :) (also action
           | type strings, action creators, object spreads, having to
           | split logic for one feature across multiple files, and all
           | the other "boilerplate" concerns that users rightfully
           | complained about over the years.)
           | 
           | - https://redux.js.org/tutorials/fundamentals/part-8-modern-
           | re...
           | 
           | - https://redux.js.org/tutorials/essentials/part-2-app-
           | structu...
           | 
           | - https://blog.isquaredsoftware.com/2022/06/presentations-
           | mode...
        
       | sebmellen wrote:
       | For anyone who has not had the pleasure of working with these
       | simpler "atom-based" state management libraries, I would implore
       | you to try Jotai (https://jotai.org/), which is mentioned in the
       | article.
       | 
       | Jotai's atomic model and ease of use has made writing complex
       | React applications far more joyful for me.
        
       | LAC-Tech wrote:
       | I think the obsession the react space has with "state management"
       | is a by-product of how incredibly convoluted reacts rendering is.
       | 
       | The other reason is a lack of exposure to how other technologies
       | for GUIs have handled state for decades.
       | 
       | Maybe look outside the react bubble and see how many of these
       | "issues" just disappear when you stop acting like react is some
       | fundamental particle of the web.
        
       | wereHamster wrote:
       | Weird that XState was not mentioned.
        
         | aarpmcgee wrote:
         | Agree. I am working on a side-project and using XState for
         | local state management, and Jotai (with Immer) to send that
         | state to various components in my app. It is working really
         | well and mitigating unnecessary rerenders.
         | 
         | More moving parts than I might like, but they play together
         | nicely and I haven't hit a single wall yet.
        
       | johtso wrote:
       | For me using xstate was a game changer. Pulling logic out into a
       | state machine gives you so much clarity over your application
       | logic. Also nice to have your business logic defined with
       | something that is framework agnostic.
        
         | ramesh31 wrote:
         | Once you see the light of state machine based UI's, it's
         | immediately obvious and you never want to go back. The problem
         | comes in convincing others to deal with the boilerplate. It's
         | worth it, but it never really sinks in until you use it.
        
         | CitizenKane wrote:
         | I've had this same experience as well! Wrapping your head
         | around the concepts at first can be a little tedious but it
         | makes application logic and behavior far more predictable. The
         | ability to visualize them is the icing on the cake as well and
         | is a nice extra tool that eliminates the need for arrows and
         | boxes in a sketchbook or a Google Drawing.
        
         | nine_k wrote:
         | Yes! An explicit state machine is my desire for the UI
         | development since the Delphi days of 1990s. It makes things so
         | much more observable and sane.
         | 
         | Redux nudges you to build that state machine by hand, in the
         | form of the reducers folder, around the centralized state.
         | While elucidating, it's still a lot of boilerplate (which you
         | can sort of factor out), and it's still not one clearly laid
         | out entity.
        
           | acemarke wrote:
           | Fun fact: one of the XState devs did a proof-of-concept
           | showing how to use XState state machines as Redux reducers
           | and integrate the side effects handling as a middleware:
           | 
           | https://github.com/mattpocock/redux-xstate-poc
           | 
           | We'd like to work together to turn that into a more official
           | integration sometime soon.
        
             | aarpmcgee wrote:
             | This looks excellent. I see a lot of potential in the idea
             | of combining the strengths of RTK(+Query) and XState. Thank
             | you for sharing!
        
               | acemarke wrote:
               | Yeah, if you've got any particular use cases or ideas for
               | how you'd like to use them, please put up a discussion
               | thread in the RTK repo and let's talk!
        
       | todd3834 wrote:
       | I've been using redux ever since it came out and a home rolled
       | flux architecture before that. I gotta say I've been using
       | zustand lately and it feels so effortless compared to other
       | solutions. I couldn't imagine going back to redux. Although redux
       | slices feel a little bit closer.
        
       | Waterluvian wrote:
       | I used Redux and loved it until I moved to typescript. Then there
       | was a terrible amount of boilerplate and magic. So I wrote my own
       | 75 line alternative that does a bare minimum. It's basically just
       | a useContext wrapper. And I haven't looked back since.
       | 
       | This is for pure client side stuff, of course.
        
         | acemarke wrote:
         | Hi, I'm a Redux maintainer. FWIW, we specifically designed our
         | official Redux Toolkit package to not only eliminate the
         | general concerns about Redux "boilerplate" [0] [1], but also
         | work great with TS. With our recommended RTK+TS usage patterns,
         | a typical "slice reducer" file only needs to define a type for
         | the reducer's state, and then define a case reducer as `(state,
         | action: PayloadAction<MyData>`) [2], and that's it.
         | 
         | We've put a _lot_ of work into making sure that our library TS
         | types minimize the amount of types that you have to write in
         | your own app code.
         | 
         | Also, one of the reasons we now teach the React-Redux hooks API
         | as default is that it's drastically easier to use the hooks
         | with TS than the legacy `connect` API.
         | 
         | If you haven't had a chance to see what "modern Redux" looks
         | like, I'd suggest going through our docs tutorials to see how
         | we want people to learn and use Redux today [3]
         | 
         | [0] https://redux.js.org/introduction/why-rtk-is-redux-today
         | 
         | [1] https://blog.isquaredsoftware.com/2022/06/presentations-
         | mode...
         | 
         | [2] https://redux.js.org/tutorials/typescript-quick-start
         | 
         | [3] https://redux.js.org/tutorials/index
        
           | monroewalker wrote:
           | RTK is what made redux usable for me. I can't imagine using
           | redux without it. ^ Mark is also very active and responsive
           | in the Reactiflux discord and has directly helped me and
           | countless others clear any hurdles with its use
        
           | Waterluvian wrote:
           | Hooks made react and redux far less ridiculous. Class based
           | react and redux wss maddening.
           | 
           | I'll poke again but last time I tried I couldn't avoid
           | Typesafe Actions library.
        
             | acemarke wrote:
             | Yeah, _please_ don't use `typesafe-actions` :)
             | 
             | It may have had some value before RTK came out, but a lot
             | of the opinions and approaches shown in its docs lead you
             | to write _wayyyy_ too much code. For example, we
             | specifically recommend _against_ writing TS unions for
             | action object types [0].
             | 
             | RTK completely obsoletes `typesafe-actions`, and the TS
             | usage patterns that we teach today should result in a
             | pretty minimal set of types that you need to write in your
             | own code.
             | 
             | For a small example see the RTK+TS template for Create-
             | React-App [1]. If you want to see what a real app codebase
             | can look like, the client app for my day job at Replay.io
             | is OSS [2]. It's admittedly a somewhat messy codebase due
             | to its long evolution and legacy (started as the FF
             | DevTools codebase, copy-pasted, and we've been slowly
             | migrating to RTK+TS and modernizing it), but files like [3]
             | show how I would write a real slice reducer with RTK+TS.
             | 
             | [0] https://redux.js.org/usage/usage-with-typescript#avoid-
             | actio...
             | 
             | [1] https://github.com/reduxjs/cra-template-redux-
             | typescript
             | 
             | [2] https://github.com/replayio/devtools
             | 
             | [3] https://github.com/replayio/devtools/blob/454804188d339
             | 00a26...
        
         | cercatrova wrote:
         | Context and Redux are somewhat different tools and context
         | doesn't necessarily solve the same problems as Redux. This
         | article by the maintainer of Redux (acemarke) goes over why
         | (looks like he replied to you as well) [0]. Have you tried
         | Redux Toolkit as well? It cleans up a lot of the complexity of
         | Redux and works well with TypeScript [1].
         | 
         | [0] https://blog.isquaredsoftware.com/2021/01/context-redux-
         | diff...
         | 
         | [1] https://redux-toolkit.js.org/
        
           | Waterluvian wrote:
           | Basically I'm not saying redux is bad. Just that after years
           | of using it for production software I concluded it's still
           | overkill for my needs.
           | 
           | IIRC Redux is also just an abstraction on top of Context.
           | Fundamentally it gives you pseudo-global access to
           | application state by being able to interact with it anywhere
           | in the component tree below the context manager.
        
             | acemarke wrote:
             | > Redux is also just an abstraction on top of Context
             | 
             | No, this is a very common but incorrect misunderstanding of
             | how Redux works.
             | 
             | It's true that React-Redux does use context internally...
             | but only to pass down the Redux store instance, _not_ the
             | current state value.
             | 
             | Also, because Redux itself is separate from React, there's
             | a lot of things you can do with it that are completely
             | different than what Context does. _One_ bit of overlap is
             | that both can be used to access state across the component
             | tree, but Redux does much more than that.
             | 
             | See my post here for more details:
             | 
             | https://blog.isquaredsoftware.com/2021/01/context-redux-
             | diff...
        
       | aerovistae wrote:
       | I'd like to share my approach to React state management, because
       | after a decent amount of industry experience I've stumbled onto a
       | solution I find to be very excellent.
       | 
       | Firstly, I use the open source library Pullstate[1], which I find
       | to be as effective as any alternative but _far, far_ simpler to
       | understand and use.
       | 
       | All my components are functional components. For any state that
       | _only_ that component needs, of course I simply use the useState
       | hook.
       | 
       | When things need to be shared among multiple components, I create
       | a Pullstate store - for instance, for an app I'm working on now I
       | have a UiStateStore like so:                   type UiStateStore
       | = {           isSidebarOpen: boolean;           // etc         };
       | export const uiStateStore = new Store<UiStateStore>({
       | isSidebarOpen: false,         });
       | 
       | Then, in the components that need to know if the sidebar is open,
       | I import this store and use its state hook _the exact same as the
       | normal useState hook_, like so:                   const
       | isSidebarOpen = uiStateStore.useState(s => s.isSidebarOpen);
       | 
       | You simply pick which properties you need off the state object
       | ("s"). When you open the sidebar, you simply update the store
       | like so:                   onClick={() => { uiStateStore.update(s
       | => { s.isSidebarOpen = true; }) }}
       | 
       | And automatically, any components using uiStateStore.useState and
       | watching the isSidebarOpen property will get updated, exactly the
       | same as the normal useState hook - just shared.
       | 
       | It's so dead simple and has made complex app-building so much
       | easier for me.
       | 
       | By comparison, Redux in my experience has a harder learning curve
       | with a lot of unnecessary pieces and boilerplate - it seems crazy
       | to me that people think it's a great solution and it feels like
       | people have convinced themselves all those pieces are
       | "necessary", where in my experience they are anything but.
       | 
       | The one caveat is that if I have a component with many handlers,
       | e.g. onClick, onMouseMove, onContextMenu, onMouseLeave, etc (and
       | in some cases I do), components can get bloated. I haven't found
       | a fix to that yet. But that's more an inherent issue with react
       | than anything to do with state management.
       | 
       | [1] https://github.com/lostpebble/pullstate
        
         | have_faith wrote:
         | You might like the atomic state management libraries mentioned
         | in the article, they simplify things to another level because
         | they sort of remove the concept of a store entirely. For
         | example in Recoil I would do this:                   export
         | const isSidebarOpenAtom = atom({key: 'isSidebarOpen', default:
         | false});
         | 
         | And in the component: (it mimics useState)
         | const [isSidebarOpen, setIsSidebarOpen] =
         | useRecoilState(isSidebarOpenAtom);
         | 
         | and later...                   setIsSidebarOpen(true)
         | 
         | Recoil will then re-render any component that relies on
         | isSidebarOpen.
         | 
         | The only real boilerplate is having to specify keys for each
         | atom, which I find a small price to pay for such simple global
         | state.
        
         | etimberg wrote:
         | In some ways this feels a lot like http://alt.js.org/
        
       | doodlesdev wrote:
       | I'm pretty sad this is the point we are at with React frontend
       | development, the library is becoming much larger than it's
       | original scope and it's getting bloated while not solving the
       | essential problems that happen. In my opinion the best solution
       | we have right now for frontend JS development is to not use JS or
       | JSX at all and instead use a DSL such as Svelte, this way the
       | compiler abstracts all complication and there is no application
       | bundle size bloat. Obviously we have Preact (which solves react-
       | dom bloat), MobX (which solves state management), etc. which are
       | all great tools but the problem is that every tech stack is
       | different and the more the core technology can do without getting
       | more bloated the easier it is to introduce new developers to a
       | codebase and keep up with changes.
        
         | sachinraja wrote:
         | How is React not solving essential problems? Suspense solves a
         | pretty essential issue. Also Svelte can quickly increase in
         | bundle size and if you have enough components, it can become
         | bigger than the equivalent in other frameworks:
         | https://github.com/yyx990803/vue-svelte-size-analysis.
        
           | doodlesdev wrote:
           | The first version of React was released on 2013, it took
           | almost 10 years for Suspense to exist (we _just_ got it now
           | with React 18), that's what I'm talking about. Even
           | functional components and hooks took a lot of time from them
           | get and implement the idea after they tried to use ES classes
           | and made everything much harder to manage. Context also isn't
           | perfect, I like it but the redraw performance is not amazing
           | and doesn't scale at all to bigger applications.
           | 
           | > https://github.com/yyx990803/vue-svelte-size-analysis
           | 
           | This is an interesting comparison I haven't seen before, I
           | wonder if it's true for a complete application using some lib
           | for state management, routing, etc. and if this isn't just a
           | kind of cherry picked example. Thanks for showing this
           | though.
        
         | nine_k wrote:
         | Svelte does wonders to code size, indeed.
         | 
         | But does it solve the problem of growing state which never gets
         | GC'd when components which used to use it are gone? Does it
         | solve the problem of only redrawing the required minimum
         | (beside the normal VDOM approach)?
         | 
         | I'm asking as someone not knowledgeable enough about Svelte.
        
           | doodlesdev wrote:
           | > Does it solve the problem of only redrawing the required
           | minimum (beside the normal VDOM approach)?
           | 
           | Yes, in fact I think it's actually pretty hard _not_ to
           | redraw the bare minimum LOL. If you want to know more about
           | Svelte (even if you're not looking to develop with it) I
           | HIGHLY recommend listening to this presentation called
           | "Rethinking reactivity" by Rich Harris (the creator)
           | https://youtu.be/AdNJ3fydeao
           | 
           | > But does it solve the problem of growing state which never
           | gets GC'd when components which used to use it are gone?
           | 
           | I think the answer to the question is yes. Although the
           | problem I'm speaking mostly about state management is the
           | source of truth problem. Svelte provides a global store to
           | store data, and data stored on local components are just
           | _variables_ (no useState or hooks or anything complicated)
           | where the Svelte compiler handles everything.
           | 
           | Something else I'm really eyeing right now is SolidJS which
           | takes a very similar approach to Svelte (compiler instead of
           | library) for frontend development but provides an API that's
           | very familiar to React developers so there's not much of a
           | learning curve (although Svelte has a very easy learning
           | curve too).
        
         | rglover wrote:
         | This is why I'm building Joystick:
         | https://github.com/cheatcode/joystick.
         | 
         | It riffs on the old, simple APIs of React but uses pure HTML,
         | CSS, and JavaScript w/o any trickery (I'm also hardcore about
         | _not_ changing the component API so WYSIWYG).
         | 
         | The bonus is that it's a part of a full-stack framework (the UI
         | framework has a Node.js counterpart), so wiring up a full app
         | is near-effortless.
        
           | doodlesdev wrote:
           | Looks pretty interesting, I'm always kind of bothered about
           | the lack of (true) full-stack frameworks for the NodeJS
           | ecosystem that handles accounts, database, frontend, API,
           | etc. like we have for Python with Django or C# with .NET.
        
             | rglover wrote:
             | Thanks. Likewise, and that's the driving motivation here.
        
       | jeroenhd wrote:
       | I've used Redux but I've never heard of any of these
       | alternatives. I have no doubt they're popular, but what is it
       | about frontend that makes everyone reinvent the wheel every five
       | years? Everything from the tooling to the tiny details somehow
       | expires and gets recreated in a similar-but-not-similar-enough
       | way that keeps the ecosystem in a constant state of flux.
       | 
       | Is it the lack of platform API support? Is it the community
       | trying to make everyone a library developer? What's wrong with
       | frontend?
        
         | rglover wrote:
         | A few different problems...
         | 
         | "Necessity is the mother of invention" comes to play here. The
         | reality is that the community _hypes_ certain tools, but in
         | practice, they tend to have gotchas buried far beyond the
         | surface level demos and documentation. The problem with that is
         | that you only figure that out after committing to those tools
         | and using them. This leads to tool abandonment, or in some
         | cases, developers taking a swing at their own version. What
         | they come up with is more often than not a rehash of the old
         | ideas but lacking any  "why" or long-term vision.
         | 
         | The other one is employability by obscurity. An old grifter
         | trick is to make something far more complicated than it needs
         | to be as a means to guarantee employment (both on the tool
         | developer side _and_ the end-user side). For the tool
         | developer, the more they can twist and turn their tool
         | (introducing novelty and potentially confusion), the more
         | sought-after their services will be. For the end-developer,
         | they can hold a  "monopoly on intelligence" and become
         | difficult to replace in a company because they're the only one
         | that understands that thing. Couple this with the conference
         | talk circuit where you see the same people constantly pitching
         | some new-fangled widget every year and you realize the goal
         | isn't to solve the problem, it's to get paid to _look like_ you
         | 're solving the problem.
         | 
         | Another problem is inexperience. A developer might have just
         | enough experience to feel confident at the code-level, but they
         | lack the practical experience to let them know why a certain
         | pattern is incorrect. Assuming that they never get that
         | practical experience, they will continue to iterate the tool
         | into an utter mess or deprecation.
        
         | gernb wrote:
         | I considered something like this last night as I stay up to 6am
         | working on a new UI library. My conclusion was in part because
         | it's easy. The goal is well defined. I got the first widget
         | working thought I'd call it a day (a night) but then it was so
         | much fun to just implement the next widget mostly because very
         | little design iteration is needed. The problem being solved is
         | well known so each thing to tick off my UI lib was only a few
         | minutes. Next thing I know it's 6am.
         | 
         | I think the same is true of 3D libraries. The real work of
         | making an app that does 3D is not the 3D engine, it's
         | everything else (UX or GameDev). The 3D part has well known
         | goals and solutions so it feels like you're making a ton of
         | progress, ie, it's fun to make. Much easier than deciding
         | harder things like which features your app should have and how
         | they should work.
        
           | sandinmyjoints wrote:
           | Great insight, this makes a lot of sense. And on top of this,
           | it SEEMS impressive. You made a whole framework! Wow! Plus
           | there's a chance of widespread adoption---so, well-defined
           | goals, fun to work on, seems impressive, potentially very
           | high payoff. No wonder there are so many.
        
           | [deleted]
        
         | ggregoire wrote:
         | It's the case in the backend and devops world too. But like for
         | Redux you probably chose some decent libraries and tools at the
         | beginning and sticked to it. If you start looking around you
         | will see there are alternatives to everything you use, and even
         | maybe that most of the industry moved to those alternatives in
         | the past 5 years.
         | 
         | How many ways are there to build an API? In Python: Falcon,
         | Flask, Django, FastAPI and so on. Just as many choices in Java,
         | Go, Node, <insert your favorite language>.
        
         | xeromal wrote:
         | "What's wrong with frontend?"
         | 
         | This is the age-old question. You're using Redux now, but I'm
         | sure some JQuery/Angular/Knockout/etc dev said the same thing
         | about what you're using back then.
         | 
         | The front-end is crazy and I don't think there's an obvious
         | answer of why it's such a developmental disaster. It's easy to
         | say it's run by script kiddies or the barrier to entry is too
         | easy, but there are a lot of smart devs working on the top
         | libraries. The culture just ended up this way. Whatever is
         | driving it probably will never stop though. Enjoy the ride. lol
        
           | dwaltrip wrote:
           | Frontend end is crazy because many UIs that do useful things
           | are inherently quite complex. UIs, by definition, are how
           | people interact with software to solve problems and
           | accomplish goals. The problems we solve and the goals we
           | achieve with software are continually evolving and expanding
           | as more and more software is created.
           | 
           | The people-software interfaces for many of the commonly used
           | pieces of software will always be complex as we will always
           | demand a lot of our software, up to the limit that can be
           | provided by the available tools for building these apps. As
           | our capabilities for building better software grow, so too
           | will the demands of the users.
           | 
           | If you aren't buying this argument, sit down and map out
           | every single possible state and every possible event (user
           | interactions, etc) of a moderately-sized app that you use
           | regularly. Or even just one page of that app. There's a lot
           | going on. It feels simpler than it is when we are using it
           | because well-designed applications become invisible to the
           | users, especially as we become familiar with them. They "just
           | work".
           | 
           | TL;DR Reality is messy and complicated. And so is the
           | software we build as well.
        
         | etimberg wrote:
         | I think it's because redux is quite painful to use with very
         | modern apps. Most of the time you need something like `redux-
         | saga` or `redux-thunk` to deal with async side effects. I'm not
         | sure which is the most popular today, but sagas are based on
         | generators and trying to use those with typescript is very very
         | painful and the underlying issue [1] is marked as a design
         | limitation in TS itself.
         | 
         | In addition, if you want to have your app load as smaller
         | chunks rather than a single large bundle, you need to be
         | careful to ensure that things work even all the backing
         | reducers aren't yet loaded.
         | 
         | 1. https://github.com/microsoft/TypeScript/issues/32523
        
           | doodlesdev wrote:
           | In my experience the experience with Redux Toolkit is
           | awesome, it's essentially an opinionated way to use Redux for
           | modern web applications and I believe they really hit the
           | mark when it comes to reducing boilerplate and the need for
           | extra deps. Although I'm still not a big fan and prefer to
           | use built-in tools of React to manage state when possible
           | (now that we have Context, Suspense, etc.)
        
           | kitten_mittens_ wrote:
           | arcanis has a PR to patch up the issue that's sat for a year
           | plus now.
           | https://github.com/microsoft/TypeScript/issues/43632
           | 
           | > In addition, if you want to have your app load as smaller
           | chunks rather than a single large bundle, you need to be
           | careful to ensure that things work even all the backing
           | reducers aren't yet loaded.
           | 
           | In the decade old application we use redux saga in at work, a
           | large portion of our 7MB minified/gzipped main chunk is redux
           | handlers. It'd be nice if there was a relatively simple way
           | to not synchronously load all the reducers up front.
        
             | acemarke wrote:
             | We have docs on code splitting reducers and other Redux
             | logic here:
             | 
             | - https://redux.js.org/usage/code-splitting
             | 
             | There have been some different community packages for
             | helping with that process, but some of them seem to have
             | become outdated (only worked with React-Redux v5, etc). I
             | did see a new one at https://github.com/fostyfost/redux-
             | eggs that seemed like it had potential, but I haven't had a
             | chance to try any of them myself.
             | 
             | I also once saw someone play around with the idea of using
             | React's still-not-technically-final Suspense support to
             | help ensure that a lazy-loaded component that relies on a
             | code-split reducer doesn't actually get rendered until that
             | reducer's state is available. Don't have the link handy
             | atm, but if someone wants it ping me and I can go figure
             | out where that was described.
             | 
             | Also, the new RTK "listener" middleware was specifically
             | designed to replace almost all saga usages, and you can
             | dynamically add more listeners at runtime via dispatch an
             | `addListener()` action:
             | 
             | - https://redux-toolkit.js.org/api/createListenerMiddleware
             | 
             | - https://blog.isquaredsoftware.com/2022/05/presentations-
             | evol...
        
           | weeksie wrote:
           | You don't need _any_ of that. You can use vanilla redux and
           | put your asynchronous code in middleware.
        
             | Rumudiez wrote:
             | More of this. Middleware is simpler to grok than reducers
             | and provides a clean, universal solution to async. You
             | don't need sagas, just dispatch events at meaningful points
             | in time, like when a request is initiated and then another
             | action when it completes. Pretty sure Dan Abramov taught
             | this approach years ago in an egghead tutorial, if it takes
             | hearing it from the horse's mouth to get you to consider
             | not just throwing more libraries at it
        
           | geraldwhen wrote:
           | You need redux saga because api interactions can be complex.
           | 
           | I need to update a remote resource. But wait! Sometimes that
           | can fail. I need to capture the failure logic and make
           | appropriate ui changes. There are 4 types of errors and they
           | require doing some library logic to figure out what to
           | display.
           | 
           | But wait! I want to wait 250ms before triggering any state
           | updates, or else the ui transitions will feel buggy.
           | 
           | Oh, and product now wants to make sure we capture some random
           | third party tracking event in between specific state changes.
           | The ui MUST NOT change until the tracking call succeeds.
           | 
           | This and more is trivial in redux saga, and you can write
           | tests around it.
        
             | weeksie wrote:
             | Saga is so heavy and overly complex and you don't really
             | get much out of it if you understand how middleware works.
             | There's really no reason to add a huge dependency to your
             | project.
             | 
             | You can do all of that pretty easily with a vanilla redux.
        
             | acemarke wrote:
             | For the record, we actually have recommended _against_
             | using sagas in most cases for a long time now, and
             | especially for data fetching.
             | 
             | Today, our recommendations are:
             | 
             | - Data fetching: default to using RTK Query, fall back to
             | thunks if needed
             | 
             | - Responding to actions or state changes: use the new RTK
             | "listener" middleware as the main approach
             | 
             | See my recent talk "The Evolution of Redux Async Logic" for
             | details:
             | 
             | - https://blog.isquaredsoftware.com/2022/05/presentations-
             | evol...
             | 
             | as well as my recent presentation going through "Modern
             | Redux with Redux Toolkit":
             | 
             | - https://blog.isquaredsoftware.com/2022/06/presentations-
             | mode...
        
               | cageface wrote:
               | I was called in to rescue a redux-saga based project that
               | had gone badly off the rails. It was one of the worst
               | codebases I've ever had to work with in many years of
               | coding. Stack traces were useless and debugging with
               | anything higher level than log statements was impossible.
        
               | dboreham wrote:
               | Apparently you don't need to debug if you're a good
               | programmer. This explains why many modern tech stacks
               | (JS, Scala, Kotlin, ...) have a horrible debugging
               | experience.
        
               | geraldwhen wrote:
               | We specifically moved off thunks because the capricious
               | whims of changing network calls with logic to support it
               | is so much easier in redux saga. Stuff just works. You
               | can handle every edge case.
               | 
               | And now there are multiple deployed production apps with
               | real users, so it's almost certainly never going to be
               | replaced. The cost would be enormous.
        
               | acemarke wrote:
               | Yeah, I'm not questioning whether you _can_ do things
               | with sagas, and there's definitely cases where their
               | capabilities are valuable.
               | 
               | But as I put it in my "Evolution" talk: "Sagas are like a
               | chainsaw. Really powerful, and really dangerous. If you
               | actually _need_ that power, great! But most of the time
               | you don't actually _need_ to use a chainsaw on a daily
               | basis."
               | 
               | As the sibling comment said, a lot of times sagas really
               | do end up as spaghetti code, largely because they are so
               | event-driven, and with all the use of generator functions
               | that can make debugging hard. (Ironically, the original
               | Flux Architecture was created to _avoid_ the problems of
               | Backbone-style event triggers causing events to ricochet
               | around the app without a way to understand how things
               | would update in response, and sagas can end up recreating
               | that problem with Redux apps.)
        
               | aidos wrote:
               | Oh my. What is this ecosystem where the maintainers are
               | downvoted for explaining the current recommendations for
               | those using their library?
        
       | russellpekala wrote:
       | I do find redux super helpful for undo/redo (as mentioned in the
       | article) and have not found a similar library for another state
       | management solution that can do quite what I need there.
        
       | melony wrote:
       | Most of these new client side state management libraries are
       | incompatible with any form of SSR. If you see the documentation
       | for Jotai/Zustand/Valtio, the solution is to avoid using with
       | Next.js at all, or fall back to hacks using context+provider at
       | which point the state manager becomes effectively redundant.
        
         | rebelos wrote:
         | Isn't SSR only really relevant when you need to optimize for
         | SEO (which only applies to a subset of apps)? Seems like it
         | doesn't confer any other _significant_ benefit.
        
           | azemetre wrote:
           | Think about how the benefits to SEO (page speed, web vitals,
           | less client work) can improve overall app performance.
           | 
           | SSR is just one technique.
        
           | purplerabbit wrote:
           | I'm sorry people are downvoting, because you are correct.
           | 
           | SSR (by which I mean Next.js) is the most over-invested in JS
           | tech of all time. It introduces a bunch of crummy DX which
           | never pays for itself from a business standpoint.
           | 
           | SSR is only potentially useful for landing pages. In which
           | case you should be using Wordpress or something like
           | Wordpress so you aren't wasting dev resources on something a
           | marketing team should be doing. (If your argument is that SSR
           | is necessary for speed, I'm pretty sure exporting your
           | Wordpress site to static HTML + CSS and using Cloudflare
           | could more than make up for the difference.)
           | 
           | The one asterisk I'll add to this is that SSR in the form of
           | the Remix framework _may_ justify its own existence as it
           | removes the need for an explicit API layer, which lets you
           | skip a ton of boilerplate code. This is a big win. The fact
           | that Remix uses SSR is just an implementation detail -- it 's
           | the DX that's actually valuable (although SSR fetishists will
           | probably still like it, too.)
        
       | cosmiccatnap wrote:
       | I find it interesting that across a decade and countless
       | frameworks from jQuery, meteor, angular, and now react the core
       | problem is still and somehow progressively worse than
       | ever...state.
       | 
       | I find it strange this is still such a hard problem to solve in
       | an environment with a slew of options for key value global,
       | local, and remote storage
        
         | bayesian_horse wrote:
         | It's easier to solve it than to agree on what is the solution
         | and to keep it. The more alternatives to redux there are, the
         | higher the chance you get thrown into projects with some lesser
         | known framework, maybe not even used to its best.
        
       | [deleted]
        
       | meling wrote:
       | I've not seen overmindjs mentioned on hacker news. We use it in
       | our React app and my students who wrote the code liked it a
       | lot... maybe others have advanced enough by now to be on par with
       | or better than overmindjs.
       | 
       | https://overmindjs.org/
        
       | abxytg wrote:
       | I've been running into nasty performance with setRecoilState and
       | large piece of state firing multiple times per frame.
        
       | rochak wrote:
       | Has React become too big for people to not consider other
       | alternatives? I used to be a big React advocate but realised that
       | it is getting too bloated with every new release. Have been
       | looking into Svelte and it is turning out to be a breath of fresh
       | air compared to whatever React is culminating to be.
        
       | sakerbos wrote:
       | I've advocated for Redux in many commercial projects because I
       | knew that it worked well at scale. There was occasional pushback
       | due to the large amount of boilerplate code involved (actions,
       | reducers, sagas, models/interfaces if using Typescript) but the
       | team mostly settled on Redux because it was the best supported
       | and most widely used state management framework at the time. IMO
       | the larger pool of devs that understand a framework, the better a
       | project's chances are of success mainly because the industry has
       | a high turnover of developers and it's easier to find
       | replacements to maintain the existing code.
       | 
       | That being said, I'm now a huge fan of react-query.
        
         | Yhippa wrote:
         | Question for you since you seem knowledgeable about React state
         | management. When I did a lot of back-end programming in Java we
         | frequently coded to interfaces where we could swap out back-end
         | implementations for ORM for example if needed. There's an
         | ongoing joke where nobody actually did that.
         | 
         | Is there something like that in React? My understanding is that
         | there's a lot of coming and going of state management
         | frameworks, and it would seem to me committing to thr API
         | methods of a particular framework would be risky. Or am I
         | thinking at the wrong abstraction level?
        
           | acemarke wrote:
           | To some extent, this was the purpose of the
           | "container/presentational" pattern that was popular for a few
           | years [0]. By splitting your components into "containers",
           | which were responsible for managing data fetching, and
           | "presentational" components, which just received data as
           | props and displayed the UI, in theory you could swap out the
           | state layer someday without having to alter most of the
           | display handling.
           | 
           | But, the community really began over-obsessing about that,
           | and often treated it as a rule you _had_ to follow (to the
           | point of people seeming to panic and asking for help about
           | whether a particular component should live in a `/containers`
           | folder, `/components`, or somewhere else).
           | 
           | Dan Abramov, who wrote the article that helped really
           | popularize that approach, later updated it to say he no
           | longer finds it very useful.
           | 
           | In addition, React hooks push you towards a very different
           | approach, where each component is now responsible for calling
           | the hooks that it relies on for data fetching. That hook may
           | still abstract where the data actually comes from, but the
           | calls are now part of the component itself. I talked about
           | this change in approach in a blog post and conference talk
           | conference talk [1] [2].
           | 
           | Finally, the testing approaches in the ecosystem have changed
           | as well. Instead of "shallow rendering" components using the
           | Enzyme library, the community has moved on towards more
           | "integration"-style tests with React Testing Library. This
           | does require more setup work in tests to ensure you have all
           | the various data providers wrapping the components under
           | tests, and real or mock data being loaded, but the tests
           | themselves become simpler and any state library usage becomes
           | basically irrelevant to the actual test implementation. See
           | [3] and [4] for some thoughts on that.
           | 
           | Soooo... yes, you _can_ write more abstraction layers, split
           | your components by "containers", and even add DI via React
           | context or some other purpose-built library if you want to.
           | You could even abstract out all the UI components you use
           | from a particular library just in case you end up swapping
           | date pickers or something. But as always, it's a question of
           | whether that will actually provide a benefit, now or in the
           | future. And in general, most React apps do not bother with
           | those extra abstractions.
           | 
           | [0] https://medium.com/@dan_abramov/smart-and-dumb-
           | components-7c...
           | 
           | [1] https://blog.isquaredsoftware.com/2019/07/blogged-
           | answers-th...
           | 
           | [2] https://blog.isquaredsoftware.com/2019/09/presentation-
           | hooks...
           | 
           | [3] https://kentcdodds.com/blog/testing-implementation-
           | details
           | 
           | [4] https://blog.isquaredsoftware.com/2021/06/the-evolution-
           | of-r...
        
       | jfvinueza wrote:
       | I've been using Pullstate for medium-sized apps for a couple
       | years and it's fantastic: uses Immer under the hood (so it's all
       | immutable even if it look as it wasn't), it's API and mental
       | model are vulgarly simple, and my impression is that it's quite
       | performant. I also like that the store is disentangled from the
       | component tree, which allows for plenty of flexibility. Totally
       | recommended!
       | 
       | https://lostpebble.github.io/pullstate/
        
       | dageshi wrote:
       | After reading the "Grug Developer" article recently, I've been
       | thinking of frontend development as "The Plane of Eternal
       | Complexity Demons".
        
         | jitl wrote:
         | This is because UI programming is inherently extremely complex,
         | especially compared to something like a stateless API tier
         | running in AWS. It's stateful software deployed to countless
         | different runtimes on hardware you don't control. Instead of a
         | smattering of API routes handling well-structured semantic
         | datatypes like `POST /burgers?pickles=false`, input comes in
         | the form of arbitrary UI events from various input devices like
         | pens, keyboards, mice, etc that must be interpreted to have a
         | semantic meaning. Often there are hundreds of API routes (event
         | handling elements) on screen at once in a complex application.
         | UI engineers are perpetually frustrated by this complexity, and
         | so some small percentage look for better ways to handle these
         | issues.
         | 
         | Of course it's best to avoid UI programming entirely, but in
         | many domains it's necessary.
        
           | mllllv wrote:
           | I disagree, I think UI programming is inherently quite
           | simple. Especially with a paradigm like immediate-mode GUIs
           | in my opinion. I believe the complexity comes from the fact
           | that the DOM is a poor API for creating user interfaces,
           | which ultimately inspired developers to create frameworks
           | that work in a more "immediate-mode" style way.
        
             | cageface wrote:
             | The native UI toolkits are even harder to use than
             | something like React and recently have been evolving to a
             | similar reactive + declarative paradigm.
             | 
             | User interfaces are complex, poorly specified, and subject
             | to rapid and often capricious changes in the middle of
             | development. Don't blame the tools.
        
           | wizofaus wrote:
           | There are definitely examples of UI programming that is more
           | complex than certain APIs that largely perform basic CRUD
           | operations, but I'd strongly disagree either is inherently
           | more complex than the other, it's just that human behaviours
           | and preferences are messy and unpredictable, which means
           | conceptually "simple and elegant" UIs are often not what
           | users actually enjoy using, and this inevitably has impacts
           | at the code level. APIs don't have to designed to deal with
           | human eccentricities as they're written for developers, and
           | we aren't like normal people.
        
           | aaaaaaaaaaab wrote:
           | Bullshit. In 1995 people were creating desktop UIs order of
           | magnitude more complex than today's anemic webapps, without
           | any of the braindamage-inducing stuff that's happening in web
           | UI development.
        
             | ChefboyOG wrote:
             | I was legitimately curious about this--my memory of Windows
             | 95 is not this nice--so I looked at Wikipedia's list of
             | software released in 1995:
             | 
             | https://en.m.wikipedia.org/wiki/Category:1995_software
             | 
             | What software specifically do you recall being "an order of
             | magnitude more complex" than today's popular web apps?
        
               | aaaaaaaaaaab wrote:
               | Just from the top of my mind: Excel, Word, Photoshop,
               | Windows Commander (called Total Commander today),
               | SolidWorks, AutoCAD, Borland Delphi.
        
           | nwh5jg56df wrote:
           | We went to the moon some +50 years ago. We ought to have
           | solved "UI programming" already, no?
           | 
           | Something is not working
        
             | syspec wrote:
             | By that logo , SpaceX shouldn't exist.
        
             | agumonkey wrote:
             | simple problems easily becomes complex in mainstream
             | contexts.. due to bazaar like soil. NASA had to solve one
             | immensely hard problem but they owned the context. Vertical
             | integration if you will.
        
             | wly_cdgr wrote:
             | UI programming is much harder than going to the moon. Do
             | not confuse danger, scale, glamour, etc with difficulty
        
             | bobthepanda wrote:
             | Ultimately, successful products are determined by customers
             | and by product managers and their executives, and it turns
             | out there is no one-size-fits-all approach to even basic UI
             | programming because everyone has an opinion.
             | 
             | Not to mention, as an example touch became a widespread new
             | UI paradigm in the last 10-20 years.
        
         | robocat wrote:
         | JavaScipt on the browser is cursed[1].
         | 
         | 1. There is no standard GUI library, as per article. A GUI can
         | be as arbitrarily complex as you wish, and every different
         | frontend system is a unique GUI system deployed in JavaScript,
         | usually using HTML for the view drawing primitives* and events
         | for input. The complexities of GUI library design bubble up to
         | developers who are implementing their own tweaks or
         | combinations of a GUI library, usually with a huge amount of
         | "needless" variation. Application developers should ideally
         | never have to be making choices about internals of a GUI
         | system, yet the core of most articles comparing frontend
         | frameworks is discussing GUI internals.
         | 
         | 2. There is no golden standard for tooling. Everyone has their
         | pet variations on how to deploy to JavaScript, CSS, and HTML.
         | 
         | 3. Back end choice. Huge variation.
         | 
         | As a developer we get APIs on the edges, but we make our own
         | spaghetti to join everything how we wish because there is not
         | one or two standard library/framework choices, and we have the
         | power to do what we will. I developed my own 100% custom
         | component framework because I could write one that suited us
         | far better than what was available at the time (OSS or
         | commercial). Browser variation used to be a huge driver for
         | complexity, but is far less so now.
         | 
         | * drawing primitives can also be Canvas or SVG or WebGL e.g.
         | https://news.ycombinator.com/item?id=27131659 is a good
         | comment.
         | 
         | [1] https://www.google.co.nz/search?q=lisp+curse
        
         | Starlevel001 wrote:
         | Server-side templating died for this.
        
         | sph wrote:
         | It makes me smile that elsewhere in this thread there's people
         | saying "I've been using <library> and state management is now
         | super easy." when you know in two months people will be saying
         | that library is over-engineered and someone will suggest to try
         | the new panacea that will solve all of your problems, for real
         | this time.
         | 
         | Such is the hype cycle of frontend development.
        
           | jcelerier wrote:
           | I mostly use Qt Widgets which hasn't fundamentally changed
           | since 1995 and still performs just fine for desktop UI
        
         | [deleted]
        
         | doitLP wrote:
         | Link: https://grugbrain.dev/
         | 
         | It is universally worth your time to read it if you haven't :)
        
           | maxekman wrote:
           | Amazing read! Missed it when it trended 10 days ago.
           | 
           | https://news.ycombinator.com/item?id=31840331
        
           | pcthrowaway wrote:
           | Plain english translation: https://github.com/reidjs/grug-
           | dev-translation
           | 
           | I haven't read it, but wish I had seen it before struggling
           | through the original
        
             | surrealize wrote:
             | Thanks so much for the link! I tried the original and
             | bounced off the style. It seemed like something that might
             | be fun and useful if I invested enough effort in reading
             | it, but I just bounced off.
             | 
             | But with the translation, I just devoured and appreciated
             | it.
        
       | memonkey wrote:
       | Absolutely great article. One thing I always see missing is why
       | front-end applications can't use sessionStorage or localStorage?
       | Why is this generally frowned upon?
        
         | wizofaus wrote:
         | I'd assume because it's often abused? There are perfectly
         | legitimate reasons to use either and I've been technical lead
         | on React projects where the decision was made to use them. In
         | at least one case it was a known "shortcut" as we didn't have
         | time to properly develop server-side persistence and local
         | storage was "good enough" for 95% of use cases. And session
         | storage is needed to allow page refreshes without cookies.
        
         | bayesian_horse wrote:
         | For what purpose? If you use it as state management inside the
         | SPA, it's actually slower than all the other approaches.
        
       ___________________________________________________________________
       (page generated 2022-07-02 23:00 UTC)