Node.js中HTTP模塊與事件模塊詳解
Node.js的http服務(wù)器
通過(guò)使用HTTP模塊的低級(jí)API,Node.js允許我們創(chuàng)建服務(wù)器和客戶端。剛開(kāi)始學(xué)node的時(shí)候,我們都會(huì)遇到如下代碼:
var http = require('http');
http.createServer(function (req,res) {
res.end('Hello World\n');
}).listen(3000,"127.0.0.1");
console.log("Server funning at
這段代碼的包括了http模塊的信息,意思是:
1.從`Node.js`的核心請(qǐng)求HTTP模塊并賦予一個(gè)變量,以便在以后的腳本中使用。
于是腳本就可以訪問(wèn)一些方法來(lái)通過(guò)`Node.js`使用`HTTP`。
2.使用`createServer`創(chuàng)建新的web服務(wù)器對(duì)象
3.腳本將一個(gè)匿名函數(shù)傳遞給服務(wù)器,告訴web服務(wù)器對(duì)象每當(dāng)其接收到請(qǐng)求時(shí)會(huì)發(fā)生的是什么
4.腳本第4行定義了web服務(wù)器的端口和主機(jī),這意味著可以使用`http://127.0.0.1:3000`
來(lái)訪問(wèn)服務(wù)器
Http頭
對(duì)于每個(gè)HTTP請(qǐng)求和響應(yīng),都會(huì)發(fā)送HTTP頭,HTTP頭發(fā)送的是附加的信息,包括內(nèi)容類型、服務(wù)器發(fā)送響應(yīng)的日期以及HTTP狀態(tài)碼
http頭包含了許多信息,以下是我的百度首頁(yè)包含的http頭的信息:
由于我的百度首頁(yè)添加了較多的網(wǎng)站,所以這里的數(shù)據(jù)和讀者們的可能不一樣。從中我們可以看出百度是web服務(wù)器是BWS/1.1
下面是剛才上面那段代碼的http頭部信息:
Node.js中的重定向
在node中,我們可以很容易地創(chuàng)建一個(gè)簡(jiǎn)單的服務(wù)器將訪問(wèn)者重定向到另外一個(gè)Web頁(yè)面上,其準(zhǔn)則如下:
1.給客戶發(fā)送301響應(yīng)代碼,告訴客戶,資源已經(jīng)移到另一個(gè)位置了;
2.發(fā)送一個(gè)位置頭告訴客戶重定向到哪里。
相關(guān)代碼如下:
var http = require('http');
http.createServer(function (req,res) {
res.writeHead(301,{
'Location':'Http://example-2.com/web'
});
res.end();
}).listen(3000,'127.0.0.1');
console.log("Server funning at
打開(kāi)瀏覽器訪問(wèn)http://127.0.0.1:3000頁(yè)面會(huì)被重定向。
響應(yīng)不同的請(qǐng)求
Node.js不單可以創(chuàng)建單一的響應(yīng),對(duì)于多種類型的請(qǐng)求,我們需要給應(yīng)用程序加一些路由。Node通過(guò)使用URL模塊讓這一切直截了當(dāng)。URL模塊使我們可以讀取URL、分析它然后對(duì)輸出做一些事情。
現(xiàn)在,我們可以分析請(qǐng)求的URL并從中截取內(nèi)容,例如,要想獲得主機(jī)名稱,我們可以輸入:
url.parse(requestURL).hostname
這時(shí),他將返回"example.com"
取得端口號(hào)可以輸入:
url.parse(requestURL).port
他將返回“1234”
事件模塊
Node.js被認(rèn)為是實(shí)現(xiàn)并發(fā)的最佳方法。Events(事件)模塊是Node.js的核心,許多其他模塊用它來(lái)圍繞著事件架構(gòu)功能。由于Node.js運(yùn)行于單一的線程中,任何同步代碼都是阻塞的。所以,在編寫(xiě)Node.js代碼的時(shí)候我們要考慮一些簡(jiǎn)單的規(guī)則:
1.別阻塞——`Node.js`是單線程的,如果代碼阻塞的話所有其他一切都停止了
2.快速返回——操作應(yīng)當(dāng)快速返回。如果不能快速返回,就應(yīng)當(dāng)將其遷移到另一個(gè)進(jìn)程中
Events模塊讓開(kāi)發(fā)人員可以為事件設(shè)置偵聽(tīng)器和處理器。在客戶端js中,我們可以對(duì)單擊事件設(shè)置一個(gè)監(jiān)聽(tīng)器,然后在事件發(fā)生時(shí)執(zhí)行一些事情:
var tar = document.getElementById("target");
tar.addEventListener("click", function () {
alert("click event fired,target was clicked");
},false);
當(dāng)然,這是在不考慮IE兼容性的一個(gè)例子,Node.js重點(diǎn)事件更常見(jiàn)的是網(wǎng)絡(luò)事件,包括:
1.來(lái)自web服務(wù)器的響應(yīng)
2.從文件讀取數(shù)據(jù)
3.從數(shù)據(jù)庫(kù)返回?cái)?shù)據(jù)
使用Events模塊我們首先要?jiǎng)?chuàng)建一個(gè)新的EventEmitter實(shí)例:
var EventEmitter= require('events').EventEmitter;
var test = new EventEmitter();
一旦在代碼中加入上述內(nèi)容,就可以添加事件和偵聽(tīng)器了,我們可以按如下方法發(fā)送事件,比如:
test.emit('msg','the message send by node');
第一個(gè)參數(shù)是對(duì)事件進(jìn)行描述的字符串,以便用于偵聽(tīng)器的匹配
為了接收消息,就必須添加偵聽(tīng)器,偵聽(tīng)器在事件觸發(fā)時(shí)處理它,例如:
test.on('message',function(data){
console.log(data);
});
Events模塊addListener/on,once,removeListener,removeAllListeners,emit等基本的事件監(jiān)聽(tīng)模式的方法實(shí)現(xiàn)。它與前端DOM樹(shù)上的事件并不相同,因?yàn)樗淮嬖诿芭?,逐層捕獲等屬于DOM的事件行為,也沒(méi)有preventDefault()、stopPropagation()、 stopImmediatePropagation() 等處理事件傳遞的方法。
1.類: events.EventEmitter:通過(guò) require('events').EventEmitter 獲取 EventEmitter 類。
2.emitter.on(event, listener):添加一個(gè) listener 至特定事件的 listener 數(shù)組尾部。 返回 emitter,方便鏈?zhǔn)秸{(diào)用,下同。
3.emitter.removeListener(event, listener)從一個(gè)事件的 listener 數(shù)組中刪除一個(gè) listener
4.emitter.listeners(event)返回指定事件的 listener 數(shù)組
更多詳情見(jiàn):Node.js API 文檔
以下代碼展示了一條能在5秒內(nèi)自我毀滅的機(jī)密消息:
var EventEmitter = require('events').EventEmitter;
var secretMessage = new EventEmitter();
secretMessage.on('message', function (data) {
console.log(data);
});
secretMessage.on('self destruct', function () {
console.log('the msg is destroyed!');
});
secretMessage.emit('message','this is a secret message.It will self deatruct in 5s');
setTimeout(function () {
secretMessage.emit('self destruct');
},5000);
在這段腳本中,發(fā)送了兩個(gè)事件,有兩個(gè)偵聽(tīng)器。當(dāng)腳本運(yùn)行時(shí),消息事件就發(fā)生,并由“message”處理器處理
在Node.js中到處都用EventEmitter,所以掌握它是很重要的。Node.js通過(guò)I/O操作獲得的數(shù)據(jù)并廣泛使用Events模塊來(lái)支持異步編程
常見(jiàn)問(wèn)題解答:
問(wèn):對(duì)于一個(gè)事件是否有最大偵聽(tīng)器數(shù)量的限制?
答:默認(rèn)情況下,如果事件有操作10個(gè)偵聽(tīng)器,它會(huì)發(fā)出警告。不過(guò),可以使用emitter.setMaxListener(n)來(lái)更改這個(gè)數(shù)量
問(wèn):是否可以偵聽(tīng)所有發(fā)送出來(lái)的事件?
答:不能。我們需要給每個(gè)想要響應(yīng)的事件創(chuàng)建偵聽(tīng)器
相關(guān)文章
一文學(xué)會(huì)如何升級(jí)npm管理的各依賴版本
npm在前端開(kāi)發(fā)流程中提供了非常完善的自動(dòng)化工具鏈,已成為每個(gè)前端開(kāi)發(fā)者必備的工具,下面這篇文章主要給大家介紹了關(guān)于如何升級(jí)npm管理的各依賴版本,文中通過(guò)圖文介紹的非常詳細(xì),需要的朋友可以參考下2022-09-09npm報(bào)錯(cuò)"A?complete?log?of?this?run?can?be?found?
這篇文章主要給大家介紹了關(guān)于npm報(bào)錯(cuò)"A?complete?log?of?this?run?can?be?found?in:"的解決辦法,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友可以參考下2023-04-04如何降低node版本,怎樣實(shí)現(xiàn)降低node版本
這篇文章主要介紹了如何降低node版本,怎樣降低node版本問(wèn)題,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-07-07詳解node登錄接口之密碼錯(cuò)誤限制次數(shù)(含代碼)
這篇文章主要介紹了nodejs登錄接口之密碼錯(cuò)誤限制次數(shù)(含代碼),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2019-10-10node.js實(shí)現(xiàn)簡(jiǎn)單爬蟲(chóng)示例詳解
這篇文章主要為大家介紹了node.js實(shí)現(xiàn)簡(jiǎn)單爬蟲(chóng)示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-04-04Linux 安裝nodejs環(huán)境及路徑配置詳細(xì)步驟
大家都知道linux安裝nodejs有兩種比較常用的方法,一種解壓即可用的方法操作比較簡(jiǎn)便,另一種方法通過(guò)編譯來(lái)安裝,本文重點(diǎn)給大家講解第一種方法,感興趣的朋友跟隨小編一起看看吧2021-11-11Node.js安裝及npm國(guó)內(nèi)鏡像配置的方法實(shí)現(xiàn)
本文主要介紹了Node.js安裝及npm國(guó)內(nèi)鏡像配置,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2023-06-06