在用 Express 構建 Web 服務器時,大部分工作都是從請求對象開始,到響應對象終止。
url的組成:
協議
協議確定如何傳輸請求。我們主要是處理 http 和 https。其他常見的協議還有 file 和 ftp。
主機名
主機名標識服務器。運行在本地計算機(localhost)和本地網絡的服務器可以簡單地表示,比如用一個單詞,或一個數字 IP 地址。在 Internet 環境下,主機名通常以一個頂級域名(TLD)結尾,比如 .com 或 .net。另外,也許還會有子域名作為主機名的前綴。請求和響應對象子域名可以是任何形式的,其中 www 最為常見。子域名通常是可選的。
端口
每一台服務器都有一系列端口號。一些端口號比較“特殊”,如 80 和 443 端口。如果省略端口值,那么默認 80 端口負責 HTTP 傳輸,443 端口負責 HTTPS 傳輸。如果不使用 80 和 443 端口,就需要一個大於 10231的端口號。通常使用容易記憶的端口號,如3000、8080 或 8088。
路徑
URL 中影響應用程序的第一個組成部分通常是路徑(在考慮協議、主機名和端口的基礎上做決定很合理,但是不夠好)。路徑是應用中的頁面或其他資源的唯一標識。
查詢字符串
查詢字符串是一種鍵值對集合,是可選的。它以問號(?)開頭,鍵值對則以與號(&)分隔開。所有的名稱和值都必須是 URL 編碼的。對此,JavaScript 提供了一個嵌入式的函數 encodeURIComponent 來處理。例如,空格被加號(+)替換。其他特殊字符被數字型字符替換。
信息片段
信息片段(或散列)被嚴格限制在瀏覽器中使用,不會傳遞到服務器。用它控制單頁應用或 AJAX 富應用越來越普遍。最初,信息片段只是用來讓瀏覽器展現文檔中通過錨點標記(<a id="chapter06">)指定的部分。
HTTP請求方法
HTTP 協議確定了客戶端與服務器通信的請求方法集合(通常稱為 HTTP verbs)。很顯然,GET 和 POST 最為常見。在瀏覽器中鍵入一個 URL(或點擊一個鏈接),服務器會接收到一個 HTTP GET 請求,其中的重要信息是 URL 路徑和查詢字符串。至於如何響應,則需要應用程序結合方法、路徑和查詢字符串來決定。對於一個網站來說,大部分頁面都響應 GET 請求。POST 請求通常用來提交信息到服務器后台(例如表單處理)。服務器將請求中包含的所有信息(例如表單)處理完成之后,用以響應的 HTML 通常與相應的 GET 請求是一樣的。與服務器通信時,瀏覽器只使用 GET 和POST 方法(如果沒有使用 AJAX)。另一方面,網絡服務通常會使用更多的創造性 HTTP 方法。例如,一個 HTTP 方法被命名注 1: 0~1023 端口為“知名端口”。為 DELETE,它就用來接受 API 指令執行刪除功能。
使用 Node 和 Express,可以完全掌控響應方法(盡管一些更復雜的方法支持得不是很好)。在 Express 中,通常要針對特殊方法編寫處理程序。
請求報頭
我們瀏覽網頁時,發送到服務器的並不只是 URL。當你訪問一個網站時,瀏覽器會發送很多“隱形”信息。這里討論的並不是個人信息泄露問題(瀏覽器被惡意軟件侵染時會出現這個問題)。服務器會因此得知優先響應哪種語言的頁面(例如,在西班牙下載 Chrome 瀏覽器,如果有西班牙語的版本,就會接收到一個西班牙語的訪問頁面)。它也會發送“用戶代理”信息(瀏覽器、操作系統和硬件設備)和其他一些信息。所有能夠確保你了解請求對象頭文件屬性的信息都將會作為請求報頭發送。如果想查看瀏覽器發送的信息,可以創建一個非常簡單的 Express 路由來展示一下:
app.get('/headers', function(req,res){
res.set('Content-Type','text/plain');
var s = '';
for(var name in req.headers) s += name + ': ' + req.headers[name] + '\n';
res.send(s);
});
響應報頭
正如瀏覽器以請求報頭的形式發送隱藏信息到服務器,當服務器響應時,同樣會回傳一些瀏覽器沒必要渲染和顯示的信息,通常是元數據和服務器信息。我們已經熟悉內容類型頭信息,它告訴瀏覽器正在被傳輸的內容類型(網頁、圖片、樣式表、客戶端腳本等)。特別要注意的是,不管 URL 路徑是什么,瀏覽器都根據內容類型報頭處理信息。因此你可以通過一個叫作 /image.jpg 的路徑提供網頁,也可以通過一個叫作 /text.html 的路徑提供圖片。(這樣做並不合情理,這里要講的重點是路徑是抽象的,瀏覽器只根據內容類型來決定內容該如何渲染。)除了內容類型之外,報頭還會指出響應信息是否被壓縮,以及使用的是哪種編碼。響應報頭還可以包含關於瀏覽器對資源緩存時長的提示。優化網站時需要着重考慮這一點。響應報頭還經常會包含一些關於服務器的信息,一般會指出服務器的類型,有時甚至會包含操作系統的詳細信息。返回服務器信息存在一個問題,那就是它會給黑客一個可乘之機,從而使站點陷入危險。非常重視安全的服務器經常忽略此信息,甚至提供虛假信息。禁用 Express 的 X-Powered-By 頭信息很簡單:
app.disable('x-powered-by');在瀏覽器的開發者工具中可以找到響應報頭信息。例如,在 Chrome 瀏覽器中查看響應報
頭信息的操作如下:
請求和響應對象
(1) 打開控制台。
(2) 點擊網絡標簽頁。
(3) 重新載入頁面。
(4) 在請求列表中選取網頁(通常是第一個)。
(5) 點擊報頭標簽頁,你就可以看到所有響應報頭信息了。
互聯網媒體類型
內容類型報頭信息極其重要,沒有它,客戶端很難判斷如何渲染接收到的內容。內容類型報頭就是一種互聯網媒體類型,由一個類型、一個子類型以及可選的參數組成。例如,text/html;charset=UTF-8 說明類型是 text,子類型是 html,字符編碼是 UTF-8。互聯網編號分配機構維護了一個官方的互聯網媒體類型清單http://www.iana.org/assignments/media-types/media-types.xhtml)。我們常見的 content type、Internet media type 和 MIME type 是可以互換的。MIME(多用途互聯網郵件擴展)是互聯網媒體類型的前身,它們大部分是相
同的。
請求體
除請求報頭外,請求還有一個主體(就像作為實際內容返回的響應主體一樣)。一般 GET請求沒有主體內容,但 POST 請求是有的。POST 請求體最常見的媒體類型是 application/x-www-form-urlendcoded,是鍵值對集合的簡單編碼,用 & 分隔(基本上和查詢字符串的格式一樣)。如果 POST 請求需要支持文件上傳,則媒體類型是 multipart/form-data,它是一種更為復雜的格式。最后是 AJAX 請求,它可以使用 application/json。
參數
“參數”這個詞可以有很多種解釋,它通常是困惑的源頭。對於任何一個請求,參數可以來自查詢字符串、會話、請求體或指定的路由參數。在 Node 應用中,請求對象的參數方法會重寫所有的參數。因此我們最好不要深究。通常這會帶來問題,一個參數在查詢字符串中,另一個在 POST 請求體中或會話中,哪個會贏呢?這會產生讓人抓狂的 bug。PHP 是產生這種混亂的主要原因:為了盡量“方便”,它將所有參數重新寫入了一個稱為 $_REQUEST 的變量,由於某種原因,人們曾認為這是個前所未有的好主意。我們將學習保存不同類型參數的專用屬性,我認為這能夠減少困惑。
請求對象
請求對象(通常傳遞到回調方法,這意味着你可以隨意命名,通常命名為 req 或 request)的生命周期始於 Node 的一個核心對象 http.IncomingMessage 的實例。Express 添加了一些附加功能。我們來看看請求對象中最有用的屬性和方法(除了來自 Node 的 req.headers 和req.url,所有這些方法都由 Express 添加)。
req.params
一個數組,包含命名過的路由參數。
req.param(name)
返回命名的路由參數,或者 GET 請求或 POST 請求參數。建議你忽略此方法。
req.query
一個對象,包含以鍵值對存放的查詢字符串參數(通常稱為 GET 請求參數)。
req.body
一個對象,包含 POST 請求參數。這樣命名是因為 POST 請求參數在 REQUEST 正文中傳遞,而不像查詢字符串在 URL 中傳遞。要使 req.body 可用,需要中間件能夠解析請求正文內容類型
req.route
關於當前匹配路由的信息。主要用於路由調試。
req.cookies/req.singnedCookies•
一個對象,包含從客戶端傳遞過來的 cookies 值。
從客戶端接收到的請求報頭。
req.accepts([types])
一個簡便的方法,用來確定客戶端是否接受一個或一組指定的類型(可選類型可以是單個的 MIME 類型,如 application/json、一個逗號分隔集合或是一個數組)。寫公共API 的人對該方法很感興趣。假定瀏覽器默認始終接受 HTML。
req.ip
客戶端的 IP 地址。
req.path
請求路徑(不包含協議、主機、端口或查詢字符串)。
req.host
一個簡便的方法,用來返回客戶端所報告的主機名。這些信息可以偽造,所以不應該用於安全目的。
請求和響應對象
req.xhr
一個簡便屬性,如果請求由 Ajax 發起將會返回 true。
req.protocol
用於標識請求的協議(http 或 https)
req.secure
一個簡便屬性,如果連接是安全的,將返回 true。等同於 req.protocol==='https'。
req.url/req.originalUrl
有點用詞不當,這些屬性返回了路徑和查詢字符串(它們不包含協議、主機或端口)。
req.url 若是出於內部路由目的,則可以重寫,但是 req.orginalUrl 旨在保留原始請求
和查詢字符串。
req.acceptedLanguages
一個簡便方法,用來返回客戶端首選的一組(人類的)語言。這些信息是從請求報頭中
解析而來的。
響應對象
響應對象(通常傳遞到回調方法,這意味着你可以隨意命名它,通常命名為 res、resp 或response)的生命周期始於 Node 核心對象 http.ServerResponse 的實例。Express 添加了一些附加功能。我們來看看響應對象中最有用的屬性和方法(所有這些方法都是由 Express添加的)。
res.status(code)
設置 HTTP 狀態代碼。Express 默認為 200(成功),所以你可以使用這個方法返回狀態404(頁面不存在)或 500(服務器內部錯誤),或任何一個其他的狀態碼。對於重定向(狀態碼 301、302、303 和 307),有一個更好的方法:redirect。
res.set(name,value)
設置響應頭。這通常不需要手動設置。
res.cookie(name,vaue,[options]),res.clearCookie(name,[options])
設置或清除客戶端 cookies 值。需要中間件支持
res.redirect([status],url)
重定向瀏覽器。默認重定向代碼是 302(建立)。通常,你應盡量減少重定向,除非永久移動一個頁面,這種情況應當使用代碼 301(永久移動)。
res.send(body),res.send(status,body)
向客戶端發送響應及可選的狀態碼。Express 的默認內容類型是 text/html。如果你想改為 text/plain,需要在 res.send 之前調用 res.set('Content-Type','text/plain\')。如果 body 是一個對象或一個數組,響應將會以 JSON 發送(內容類型需要被正確設置),不過既然你想發送 JSON,我推薦你調用 res.json。
res.json(json),res.json(status,json)
向客戶端發送 JSON 以及可選的狀態碼。
res.jsonp(json),req.jsonp(status,json)
向客戶端發送 JSONP 及可選的狀態碼。
res.type(type)
一個簡便的方法,用於設置 Content-Type 頭信息。基本上相當於 res.set('Content-Type','type'),只是如果你提供了一個沒有斜杠的字符串,它會試圖把其當作文件的擴展名映射為一個互聯網媒體類型。比如,res.type('txt') 會將 Content-Type 設為text/plain。此功能在有些領域可能會有用(例如自動提供不同的多媒體文件),但是通常應該避免使用它,以便明確設置正確的互聯網媒體類型。
res.format(object)
這個方法允許你根據接收請求報頭發送不同的內容。這是它在 API 中的主要用途,我們將會在第 15 章詳細討論。這里有一個非常簡單的例子:res.format({'text/plain':'hithere','text/html':'<b>hi there</b>'})。
res.attachment([filename]),res.download(path,[filename],[callback])
這兩種方法會將響應報頭 Content-Disposition 設為 attachment,這樣瀏覽器就會選擇下載而不是展現內容。你可以指定 filename 給瀏覽器作為對用戶的提示。用 res.download 可以指定要下載的文件,而 res.attachment 只是設置報頭。另外,你還要將內容發送到客戶端。
res.sendFile(path,[option],[callback])
這個方法可根據路徑讀取指定文件並將內容發送到客戶端。使用該方法很方便。使用靜態中間件,並將發送到客戶端的文件放在公共目錄下,這很容易。然而,如果你想根據條件在相同的 URL 下提供不同的資源,這個方法可以派上用場。
res.links(links)
設置鏈接響應報頭。這是一個專用的報頭,在大多數應用程序中幾乎沒有用處。
res.locals,res.render(view,[locals],callback)
res.locals 是一個對象,包含用於渲染視圖的默認上下文。res.render 使用配置的模
請求和響應對象
板引擎渲染視圖(不能把 res.render 的 locals 參數與 res.locals 混為一談,上下文
在 res.locals 中會被重寫,但在沒有被重寫的情況下仍然可用)。res.render 的默認響
應代碼為 200,使用 res.status 可以指定一個不同的代碼。
---------------------
作者:Seven_Cld
來源:CSDN
原文:https://blog.csdn.net/christine95/article/details/50500171
版權聲明:本文為博主原創文章,轉載請附上博文鏈接!