Request encapsulation preamble

  • Usually in small program projects, wechat already provides network request API, but often this is not enough for us, so we have the following package
  • We often have a lot of requirements for Requset requests. Here we simply list the requirements and code implementation
    1. According to different versions of the small programdevelop --> trial --> releaseVersions use different domain names
    2. Request interceptor, which processes the current request before it is sent
    3. Controllable request loading animation, and support to expand the custom loading text prompt
    4. Perform corresponding processing according to the response result of the request returned by the back end (columns 210 not logged in and 220 login invalid must be jointly defined with the back end)
  • The author usedTaroRequest encapsulation, explain the steps are basically described in the code, the author did not elaborate on each method split
  • The author is based on the previously shared request encapsulation in the Taro template, split to tell the idea for reference
  • Preamble too much nonsense below the code

start

  • First of all in the projectpagesPeers createserviceFolder, and then create 3 files respectively:
    1. interceptors.tsRequest response interceptor.
    import Taro from '@tarojs/taro'
    import { HTTP_STATUS } from './status'
    // Mobx is used to deal with login failure, login failure, etc
    import cartStroe from '.. /store/user'
    
    const customInterceptor = (chain:any) = > {
    
        const requestParams = chain.requestParams
    
        return chain.proceed(requestParams).then((res:any) = > {
            / / remove loading
            if(requestParams.loading) Taro.hideLoading()
            switch(res.statusCode) {
                case HTTP_STATUS.SUCCESS:
                    const result = res.data
                    if(res.data.code === 200) {
                        // The interface is normal and there is no exception
                        result.success = true
                    } else {
                        If an error message is displayed, add openErrTips: false to disable the request
                        if(requestParams.openErrTips && result.msg) Taro.showToast({ title: result.msg, icon: 'none' })
                        // Login expired or not logged in needs to be defined with the backend
                        if(result.code === 210 || result.code === 220) {
                            // Jump login to clear user information and other processing
                            cartStroe.setStatus(false)
                            cartStroe.setUser({})
                            Taro.showToast({ title: (result.code === 210 ? 'Not logged in, please log in first' : 'Login info invalid, please log in again' ), icon: 'none' })
                            Taro.navigateTo({ url: '/pages/login/index' })
                            return Promise.reject(result)
                        }
                    }
                    return result
    
                case HTTP_STATUS.CREATED:
                    return Promise.reject('Request successful and server creates new resource')
    
                case HTTP_STATUS.ACCEPTED:
                    return Promise.reject('Request accepted but no resource created')
    
                case HTTP_STATUS.CLIENT_ERROR:
                    return Promise.reject('Server does not understand request syntax')
    
                case HTTP_STATUS.AUTHENTICATE:
                    return Promise.reject('The request requires authentication. For web pages that require login, the server may return this response '.)
    
                case HTTP_STATUS.FORBIDDEN:
                    return Promise.reject('Server rejected request')
    
                case HTTP_STATUS.NOT_FOUND:
                    return Promise.reject('Server could not find requested page')
    
                case HTTP_STATUS.SERVER_ERROR:
                    return Promise.reject('(Server internal error) The server encountered an error and could not complete the request ')
    
                case HTTP_STATUS.BAD_GATEWAY:
                    return Promise.reject('(Error gateway) Server acting as gateway or proxy receives invalid response from upstream server ')
    
                case HTTP_STATUS.SERVICE_UNAVAILABLE:
                    return Promise.reject('The server is currently unavailable (due to overloading or downtime for maintenance). Usually, this is a temporary state. ')
    
                case HTTP_STATUS.GATEWAY_TIMEOUT:
                    return Promise.reject('(Gateway timeout) Server acted as gateway or proxy but did not receive request from upstream server in time ')
    
                default:
                    console.log('Developer please check request interception for unmatched error and return statusCode :>>', res.statusCode)
                    break}})}Taro provides two built-in interceptors
    // logInterceptor - Prints information about the request
    // timeoutInterceptor - Throws an error when the request times out.
    const interceptors = [customInterceptor, Taro.interceptors.logInterceptor]
    
    export default interceptors
    Copy the code
    1. status.tsHTTP common response status code prompt (easy for developers to find the source of the request error).
    export const HTTP_STATUS = {
        // The request was successfully processed. This status code is normally returned
        SUCCESS: 200.// The request succeeds and the server creates a new resource
        CREATED: 201.// The request was accepted but the resource was not created
        ACCEPTED: 202.// The server does not understand the request syntax
        CLIENT_ERROR: 400.// The request requires authentication. The server may return this response for a web page that requires login
        AUTHENTICATE: 401.// The server rejected the request
        FORBIDDEN: 403.// The server could not find the requested page
        NOT_FOUND: 404.// (server internal error) The server encountered an error and could not complete the request
        SERVER_ERROR: 500.// (error gateway) The server acting as a gateway or proxy received an invalid response from the upstream server
        BAD_GATEWAY: 502.// The server is currently unavailable (due to overloading or downtime for maintenance). Usually, this is a temporary state.
        SERVICE_UNAVAILABLE: 503.// (gateway timeout) The server acted as a gateway or proxy, but did not receive the request from the upstream server in time
        GATEWAY_TIMEOUT: 504
    }
    
    /** ** const HTTP_STATUS = {* '200': 'request server succeeded ', * '201': '' * } * if(HTTP_STATUS[res.statusCode]) * console.log(HTTP_STATUS[res.statusCode]) * else * Console. log(' please check request interception for unmatched error and return statusCode :>> ${res.statuscode} ') */
    Copy the code
    1. index.tsEncapsulate the request export for invocation.
    import Taro from '@tarojs/taro'
    
    import interceptors from './interceptors'
    
    interceptors.forEach(interceptorItem= > Taro.addInterceptor(interceptorItem))
    // Module, namespace, basic interface declaration
    declare namespace RequestProps {
        interface Method {
            'GET'.'POST'.'PUT'.'DELETE'
        }
        interface Options {
            url: string,
            method: keyof Method, 
            data: any, loading? : boolean, loadingTitle? : string, contentType? : string, openErrTips? : boolean } interface requestParams {url: string,
            method: keyof Method,
            data: any,
            header: any, loading? : boolean, loadingTitle? : string, contentType? : string, openErrTips? : boolean } }* develop: 'trial ',' trial ', release: NODE_ENV: dev -> beta -> Uat -> pro *@returns The domain name * /
    const getVersion = () = > {
        // @ts-ignore
        switch (__wxConfig.envVersion)
        {
        case 'develop':
            return 'http://develop.gavinpeng.club'
    
        case 'trial':
            return 'http://trial.gavinpeng.club'
    
        case 'release':
            return 'http://release.gavinpeng.club'
    
        default:
            return 'http://develop.gavinpeng.club'}}class Request {
        baseOptions(options: RequestProps.Options) {
            let { url, method, data } = options
            // Filter extended attributes
            let{ loading, loadingTitle, contentType, openErrTips, ... rest } = dataif(loading) Taro.showLoading({ title: loadingTitle || 'Loading... '.mask: true  })
            const requestParams: RequestProps.requestParams = {
                url: getVersion() + url,
                method,
                data: rest,
                header: {
                    // Support custom contentType
                    'content-type': contentType || 'application/json'.// Token
                    'Authorization': Taro.getStorageSync('token')
                    // Add a header object to the request data parameter to filter syntax sugar... Header here do not do too much explanation, need to add their own understanding
                    / /... header
                },
                // Whether the request is loaded is passed to the request response interceptor to clear loading
                loading,
                openErrTips
            }
            return Taro.request(requestParams)
        }
        
        get(url:string, data:any) {
            return this.baseOptions({ url, method:'GET', data })
        }
    
        post(url:string, data:any) {
            return this.baseOptions({ url, method:'POST', data })
        }
    }
    
    export default new Request()
    Copy the code
  • Use mode (THE author distinguishes interface management for interface modules)
    1. In the projectpagesPeers createapiFolder (Unified Management Interface)
    2. inapiTo establishindex.ts(Export interface)
    import * as test from './test'
    
    const Api = {
        // Test the module. test,/ / XXX module
    }
    // Export all interfaces
    export default Api
    Copy the code
    1. inapiEstablish the test module interface listtest.ts
    /* * @author: Gavin * @createTime: XXXX * @describe: Test module related interface */
    // Introduce the encapsulated request method
    import request from '@/service/index'
    
    /** * test *@param params 
    * @returns * /
    export const isTest = (url:string, data:any) = > {
        return request.post(url, data)
    }
    Copy the code
    1. inpagePage import interfaceimport Api from '@/api/index'And use the interface
    Api.isTest({
        id: 1.name: 'Gavin'.// Extended parameters - Whether to load Non-mandatory Default: false
        loading: true.// Extension parameters - Whether to customize loadingTitle Optional Default: Loading... (Note: This parameter is invalid if loading is not enabled)
        loadingTitle: 'Custom load Prompt'.ContentType Optional Default: application/json
        contentType: 'x-www-form-urlencoded'.// Extended parameters n/A Request error Message openErrTips Optional Default: false
        openErrTips: true.// Extension parameters - The custom headers mentioned above need to be added to the wrapper
        // header: { }
    }).then((res:any) = > {
        / / success
    }).catch((err:any) = > {
        / / fail
    })
    Copy the code

At the end

  • If there is any wrong or wrong place in the process of telling, please point out, welcome all leaders to advise
  • Every sharing is for progress. In this process, talking about code ideas can also exercise my expression ability
  • Growth is the power of life, come onNew generation of migrant workers!

The TypeScript Chinese documentation guides requests to encapsulate statement source addresses