為什麼向後端工程師推薦Node.js

2020-12-14 電子產品世界

科普文一則,說說我對Node.js的一些認識,以及我作為前端工程師為什麼會向後端工程師推薦Node.js
Node.js 是伺服器端的 JavaScript 運行環境,它具有無阻塞(non-blocking)和事件驅動(event-driven)等的特色,Node.js 採用V8引擎,同樣,Node.js實現了類似 Apache 和 nginx 的web服務,讓你可以通過它來搭建基於 JavaScript的Web App。」
我想不僅僅是Node.js,當我們要引入任何一種新技術前都必須要搞清楚幾個問題:
1. 我們遇到了什麼問題?
2. 這項新技術解決什麼問題,是否契合我們遇到的問題?
3. 我們遇到問題的多種解決方案中,當前這項新技術的優勢體現在哪兒?
4. 使用新技術,帶來哪些新問題,嚴重麼,我們能否解決掉?
我們的問題:Server端阻塞
Node.js被設計用來解決服務端阻塞問題.下面通過一段簡單的代碼解釋何為阻塞:

1
2
3
4
//根據ID,在資料庫中Persons表中查出Name
var name = db.query(select name from persons where id=1);
//進程等待數據查詢完畢,然後使用查詢結果。
output(name)



這段代碼的問題是在上面兩個語句之間,在整個數據查詢的過程中,當前程序進程往往只是在等待結果的返回.這就造成了進程的阻塞.對於高並發,I/O 密集行的網絡應用中,一方面進程很長時間處於等待狀態,另一方面為了應付新的請求不斷的增加新的進程.這樣的浪費會導致系統支持QPS遠遠小於後端數據服 務能夠支撐的QPS,成為了系統的瓶頸.而且這樣的系統也特別容易被慢連結攻擊(客戶端故意不接收或減緩接收數據,加長進程等待時間)。
如何解決阻塞問題
可以引入事件處理機制解決這個問題。在查詢請求發起之前註冊數據加載事件的響應函數,請求發出之後立即將進程交出,而當數據返回後再觸發這個事件並在預定好的事件響應函數中繼續處理數據:
1
2
3
4
5
6
//定義如何後續數據處理函數
function onDataLoad(name){
output(name);
}
//發起數據請求,同時指定數據返回後的回調函數
db.query(select name from persons where id=1,onDataLoad);



我們看到若按照這個思路解決阻塞問題,首先我們要提供一套高效的異步事件調度機制.而主要用於處理瀏覽器端的各種交互事件的JavaScript。相對於其他語言,至少有兩個關鍵點特別適合完成這個任務。
為什麼JS適合解決阻塞問題
首先JavaScript是一種函數式程式語言,函數程式語言最重要的數學基礎是λ演算(lambda calculus) — 即函數對象可以作為其他函數對象的輸入(參數)和輸出(返回值)。
這個特性使得為事件指定回調函數變得很容易。特別是JavaScript還支持匿名函數。通過匿名函數的輔助,之前的代碼可以進行簡寫如下:
1
2
3
db.query(select name from persons where id=1,function(name){
output(name);
});



還有另一個關鍵問題是,異步回調的運行上下文保持(本文暫稱其為」狀態保持」)。我們先來看一段代碼來說明何為狀態保持:
1
2
3
4
5
6
7
//傳統同步寫法:將查詢和結果列印抽象為一個方法
function main(){
var id = 1;
var name = db.query(select name from persons where id= + id);
output(person id: + id + , name: + name);
}
main();



前面的寫法在傳統的阻塞是編程中非常常見,但接下來進行異步改寫時會遇到一些困擾:
1
2
3
4
5
6
7
8
//異步寫法:
function main(){
var id = 1;
db.query(select name from persons where id= + id,function(name){
output(person id: + id + , name: + name);//n秒後數據返回後執行回調
});
}
main();



細心的朋友可能已經注意到,當等待了n秒數據查詢結果返回後執行回調時。回調函數中卻仍然使用了main函數的局部變量」id」,而」id」似乎應 該在n秒前走出其作用域。為什麼此時」id」仍然可以訪問呢,這是因為JavaScript的另外一個重要語言特性:閉包(Closures)。接下來我 來詳解閉包的原委。
在複雜的應用中,我們一定會遇到這類場景。即在函數運行時需要訪問函數定義時的上下文數據(注意:一定要區分函數定義時和函數運行時兩個不同的時 刻)。特別是在異步編程模型中,函數的定義和運行又分處不同的時間段,那麼保持上下文的問題變得更加突出了。因為我們在任務執行一半時把資源交出去沒有問 題,但當任務需要再次繼續時我們必須還原現場。
在這個例子中,db.query作為一個公共的資料庫查詢方法,把」id」這個業務數據傳入給db.query,交由其保存是不太合適的。但我們可 以稍作抽象,讓db.query再支持一個需要保持狀態的數據對象傳入,當數據查詢完畢後可以把這些狀態數據原封不動的回傳。如下:
1
2
3
4
5
6
7
8
9
function main(){
var id = 1;
var currentState = new Object();
currentState.person_id = id;
db.query(select name from persons where id= + id, function(name,state){
output(person id: + state.person_id + , name: + name);
},currentState);//注意currentState是db.query的第三個參數
}
main();



記住這種重要的思路,我們再看看是否還能進一步的抽象?可以的,不過接下的動作之前,我們還要了解在JavaScript中一個函數也是一個對象。 一個函數實例fn除了函數體的定義之外,我們仍然可以在這個函數對象實例之本身擴展其他屬性,如fn.a=1;受到這個啟發我們嘗試把需要保持的狀態直接 綁定到函數實例上:
1
2
3
4
5
6
7
8
9
10
function main(){
var id = 1;
var currentState = new Object();
currentState.person_id = id;
function onDataLoad(name){
output(person id: + onDataLoad.state.person_id + , name: + name);
}
onDataLoad.state = currentState ;//為函數指定state屬性,用於保持狀態
db.query(select name from persons where id= + id, onDataLoad);
}



我們做了什麼?生成了currentState對象,然後在函數onDataLoad定義時,將currentState綁定給 onDataLoad這個函數實例。那麼在onDataLoad運行時,就可以拿到定義時的state對象了。JavaScript的閉包特性就是內置了 這個過程而已。
在每個JavaScript函數運行時,都有一個運行時內部對象稱為Execution Context,它包含如下Variable Object(VO,變量對象), Scope Chain(作用域鏈)和」this」 Value三部分。如圖:

相關焦點

  • Node.js為何在後端開發中不受重視?
    語言只是一個工具,對高手來講Java、golang、python、Javascript都可以完成複雜的後端開發工作,這些語言最大的區別是生態。Java無疑是所有後端開發語言中的佼佼者,它的生態完善度超乎你的想像,這也是Java在後端開發領域無法撼動的根本。其他幾種語言我覺得沒有根本性的區別,論生態完善度,都是半斤八兩,論高並發,golang當之無愧,論語言友好度,Node.js可以排到首位。
  • node.js、MongoDB下一代的LAMP
    node.js、MongoDB下一代的LAMP 我們大部分人在做網站時,都用的是LAMP,殊不知LAMP已成過去式,新一代的小生:nix、node.js、MongoDB誕生了,讓我們走進他們,知道他們的故事!
  • Node.js 是什麼?我為什麼選擇它?
    在 2009 這一時間線之後 Javascript 不只運行於瀏覽器,還可以運行於服務端,簡直打通了前端與後端的任督二脈,當然這要歸功於 Node.js 之父 Ryan Dahl。一度認為這是很偉大的,在眾多程式語言裡,為什麼會選擇 JavaScript 呢?且看下面介紹。為什麼是 JavaScript?Node.js 使用了一個事件驅動、非阻塞式 I/O 的模型,使其輕量又高效。
  • Node.js開發後端服務這幾點你做了麼?
    用Node.js開發後端服務的程式設計師大部分偏前端的全棧工程師,他們中很多人對如何開發後端服務掌握的並不系統。通常意義上來說,如果只是單純的會用Node.js寫一些很基礎的服務,對原理性的東西一竅不通,這些人並不能稱之為全棧工程師。
  • 為什麼Node.js是後端開發區塊最酷的孩子!
    Node.js已經迅速成為後端開發最流行的框架之一。仔細閱讀以了解為什麼。昨天,我遇到了一些關於Node.js的有趣信息 - 它正在被一些最大的全球性組織使用,包括NASA,PayPal,LinkedIn,Netflix和Walmart。
  • centos7編程實踐:安裝nodejs
    Node.js是一個javascript運行環境。它讓javascript可以開發後端程序,實現幾乎其他後端語言實現的所有功能,可以與PHP、Java、Python、.NET、Ruby等後端語言平起平坐。
  • 推薦一些Node.js超好用的工具庫
    首先明確一下庫和框架的區別:一般而言,一個工程中可以使用多個庫,但只能使用一個框架,本文只推薦庫,不涉及Express, egg.js, Koa 這類框架。開源地址:https://github.com/moment/moment/axiosaxios是一個http請求庫,體積小巧,功能豐富,前後端都可用,自發布以來,好評如潮。
  • 我開始討厭node.js了
    過了沒多久,我發現了node,原來js還可以寫後臺,這領我萌生了一個幼稚的想法,用js就可以橫掃天下了。現在很多前端新人還保持著這樣的想法。冰山一角直到我接觸到java,我才想明白我為什麼感覺node零散。java的語法和c#的語法簡直一模一樣,但是並不像.net體系那樣過度封裝,寫起來雖然沒有那种放蕩不羈愛自由的感覺,但是整體好像規矩了很多。這領我對node一統天下的想法感覺到一絲遲疑。node好像只是冰山一角,世界這麼大,我想去看看。
  • 後端Web開發:Node.js和Java
    在本文中,我們將重點關注Node.js作為後端開發環境的日益普及,以及Java開發人員在後端所做的事情。介紹對於今年的DZone資料庫指南,我們對來自整個IT行業的軟體專業人員進行了調查。我們收到了1,202條回復,完成率為64%。
  • 如何使用Node.js上傳文件
    Node.js正在迅速成為更受歡迎的Web開發框架之一。繼續閱讀以熟悉這個強大的JavaScript技術!如今,前端開發對後端進程造成了很大的影響,尤其是在JavaScript領域。JS最初是一種針對瀏覽器的語言,已經成熟為現代工具的每一個角落。
  • 什麼是伺服器端JavaScript Node.js?
    你呢 Node.js用戶以Heroku和OpenShift等伺服器而聞名,但由於它們是海外服務,因此需要英語技能。 缺點2:您需要在伺服器上設置Node.js。  租賃伺服器上已經設置了諸如PHP,Ruby和Java之類的後端語言,但是您需要自己設置Node.js。我們將構建自己的伺服器程序。與其他後端語言的性能比較儘管它不如Java和C,但是您可以看到其處理速度比PHP快。
  • 2021了你該知道的6個Node.js後端框架
    作為開發人員,大家都至少熟悉一個後端框架。以下將推薦一些2021年應該使用的6個流行的後端框架。 2.Nest Nest 是一個用於構建高效,可擴展的 Node.js 伺服器端應用程式的框架。真正完備的、工業級的框架。
  • 前端開發為什麼要學Node.js?小白如何深入理解Node.js?
    有人好奇從事Web前端為什麼要學習Node.js?今天千鋒廣州Web前端培訓老師就給大家詳細的分析一下。Node.js是什麼?Node是一個讓JavaScript運行在服務端的開發平臺,它讓JavaScript成為與PHP、Python、Perl、Ruby等服務端語言平起平坐的腳本語言。
  • 如何利用Node.js 構建分布式集群
    本文為UCloud 公司高級工程師文天樂在深JS大會上發表的演講內容,主要介紹了UCloud內部如何利用Node.js 構建分布式集群,並分享了實踐過程中走過的坑,希望對正在使用Node.js或是即將使用Node.js的朋友有一些幫助。
  • 10+ 最佳的 Node.js 教程結合實例
    對於完全的Node.js初學者,  在深入挖掘本文章後續提到的學習項目之前,一步步按照airpair.com上面入門指南的要點 或 Node.js入門指南 之類的文章學習是不錯的選擇。Nodeschool.io是另一個比較好的網站,上面有著非常多的資料,可以學習基本的node.js及相關的技術。
  • Node.js與Ruby on Rails:二者哪個最適合Web開發?
    它類似於node . js的npm。所有Rails應用程式都有一個gem文件,您可以在其中指定gem。然後您可以運行一個bundler命令來安裝所有的程序,類似於npm安裝node . js。關於Ruby on Rails的另一件偉大的事情是它已經存在了一段時間,它有一個非常受人尊敬的智能社區。維護Ruby on Rails的開發人員非常聰明,對框架非常熱情。
  • Node.JS快速入門
    -v會顯示當前node的版本號2.快速入門2.1 控制臺輸出我們現在做個最簡單的小例子,演示如何在控制臺輸出,在e盤創建文件夾nodedemo ,創建文本文件demo1.js,代碼內容我們在命令提示符下輸入命令node demo1.js ,結果如下:2.2 使用函數我們剛才的例子非常簡單,咱們這裡再看一下函數的使用:我們在命令提示符下輸入命令node demo2.js ,結果如下:
  • 10 個最適合 Web 和 APP 開發的 NodeJS 框架
    Node.js Express 對於一個已經在使用 node.js 的開發人員來說,Express 或者」node.js express」並不是一個新鮮事。Express 框架提供了對 node.js 原生 API 的比較好的封裝,從而使開發者更加容易地使用node.js。 Express 框架提供了用來開發強壯的 web/移動應用,以及 API 的所有功能。
  • SDCC講師專訪:淘寶樸靈談Node.js
    曾經是一個專職的前端工程師,曾在SAP做Mobile Web App的研究開發,2011年期間在上海組織CNode社區的線下分享會,2012年加入淘寶的數據產品團隊專職參與Node的開發。曾在InfoQ上主持《深入淺出Node.js》專欄。
  • 2017年Node.js使用大調查,後端使用多於前端!
    【IT168評論】之前,就有網友針對「Node.js用在前端還是後端?」的問題進行討論。近日,Node.js基金會發布了Node.js 2017用戶調查,我們用數據說話,看看Node.js到底適用於哪些應用和開發環境?同時也看看全世界的程式設計師都是怎樣用Node.js。