Why does it feel like React (not just the lib but the community/ecosystem/everything) took something as straightforward and easy to understand as functional programming and surrounded it with so much fluffy pomp and circumstance that it is unrecognizable?
In React {Transitions} = F(state)
41–50 of 55 posts
Re: In React {Transitions} = F(state)
#42The #1 reason I push for SSR/vanilla web is to consolidate all state to the server. Literally the only thing on the client could be a session cookie. A few hundred bits of entropy. That's the client's state. Imagine how simple that would be. The cost of a round trip for every UI interaction might seem high, but I've never seen a distributed client/server state machine model that could compensate for any of these alle…
Nor would I call it simple that the server has to be able to send the whole UI over the wire instead of just data. And it ties your server to the web browser instead of providing a simple data API that can be used by anything that can make an http request.
There are always trade-offs.
Re: In React {Transitions} = F(state)
#43"This is the famous UI = f(state) mental model of React". Famously incorrect generalization. Why? For example, the useRef hook enables components to hold their own state. React components are not guaranteed to be pure functions. Of course, it can depend on how one writes their code, but it's not a guaranteed that UI = f(state) in React in general.
Re: In React {Transitions} = F(state)
#44Earlier quoted context omitted.
I want to disagree with you, but I just can't. Every simple example on the different ideas for managing state in React is easy and seems reasonable. Every application I encounter seems to quickly take that and just start laughing at me.
I think state management is the worst part of using React. All of the popular/highly recommended packages to manage state require you to write code in unconventional ways without really explaining the design decisions. Why use reducers? They're basically different (worse) syntax for mutable object method calls.
You have your app state in an object/class, and components automatically rerender when the part of the store changes that they access during render.
class Store {
counter = 0
constructor() { makeAutoObservable(this) }
increment() { this.counter++ }
}
const Component = observer(() {
const store = useStore()
const click = () => store.increment())
return {store.counter}
})
It has a very light set of idiosyncrasies for what it gives you unlike, say, redux.Re: In React {Transitions} = F(state)
#45Earlier quoted context omitted.
Hooks are the best thing for frontend dev since async/await.
I can't count how many issues I've seen due to: missing useEffect dependencies, cyclical hooks, unnecessary rerenders, etc. linked to this API. It has a lot of expressivity but is incredibly brittle and dangerous.
Angular too many digest cycles anyone?
Re: In React {Transitions} = F(state)
#46The vast majority of state problems in React are a result of nonsense cargo culting around the idea that classes are somehow bad.
Both paradigms have foot guns but having used both I much prefer the hook version.
Re: In React {Transitions} = F(state)
#47Every time I delve into a large React codebases (and I have worked on some real monsters) I have a laugh to myself at how badly these guys tie themselves up in knots in order to preserve the supposed simplicity of the state -> UI function. When you invent something as insane as the hooks API in order to maintain purity it's time to step back and consider if you're really on the right track.
Re: In React {Transitions} = F(state)
#48I've never seen a Teact project where UI = f(state). There is always heavy reliance on the "lifecycle" of components. So you compose "functions", but every function is using some global state, shared or not, it's meaningless to describe it as "functions". The one project I've used that had redux was also a complete nightmare to work with, and hooks are the blessed way now apparently.
Re: In React {Transitions} = F(state)
#49Earlier quoted context omitted.
I think state management is the worst part of using React. All of the popular/highly recommended packages to manage state require you to write code in unconventional ways without really explaining the design decisions. Why use reducers? They're basically different (worse) syntax for mutable object method calls.
Try MobX. I think it's the holy grail of state management. You have your app state in an object/class, and components automatically rerender when the part of the store changes that they access during render. class Store { counter = 0 constructor() { makeAutoObservable(this) } increment() { this.counter++ } } const Component = observer(() { const store = useStore() const click = () => store.increment()) return {store.…
https://github.com/Facepunch/react-class-model (note: context is not required)
Re: In React {Transitions} = F(state)
#50Earlier quoted context omitted.
Out of curiosity, I just looked through some of my old code calling useEffect. Most of it was for fetching data from an API on mount; I'd also written a custom little hook that returns a callback to signal that the data should be refreshed. But a few instances were to conditionally set one piece of state whenever another piece of state was changed, arguably an abuse of the mechanism. I suppose the proper way would be…
> But a few instances were to conditionally set one piece of state whenever another piece of state was changed That use case is explicitly called out on the "You Might Not Need An Effect" article in the docs (which everyone writing React should read, and arguably was published years too late): https://react.dev/learn/you-might-not-need-an-effect TLDR: When updating a useState based on another useState, don't use the…
> When updating a useState based on another useState, don't use the first useState at all, just compute it inline. If it's expensive, wrap it in a useMemo.
Well, the problem in this case was that the affected useState was not just a pure function of the useState that caused it to be modified: other actions could modify it as well. (E.g., you have some form state that should get updated whenever a state value somewhere else is changed.)
I believe useReducer is a bit closer to the use case I'm thinking of, but the dispatch functions for that are verbose and unpleasant to write. Presumably ad-hoc closures wrapping the setter functions would be somewhat more lightweight.