node connect


var connect = require('./connect');

var cnt =

    connect()

    .use(function (req, res) {

        res.end('hello word\n')

    })

    .listen(3000);

  1. connect() 執(zhí)行后:生成app函數(shù)及app下掛載的幾個方法:

function app(req, res, next) {

app.handle(req, res, next);

}

app.handle = function xxx

app.use = function(route, fn)

app.route = ‘/’

app.stack = []

  1. .use(route, func)

path 保存路徑

handle 保存處理函數(shù)

對傳入的參數(shù)進行判斷

if route == ‘/aaaa/’

則 route.slice(0, -1) 處理成 ‘/aaa’

結(jié)果:

path: ‘/aaa’

handle: undefined

if route != ‘string’

結(jié)果

path: ‘/’

handle: route

將每個use的配置保存到app.stack中,即成為一種中間件,當(dāng)請求到達后,根據(jù)是否手動調(diào)用next順序執(zhí)行handle:

app.stack.push(

{

path,

handle

}

)

  1. listen()

http.createServer啟動server


http.createServer(

  function app(req, res, next) {

    app.handle(req, res, next);

  }

)

每個請求都會依次遍歷stack中的handle,根據(jù)route篩選符合條件的請求,并執(zhí)行

當(dāng)請求進來后:執(zhí)行app.handle(req, res, next),此時next為undefined

每個請求的所有內(nèi)容都在app.handle()這個閉包里。

index 用于記錄當(dāng)前正在處理第幾個handle

protohost 根據(jù)url拿到host

removed

slashAdded

stack 所有的中間件函數(shù)

req.originUrl = req.url 存儲url

執(zhí)行next()

next中的邏輯:

if(skip this layer if the route doesn't match)next()進入下一個stack

// eg: url: /foo

          route: /  ‘’

          匹配成功

if (route match does not border "/", ".", or end) next()進入下一個stack

// eg: url: /foo/ /foo.xxx /foo

      route: /foo

      匹配成功

trim off the part of the url that matches the route

請求進入 -> 自調(diào)用next()執(zhí)行第1個stack里的handle -> 遇到next()執(zhí)行第2個handle -> … -> 遇到next()執(zhí)行第n個handle -> 執(zhí)行第n個handle的剩余部分 -> … -> 第二個handle的剩余部分 -> 第一個handle的剩余部分

執(zhí)行app.handle(),如果use中的函數(shù)參數(shù)為req, res, next并且無異常,需要手動調(diào)用next,否則不會到下一個use中。

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容