<span id="mktg5"></span>

<i id="mktg5"><meter id="mktg5"></meter></i>

        <label id="mktg5"><meter id="mktg5"></meter></label>
        最新文章專題視頻專題問答1問答10問答100問答1000問答2000關鍵字專題1關鍵字專題50關鍵字專題500關鍵字專題1500TAG最新視頻文章推薦1 推薦3 推薦5 推薦7 推薦9 推薦11 推薦13 推薦15 推薦17 推薦19 推薦21 推薦23 推薦25 推薦27 推薦29 推薦31 推薦33 推薦35 推薦37視頻文章20視頻文章30視頻文章40視頻文章50視頻文章60 視頻文章70視頻文章80視頻文章90視頻文章100視頻文章120視頻文章140 視頻2關鍵字專題關鍵字專題tag2tag3文章專題文章專題2文章索引1文章索引2文章索引3文章索引4文章索引5123456789101112131415文章專題3
        問答文章1 問答文章501 問答文章1001 問答文章1501 問答文章2001 問答文章2501 問答文章3001 問答文章3501 問答文章4001 問答文章4501 問答文章5001 問答文章5501 問答文章6001 問答文章6501 問答文章7001 問答文章7501 問答文章8001 問答文章8501 問答文章9001 問答文章9501
        當前位置: 首頁 - 科技 - 知識百科 - 正文

        深入koa-bodyparser原理解析

        來源:懂視網 責編:小采 時間:2020-11-27 22:02:12
        文檔

        深入koa-bodyparser原理解析

        深入koa-bodyparser原理解析:一、前置知識 在理解koa-bodyparser原理之前,首先需要了解部分HTTP相關的知識。 1、報文主體 HTTP報文主要分為請求報文和響應報文,koa-bodyparser主要針對請求報文的處理。 請求報文主要由以下三個部分組成: 報文頭部 空行 報文主體 而koa-
        推薦度:
        導讀深入koa-bodyparser原理解析:一、前置知識 在理解koa-bodyparser原理之前,首先需要了解部分HTTP相關的知識。 1、報文主體 HTTP報文主要分為請求報文和響應報文,koa-bodyparser主要針對請求報文的處理。 請求報文主要由以下三個部分組成: 報文頭部 空行 報文主體 而koa-

        一、前置知識

        在理解koa-bodyparser原理之前,首先需要了解部分HTTP相關的知識。

        1、報文主體

        HTTP報文主要分為請求報文和響應報文,koa-bodyparser主要針對請求報文的處理。

        請求報文主要由以下三個部分組成:

      1. 報文頭部
      2. 空行
      3. 報文主體
      4. 而koa-bodyparser中的body指的就是請求報文中的報文主體部分。

        2、服務器端獲取報文主體流程

        HTTP底層采用TCP提供可靠的字節流服務,簡單而言就是報文主體部分會被轉化為二進制數據在網絡中傳輸,所以服務器端首先需要拿到二進制流數據。

        談到網絡傳輸,當然會涉及到傳輸速度的優化,而其中一種優化方式就是對內容進行壓縮編碼,常用的壓縮編碼方式有:

      5. gzip
      6. compress
      7. deflate
      8. identity(不執行壓縮或不會變化的默認編碼格式)
      9. 服務器端會根據報文頭部信息中的Content-Encoding確認采用何種解壓編碼。

        接下來就需要將二進制數據轉換為相應的字符,而字符也有不同的字符編碼方式,例如對于中文字符處理差異巨大的UTF-8和GBK,UTF-8編碼漢字通常需要三個字節,而GBK只需要兩個字節。所以還需要在請求報文的頭部信息中設置Content-Type使用的字符編碼信息(默認情況下采用的是UTF-8),這樣服務器端就可以利用相應的字符規則進行解碼,得到正確的字符串。

        拿到字符串之后,服務器端又要問了:客戶端,你這一段字符串是啥意思啊?

        根據不同的應用場景,客戶端會對字符串采用不同的編碼方式,常見的編碼方式有:

      10. URL編碼方式: a=1&b=2
      11. JSON編碼方式: {a:1,b:2}
      12. 客戶端會將采用的字符串編碼方式設置在請求報文頭部信息的Content-Type屬性中,這樣服務器端根據相應的字符串編碼規則進行解碼,就能夠明白客戶端所傳遞的信息了。

        下面一步步分析koa-bodyparser是如何處理這一系列操作,從而得到報文主體內容。

        二、獲取二進制數據流

        NodeJS中獲取請求報文主體二進制數據流主要通過監聽request對象的data事件完成:

        // 示例一
        const http = require('http')
        
        http.createServer((req, res) => {
         const body = []
        
         req.on('data', chunk => {
         body.push(chunk)
         })
         
         req.on('end', () => {
         const chunks = Buffer.concat(body) // 接收到的二進制數據流
        
         // 利用res.end進行響應處理
         res.end(chunks.toString())
         })
        }).listen(1234)
        
        

        而koa-bodyparser主要是對co-body 的封裝,而【co-body】中主要是采用raw-body 模塊獲取請求報文主體的二進制數據流,【row-body】主要是對上述示例代碼的封裝和健壯性處理。

        三、內容解碼

        客戶端會將內容編碼的方式放入請求報文頭部信息Content-Encoding屬性中,服務器端接收報文主體的二進制數據了時,會根據該頭部信息進行解壓操作,當然服務器端可以在響應報文頭部信息Accept-Encoding屬性中添加支持的解壓方式。

        而【row-body】主要采用 inflation 模塊進行解壓處理。

        四、字符解碼

        一般而言,UTF-8是互聯網中主流的字符編碼方式,前面也提到了還有GBK編碼方式,相比較UTF-8,它編碼中文只需要2個字節,那么在字符解碼時誤用UTF-8解碼GBK編碼的字符,就會出現中文亂碼的問題。

        NodeJS主要通過Buffer處理二進制數據流,但是它并不支持GBK字符編碼方式,需要通過 iconv-lite 模塊進行處理。

        【示例一】中的代碼就存在沒有正確處理字符編碼的問題,那么報文主體中的字符采用GBK編碼方式,必然會出現中文亂碼:

        const request = require('request')
        const iconv = require('iconv-lite')
        
        request.post({
         url: 'http://localhost:1234/',
         body: iconv.encode('中文', 'gbk'),
         headers: {
         'Content-Type': 'text/plain;charset=GBK'
         }
        }, (error, response, body) => {
         console.log(body) // 發生中文亂碼情況
        })
        
        

        NodeJS中的Buffer默認是采用UTF-8字符編碼處理,這里借助【iconv-lite】模塊處理不同的字符編碼方式:

        const chunks = Buffer.concat(body)
         res.end(iconv.decode(chunks, charset)) // charset通過Content-Type得到
        

        五、字符串解碼

        前面已經提到了字符串的二種編碼方式,它們對應的Content-Type分別為:

      13. URL編碼 application/x-www-form-urlencoded
      14. JSON編碼 application/json
      15. 對于前端來說,URL編碼并不陌生,經常會用于URL拼接操作,唯一需要注意的是不要忘記對鍵值對進行decodeURIComponent()處理。

        當客戶端發送請求主體時,需要進行編碼操作:

        'a=1&b=2&c=3'

        服務器端再根據URL編碼規則解碼,得到相應的對象。

        // URL編碼方式 簡單的解碼方法實現
        function decode (qs, sep = '&', eq = '=') {
         const obj = {}
         qs = qs.split(sep)
        
         for (let i = 0, max = qs.length; i < max; i++) {
         const item = qs[i]
         const index = item.indexOf(eq)
        
         let key, value
        
         if (~index) {
         key = item.substr(0, index)
         value = item.substr(index + 1)
         } else {
         key = item
         value = ''
         }
         
         key = decodeURIComponent(key)
         value = decodeURIComponent(value)
        
         if (!obj.hasOwnProperty(key)) {
         obj[key] = value
         }
         }
         return obj
        }
        
        console.log(decode('a=1&b=2&c=3')) // { a: '1', b: '2', c: '3' }
        
        

        URL編碼方式適合處理簡單的鍵值對數據,并且很多框架的Ajax中的Content-Type默認值都是它,但是對于復雜的嵌套對象就不太好處理了,這時就需要JSON編碼方式大顯身手了。

        客戶端發送請求主體時,只需要采用JSON.stringify進行編碼。服務器端只需要采用JSON.parse進行解碼即可:

        const strictJSONReg = /^[\x20\x09\x0a\x0d]*(\[|\{)/;
        function parse(str) {
         if (!strict) return str ? JSON.parse(str) : str;
         // 嚴格模式下,總是返回一個對象
         if (!str) return {};
         // 是否為合法的JSON字符串
         if (!strictJSONReg.test(str)) {
         throw new Error('invalid JSON, only supports object and array');
         }
         return JSON.parse(str);
        }
        

        除了上述兩種字符串編碼方式,koa-bodyparser還支持不采用任何字符串編碼方式的普通字符串。

        三種字符串編碼的處理方式由【co-body】模塊提供,koa-bodyparser中通過判斷當前Content-Type類型,調用不同的處理方式,將獲取到的結果掛載在ctx.request.body:

        return async function bodyParser(ctx, next) {
         if (ctx.request.body !== undefined) return await next();
         if (ctx.disableBodyParser) return await next();
         try {
         // 最重要的一步 將解析的內容掛載到koa的上下文中
         const res = await parseBody(ctx);
         ctx.request.body = 'parsed' in res ? res.parsed : {};
         if (ctx.request.rawBody === undefined) ctx.request.rawBody = res.raw; // 保存原始字符串
         } catch (err) {
         if (onerror) {
         onerror(err, ctx);
         } else {
         throw err;
         }
         }
         await next();
         };
        
         async function parseBody(ctx) {
         if (enableJson && ((detectJSON && detectJSON(ctx)) || ctx.request.is(jsonTypes))) {
         return await parse.json(ctx, jsonOpts); // application/json等json type
         }
         if (enableForm && ctx.request.is(formTypes)) {
         return await parse.form(ctx, formOpts); // application/x-www-form-urlencoded
         }
         if (enableText && ctx.request.is(textTypes)) {
         return await parse.text(ctx, textOpts) || ''; // text/plain
         }
         return {};
         }
        };
        
        

        其實還有一種比較常見的Content-type,當采用表單上傳時,報文主體中會包含多個實體主體:

        ------WebKitFormBoundaryqsAGMB6Us6F7s3SF
        Content-Disposition: form-data; name="image"; filename="image.png"
        Content-Type: image/png
        
        
        ------WebKitFormBoundaryqsAGMB6Us6F7s3SF
        Content-Disposition: form-data; name="text"
        
        ------WebKitFormBoundaryqsAGMB6Us6F7s3SF--
        

        這種方式處理相對比較復雜,koa-bodyparser中并沒有提供該Content-Type的解析。(下一篇中應該會介紹^_^)

        五、總結

        以上便是koa-bodyparser的核心實現原理,其中涉及到很多關于HTTP的基礎知識,對于HTTP不太熟悉的同學,可以推薦看一波入門級寶典【圖解HTTP】。

        最后留圖一張:

         

        聲明:本網頁內容旨在傳播知識,若有侵權等問題請及時與本網聯系,我們將在第一時間刪除處理。TEL:177 7030 7066 E-MAIL:11247931@qq.com

        文檔

        深入koa-bodyparser原理解析

        深入koa-bodyparser原理解析:一、前置知識 在理解koa-bodyparser原理之前,首先需要了解部分HTTP相關的知識。 1、報文主體 HTTP報文主要分為請求報文和響應報文,koa-bodyparser主要針對請求報文的處理。 請求報文主要由以下三個部分組成: 報文頭部 空行 報文主體 而koa-
        推薦度:
        標簽: Koa 深入 bodyparser
        • 熱門焦點

        最新推薦

        猜你喜歡

        熱門推薦

        專題
        Top
        主站蜘蛛池模板: 亚洲av伊人久久综合密臀性色 | 色窝窝免费一区二区三区| 亚洲AV无码久久久久网站蜜桃| 亚洲国产精品yw在线观看| 一级做a爰黑人又硬又粗免费看51社区国产精品视 | 国产va免费精品| 国产成人精品曰本亚洲79ren| 另类小说亚洲色图| 婷婷亚洲天堂影院| 国产日韩AV免费无码一区二区三区 | 成年女人免费碰碰视频| 四虎必出精品亚洲高清| 日本不卡高清中文字幕免费| 亚洲精品动漫免费二区| 国产大片91精品免费看3| 国产精品观看在线亚洲人成网| 亚洲av无码乱码在线观看野外| 久青草视频97国内免费影视| 亚洲中文字幕无码日韩| 日韩插啊免费视频在线观看| 亚洲专区中文字幕| 在线观看永久免费视频网站| 一级毛片a免费播放王色| 亚洲精品色午夜无码专区日韩| 性无码免费一区二区三区在线| 亚洲一级毛片免费看| 国产网站免费观看| 国产免费爽爽视频在线观看| 亚洲日韩中文字幕| www国产亚洲精品久久久| 日本道免费精品一区二区| 亚洲中文字幕无码一去台湾| 亚洲成a人片在线观看老师| 永久免费av无码入口国语片| 亚洲已满18点击进入在线观看| 国产一级淫片视频免费看| 最近免费mv在线观看动漫| 亚洲色偷偷综合亚洲AV伊人蜜桃| 亚洲乱码中文字幕综合234| 最近免费中文字幕高清大全| 久久亚洲色WWW成人欧美|