成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

React Hooks 之 useFetch

Ryan_Li / 1199人閱讀

摘要:而每次捕獲出的錯(cuò)誤可能需要打印出來以檢測(cè)。同時(shí)有些同學(xué)不習(xí)慣使用來捕獲錯(cuò)誤,這就可能造成不可預(yù)計(jì)的問題。是否立即請(qǐng)求并接受初始化返回值業(yè)務(wù)我們并不希望初始化的是否立即發(fā)送請(qǐng)求。

前言

自 React Hooks 16.8.0 后帶來了 React hooks 這一特性。這一特性在沒有破壞性的更新下為我們帶來了更加舒爽的開發(fā)方式。過去我們常常因providers,consumers,高階組件,render props 等形成“嵌套地獄”。盡管 Class Component 在某種程度上為我們提供了更方便的寫法以及生命周期,但同時(shí)也帶來了一些不好的地方。例如難以理解的 class 內(nèi)部原理、難以測(cè)試的聲明周期。而 React Hooks 為我們提供了一種 Function Component 的寫法,讓我們用更少的代碼寫出更加優(yōu)雅、易懂的代碼。本文不做 React Hooks API的講述,如有不懂,請(qǐng)移步 Hooks 簡介

發(fā)送服務(wù)端請(qǐng)求所面臨的問題

1. try / catch問題

在開發(fā)代碼時(shí),我們發(fā)送后端請(qǐng)求后接受到的數(shù)據(jù),需要使用try/catch來捕獲錯(cuò)誤。而每次捕獲出的錯(cuò)誤可能需要打印出來以檢測(cè)bug。這樣我們每次都會(huì)寫同樣的代碼,這樣在開發(fā)過程中很不友好。同時(shí)有些同學(xué)不習(xí)慣使用 try/catch 來捕獲錯(cuò)誤,這就可能造成不可預(yù)計(jì)的問題。

import React, { useCallback, useReducer, useEffect } from "react"
import { TimeNumberType, PageType } from "common/constant/interface"

type ParamsType = PageType & TimeNumberType

const reducer = (state: ParamsType, action: Actions) => {
  const { payload } = action
  return { ...state, ...payload }
}
const postListData = (params: ParamsType) => post("/network/api/test/getlist", params)
const initialParams = {
  pageSize: 10,
  pageNumber: 1,
  startTime: 0,
  endTime: 0
}

const ListComponent = () => {
  const [params, dispatch] = useReducer(reducer, initialState)
  const getList = async () => {
    // try catch
    try {
      const res = await postListData(params)
      console.log(res)
    } catch (err) {
      console.error(err)
    }
  }

  useEffect(() => {
    getList()
  }, [params])
}

demo中展示了在業(yè)務(wù)場(chǎng)景中發(fā)送請(qǐng)求的場(chǎng)景,當(dāng)發(fā)送請(qǐng)求多了之后我們會(huì)每次手動(dòng)try / catch,雖然不是大問題,但是重復(fù)代碼寫多了會(huì)覺得難受...。下面看第二個(gè)功能。

2. 請(qǐng)求狀態(tài)

在實(shí)際的業(yè)務(wù)場(chǎng)景中,我們向后端發(fā)送請(qǐng)求時(shí),往往伴隨著用戶點(diǎn)擊多次,但是只能發(fā)送一次請(qǐng)求的問題,這時(shí)我們需要手動(dòng)加鎖。并且在很多場(chǎng)景中我們需要知道請(qǐng)求狀態(tài)來為頁面設(shè)置loading。例如:

import React, { useCallback, useReducer, useEffect } from "react"
import { TimeNumberType, PageType } from "common/constant/interface"
import { DateRangePicker, Table } from "UI"

type ParamsType = PageType & TimeNumberType

const TIME = Symbol("time")
const PAGE = Symbol("page")
const reducer = (state: ParamsType, action: Actions) => {
  const { payload } = action
  return { ...state, ...payload }
}
const postListData = (params: ParamsType) => post("/network/api/test/getlist", params)
const initialParams = {
  pageSize: 10,
  pageNumber: 1,
  startTime: 0,
  endTime: 0
}

const ListComponent = () => {
  const [params, dispatch] = useReducer(reducer, initialState)
  const [loading, setLoading] = useState(false)
  const [list, setList] = useState({})
  
  const getList = async () => {
    // loading is true
    if (loading) return
    // set loading status
    setLoading(true)
    // try catch
    try {
      const res = await postListData(params)
      setList(res)
      setLoading(false)
    } catch (err) {
      console.error(err)
      setLoading(false)
    }
  }

  useEffect(() => {
    getList()
  }, [params])
  
  return (
      
{ dispatch({ payload: { pageNumber }, type: PAGE }) }} list={list} // 數(shù)據(jù)是否正在加載,以此來判斷是否需要展示loading loading={loading} /> ) }

demo中展示了日期組件以及包含有分頁器的 Table組件,當(dāng)日期發(fā)生變更,或者分頁器發(fā)生變更時(shí),我們需要dispatch來更新請(qǐng)求參數(shù),從而發(fā)送請(qǐng)求。在發(fā)送請(qǐng)求時(shí)如果正在請(qǐng)求,則忽略,而不在請(qǐng)求時(shí)需要手動(dòng)加鎖,來防止多次請(qǐng)求。
同時(shí)Table需要根據(jù)請(qǐng)求狀態(tài)來判斷是否需要展示loading。

解決問題

基于以上的問題,我們能否通過 Hooks 來封裝一個(gè) custom hooks來解決問題。

1. 明確目標(biāo)

custom hooks 解決的問題

解決每個(gè)函數(shù)都要統(tǒng)一寫try/catch的流程

解決發(fā)送請(qǐng)求需要手動(dòng)加鎖防止多次重復(fù)請(qǐng)求的痛點(diǎn)

不需要在手動(dòng)useState loading,直接獲取loading值

所以我們需要在 custom hooks 中發(fā)送請(qǐng)求、暴露出請(qǐng)求后的值、暴露 loading 狀態(tài)、以及用戶可能需要多次請(qǐng)求,這就需要暴露一個(gè)勾子。在發(fā)生請(qǐng)求錯(cuò)誤時(shí)可能需要做某些操作,所以還需要暴露在錯(cuò)誤時(shí)回調(diào)的勾子函數(shù)。

是否立即請(qǐng)求并接受初始化返回值

業(yè)務(wù)我們并不希望初始化的是否立即發(fā)送請(qǐng)求。 并且能夠有初始化的返回值

支持泛型

在TS中,開發(fā)者希望能夠自定義請(qǐng)求的參數(shù)類型,以及請(qǐng)求結(jié)果的類型

2. 定義函數(shù)

useFetch 函數(shù)

import { useState, useEffect } from "react";

/**
 * 1. 解決每個(gè)函數(shù)都要統(tǒng)一寫try/catch的流程
 * 2. 解決發(fā)送請(qǐng)求需要手動(dòng)加鎖防止多次重復(fù)請(qǐng)求的痛點(diǎn)
 * 3. 不需要在手動(dòng)useState loading了~,直接獲取fetching值
 * 4. (甚至在參數(shù)發(fā)生變化時(shí)只需要傳入更改的參數(shù)就OK)已刪除
 * @param getFunction 發(fā)送請(qǐng)求的函數(shù)
 * @param params 參數(shù)
 * @param initRes 初始化值
 * @param execute 是否立即執(zhí)行請(qǐng)求函數(shù)
 */

// R, P支持泛型
function UseFetch(
  getFunction: any,
  params: P,
  initRes");

3. 如何使用

根據(jù)最初的demo我們改造一下代碼

import React, { useCallback, useReducer, useEffect } from "react"
import { TimeNumberType, PageType } from "common/constant/interface"
import { DateRangePicker, Table } from "UI"
// 導(dǎo)入 useFetch
import { useFetch } from "custom-hooks" 

type ParamsType = PageType & TimeNumberType
type ListInfo = {list: Array, total: number}

const TIME = Symbol("time")
const PAGE = Symbol("page")
const reducer = (state: ParamsType, action: Actions) => {
  const { payload } = action
  return { ...state, ...payload }
}
const postListData = (params: ParamsType) => post("/network/api/test/getlist", params)
const initialParams = {
  pageSize: 10,
  pageNumber: 1,
  startTime: 0,
  endTime: 0
}

const ListComponent = () => {
  const [params, dispatch] = useReducer(reducer, initialState)
  
  const [list, loading, getList] = useFetch(
    getWithDraw,
    state,
    { list: [], total: 0 },
    false
  )

  useEffect(() => {
    getList()
  }, [params])
  
  return (
      
{ dispatch({ payload: { pageNumber }, type: PAGE }) }} list={list} // 數(shù)據(jù)是否正在加載,以此來判斷是否需要展示loading loading={loading} /> ) }

對(duì)比代碼我們可以看到中間的請(qǐng)求的代碼被我們干掉了,使用 useFetch 來將狀態(tài)以及發(fā)送請(qǐng)求封裝在一起。能夠讓我們寫更少的代碼。


同時(shí) useFetch的第3個(gè)參數(shù)當(dāng)傳入的為 null 時(shí),可以模擬請(qǐng)求發(fā)送錯(cuò)誤,這樣我們可以在開發(fā)時(shí)做兜底方案。

4. 也許并不想要那么多值。

也許有些請(qǐng)求不需要關(guān)注請(qǐng)求狀態(tài)

  // 解構(gòu)賦值、空著就好
  const [list, , getList] = useFetch(
    getWithDraw,
    state,
    { list: [], total: 0 },
    false
  )

本文完~

如有問題,歡迎指出~

文章版權(quán)歸作者所有,未經(jīng)允許請(qǐng)勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請(qǐng)注明本文地址:http://systransis.cn/yun/6780.html

相關(guān)文章

  • React Hooks 從入門到上手

    摘要:前言樓主最近在整理的一些資料,為項(xiàng)目重構(gòu)作準(zhǔn)備,下午整理成了這篇文章。給傳入的是一個(gè)初始值,比如,這個(gè)按鈕的最初要顯示的是。取代了提供了一個(gè)統(tǒng)一的。 showImg(https://segmentfault.com/img/bVbpUle?w=900&h=550); Hooks are a new addition in React 16.8. They let you use sta...

    XFLY 評(píng)論0 收藏0
  • React Hooks 從入門到上手

    摘要:前言樓主最近在整理的一些資料,為項(xiàng)目重構(gòu)作準(zhǔn)備,下午整理成了這篇文章。給傳入的是一個(gè)初始值,比如,這個(gè)按鈕的最初要顯示的是。取代了提供了一個(gè)統(tǒng)一的。 showImg(https://segmentfault.com/img/bVbpUle?w=900&h=550); Hooks are a new addition in React 16.8. They let you use sta...

    zhouzhou 評(píng)論0 收藏0
  • React 異步數(shù)據(jù)管理思考

    摘要:異步數(shù)據(jù)管理一直是前端的一個(gè)重點(diǎn)和難點(diǎn),可以這么說,的應(yīng)用會(huì)有異步數(shù)請(qǐng)求據(jù)并在中消費(fèi),并且在相當(dāng)多的應(yīng)用中,處理異步數(shù)據(jù)是它的核心業(yè)務(wù)邏輯??偨Y(jié)個(gè)人認(rèn)為,異步數(shù)據(jù)不應(yīng)該使用狀態(tài)管理來維護(hù),應(yīng)該放在組件內(nèi)。 異步數(shù)據(jù)管理一直是前端的一個(gè)重點(diǎn)和難點(diǎn),可以這么說,80%的 web 應(yīng)用會(huì)有異步數(shù)請(qǐng)求據(jù)并在 UI 中消費(fèi),并且在相當(dāng)多的 web 應(yīng)用中,處理異步數(shù)據(jù)是它的核心業(yè)務(wù)邏輯。 在 R...

    BearyChat 評(píng)論0 收藏0
  • React Hooks 入門(2019)

    摘要:到目前為止,表達(dá)這種流程的基本形式是課程。按鈕依次響應(yīng)并更改獲取更新的文本。事實(shí)證明不能從返回一個(gè)??梢栽诮M件中使用本地狀態(tài),而無需使用類。替換了提供統(tǒng)一,和。另一方面,跟蹤中的狀態(tài)變化確實(shí)很難。 備注:為了保證的可讀性,本文采用意譯而非直譯。 在這個(gè) React鉤子 教程中,你將學(xué)習(xí)如何使用 React鉤子,它們是什么,以及我們?yōu)槭裁催@樣做! showImg(https://segm...

    GitCafe 評(píng)論0 收藏0
  • 精讀《Function Component 入門》

    摘要:比如就是一種,它可以用來管理狀態(tài)返回的結(jié)果是數(shù)組,數(shù)組的第一項(xiàng)是值,第二項(xiàng)是賦值函數(shù),函數(shù)的第一個(gè)參數(shù)就是默認(rèn)值,也支持回調(diào)函數(shù)。而之所以輸出還是正確的,原因是的回調(diào)函數(shù)中,值永遠(yuǎn)指向最新的值,因此沒有邏輯漏洞。 1. 引言 如果你在使用 React 16,可以嘗試 Function Component 風(fēng)格,享受更大的靈活性。但在嘗試之前,最好先閱讀本文,對(duì) Function Com...

    Scholer 評(píng)論0 收藏0

發(fā)表評(píng)論

0條評(píng)論

最新活動(dòng)
閱讀需要支付1元查看

<