React Hook là một “luồng gió” mà nhà phát hành React đã giới thiệu trong thời gian gần đây. Trên VNTALKING cũng có một bài viết giới thiệu về React Hook mà bạn nên đọc: React Hook là gì?
So với thời điểm mới ra mắt, hiện tại có rất nhiều thư viện hỗ trợ React Hook, giúp cho bạn phát triển dự án với React được dễ dàng hơn rất nhiều. Khi tìm kiếm trên internet về React, bạn sẽ gặp nhan nhản các từ khóa, các kỹ thuật liên quan tới “Hooks”, đây cũng là xu hướng mà chính nhà hành React cũng mong muốn như vậy. Nếu dự án của bạn chưa sử dụng Hook, có lẽ bạn nên suy nghĩ lại.
💦 Đọc thêm về ReactJS:
- Tài liệu học ReactJS tiếng việt – (bán chạy nhất 2021)
- Học React qua 10 dự án thực tế (từ cơ bản – nâng cao)
- Quản lý State với React Hooks – Không cần Redux hay Context API
Hook giúp cho mã nguồn dự án trở nên rõ ràng, đảm bảo khả năng đọc code, khả năng bảo trì, khả năng tái sử dụng và có ít dòng mã hơn. Đây đều là những yếu tố rất quan trọng trong quá trình phát triển React.
Vì vậy trong blog này, mình sẽ giới thiệu cho bạn 10 thư viện React Hook hàng đầu mà bạn nên bắt đầu sử dụng ngay lập tức. Không để chậm trễ hơn nữa, chúng ta hãy bắt đầu tìm hiểu 10 thư viện đó nào.
Nội dung chính của bài viết
1. Use-http
Use-http là một thư viện cực kì hữu ích được sử dụng để thay thế cho Fetch API. Được xây dựng và bảo trì với chất lượng cao, nó làm cho việc viết mã của bạn trở nên đơn giản và dễ hiểu hơn nhiều với sự chú trọng đặc biệt vào phần xử lý dữ liệu. Bản thân hook sử dụng TypeScript và thậm chí còn hỗ trợ SSR và GraphQL. Nó trả về một response, loading, error data và các phương thức yêu cầu khác nhau như Get, Post, Put, Patch và Delete.
Các tính năng chính mà nó cung cấp là:
- Request/Response interceptors
- Suspense (hiện đang được thử nghiệm)
- Chức năng retry
- Bộ nhớ đệm
Một ví dụ sử dụng thư viện này.
import useFetch from "use-http" const Example = () => { const [todos, setTodos] = useState([]) const { get, post, response, loading, error } = useFetch("https://example.com") useEffect(() => { get("/todos") }, []) const addTodo = async () => { await post("/todos", { title: "example todo" }); if (response.ok) setTodos([...todos, newTodo]) } return ( <> <button onClick={addTodo}>Add Todo</button> {error && 'Error!'} {loading && 'Loading...'} {todos.map(todo => ( <span key={todo.id}>{todo.title}</span> )} </> ); };
2. UseMedia
Bạn đã bao giờ cần phải theo dõi các câu truy vấn CSS media query?
useMedia Hook cung cấp một cách tiếp cận đơn giản để giải quyết cho vấn đề này. Media queries thực sự quan trọng trong các ứng dụng cần khả năng hiển thị responsive, tức là ứng dụng web hiển thị đẹp trên nhiều kích thước màn hình khác nhau
Được viết bằng TypeScript, nên Hook này đương nhiên sẽ hỗ trợ Typescript. Đặc biệt, thư viện này có nguồn tài liệu hướng dẫn rất đầy đủ và rõ ràng, nên bạn hoàn toàn yên tâm tích hợp hook nào vào ứng dụng.
Ví dụ cách sử dụng:
import useMedia from 'use-media'; const Example = () => { const isWide = useMedia({minWidth: '1000px'}); return ( <span> Screen is wide: {isWide ? "WideScreen" : "NarrowScreen"} </span> ); };
3. Constate
Constate là một hook package cung cấp khả năng nâng local stage dựa lên React Context.
Điều này có nghĩa là bất kỳ state nào từ bất kỳ component nào cũng có thể dễ dàng được nâng lên Context chỉ với một dòng code đơn giản. Điều này rất hữu ích trong trường hợp bạn muốn sử dụng cùng một state ở nhiều vị trí hoặc cung cấp cùng một state cho nhiều component. Cái tên này xuất phát từ một cách chơi chữ kết hợp giữa Context và State.
Thư viện này được viết bằng TypeSript và có kích thước rất nhỏ. Tài liệu không quá chi tiết nhưng nó đủ giúp bạn hoàn thành công việc.
import React, { useState } from "react"; import constate from "constate"; // custom hook function useCounter() { const [count, setCount] = useState(0); const increment = () => setCount(prevCount => prevCount + 1); return { count, increment }; } // hook passed in constate const [CounterProvider, useCounterContext] = constate(useCounter); function Button() { // use the context const { increment } = useCounterContext(); return <button onClick={increment}>+</button>; } function Count() { // use the context const { count } = useCounterContext(); return <span>{count}</span>; } function App() { // wrap the component with provider return ( <CounterProvider> <Count /> <Button /> </CounterProvider> );
4. Redux hooks
Redux là một công cụ nổi tiếng đối với nhiều nhà phát triển React, nếu không muốn nói là tất cả. Nó được sử dụng như một trình quản lý global state trong toàn bộ ứng dụng.
Redux đã đi vào hoạt động với những ưu điểm hấp dẫn chỉ trong một vài tháng sau khi phát hành lần đầu tiên của React. Redux cung cấp một giải pháp thay thế cho mẫu HOC (Higher Order Component) với phương thức connect()
được xây dựng sẵn
Các hook đáng chú ý nhất được cung cấp là:
useSelector
useDispatch
useStore
Tài liệu này có một chút phức tạp nhưng nó khá tốt, nó sẽ cung cấp cho bạn mọi thông tin cần thiết để bắt đầu sử dụng chúng.
import {useSelector, useDispatch} from "react-redux"; import React from "react"; import * as actions from "./actions"; const Example = () => { const dispatch = useDispatch() const counter = useSelector(state => state.counter) return ( <div> <span> {counter.value} </span> <button onClick={() => dispatch(actions.incrementCounter)}> Counter +1 </button> </div> ); }
5. React hook form
React hook form là một thư viện form hook tương tự như biểu mẫu Formik và Redux, nhưng tốt hơn. Với cú pháp đơn giản, tốc độ nhanh, render ít hơn và khả năng bảo trì tốt hơn, nó bắt đầu leo lên các bảng xếp hạng trên GitHub.
React hook form có kích thước nhỏ và được xây dựng với đặc biệt chú trọng về hiệu suất. Thư viện còn cung cấp một công cụ form builder tuyệt vời. Và nó có một trong những repo về React có lượng star lớn trên GitHub – 14,8k.
import React from "react"; import { useForm } from "react-hook-form"; function App() { const { register, handleSubmit, errors } = useForm(); const onSubmit = (data) => { // logs {firstName:"exampleFirstName", lastName:"exampleLastName"} console.log(data); }; return ( <form onSubmit={handleSubmit(onSubmit)}> <input name="firstName" ref={register} /> <input name="lastName" ref={register({ required: true })} /> {errors.lastName && <span>"Last name is a required field."</span>} <input name="age" ref={register({ required: true })} /> {errors.age && <span>"Please enter number for age."</span>} <input type="submit" /> </form> ); }
6. useDebounce
useDebounce là một hook nhỏ được sử dụng cho mục đích hỗ trợ debug. Hook này được sử dụng để trì hoãn việc thực thi chức năng, và nó cũng thường được sử dụng trong các input trong form nơi dùng để nhập dữ liệu.
import React, { useState } from "react"; import { useDebounce } from "use-debounce"; export default function Input() { const [text, setText] = useState("Hello"); const [value] = useDebounce(text, 1000); return ( <div> <input defaultValue={"Hello"} onChange={(e) => { setText(e.target.value); }} /> <p>Value: {text}</p> <p>Debounced value: {value}</p> </div> ); }
7. useLocalStorage
useLocalStorage là một hook nhỏ giống như cái ở trên. Nó thực sự hữu ích để giải nén và thiết lập dữ liệu bên trong localStorage. Với hook này, manipulation được thực hiện dễ dàng.
Hook cung cấp JSON serialization và đồng bộ hóa JSON tự động trên nhiều tab và được viêt bằng TypeScript nên nó cung cấp nhiều type.
Tài liệu được viết một cách chất lượng và khá dễ hiểu với nhiều ví dụ.
import React, { useState } from "react"; import { writeStorage } from '@rehooks/local-storage'; export default function Example() { let counter = 0; const [counterValue] = useLocalStorage('counterValue'); return ( <div> <span>{counterValue}</span> <button onClick={() => writeStorage('i', ++counter)}> Click Me </button> </div> ); }
8. usePortal
usePortal giúp việc tạo dropdowns, modals, notification popups, tooltips… cực kì dễ dàng! Nó cũng cho phép tạo các phần tử bên ngoài hệ thống phân cấp DOM của ứng dụng (để tìm hiểu cách Portals hoạt động, bấm vào đây ).
Hook này làm việc với cả SSR (Server Side Rendering). Nó được viết bằng TypeScript và có một built-in state. Đối với các chức năng, nó cung cấp tùy chỉnh đầy đủ về styling portal và rất nhiều tùy chọn khác.
Tài liệu được viết khá tốt – đặc biệt là có sẵn nhiều ví dụ minh họa sẽ là quá đủ để bắt đầu tự sử dụng thư viện/hook này đúng không!?
import React, { useState } from "react"; import usePortal from "react-useportal"; const Example = () => { const { ref, openPortal, closePortal, isOpen, Portal } = usePortal() return ( <> <button ref={ref} onClick={() => openPortal()}> Open Portal </button> {isOpen && ( <Portal> <p> This Portal handles its own state.{' '} <button onClick={closePortal}>Close me!</button>, hit ESC or click outside of me. </p> </Portal> )} </> ) }
9. useHover
useHover là React state để xác định xem một phần tử React có đang được di chuột hay không. Hook này khá trực quan và dễ sử dụng. Thư viện có kích thước nhỏ nhưng rất mạnh nếu bạn đủ sáng tạo.
Nó cung cấp độ trễ của hiệu ứng di chuột và hỗ trợ TypeScript. Tài liệu không quá chi tiết, nhưng nó sẽ chỉ cho bạn cách sử dụng nó tốt nhất.
import useHover from "react-use-hover"; const Example = () => { const [isHovering, hoverProps] = useHover(); return ( <> <span {...hoverProps} aria-describedby="overlay">Hover me</span> {isHovering ? <div> I’m a little tooltip! </div> : null} </> ); }
10. React router hooks
React router là một trong những thư viện phổ biến nhất cho React. Nó được sử dụng để định tuyến và lấy lịch sử URL của ứng dụng, …
Các hook được cung cấp là:
useHistory
useLocation
useParams
useRouteMatch
Chỉ cần đọc tên hook là bạn đủ để bạn hiểu chức năng chính của nó là gì rồi đúng không?
UseHistory
sẽ lấy dữ liệu về lịch sử của ứng dụng và các method, chẳng hạn như push, cái mà sẽ đẩy đến một route mới. UseLocation
sẽ trả về đối tượng đại diện cho URL hiện tại. UseParams
sẽ trả về một đối tượng gồm các cặp key-value của các tham số URL của route hiện tại. Và cuối cùng, useRouteMatch
sẽ cố gắng khớp URL hiện tại với URL đã cho cái mà có thể là một chuỗi hoặc một đối tượng của các option khác nhau.
Tài liệu mô tả của thư viện này rất tốt và tất nhiên là có rất nhiều ví dụ minh họa trong tài liệu để bạn tham khảo.
import { useHistory, useLocation, useRouteMatch } from "react-router-dom"; const Example = () => { let history = useHistory(); let location = useLoction(); let isMatchingURL = useRouteMatch("/post/11"); function handleClick() { history.push("/home"); } return ( <div> <span>Current URL: {location.pathname}</span> {isMatchingURL ? <span>Matching provided URL! Yay! </span> : null} <button type="button" onClick={handleClick}> Go home </button> </div> ); }
Nhiều cái hơn nữa để lựa chọn
Có rất nhiều thư viện react hook khác trên mạng, nhưng đây là những thứ mà mình cảm thấy có ích nhất cho dự án của bạn. Nếu thực sự thích chúng, hãy thử dùng ngay cho dự án.
Hy vọng bạn đã thấy bài viết này thú vị và bạn sẽ học được điều gì đó mới mẻ. Chúc bạn tìm thấy niềm vui khi khám phá thêm về các hooks.
Bình luận. Cùng nhau thảo luận nhé!