JavaScript 는 promise 를 사용 하여 중복 요청 을 처리 합 니 다.

6108 단어 jspromise반복
1.왜 이 글 을 써 야 합 니까?
중복 요청 을 처리 하 는 글 은 여러분 도 많이 보 셨 을 것 입 니 다.대부분 response 가 돌아 오기 전에 중복 요청 을 발견 하면 return 이 떨 어 지 는 것 과 절 류/떨 림 방지 로 사용자 의 빈번 한 조작 을 간접 적 으로 피 하 는 두 가지 버 전 으로 나 뉘 어 있 습 니 다.최근 에 사용 하 는 과정 에서 이 두 버 전 은 일부 장면 에서 한계 가 있 음 을 발견 했다.
2.문제 장면
그림 에서 보 듯 이 h5 페이지 의 상단 과 아래쪽 에 이 명함 구성 요 소 를 표시 해 야 합 니 다.이 명함 들 의 정 보 는 하나의 인 터 페 이 스 를 통 해 얻 을 수 있 습 니 다.이 구성 요소 가 현재 페이지 에서 초기 화 되면 두 번 반복 되 는 요청 이 발생 합 니 다.


이 럴 때 몇 가지 선택 에 직면 하 게 된다.
1.중복 요청 에 대해 어떠한 처리 도 하지 않 는 다.
  • 단점 1:불필요 한 자원 낭 비 를 초래 하고 서버 의 압력 을 증가 시킨다
  • 단점 2:http 요청 은 브 라 우 저 에서 병발 수 제한 이 있 습 니 다.만약 에 페이지 첫 화면 에 대한 요청 이 많 고 등급 별로 불 러 오지 않 으 면 요청 이 막 히 기 쉬 우 며 사용자 가 주요 내용 을 처음 보 는 데 영향 을 줍 니 다
  • 2.중복 요청 에 대해 서 는 직접 return 합 니 다.이것 도 일부 문장의 방법 이지 만 이런 방법 은 한계 가 있다.바로 뒤의 중복 요청 이 모두 무효 요청 이 라 고 직접 인정 하 는 것 이다.
  • 무효 요청 장면:사용자 가 특정한 단 추 를 누 르 면 조회 하거나 저장 합 니 다.요청 결과 가 돌아 오기 전에 뒤에 누 르 면 기본적으로 무효 요청 이 라 고 할 수 있 습 니 다.이런 요청 은 막 아야 합 니 다.물론 버튼 에 절 류/떨 림 방지 기능 을 추가 하여 이 문 제 를 피 할 수도 있다
  • 왜 현재 장면 에 적용 되 지 않 습 니까?이 두 명함 의 구성 요 소 는 모두 데이터 로 렌 더 링 해 야 합 니 다.두 번 째 중복 요청 이 return 되면 그 중의 한 구성 요소 의 명함 은 데이터 가 없습니다.
  • 3.구성 요소 에서 요청 을 빼 서 부모 급 업무 페이지 에 넣 고 props 방식 으로 구성 요소 에 전달 합 니 다.
  • 장점:한 번 만 요청 하면 두 구성 요소 가 데 이 터 를 공유 할 수 있 습 니 다.
  • 한계 성:단일 업무 페이지 에 만 사용 할 수 있 는 상황.사실 이 구성 요 소 는 많은 업무 페이지 에서 사용 되 고 있 습 니 다.요청 한 함 수 를 공용 api 로 추출 하 더 라 도 모든 업무 페이지 가 초기 화 될 때 한 번 호출 한 다음 에 props 방식 으로 구성 요 소 를 전달 해 야 합 니 다.
  • 해결 방법
    핵심 사상
  • handle List 의 배열 초기 화
  • 요청 발송 전 입 참 여부 에 따라 중복 요청 여 부 를 판단 합 니 다.
  • 반복 되 지 않 는 요청:요청 한 인자 와 요청 한 Promise 를 배열 에 추가 합 니 다
  • 중복 요청:find 찾기 를 사용 하여 해당 하 는 Promise
  • 를 직접 되 돌려 줍 니 다.
  • 요청 이 완료 되면 handle List 에 추 가 된 요청 정 보 를 제거 합 니 다.
  • 이 방안 은 axios,jq,fetch,애플 릿 request 를 사용 하 든 무엇이든 사용 할 수 있 습 니 다.여기에 실현 의 원 리 를 쓰 고 사용 할 때 해당 하 는 코드 를 해당 하 는 요청 시기 에 직접 놓 으 면 된다.
    코드 예제
    
    let handleList = [] //     
    /**
     *     
     * @author waldon
     * @date 2020/6/9
     */
    const httpRequest = () => {
      return new Promise((resolve) => {
        setTimeout(() => {
          resolve(`    ,    :${new Date().getTime()}`)
        }, 1000)
      })
    }
    /**
     *        
     * @author waldon
     * @date 2020/6/9
     * @param {String} url -
     * @param {Object} requestObj -     
     * @returns {Promise} -    promise
     */
    function requestTest(url, requestObj = {}) {
      //                ,JSON.stringify            
      //                      ,                     
      //          ,         api,lodash     api
      const sameHandle = handleList.find(
        (item) => item.url === url && JSON.stringify(item.requestObj) === JSON.stringify(requestObj)
      )
      if (sameHandle) {
        //                promise
        console.log(`      ,    `)
        return sameHandle.handle
      }
      const handle = new Promise((resolve, reject) => {
        httpRequest()
          .then((res) => {
            resolve(res)
          })
          .catch((err) => {
            reject(err)
          })
          .finally(() => {
            //         ,            
            handleList = handleList.filter(
                  (item) =>
                    item.url !== url && JSON.stringify(item.requestObj) !== JSON.stringify(requestObj)
                )
          })
      })
      handleList.push({ url, requestObj, handle })
      return handle
    }
    
    // *******************************             *******************************
    const params = {
      name: 'waldon'
    }
    requestTest('/ajax/sameUrl', params).then((res) => {
      console.log(`      `, res)
      console.log(`handleList:`, handleList)
    })
    requestTest('/ajax/sameUrl', params).then((res) => {
      console.log(`      `, res)
      console.log(`handleList:`, handleList) //              
      setTimeout(() => {
        console.log(`      handleList:`, handleList) //     handleList         
      }, 100)
    })
    setTimeout(() => {
      //     500ms  ,         1s   ,           
      requestTest('/ajax/sameUrl', params).then((res) => {
        console.log(`      `, res)
        console.log(`handleList:`, handleList)
      })
    }, 500)
    
    
    출력 결과
    중복 요청 이 있 으 면 바로 되 돌려 줍 니 다.
    중복 요청 이 있 으 면 바로 되 돌려 줍 니 다.
    첫 번 째 요청 결과 요청 성공,시간 스탬프:1621650375540
    handleList: [
      {
        url: '/ajax/sameUrl',
        requestObj: { name: 'waldon' },
        handle:Promise{'요청 성공,시간 스탬프:1621650375540'}
      }
    ]
    중복 요청 결과 요청 성공,시간 스탬프:1621650375540
    handleList: [
      {
        url: '/ajax/sameUrl',
        requestObj: { name: 'waldon' },
        handle:Promise{'요청 성공,시간 스탬프:1621650375540'}
      }
    ]
    중복 요청 결과 요청 성공,시간 스탬프:1621650375540
    handleList: [
      {
        url: '/ajax/sameUrl',
        requestObj: { name: 'waldon' },
        handle:Promise{'요청 성공,시간 스탬프:1621650375540'}
      }
    ]
    요청 완료 후 handleList:[]
    코드 주소 codepen
    https://codepen.io/waldonUB/pen/ZEeeONM
    주의 점
  • response 의 데 이 터 를 추가 삭제 하지 마 세 요.반복 요청 이 Promise 에 있 는 대상 의 인용 주소 가 모두 같 기 때문에 변경 하면 데이터 오염 이 발생 할 수 있 습 니 다.특수 한 경우 응답 결 과 를 간단하게 복사 하여 처리 하거나 해당 하 는 단언 을 추가 할 수 있 습 니 다.
  • 중복 되 는 요청 을 처리 할 때 log 에서 알려 주 는 것 이 좋 습 니 다.또한 구성 요소 에 원인 과 장면 을 주석 하여 다른 사람 이 잘못 고치 지 않도록 하 는 것 이 좋 습 니 다
  • 극단 적 인 상황 에서 요청 이 실 패 했 습 니 다.유효 시간 을 설정 하고 요청 정 보 를 제거 하 며 패 킷 이 너무 많이 쌓 여 쓸모없는 요청 정보 로 인해 메모리 가 누 출 되 지 않도록 합 니 다.
  • 자 바스 크 립 트 가 promise 를 사용 하여 중복 요청 을 처리 하 는 것 에 관 한 이 글 은 여기까지 소개 되 었 습 니 다.더 많은 관련 js promise 중복 요청 내용 은 우리 의 이전 글 을 검색 하거나 아래 의 관련 글 을 계속 조회 하 시기 바 랍 니 다.앞으로 많은 응원 바 랍 니 다!

    좋은 웹페이지 즐겨찾기