Hacker News new | ask | show | jobs
by paulddraper 1117 days ago
Hooks are IMO one of the greatest innovations in UI programming.

I'll draw an analogy.

---

Why did async/await replace callbacks? They are really the same thing, aren't they? Aren't callbacks good enough?

Async/await allowed programmers to write asynchronous code as if it were synchronous.

---

Why did hooks replace classes/imperative? They are really the same thing, aren't they? Aren't classes/imperative good enough?

Hooks allowed programmers to write stateful code as if it were stateless.

    function MyComponent() {
      const [value, setValue] = useState(false);

      const buttonClass = value ? "on" : "off";

      return (
        <button
          className={buttonClass}
          onClick={() => setValue(!value)}
        >
          {String(value)}
        </button>
      );
    }
This is functional code, without scary, hard-to-reason side-effects. Except for one limited part, which operates in a stateful way.

I argue that this is simpler than the equivalent imperative-DOM modification code, and the gap between these only increases with real programs.

This isn't just a weird "web bro" thing; the hooks paradigm is useful (in theory and practice) to every UI platform.

I even wrote an implementation (closed source) for hooks in Angular. It was lovely.

3 comments

This isn't "functional code" in the sense of functional programming.

It is some pseudo DSL with hidden hard to reason mutable state.

Of course it's not functional code. Just as

    let result;
    for (const item of items) {
      result = await foo(item);
      if (result) {
        break;
      }
    }
is not synchronous code. But you can write it very close to the mental model of synchronous programming.

The same is true of hooks. The code is not stateless, but you can write it very close to the mental model of stateless programming.

That is why -- despite them being optional -- hooks have become incredibly popular.

This is the best explanation for both async/await and hooks that I've ever heard, thank you!

It also shows that although there might be some learning investment required to use the more modern version of both, it's well worth the effort. I can't imagine going back to callback-riddled javascript

what do you mean async/await "replaced callbacks"? Async/await "replaced" Promises, specifically then/catch chaining. Turns out Promises can be syntactically-sugared to imperative try/catch blocks.
Ah but if I said "async/await replaced Promises", a pedantic HN poster would correct me :/ "No it didn't replace them"
I’ll be more pedantic than that! Await is more akin to yield, the fact that it’s specific to promise resolution is a specialization of the more general function body suspension used by generators, with an extra specialization for event loop scheduling. And async just means you’re returning a promise no matter how your function exits.
hah, good point. Just wanted to point out that callbacks and async/await are different things, and callbacks are still the preferred way to customize behavior.