今天開始學(xué)習(xí)Nodejs官網(wǎng)提供api(一般稱這為模塊)練習(xí),類似java JDK, 根據(jù)第一天代碼:
//導(dǎo)入 http模塊
var http = require('http');
//創(chuàng)建一個(gè)httpServer 并監(jiān)聽8081端口
http.createServer(function (req, res) {
//響應(yīng)客戶端請(qǐng)求,并輸出信息 --> Hello, World.
res.writeHead(200, {'Content-Type': 'text/plain'});
res.write('Hello, World.');
res.end(); //結(jié)束本次請(qǐng)求
}).listen(8081);
以上是一個(gè)很簡(jiǎn)單的web程序,提供了從服務(wù)器端到應(yīng)用端的全部流程,這里的業(yè)務(wù)邏輯非常簡(jiǎn)單,只是向頁面輸出字符串 Hello, World. .
接下來,根據(jù)我學(xué)習(xí)后的理解全手動(dòng)編寫了如下代碼(#-_-),稍微能處理來自不同的請(qǐng)求,類似java # DispatcherServlet :
首先,先定義程序的入口,雖然js沒有main函數(shù), 新建一個(gè)index.js, 先不計(jì)劃編碼任何代碼。
然后,新建server.js,用來存放第一天學(xué)習(xí)的部分內(nèi)容,就像文件名一樣,是一個(gè)類似server的功能,代碼如下:
//導(dǎo)入http 和 url模塊 類似java的 Map\\\\List等工具類
var http = require('http'),
url = require('url') ;
function start() {
//請(qǐng)求處理函數(shù),就是第一天學(xué)習(xí)的箭頭函數(shù),這里不再是一個(gè)匿名函數(shù)
function onRequest(req,res) {
//這里通過url模塊提供函數(shù) parse獲得請(qǐng)求方法,詳細(xì)可以參考node官方網(wǎng)站document說明
var pathName = url.parse(req.url).pathname ;
console.log('request path ',pathName) ;
//響應(yīng)狀態(tài)碼 和格式
res.writeHead(200,{'Content-Type':'text/plain'}) ;
res.write('Hello,World.') ;
res.end() ;
}
http.createServer(onRequest).listen(8081) ;
console.log('server has started.') ;
}
//將函數(shù)start函數(shù)導(dǎo)出為一個(gè)模塊
//export
exports.start = start ;
然后回到index.js中 編寫如下代碼:
//導(dǎo)入剛才我們編寫的server模塊
var server = require('./server') ;
//調(diào)用模塊提供server功能
server.start() ;
然后可以運(yùn)行如下命令:
node index.js
訪問http://localhost:8081 ,可以看到輸出。
上面代碼將業(yè)務(wù)邏輯放到了 server中,在實(shí)際工作中,這明顯是非常不合理的,因?yàn)闃I(yè)務(wù)邏輯變更比女人翻臉還快,放到server中后果可想而知。這里需要調(diào)整,記得在剛開始學(xué)習(xí)java #servlet 的時(shí)候,我們最開始是使用get方式將方法傳遞到服務(wù)器端,然后通過永遠(yuǎn)也寫不完的if....else if.... else if.... 來進(jìn)行不同功能的分發(fā),這里如果提供一個(gè)類似路由表的東西就可以達(dá)到類似的目的,由于javaScript對(duì)象是key-value的形式出現(xiàn),這給這一功能提供了方便,例如:
var handle = {} ;
handle['/'] = root ; //代表訪問項(xiàng)目首頁
handle['/start'] = start ; //代表訪問項(xiàng)目首頁
handle['/upload'] = upload ; //代表上傳文件請(qǐng)求
這樣,不同的功能類似一張路由表被關(guān)聯(lián)起來了,例如:
//dispatcher.js
function start() {
console.log('call /start') ;
return 'call /start' ;
}
function upload() {
console.log('call /upload') ;
return 'call /upload' ;
}
function root() {
console.log('call /') ;
return 'call /' ;
}
exports.start = start ;
exports.upload = upload ;
exports.root = root ;
以上代碼表示不同需求的功能函數(shù)。然后再提供一個(gè)路由轉(zhuǎn)發(fā)功能的模塊,例如:
//router.js
function route(path,handle) {
console.log('route path ',path) ;
var fun = handle[path] ;
if(typeof fun === "function") {
return fun.call(null,arguments) ;
}else {
console.log('unknown path.') ;
return 'unknown path.' ;
}
}
exports.route = route ;
然后我們需要對(duì)index.js 和server.js 中的代碼進(jìn)行適當(dāng)?shù)男薷?,如下?/p>
server.js
//server.js
//導(dǎo)入http 和 url模塊 類似java的 Map\\\\List等工具類
var http = require('http'),
url = require('url') ;
//服務(wù)啟動(dòng)需要傳遞兩個(gè)參數(shù),handle為轉(zhuǎn)發(fā)提供映射表,route執(zhí)行轉(zhuǎn)發(fā)
function start(handle,route) {
//請(qǐng)求處理函數(shù),就是第一天學(xué)習(xí)的箭頭函數(shù),這里不再是一個(gè)匿名函數(shù)
function onRequest(req,res) {
//這里通過url模塊提供函數(shù) parse獲得請(qǐng)求路徑,詳細(xì)可以參考node官方網(wǎng)站document說明
var pathName = url.parse(req.url).pathname ;
console.log('request path ',pathName) ;
//響應(yīng)狀態(tài)碼 和格式
res.writeHead(200,{'Content-Type':'text/plain'}) ;
//使用route 模塊進(jìn)行轉(zhuǎn)發(fā)請(qǐng)求,這里為了能看到明顯的效果,將不同功能信息輸出到頁面
//dispatcher
var content = route(pathName,handle) ;
console.log('return content',content) ;
res.write(content) ;
//res.write('Hello,World.') ;
res.end() ;
}
http.createServer(onRequest).listen(8081) ;
console.log('server has started.') ;
}
//將函數(shù)start函數(shù)導(dǎo)出為一個(gè)模塊
//export
exports.start = start ;
index.js
//index.js
var server = require('./server'),
router = require('./router'),
dispatcher = require('./dispatcher');
var handle = {} ;
handle['/'] = dispatcher.root ;
handle['/start'] = dispatcher.start ;
handle['/upload'] = dispatcher.upload ;
server.start(handle,router.route) ;
運(yùn)行 node index.js ,并訪問映射路徑可以看到不同的輸出信息, 例如: http://localhost:8081/upload // call /upload
至此,第二天nodejs的學(xué)習(xí)到這里就結(jié)束啦,#-_- 晚安! 以上內(nèi)容如有發(fā)現(xiàn)錯(cuò)誤一定請(qǐng)各位朋友指出,非常感謝!