Node.js 是什么?我为何选择它?

当咱们学习一项新的事物的时候,咱们首先要知道它来自哪里?它是什么?能作什么或者换句话说,能解决什么问题?没有同样东西是最好的,是能够替代全部的,但在某一领域它是最适合的,正如 Node.js 它多是某些程序员苦苦追寻的东西,也多是某些程序员不会去关心的东西。本文主要为您介绍 Node.js 的背景及它能作什么,擅长什么,不会涉及到复杂的代码层面的知识讲解,若是你以为本身很熟悉了,也能够忽略它。html

做者简介:五月君,Nodejs Developer,热爱技术、喜欢分享的 90 后青年,公众号「Nodejs技术栈」,Github 开源项目 www.nodejs.red前端

文末附上笔者最近整理的 Node.js 技术栈学习指南路线图 供你们学习参考!node

背景介绍

Node.js® is a JavaScript runtime built on Chrome's V8 JavaScript engine. 这是来自 Node.js 官网 nodejs.org/en/ 的一段介绍,翻译成中文意为 Node.js 是一个基于 Chrome V8 引擎的 JavaScript 运行环境。这里重点几个关键词 V8JavaScript 后续会讲解,从这里能够看出 Node.js 并非一门新的编程语言,作为初学者这点先要弄清楚,它是 JavaScript 的运行环境,更进一步的说是在服务端的运行环境,所以这里的编程语言指的是 JavaScript。git

时间回归到 2009 年,在当时 JavaScript 仍是一个跑在浏览器环境里的一门脚本语言,当时的笔者仍是一名高中生,接触的编程语言是 VB 并不知 JavaScript 为什么物,但随后接触 JavaScript 以后了解到这以前用它能够写一些浏览器脚本,作一些动态特效,主要用于前端页面交互。在 2009 这一时间线以后 Javascript 不仅运行于浏览器,还能够运行于服务端,简直打通了前端与后端的任督二脉,固然这要归功于 Node.js 之父 Ryan Dahl。一度认为这是很伟大的,在众多编程语言里,为何会选择 JavaScript 呢?且看下面介绍。程序员

为何是 JavaScript?

Node.js 使用了一个事件驱动、非阻塞式 I/O 的模型,使其轻量又高效。这是来自于 Node.js 的另外一个介绍,关键词 事件驱动非阻塞式 I/O 所以,在基于这些条件之下 Node.js 做者 Ryan Dahl 在评估了 C、Lua、Haskell、Ruby、JavaScript 等语言以后,最终选择了 JavaScript,为何呢?github

JavaScript 是一个单线程的语言,单线程的优势是不会像 Java 这些多线程语言在编程时出现线程同步、线程锁问题同时也避免了上下文切换带来的性能开销问题,那么其实在浏览器环境也只能是单线程,能够想象一下多线程对同一个 DOM 进行操做是什么场景?不是乱套了吗?那么单线程可能你会想到的一个问题是,前面一个执行不完,后面不就卡住了吗?固然不能这样子的,JavaScript 是一种采用了事件驱动、异步回调的模式,另外 JavaScript 在服务端不存在什么历史包袱,在虚拟机上因为又有了 Chrome V8 的支持,使得 JavaScript 成为了 Node.js 的首选语言。数据库

为何选择 JavaScript 做者 Ryan Dahl 应该是最有发言权的,这里查了一些资料及参考了 深刻浅出 Node.js 一书,供你们有个初步的认知。编程

Node.js 架构

Node.js 由 Libuv、Chrome V八、一些核心 API 构成,以下图所示:后端

图片描述

以上展现了 Node.js 的构成,下面作下简单说明:api

  • Node Standard Library:Node.js 标准库,对外提供的 JavaScript 接口,例如模块 http、buffer、fs、stream 等

  • Node bindings:这里就是 JavaScript 与 C++ 链接的桥梁,对下层模块进行封装,向上层提供基础的 API 接口。

  • V8:Google 开源的高性能 JavaScript 引擎,使用 C++ 开发,而且应用于谷歌浏览器。若是您感兴趣想学习更多的 V8 引擎知识,请访问 What is V8?

  • Libuv:是一个跨平台的支持事件驱动的 I/O 库。它是使用 C 和 C++ 语言为 Node.js 所开发的,同时也是 I/O 操做的核心部分,例如读取文件和 OS 交互。来自一份 Libuv 的中文教程

  • C-ares:C-ares 是一个异步 DNS 解析库

  • Low-Level Components:提供了 http 解析、OpenSSL、数据压缩(zlib)等功能。

以上只是作一个初步的认知,若是你想深刻了解 Node.js 那么多每一个点都是值得你深刻研究的。

来自 stack overflow 的一个参考:which-is-correct-node-js-architecture

Node.js 特色

在了解了 Node.js 的一些背景及架构模型以后,已经解决了它来自哪里?是什么?这个问题,如今咱们来看看能解决什么问题?它适合作什么?

在这以前不知道您有没有据说过,Node.js 很擅长 I/O 密集型任务,应对一些 I/O 密集型的高并发场景仍是颇有优点的,事实也如此,这也是它的定位:提供一种简单安全的方法在 JavaScript 中构建高性能和可扩展的网络应用程序

  • 单线程

Node.js 使用单线程来运行,而不是向 Apache HTTP 之类的其它服务器,每一个请求将生产一个线程,这种方法避免了 CPU 上下文切换和内存中的大量执行堆栈,这也是 Nginx 和其它服务器为解决 “上一个 10 年,著名的 C10K 并发链接问题” 而采用的方法。

  • 非阻塞 I/O

Node.js 避免了因为须要等待输入或者输出(数据库、文件系统、Web服务器...)响应而形成的 CPU 时间损失,这得益于 Libuv 强大的异步 I/O。

  • 事件驱动编程

事件与回调在 JavaScript 中已经是家常便饭,同时这种编程对于习惯同步思路的同窗来讲可能一时很难理解,可是这种编程模式,确是一种高性能的服务模型。Node.js 与 Nginx 均是基于事件驱动的方式实现,不一样之处在于 Nginx 采用纯 C 进行编写,仅适用于 Web 服务器,在业务处理方面 Node.js 则是一个可扩展、高性能的平台。

  • 跨平台

起初 Node.js 只能运行于 Linux 平台,在 v0.6.0 版本后得益于 Libuv 的支持能够在 Windows 平台运行。

Node.js 适用于什么

讲了这么多那么谈下 Node.js 适合什么场景?

  • I/O 密集型场景

Node.js 的优点主要在于事件循环,非阻塞异步 I/O,只开一个线程,不会每一个请求过来我都去建立一个线程,从而产生资源开销。

  • ResutFul API

一般咱们可使用 Node.js 来作为中间层,负责组装数据提供 API 接口给到前端调用,这些数据源可能来自第三方接口或者数据库,例如,之前可能咱们经过后端 Java、PHP 等其它语言来作,如今咱们前端工程师经过 Node.js 便可完成,后端则能够更专一于业务开发。

既然提到了 ResultFul API,顺便推荐一个去哪儿开源的 API 管理工具 YAPI:github.com/YMFE/yapi 使用的 Node.js 进行开发的(声明下这里不是打广告,只是这个用起来真的很赞!忍不住向给你们推荐!)。

  • RPC 服务

RPC(Remote Procedure Call)中文名「远程过程调用」,也许你对它很陌生,可是在当今微服务模式下,咱们多是针对功能或者具体的业务形态进行服务化,那么服务之间的通讯一种常见的模式咱们都知道经过 HTTP 来实现,了解网络模型的同窗可能知道,若是咱们如今经过 TCP 的方式是否是会更高效呢?

固然是的,HTTP 属于应用层协议,在这之下就是传输层,显然以 TCP 形式是颇有优点的,RPC 服务也就是采用的 TCP,如今出名的 RPC 服务例如,Google 的 gRPC、阿里的 Dubble。

  • 基础工具

能够作为基础工具,前端领域中的编译器、构建工具、搭建脚手架等。比较出名的例如 Webpack、Gulp 都是很成功的。

  • 论坛社区

Nodeclub 是使用 Node.js 和 MongoDB 开发的社区系统,界面优雅,功能丰富,小巧迅速,能够用它搭建本身的社区。Cnode 社区就是一个成功的例子,Cnode 地址:cnodejs.org/

github.com/cnodejs/nod…

  • Backend For Frontend

Backend For Frontend,简称 BFF,服务于前端的后端,并不是是一种新技术只是一种逻辑上的分层,在这一层咱们能够作一些资源的整合,例如:原先前端须要从三个不一样的地方来获取资源,那么,有了这一层以后,咱们是否是能够作个聚合,统一处理以后返回给前端,同时也不授后端系统的变迁,致使也要去更改。

  • Serverless

这将是将来常常会听到的一个词,ServerLess 是一种 “无服务器架构”,它不须要开发者去关心运维、流量处理这些工做,开发者则能够更关注于业务自己。

函数即服务,那么写一个函数就能够实现一个 API 接口给到前端,显然对开发工做是减轻了不少,在 JavaScript 中函数则是一等一的公民,在 ServerLess 这一场景下 Node.js 自己也很轻量级,仍是拥有着很大的优点。

  • Microservices

微服务也是近两年一个很火热的词,这里提几个微服务主要的特色:小型服务、以独立进程运行、可使用不一样语言。那么这里则能够根据业务形态来选择不一样的语言实现,Node.js 自己也是很轻量级的,实现起来也很快,在一些 I/O 密集场景仍是很适用的。

什么场景选择什么工具,没有最好的只有更合适的!

为何选择 Node.js

谈一些我的感觉及经历,其实接触计算机行业说不晚也不早,在高中阶段开始接触的编程,在接触 Node.js 以前也学过不少编程语言,大体曲线是这样的 VB(这个是在高中时期)、C、C#(.Net)、Java、PHP 这些都是在学校的时候没事玩弄的,还有接触到前端,真的很杂,但没有同样精通的,这也是最可怕的,在大三暑假去了北京一家公司在那里实习了两个月 PHP,可是之间有碰见作 Node.js 的同窗,当时很好奇,哇奥,这是什么东东,居然可让 JavaScript 作后端,就是没见过市面那种。后来简单的作了了解,回到学校以后开始学习 Node.js 网上找各类资料看,阴差阳错吧,就这样选择了 Node.js 直到如今,其实语言只是一种工具,例如在后端中,抛开语言这一层,还有不少东西是须要咱们去不断学习的。

最后一点建议:不要给本身设定边界,例如:我必定要学习 Node.js 或者我必定要学习 Java 又或者 Python,其实在有条件的状况下能够多接触一些其它东西,一方面扩展了本身的边界,另外一方面本身也能够从中获取收益。

Node.js 技术栈学习指南路线图

这是最近画的一张 Node.js 技术栈学习指南路线图,从中能够看出抛开语言这一层面,剩下的都是咱们要学习的。欢迎你们关注公众号「Nodejs技术栈」专一于 Node.js 相关技术栈研究分享,如有 Node.js 相关文章也欢迎你们投稿!共同成长!