1 error: 2 EventEmitter定義了一個特殊的時間error,它包含了‘錯誤’的語義,當error被發射時,EventEmitter規定如果沒有 3 響應的監聽器,Node.js會把它當做異常,退出程序並打印調用棧,一般我們要為會發射error事件的對象設置監聽器, 4 避免遇到錯誤后整個程序崩潰。 5 6 /* 7 *author:e路相扶 8 *filename error.js 9 */ 10 var events=require('events'); 11 var emitter=new events.EventEmitter(); 12 emitter.emit('error'); 13 14 大多數時候,我們不會直接使用EventEmitter,而是在對象中繼承它,包括fs,net,http在內的只要是支持事件 15 響應的核心模塊都是EventEmitter的子類 16 because: 17 1.具有某個實體功能的對象實現事件符合語義,時間的監聽和發射應該是一個對象的方法 18 2.javascript的對象機制是基於原型的,支持部分多重繼承,繼承EventEmitter不會打亂對象原有的繼承關系 19 20 file system :fs 21 fs模塊時文件操作的封裝,提供了對文件的讀取,寫入,更名,刪除,遍歷目錄,鏈接等POSIX文件系統操作 22 23 fs.readFile(filename,[encoding],[callback(err,data)])異步讀取文件 24 err表示錯誤,data解析后是字符串,否則以buffer形式表示二進制數據 25 /* 26 *author:e路相扶 27 *filename read.js 28 */ 29 var fs=requier('fs'); 30 fs.readFile('zj.txt','utf-8',function(err,data)){ 31 if(err){ 32 console.log(err); 33 }else{ 34 console.log(data); 35 } 36 }) 37 38 fs.readFileSync(filename,[encoding])同步讀取try{..}catch(){..}捕捉異常 39 40 fs.open(path,flags,[mode],[callback(err,fd)]) 打開文件 41 flags:r,r+,w,w+,a,a+ 42 mode:指定文件權限 43 fs.read(fd,buffer,offset,length,position,[callback(err,bytesRead,buffer)]) POSIX read函數封裝 44 offeset:是buffer的寫入偏移量 45 length:文件中讀取的字節數 46 position:文件讀取的起始位置,如果為null,則從當前文件指針的位置讀取 47 bytesRead:讀取的字節數 48 buffer:緩沖區對象 49 50 /* 51 *author:e路相扶 52 *filename read2.js 53 */ 54 var fs=require('fs'); 55 fs.open('zj.txt',r,function(err,fd){ 56 if(err){ 57 console.error(err); 58 return; 59 } 60 var buf=new Buffer(8); 61 fs.read(fd,buf,0,8,null,function(err,bytesRead,buffer){ 62 if(err){ 63 console.error(err); 64 return; 65 } 66 console.log('bytesRead '+bytesRead); 67 console.log(buffer); 68 }); 69 }); 70![]()
1 HTTP服務器和客戶端 2 Node.js提供了http模塊,其中封裝了一個高效的HTTP服務器和一個簡易的HTTP客戶端 3 http.Server是一個基於事件的HTTP服務器,核心是由Node.js下層C++部分實現,接口是由Javascript封裝。 4 http.request是HTTP客戶端工具用於向HTTP服務器發送請求 5 6 HTTP服務器 7 8 /* 9 *author:e路相扶 10 *filename app.js 11 */ 12 var http=require('http'); 13 http.createServer(function(req,res){ 14 res.writeHead(200,{'Content-Type':'text/html'}); 15 res.write('<h1>Node.js</h1>'); 16 res.end('<p>Hello world</p>'); 17 }).listen(3000); 18 console.log('HTTP server is listening at port 3000'); 19 20 http.createServer創建http.Server實例,請求對象req,響應對象res,響應代碼200表示請求成功。 21 22 http.Server提供了幾個事件: 23 request:當客戶請求到來時,該事件被觸發,提供了兩個參數req,res分別是http.ServerRequset, 24 http.ServerResponse 表示請求和響應信息 25 connection:當TCP連接建立,該事件被觸發,提供了一個參數socket,為net.socket實例 26 connection事件的粒度要大於request,因為客戶端在Keep-Alive模式下可能在同一個連接內發送多次請求 27 close:當服務器關閉時,事件被觸發 28 29 /* 30 *author:e路相扶 31 *filename httpserver.js 32 */ 33 var server=new http.Server(); 34 server.on('request',function(req,res){ 35 res.writeHead(200,{'Content-Type':'text/html'}); 36 res.write('<h1>Node.js</h1>'); 37 res.end('<p>Hello world</p>'); 38 }).listen(3000); 39 40 http.ServerRequest是HTTP請求的信息,是后端開發者最關注的內容 41 42 HTTP請求一般分為:請求頭(Request Header)請求體(Request Body) 43 http.ServerRequest提供了三個事件用於控制請求體傳輸 44 data:請求數據到來之后該事件被觸發,事件提供了一個參數chunk,表示接收到的數據,如果該事件沒有被監聽 45 那么請求體將會被拋棄 (可能會被多次調用) 46 end:當請求體數據傳輸完成時,事件被觸發,此后不再有數據到來 47 close:用戶當前請求結束,該事件被觸發,不同於end,用戶強制終止傳輸,也還是調用close 48 49 獲取GET請求內容 50 /* 51 *author:e路相扶 52 *filename httpserverrequestget.js 53 */ 54 var http=require('http'); 55 var url=require('url'); 56 var util=require('util'); 57 http.createServer(function(req,res){ 58 res.write(200,{'Content-Type':'text/plain'}); 59 res.end(util.inspect(url.parse(req.url,true))); 60 }).listen(3000); 61 62 訪問http://127.0.0.1:3000/user?name=zj&email=zhangjun516@126.com 63 output: 64 {search:'?name=zj&email=zhangjun516@126.com', 65 query:{name:'zj',email:'zhangjun516@126.com'},//GET請求的內容 66 pathname:'/user', 67 path:'/user?name=zj&email=zhangjun516@126.com', 68 href:'/user?name=zj&email=zhangjun516@126.com' 69 } 70 71 72 獲取Post請求內容 73 /* 74 *author:e路相扶 75 *filename httpserverrequestpost.js 76 */ 77 var http=require('http'); 78 var querystring=require('querystring'); 79 var util=require('util'); 80 81 http.createServer(function(req,res){ 82 var post=''; 83 req.on('data',function(chunk){ 84 post+=chunk; 85 }); 86 req.on('end',function(){ 87 post=querystring.parse(post); 88 res.end(util.inspect(post)); 89 }) 90 }).listen(3000); 91 92 這個僅僅是例子,真實情況中的要復雜 93 94 http.ServerResponse 返回給客戶端的信息,決定了用戶最終能看到的結果 95 response.writeHead(statusCode,[headers])向請求的客戶端發送響應頭 96 response.write(data,[encoding])向請求的客戶端發送響應內容(在response.end之前,可以多次調用) 97 response.end([data],[encoding])響應結束,告知客戶端所有的發送已經完成,如果不調用改函數,客戶端將處於等待狀態 98 99 HTTP客戶端 100 http模塊提供了兩個函數http.request和http.get,功能是作為客戶端向HTTP服務器發起請求。 101 http.request(option,callback) 發起HTTP請求,option=》關聯數組 參數: 102 host:請求網站的域名或IP地址 103 port:請求網站的端口,默認80 104 method:請求方法,默認GET 105 path:請求的相對於根的路徑 106 headers:一個關聯數組對象,為請求頭的內容 107 callback:傳遞一個參數,為http.ClientResponse實例 108 109 http.request返回一個http.ClientRequest的實例 110 111 /* 112 *author:e路相扶 113 *filename httprequest.js 114 */ 115 var http=require('http'); 116 var querystring=require('querystring'); 117 118 var contents=querystring.stringify({ 119 name:'zj', 120 email:'zhangjun516@126.com', 121 }); 122 var oprionts={ 123 host:127.0.0.1, 124 path:/var/www/post.php, 125 method:'POST', 126 headers:{ 127 'Content-Type':'application/x-www-form-urlencoded', 128 'Content-Length':'contents.length' 129 } 130 }; 131 var req=http.request(options,function(res){ 132 res.setEncoding('utf8'); 133 res.on('data',function(data){ 134 console.log(data); 135 }); 136 }); 137 req.write(contents); 138 req.end(); 139

1 Notice:不要忘記寫req.end(),不然服務器接收不到信息 2 3 http.get(options,callback)是http.request的簡化版,唯一的區別就是http.get自動將請求的方法設為Get請求 4 同時不需要調用req.end(); 5 6 /* 7 *author:e路相扶 8 *filename httpget.js 9 */ 10 var http=require('http'); 11 http.get({host:'127.0.0.1'},function(res){ 12 res.setEncoding('utf8'); 13 res.on('data',function(data){ 14 console.log(data); 15 }); 16 }); 17 18 http.ClientRequest 是由http.request或http.get返回產生的對象 表示一個已經產生而且正在進行中的HTTP請求 19 /* 20 *author:e路相扶 21 *filename httpresponse.js 22 */ 23 var http=require('http'); 24 var req=http.get({host:'127.0.0.1'}); 25 req.on('response',function(res){ 26 res.setEncoding('utf8'); 27 res.on('data',function(data){ 28 console.log(data); 29 }); 30 }); 31 http.ClientRequest 像http.ServerResponse一樣提供了write和end函數,用於服務器發送請求體,通常用於post 32 put等操作,所有寫操作結束以后必須調用end函數以通知服務器,否則請求無效。 33 34 request.abort():終止正在發送的請求 35 requset.setTimeout(timeout,[callback])設置請求超時時間,timetout(毫秒數) 36 37 and so on 38 39 http.ClientResponse 40 response.setEncoding([encoding]):設置默認的編碼當data事件被觸發時,數據將會以encoding編碼, 41 默認值是null,記不編碼,以buffer形式存儲, 42 response.pause():暫停接收數據和發送事件,方便下載功能 43 response.resume():從暫停的狀態中恢復