What are React Hooks? 🎣
Tags: react, javascript, discuss, hooks
Published: 2021-07-28 15:37:31

## Table Of Contents
   * [Introduction](#1)
   * [What are Hooks?](#2)
   * [useState](#3)
   * [useEffect](#4)
   * [Rules of Hooks](#5)
   * [Building your own Hooks](#6)
   * [Additional Hooks and API Reference](#7)
   * [Conclusion](#8)

## Introduction <a name="1"></a>

React is a free and open-source front-end JavaScript library for UI components, maintained by Facebook and a group of individual developers. However it's used, React is only concerned with state management and rendering that state to the DOM, initially through React state and lifecycle methods.

But that all changed when React 16.8 was introduced, its new addition of Hooks allow the use of state and other React features without writing a class. Hooks were developed to solve a bunch of unconnected problems in React. Some of the problems (are not limited too) include:

1. [It’s hard to reuse stateful logic between components](https://reactjs.org/docs/hooks-intro.html#its-hard-to-reuse-stateful-logic-between-components)

2. [Complex components become hard to understand](https://reactjs.org/docs/hooks-intro.html#complex-components-become-hard-to-understand)

3. [Classes confuse both people and machines](https://reactjs.org/docs/hooks-intro.html#classes-confuse-both-people-and-machines)

## What are Hooks? <a name="2"></a>

Hooks are simply just functions that let you “hook into” React state and lifecycle features. Unlike lifecycle methods, Hooks don’t work inside classes. Which can make working with them super flexible, since they let you use lifecycle features in function components. While React provides a few built-in Hooks like useState, you can also create your own Hooks to reuse stateful behavior between components. 

## useState <a name="3"></a>

*This example was taken from and can be seen in the [React Documentation](https://reactjs.org/docs) for Hooks.*

If you are familiar with React, then you may use to seeing state handled like so:

```javascript
class Example extends React.Component {
  constructor(props) {
    super(props);
    this.state = {
      count: 0
    };
  }

  render() {
    return (
      <div>
        <p>You clicked {this.state.count} times</p>
        <button onClick={() => this.setState({ count: this.state.count + 1 })}>
          Click me
        </button>
      </div>
    );
  }
}
```
But with React Hooks, that turns into this:

```javascript
// This example renders a counter. When you click the button, it increments the value:
import React, { useState } from 'react';

function Example() {
  // Declare a new state variable, which we'll call "count"
  const [count, setCount] = useState(0);

  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}>
        Click me
      </button>
    </div>
  );
}
```

The first Hook we'll be examining, is the State Hook. **useState** is a Hook called inside a function component to add local state. Once added, React uses the Hook to preserve this state between re-renders by returning two things: the current state value and a function for updating it. This function can be called from anywhere, such as an event handler. If you familiar with React, compare it to this.setState in a class, without merging the old and updated state together.

"useState" only takes in one initial argument, which is only used during the first render. In the previous example, this argument is "0" because the counter starts from zero. *Keep in mind that unlike this.state, the state here doesn’t have to be an object.* 

You can understand out how to declare multiple variables with the "useState" hook [here](https://reactjs.org/docs/hooks-overview.html#declaring-multiple-state-variables).

## useEffect <a name="4"></a>

When coding with React, you may perform data fetching, subscriptions, or manually changing the DOM. The React developers like to call these “side effects” since they affect other components, and can’t be done while rendering.

The Effect Hook, **useEffect**, adds the ability to effect from, *you guessed it*, a function component. Similar to componentDidMount, componentDidUpdate, and componentWillUnmount in React classes, "useEffect" is unified into a single API. 

Going off the example before, after React updates the DOM, the component sets the document title:

```javascript
import React, { useState, useEffect } from 'react';

function Example() {
  const [count, setCount] = useState(0);

  // Similar to componentDidMount and componentDidUpdate:
  useEffect(() => {
    // Update the document title using the browser API
    document.title = `You clicked ${count} times`;
  });

  return (
    <div>
      <p>You clicked {count} times</p>
      <button onClick={() => setCount(count + 1)}>
        Click me
      </button>
    </div>
  );
}
```

By calling "useEffect", you’re telling React to run the “effect” function you created after pushing changes to the DOM. Effects are declared inside the component, so they have access to props and state. By default, React runs the effects after every render, starting with the first one. Effects can also optionally specify actions to take after by returning a function. Hooks let you organize side effects in a component by what ideas are related, rather than forcing a split based on lifecycle methods.

Unlike the lifecycle methods, componentDidMount or componentDidUpdate, effects scheduled with useEffect don’t block the browser from updating the screen. This cut back on processing time, since the majority of effects don’t need to happen synchronously, making your app feel more responsive. In a case where effects do need to occur synchronously(such as measuring the layout), there is a separate useLayoutEffect Hook with an API identical to useEffect. You can learn more about that in the [Additional Hooks and API Reference](#7) section.

## Rules of Hooks <a name="5"></a>

Despite Hooks being Javascript functions, there are still several rules they must follow in order to maintain the black magic that gives them lifecycle features. 

1. **Only Call Hooks at the Top Level**
   +  Always use Hooks at the top level of your React function, before any early returns. This means don’t call Hooks inside loops, conditions, or nested functions. This ensures that Hooks are called in the same order each time a component renders, which allows React to correctly preserve the state of Hooks between varying useState and useEffect calls.

2. **Only Call Hooks from React Functions**
   + Don’t call Hooks from regular JavaScript functions. 
     Try the following instead:
           + Call Hooks from custom Hooks 
           + Call Hooks from React function components.

*To make things easy, the React developers made this [plugin](https://www.npmjs.com/package/eslint-plugin-react-hooks) that automatically enforces these rules. But, that doesn't mean you should skip over knowing proper Hook etiquette.*

## Building your own Hooks <a name="6"></a>

What if you want to go beyond just the Effect Hook? Well, there's an answer for that, build your own! By building your own Hooks, you can extract component logic into reusable functions. You may be use to doing this in React through: render props and higher-order components. But with the addition of Hooks, you can solve many of the same problems without adding more components to the tree. *No one likes cluttered code!*

*Think about how share logic between two JavaScript functions, you extract it into yet another function. And since components and Hooks are functions, this works for them too!*

**A custom Hook is a JavaScript function whose name starts with ”use” and has the ability to call other Hooks.** 

You can write custom Hooks that cover a variety of cases such as form handling, animation, timers, and much more. Don't be afraid to experiment with creating your own Hooks, because you might find yourself making a meaningful contribution to others down the line. *React even provides [documentation](https://reactjs.org/docs/how-to-contribute.html) on how to contribute to the open source project.*

For more information about building your own custom Hooks and some examples, see the [React Documentation](https://reactjs.org/docs/hooks-custom.html) for creating custom Hooks. 

As an additional resource, here is another recent blog post that further explains how to build your own Hooks, and supplies you with some great examples such as a "useFetch" custom hook. Check it out [here](https://alterclass.io/blog/5-react-custom-hooks-you-should-start-using-explained)!

## Additional Hooks and API Reference <a name="7"></a>

If you're interested in learning about the Hooks API reference, the React documentation provides a reader friendly explanation for the [basic hooks](https://reactjs.org/docs/hooks-reference.html#basic-hooks):

+ [useState](https://reactjs.org/docs/hooks-reference.html#usestate)
+ [useEffect](https://reactjs.org/docs/hooks-reference.html#useeffect)
+ [useContext](https://reactjs.org/docs/hooks-reference.html#usecontext)

You can also use [additional Hooks](https://reactjs.org/docs/hooks-reference.html#additional-hooks) which are either variants of the basic ones, or only needed for specific edge cases. While helpful, they are just additions, so don't worry about learning them right away. These Hooks include:

+ [useReducer](https://reactjs.org/docs/hooks-reference.html#usereducer)
+ [useCallback](https://reactjs.org/docs/hooks-reference.html#usecallback)
+ [useMemo](https://reactjs.org/docs/hooks-reference.html#usememo)
+ [useRef](https://reactjs.org/docs/hooks-reference.html#useref)
+ [useImperativeHandle](https://reactjs.org/docs/hooks-reference.html#useimperativehandle)
+ [useLayoutEffect](https://reactjs.org/docs/hooks-reference.html#uselayouteffect)
+ [useDebugValue](https://reactjs.org/docs/hooks-reference.html#usedebugvalue)

## Conclusion <a name="8"></a>

React is constantly changing, and programmers who are focused on developing products may not have the time to learn and use every new API released. Hooks are still fairly new, so while they may come in handy, there's no rush to adopt them into your every day practices, *unless that's what your heart desires*. 

Hooks were made to work side-by-side with existing code, which allows you to adopt them gradually, *meaning there is no rush to migrate to Hooks.* Do not feel the need to do some “big rewrite”, especially for existing, complex class components. It's a bit of a learning curve to start “thinking in Hooks”. So practice using Hooks in your *unimportant* work first, and once you, *and anyone you're working with*, feel comfortable with them, give them a go! 

Hooks were made in hopes to one day cover all existing use cases for classes, but don't worry because class components aren't going anywhere soon. If you don't believe me, I'll quote the React developers themselves, 

>"At Facebook, we have tens of thousands of components written as classes, and we have absolutely no plans to rewrite them. Instead, we are starting to use Hooks in the new code side by side with classes."

Hopefully this article has inspired you to hook into your full React potential, or maybe you decided to not bother learning and using *yet another* API. Either way, let me know your opinion about Hooks, and where you see them going in the future. ✨ Happy Hooking! ✨