Node.js 基礎
Node.js 簡介
- Node.js創始人是大名鼎鼎的 Ryan Dahl。
- Node.js不是一個JavaScript應用,而是一個由C++語言編寫而成的JavaScript的運行環境。
- Node.js是一個基於Google所開發的瀏覽器Chrome V8引擎的JavaScript運行環境,簡單來說,就是運行在服務端或後端的JavaScript,支持跨平台。
Node.js 的結構
Node.js的結構大致可以分為三個層次:
Node.js標準庫
Node.js標準庫,包含Node.js的包管理器npm以及Node.js的核心模塊等,這部分由JavaScript編寫而成,是開發者開發過程直接接觸調用的。
中間層
這一層是JavaScript與底層C/C++溝通的橋樑:
- Node bindings:是Nodejs標準庫和底層V8引擎等溝通的橋樑,前者通過bindings調用後者,相互交換數據。
- C/C++ Addons(插件):是開發者開發過程中基於基礎的V8 API編寫的Node.js C++動態鏈接庫,用作高性能或底層模塊,供上層的JavaScript調用。
Node.js基礎構建層
- V8:Google推出的JavaScript引擎,為JavaScript提供了在非瀏覽器端運行的環境。
- libuv:為 Node.js提供了跨平台、線程池、事件池、非同步IO等能力,是Node.js強大的關鍵。
- C-ares:提供了非同步處理DNS相關的能力。
- http parser、OpenSSL、zlib等:提供包括HTTP解析、SSL、數據壓縮等能力。
Node.js的特點
單線程
Node.js保持了JavaScript在瀏覽器中單線程的特點。這裡的單線程是指主線程為「單線程」,所有阻塞部分交給一個線程池處理,然後主線程通過一個隊列跟線程池協作。代碼主要由一堆callback回調構成,然後主線程在循環過程中適時調用這些代碼。
像瀏覽器中JavaScript與UI共用一個線程一樣,JavaScript長時間執行會導致UI的渲染和響應被中斷。在Node.js中,長時間的CPU佔用也會導致後續的非同步I/O發不出調用,已完成的非同步I/O的回調函數也會得不到及時執行。
HTML5定製了Web Workers的標準,Web Workers能夠創建工作線程來進行計算,以解決JavaScript大計算阻塞UI渲染的問題。工作線程為了不阻塞主線程,通過消息傳遞的方式來傳遞運行結果,這也使得工作線程不能訪問到主線程中的UI。
Node.js採用了與Web Workers相同的思路來解決單線程中大計算量的問題:child_process。子進程的出現意味著Node可以從容地應對單線程在健壯性和無法利用多核CPU方面的問題。通過將計算分發到各個子進程,可以將大量計算分解掉,然後通過進程之間的事件消息來傳遞結果。
非同步、非阻塞I/O
Node.js中絕大多數操作都是以非同步的方式進行調用,從文件讀取到網路請求等,類似於發起ajax調用。每個調用之間無需等待之前的I/O調用結束,比如兩個文件讀取任務的耗時取決於最慢的那個文件讀取耗時。
事件驅動和回調函數
Node.js的設計思想以事件驅動為核心,配合非同步I/O,將事件點暴露給業務邏輯。因此Node.js提供的絕大多數API都是基於事件的、非同步的風格,開發人員需要根據自己的業務邏輯註冊響應的回調函數,回調函數等待相應的事件觸發。
Node.js的應用場景
- 提供 Rest/JSON API 服務
- 網站(express/koa等)
- im即時聊天(http://socket.io)
- http proxy,組裝rpc服務,作為微服務的一部分
- 前端構建工具(grunt/gulp/bower/webpack/fis3)
- 跨平台打包工具(nw.js、electron、cordova)
- 命令行工具
- 編輯器(atom,vscode)
Node.js核心模塊
- http模塊:創建HTTP伺服器、客戶端
- fs模塊:文件讀寫模塊
- url模塊:url地址處理模塊
- querystring模塊:查詢字元串處理模塊
Node.js常用模塊
- util模塊:工具模塊,提供對象反序列化等工具函數
- path模塊:路徑處理模塊
- dns模塊:域名處理和域名解析模塊
參考資料
- 《Node.js 開發實戰》
- 《深入淺出 Node.js》
- 知乎live:大前端和 Node.js 那些事
推薦閱讀:
TAG:Node.js |