Node.js开发实战详解(txt+pdf+epub+mobi电子书下载)


发布时间:2020-10-06 22:08:25

点击下载

作者:黄丹华

出版社:清华大学出版社

格式: AZW3, DOCX, EPUB, MOBI, PDF, TXT

Node.js开发实战详解

Node.js开发实战详解试读:

前言

Node.js是一个JavaScript运行环境(runtime)。实际上它是对GoogleV8引擎(应用于Google Chrome浏览器)进行了封装。由于其拥有异步非阻塞、环境搭建简单、实践应用快等特性,使得其在新一代编程开发中更为流行。同时,由于Node.js基于JavaScript语法,因此在学习Node.js时也可以了解和学习JavaScript的语法,拓宽和加深读者对Web前端开发技术的理解。

当前,Node.js主要应用于HTTP Web服务器的搭建和快速实现的独立服务器应用。在实践项目中,Node.js更适合做一些小型系统服务或者一些大项目的部分功能的实现。由于其版本不稳定,很多公司中主要将其应用于一些小项目中。如果以后其版本能够更加稳定可控,相信会有更多的公司将其应用于各种项目和服务中。

目前,国内Node.js的相关技术图书还非常稀缺。为了给想要学习Node.js开发技术的人员一个必要的指导,笔者编写了这本书。本书既注重基础知识讲解,又非常注重编程实践练习,讲解时给出了有针对性的实例,各章还给出了一些编程实践练习题。相信读者通过阅读本书,不仅可以全面掌握Node.js开发技术,还可以不需要借助任何框架而独立运用Node.js实现HTTP Web服务器的相关功能,从而摒弃对框架的依赖,进一步加深读者自我研发及独立思考的能力。

本书的特点

1.编码不依赖任何框架

为了便于读者更好地了解原生Node.js的开发实践,本书没有借助任何其他框架来讲解Web实践应用,书中的所有模块都是通过编写原生代码来实现。2.结构合理,内容全面、系统

本书全面、系统地介绍了Node.js从入门到编程实践的各种技术,涵盖Node.js网络编程、Node.js与数据库等方方面面的知识。3.叙述详实,例程丰富

本书提供了大量例程,便于读者实践演练。书中的每个例子都经过精挑细选,有很强的针对性。这些实例都给出了完整的代码和详细的代码注释。这些代码非常简洁和高效,便于读者学习和调试。当然,读者也可以直接重用这些代码来解决自己的问题。4.结合实际,编程技巧贯穿其中

本书写作时特意给出了大量的实用编程技巧,对这些编程技巧的灵活使用,将会使读者的开发事半功倍。5.语言通俗,图文并茂

本书以通俗易懂的语言讲解每一个技术点和实例,讲解时还穿插了大量效果图,并给出了程序的运行结果插图,便于读者更加直观地学习和理解。6.大量习题,详尽解答

本书提供了大量的编程实践练习题和详尽的解答,便于读者进一步巩固和加深所学的各个技术点,从而达到更好的学习效果。7.配多媒体教学视频

为了便于读者更加高效、直观地理解书中的技术点,作者为本书专门录制了8小时配套的多媒体教学视频。这些视频和本书源代码一起收录于配书光盘中。虽然视频录制的设备条件有限(主要靠耳麦),但依然相信这些视频可以给读者的学习提供有益的帮助。

本书内容体系

本书共分11章,各章的具体内容介绍如下。

第1章主要介绍了Node.js的概念、配置、第一个Node.js程序Hello World的实现及异步编程思想等。

第2章主要介绍了Node.js中的模块的概念,以及Node.js中exports和module.exports之间的联系和区别。Node.js中的NPM模块包含request、socket.io、express、jade和forever模块。Node.js中的设计模式包含单例、适配器和装饰模式。

第3章主要介绍了Node.js的Web开发技术。包含HTTP简单服务搭建、Node.js静态资源服务器实现、文件处理、Cookie和Session实践、Crypto模块加密及Node.js与Nginx配合实践等。

第4章主要介绍了Node.js中UDP服务器的搭建实践及Node.js与PHP之间的合作方式。

第5章主要介绍了Node.js中require机制的实现、Node.js的C++扩展(同步和异步接口)编译实践方法。

第6章主要介绍了一些关于Node.js的编码习惯。

第7章主要介绍了利用Node.js操作MySQL和MongoDB的实例,其中包含实现Node.js的两个基类分别对应于MySQL和MongoDB。另外,还介绍了MySQL和MongoDB环境的搭建,以及两个数据中Node.js的NPM模块。

第8章主要从框架开发的角度介绍了一个基于Node.js的Myweb框架的基本设计架构及其实现的功能,以及该框架的实现。其中用到了express模块和jade解析模板,可帮助读者进一步了解Node.js的Web应用开发和express框架的应用。

第9章主要从框架应用的角度介绍了如何使用框架做一个简单的项目开发,即利用第8章的MyWeb 1.0框架实现一个简单的Web聊天室MyChat应用。

第10章主要介绍了两个实例:在线聊天室和联网在线中国象棋。这两个应用都是用本书中自我实践的代码框架MyWeb 2.0来实现的。

第11章主要介绍了Node.js的一些应用工具,包含日志模块、curl模块、crontab模块、forever模块、xml模块和邮件发送模块。

本书读者对象

● Node.js初学者;

● PHP或者JavaScript程序员;

● 想全面、系统地学习Node.js的人员;

● Node.js技术爱好者;

● 利用Node.js进行开发的技术人员;

● 大中专院校的学生和老师;

● 相关培训学校的学员。

本书作者

本书由黄丹华主笔编写。其他参与编写和资料整理的人员有陈杰、陈贞、樊俊、高彩丽、高莹婷、管磊、郭丽、韩亚、李红、李龙海、梁伟、刘忆智、曲宝军、孙忠贤、唐正兵、王全政、王勇浩、武文琛、徐学英、闫伍平、于轶、占海明、张帆。

致谢

本书在写作过程中参阅了大量的相关资料。在此对原文的作者、相关网站及社区表示特别的感谢!没有这些资料,笔者完成本书将会需要花费更多的时间,本书的推出时间也会延迟。下面给出本书参考的主要资料及来源。

CSDN社区中的《程序员如何说服老板采用Node.js》:由于Node.js已经越来越多地被程序员和公司关注,基于此CSDN有针对性地写了这篇文章,系统地告诉程序员在适当的机会下从哪些方面入手才能让团队及老板来支持Node.js的项目实现。本书中多处参考了该文章。

HACK SPARROW的Node.js Module-exports vs module.exports和Create NPM Package-Node.js Module:本书中介绍的exports与module.exports之间的区别和联系参考了英文资料Node.js Module-exports vs module.exports;本书中介绍的Node.js NPM模块发布参考了文章Create NPM Package-Node.js Module。

CNode社区ctrlacv的《静态文件服务器代码整理》:本书实现的一个静态服务器参考了国内知名Node.js社区CNode中的ctrlacv文章《静态文件服务器代码整理》。

田永强编著的《深入浅出Node.js(三):深入Node.js的模块机制》:本书在深入Node.js中介绍的require机制实现则是参阅了田永强的文章《深入浅出Node.js(三):深入Node.js的模块机制》编写而成。

移动开发博客lishen的《编写Node.js原生扩展》:本书中介绍的关于实现Node.js原生扩展模块方法,主要参考了国内网站移动开发博客lishen的文章《编写Node.js原生扩展》。

笔者在本书中给出了大量的脚注,注明这些资料的来源。其目的一是表示对原作者的尊重和感谢;二是便于读者查阅和学习。

本书的编写对笔者而言是一个“浩大的工程”。虽然笔者投入了大量的精力和时间,但只怕百密难免一疏。若有任何疑问或疏漏,请发邮件至bookservice2008@163.com。最后祝读者读书快乐!编著者第1章Node.js基础知识本章主要介绍Node.js的概念,以及Node.js的出现给我们程序员带来了什么方便、解决了什么问题、在项目开发中是否应该选择使用Node.js。同时介绍Node.js的配置、开发,以及Node.js的入门程序Hello world。最后介绍Node.js的编程思想、如何得到一个异步结果、区分同步和异步的编程思想的不同之处。1.1概述

本节主要介绍Node.js基本概念,包括什么是Node.js、它与其他编程语言之间的区别、它的特点和优势在哪里,以及项目开发过程中如何抉择是否使用Node.js开发应用。1.1.1 Node.js是什么

Node.js是一个JavaScript运行环境(runtime)。实际上它是对GoogleV8引擎(应用于Google Chrome浏览器)进行了封装。Node.js对一些特殊用例进行了优化,提供了替代的API,使得V8在非浏览器环境下运行得更好。其目的是可以在服务器端执行和运行JavaScript代码。长久以来JavaScript都是一个基于浏览器的客户端脚本语言,通过将其运行环境抽离出来,就可以在服务器端运行JavaScript代码,而并非仅仅依赖浏览器解析,从而就可以将其作为服务器端语言,由于其拥有异步非阻塞特性,因此其在长连接、多请求的环境下优势非常明显。

Node.js的编程语言是基于JavaScript的语法,因此想深入学习Node.js的入门者,可以先熟悉JavaScript编程语言,了解其基本的语法(本书不会介绍JavaScript的语法),同时要对服务器端开发有所了解。当然,如果你是初学者也可以通过本书学习Node.js的编程,但需要你对知识了解更深入一些。Node.js提供了一些特殊的API(Node.js官网提供了详细的API说明)库,因此在编写Node.js的时候可以理解为,使用JavaScript语言,利用Node.js的API库进行服务器端开发。1.1.2 Node.js带来了什么

初学者经常会提及一个问题——Node.js到底有什么用?这个问题也经常令我苦恼,是不是有了Node.js我们就可以抛弃PHP或者其他服务器语言了呢?答案是否定的。

首先要理解Node.js的优点,以及Node.js与其他语言之间的区别和联系。传统的服务器语言,如PHP和Java等,每个Web HTTP请求连接都会产生一个线程,假设每个线程需要2MB的配置内存,因此相对一个8GB的服务器主机,也只能承受来自4000个并发用户的请求,当服务器承受不了这么多用户的情况下就需要添加服务器,从而导致增加项目运营成本(当然现在有Nginx支撑,可以提供更高的并发量请求)。

其次,理解Node.js解决的问题是什么?Node.js解决多请求的方法,在于其处理连接服务器的方式。在Node.js中每个HTTP连接都会发射一个在Node.js引擎的进程中运行的事件,而不是为每个连接生成一个新的OS进程(并为其分配一些配套内容)。

综上所述就可以清晰地看出Node.js相对PHP来说其优点在于能处理高并发请求,并且由于Node.js是事件驱动,因此可以更好地节约服务器内存资源。

在项目的开发中,我们应该如何抉择是否使用Node.js作为项目开发实现呢?首先,必须要了解项目的类型是不是适合Node.js去开发项目。例如需要开发一个博客、论坛或者微博,那么是否能使用Node.js去开发?回答是肯定的,但是不合适,相对来说PHP在这方面已经很成熟。其次,要理解一个事实,在本书编写过程中Node.js版本还不是很稳定,在Node.js版本升级的过程中,可能引发一些项目代码中的问题,例如Node.js官方提供的API有所改动时,以及当项目Node.js版本升级时,则必须修改代码。

Node.js可以单独实现一个server,这也是Node.js一个非常大的优点,对于那些简单的server,通过Node.js实现比使用C++实现会简单得多。最后,牢记Node.js解决了长连接、多请求引发的成本问题,因此在一些项目,例如实时在线Game(如一起来画画、黑暗杀人游戏、实时休闲游戏等)、实时在线聊天室、实时消息推送功能、SNS实时交流、实时监控系统(如股票、系统运行状态等)等开发过程中,应该把握住机会,应用Node.js来开发。那么在如此好的机会面前,应该如何去说服团队和老板呢?

在CSDN社区中有一篇博文《程序员如何说服老板采用Node.js》,详细说明了一个项目是否适合用Node.js开发,当适合时应该如何用事实说服老板、团队和客户。总结其过程包括如下几个阶段,如图1-1所示。图1-1 说服过程

● 建立原型:对于老板来说他希望看到的是结果,不管你使用什么开发,他的最终目的是节省资源、快速开发、满足客户。因此首先需要给老板看到一个系统原型,能够让老板明白你的系统开发是有条理的,不是简简单单的一个想法。

● 寻找合作开发者:项目开发是一个团队的事情,我们依靠的是团队力量,因此想成功开发一个Node.js应用,必须要说服团队的成员和你共同开发。有团队的依靠才能更进一步地让老板放心。

● 充满活力的社区:此刻,Node.js社区用户数正以一个疯狂的速度增长,该社区吸引了众多顶尖开发者。也就是说,Node.js生态系统每天都在完善,并且通过不同渠道获得了各个企业的免费支持。你需要告诉老板的是,现在这门新技术正在蓬勃的发展,并且也会是未来Web应用的一门比较重要的语言。

● 性能:在合适的项目中,更要突出Node.js开发项目的优点,以及可行性。可以在一个项目的会议上,通过你的讲解更进一步地说服老板,让老板认为你的想法是正确并且可靠的。

● 说服客户:最后你需要做的就是说服客户,需要让他们知道的是,Node.js的开发更能够满足他们的需求,能够更快地开发出他们需要的产品。

把握以上几点以后,还需要我们加强个人的Node.js知识,多了解一些服务器端的知识扩展自己的知识层面。可以说Node.js给我们带来的是一个选择,在项目开发中遇到问题时,我们可以考虑使用Node.js来解决问题。对于程序员来说,给我们带来的是一个机遇和挑战,能够让我们成为小组Node.js项目开发中不可或缺的成员。1.2Node.js配置开发

本节将会介绍如何搭建Node.js的运行环境,包括Linux系统和Windows系统环境,同时学习一门语言的第一个程序“Hello World”。学完本节,需要掌握Linux系统和Windows系统下的Node.js环境搭建,以及编写简单的Node.js程序、运行和调式方法。

注意:在学习本节时,需要注意在本书编写过程中安装配置可能会和读者阅读本书时的版本安装存在差异,这些知识笔者后续会通过论坛告知大家,但是大致的安装和配置过程是类似的。1.2.1 Windows配置

Node.js的Windows运行环境安装步骤简单,只需要注意将执行文件node.exe路径添加到环境变量。安装主要分为4个步骤,其中安装步骤1中建议下载msi的后缀执行文件,主要是便于后续的项目开发。安装步骤4中介绍如何将node.exe添加到全局执行环境中,本步骤没有介绍如何在Window中添加环境变量,这些基本知识在这里就不详细介绍了。主要安装过程如下所述。(1)官网(http://nodejs.org)下载Node.js的Windows系统(32位和64位)最新版本,建议下载msi为后缀的版本,如图1-2中方框内所示的版本。exe为执行文件,但其缺少一些Node.js的模块和npm等。(2)下载完成后,执行MSI的安装文件。(3)安装完成,查看Node.js启动文件目录(右键单击Node.js启动快捷方式),如图1-3所示,启动文件目录一般默认情况下是在“C:\Program Files\nodejs\node.exe”。(4)将node.exe可执行文件路径添加到Windows的环境变量中;运行cmd,进入dos操作命令窗口,输入node-v查看是否安装成功,如图1-4所示,表明已经成功安装Node.js。图1-2 Node.js官网下载页面图1-3 Node.js右键快捷图标属性

注意:Windows添加环境变量的方法:右键计算机桌面图片,打开右侧导航栏中的“高级系统设置”,打开以后选择其中的“环境变量”,之后再更改用户的PATH值,在其原有变量值上加上Node.js可执行文件路径,两者使用分号分割,例如:C:\Users\danhuang\AppData\Roaming\npm\; C:\Program Files\nodejs\node.exe。图1-4 Node.js查看版本信息

成功安装后可以看到当前的Node.js的版本信息,如图1-4所示。如果没有成功添加到系统的环境变量中,cmd运行窗口会提示没有node指令,这时候应该检查是否已经将Node.js的可执行路径成功添加到环境变量中。1.2.2 Linux配置

Linux下的Node.js环境部署方法较多,本书就一种方法进行讲解。官网现在提供了两种Linux包,一个是源码安装包,另外一个是已经编译好的可执行文件,本书介绍Node.js源码的编译安装方法。相对Windows下的环境部署,Linux较为简单,里面只涉及一些Linux的解压和编译,以及软件安装指令。在编译安装Node.js时需要先查看一下README.md文件,其中会告诉你安装时依赖的库和软件版本信息。例如0.8.14版本中的README.md明确提示“Python 2.6 or 2.7”和“GNU Make 3.81 or newer”,以及“libexecinfo(FreeBSD and OpenBSD only)”。其说明Python版本在2.6或者2.7,而Make版本要3.81以上。可以通过如下指令,查看系统的Python和Make版本信息是否符合Node.js安装环境。

Linux系统下安装的相关步骤如下:(1)从官网下载最新版的Node.js for Linux的源码安装包(32位和64位)。(2)解压压缩包tar -zxvf node-v0.8.8.tar.gz(版本不同,名称也会不同)。(3)进入解压文件夹cd node-v0.8.8.。(4)执行./configure。(5)执行make。(6)执行make install。(7)安装完成后执行node-v查看版本信息。

Node.js在./configure时会先检查它安装所要依赖的包和库,如果系统已经安装,那么就可以正常通过,如果缺少安装包,系统会报错,把需要的安装包补上即可,如下是笔者在安装时遇到的依赖包问题,两个依赖包和库下载和配置方法如下:

以下一些错误信息,以及解决办法,可以作为参考。

./configure检查Node.js编译环境的依赖软件和依赖库是否支持,以上错误是Python版本过低,为2.4.3,必须升级为2.6和2.7版本以上。Python安装方法可以参考《Linux下Python开发环境安装》文章。

以上错误包含两个问题,第一是Make版本过低,第二个是需要创建一个linker.lock文件。可以首先检查Make的版本信息,之后再创建一个linker.lock文件,就能够成功安装了。1.2.3 Hello World

成功搭建好Node.js的运行环境后,我们就可以开始编写第一个程序Hello World。实现的主要需求是使用Node.js建立一个Web服务器,当请求服务器资源时,服务器响应一个HTTP请求,并显示Hello World字符串。

实现本需求会涉及Node.js的HTTP模块,该模块可以实现一个简单的HTTP服务器,相关代码以及实践步骤如下所述。(1)在任意文件夹中,创建app(可以在系统的任何地方)文件夹,同时在文件夹app中创建app.js的Node.js文件,用任意编辑器打开app.js文件,输入如下Node.js代码后保存并退出。【代码说明】

● require(' http' ):获取Node.js原生模块提供的HTTP模块对象。

● res.writeHead:通过res的HTTP响应对象,编写HTTP响应的头信息,并设定Content-Type指定返回的数据类型为文本text,当然这里的数据类型也可以是其他格式,例如html、css和image等。

● http.createServer():使用HTTP对象API方法createServer来创建服务器。

● listen:是HTTP对象的一个方法,其主要是启动服务器监听的端口和IP,第二个参数为可选参数,默认为本地127.0.0.1。

● console.log():是Node.js和JavaScript共有的调试接口。

本段代码是应用require来调用HTTP模块中的方法和属性,该require模块成功返回的是Node.js中HTTP模块中的方法和属性。如上代码中的listen接口有两个参数分别是运行端口号和服务器地址,其中的端口号为一个Number类型,服务器地址为字符串,运行时如果端口号数据类型不正确会报错,只要端口不被其他应用程占用,都可以应用作为Node.js的服务端口。(2)进入第一步创建的app文件夹,运行node app.js指令,执行正确后,将会看到屏幕中输出的信息:Server running at http://127.0.0.1:1337,如图1-5所示,表明已经成功启动本地IP的1337端口HTTP服务器。图1-5 Node.js的app.js运行结果(3)打开任意浏览器,输入server服务器地址:http://127.0.0.1:1337,在Web页面中我们将可以看到Hello World字符串,如图1-6所示。图1-6 Node.js Web页面返回

上面就是我们的第一个程序Hello World的整个实践过程,作为新的语言读者一般都会遇到一些棘手的问题,在1.2.4节中列举了一些在QQ群以及论坛经常被提及的新手入门问题。1.2.4 常见问题

初学者一般会遇到以下几个问题,这里是个人在QQ群里面解答问题时积累下来的一些问题。

● 出现Error:Cannot find module。这个问题主要原因是在当前目录没有找到app.js文件,也就是执行的app.js文件不在当前目录,需要指定执行app.js文件的路径。例如app.js在C:\Users\Administrator>Desktop文件夹,而当我们在C:\Users\Administrator文件夹下运行app.js时就会出现如上问题,如图1-7所示。通俗地说,就是希望运行app.js,但是当前目录下没有该文件存在,因此导致无法运行。图1-7 错误执行app.js脚本

● 出现Error:listen EACCES。这个问题的主要原因是监听端口被其他应用程序占用了,可以修改当前监听端口,例如将1337修改为3000, Windows下可以通过netstat-aon—findstr "1337"来查看被哪个程序占用,Linux下可以应用ps -ef — grep 1337来查看。这种异常情况很多时候是因为上一次服务器启动监听后非正常的退出,导致上一个端口未被释放,例如在Linux下使用快捷键Ctrl+Z退出。

● 如何退出当前运行程序?正常退出监听端口的方法是按快捷键Ctrl+C(Windows和Linux是一样的)。

● 更改Node.js文件,希望服务器立即响应更改,而不需要重新运行文件。app.js输出的是Hello World,但现在想输出hello baby,难道要重启Node.js的启动文件吗?使用node命令运行js文件时,服务器是不会自动监控文件更改然后重启的,这里需要使用到一些github用户开发的Node.js开源模块。常见的有node-dev和forever,其安装配置方法这里就不细介绍,关于Node.js的模块安装将会在第2章详细介绍。1.3异步编程

什么是异步编程?异步编程给程序员带来了哪些编程困难?我们应该如何克服异步编程带来的困难?这些都是本节需要解决的问题,学完本节需要掌握异步编程的基本概念,以及异步编程的一些基本知识。

在笔者的博客中有一篇文章叫做《同步调用、回调和异步调用区别》里面使用伪代码的“烽火长城”例子介绍这三者之间的关系,本节将会更详细地通过代码来阐述它们的区别和联系,同时介绍Node.js的异步编程思想和注意的问题。1.3.1 同步调用和异步调用

同步调用是一种阻塞式调用,一段代码调用另一段代码时,必须等待这段代码执行结束并返回结果后,代码才能继续执行下去。例如考试的时候,有的同学是这样的:一道题一道题往下做,当有一道题没做出来时,绝对不会继续做下去,这就如同同步调用的过程,一段逻辑没有执行完成时,代码会一直等待,直到代码执行结束,才执行下面的逻辑。下面看一个同步调用的PHP例子,通过例子来详细说明同步调用的思想。代码如下:【代码说明】

● Person:Person是一个静态类,其中有两个方法think和answer。

● think方法:思考5秒钟,并返回成功结果。

● answer方法:回答问题,并且输出结果。

从代码运行结果可以看出,我们必须等待think方法执行5秒结束后,得到返回结果,才能执行answer方法。像这种必须等待一个程序运行结束,才能执行下一段程序的调用模式称为阻塞式调用,也就是同步调用。

异步调用是一种非阻塞式调用,一段异步代码还未执行完,可以继续执行下一段代码逻辑,当代码执行完以后,通过回调返回继续执行相应的逻辑,而不耽误其他代码的执行。

例如,一个经理拿到多个任务,他可以将任务同时分配给多个人去完成,而下属完成后就将结果反馈给他,当他接到所有反馈后就表明该任务完成了。经理分配给员工完成任务就相当于一个异步执行的代码执行过程,每个员工之间是不会相互阻碍的,当员工完成时,他会告知经理“我已经完成任务了”。这整个任务的执行就是一个异步执行的过程,代码的异步调用也一样。

同样,在考试时,有的学生思考一道问题,当问题没有解决时会继续看下一题,而当该问题有所思路时,则会返回继续解答该题,这就如同异步调用的过程。下面的代码是如上例子的一个异步调用方法,代码先执行think方法,当think方法没有结束时,代码会继续执行answer方法,当think方法结束时,通过回调函数执行相应逻辑,示例Node.js代码如下:【代码说明】

● Person:Person是一个类,其中有两个方法think和answer;

● think异步方法:异步等待思考5秒钟,思考结束后输出’thinking~~~’同时执行callback()函数;

● answer方法:输出正在解答其他问题’I am answering other question'。

以上代码执行结果如图1-8所示。图1-8 Node.js异步代码执行结果

如图1-8所示的结果中我们可以看到输出的首先是person.answer()的执行结果,而person.think输出结果在5秒后输出。因此可以看出当我们还在think的时候(输出提示'thinking~~~' ),就已经在解答其他问题了(输出提示’I am answering other question' )。

代码执行过程是先输出person.answer()的结果,而当思考函数think方法结束后才执行输出’think~~~! ’和’tinking 5 second, get the right answer! '。由此看出,虽然person.think()先执行,由于该方法是一个异步函数(该函数中使用了Node.js中的setTimeout异步接口),因此异步调用时并不等待think的思考结束,而是先执行person.answer()。像这样一段代码未执行完,代码运行不会被阻塞,而是继续执行下一段代码的调用模式称为异步调用。

上面代码在说明,虽然person.think()这个函数需要思考5秒,但是由于person.think()是一个异步执行代码,因此整个代码逻辑的执行过程不会被阻塞,所以会继续执行person.answer()方法,因此先返回person.answer()执行的结果,5秒结束后才返回person.think()执行结果。

注意:有读者会提问“为什么person.think()是一个异步方法,而person.answer()却不是”?主要原因在于person.think()调用了Node.js中的异步函数setTimeout(),因此我们常说的Node.js拥有异步非阻塞特性,并不是说Node.js中所有的代码逻辑都是异步执行的,这要取决于是否在代码逻辑中应用其异步函数。1.3.2 回调和异步调用

首先明确一点,回调并非是异步调用,回调是一种解决异步函数执行结果的处理方法。在异步调用,如果我们希望将执行的结果返回并且处理时,可以通过回调的方法解决。为了能够更好的区分回调和异步回调的区别,我们来看一个简单的例子,代码如下:【代码说明】

● waitFive():同步函数,逻辑是等待5秒钟后,执行一个回调函数;

● echo()函数方法:输出name信息。

上面代码逻辑是通过while循环来判断等待的时间是否超过5秒,时间超出5秒后执行一个回调函数echo(),打印输出信息。注意这里的waitFive()是一个同步函数,因为其实现没有应用到任何异步接口。在代码等待5秒后执行结果如图1-9所示。图1-9 同步Node.js示例代码运行结果

从执行结果上来看,其执行过程是一个同步执行过程。如果是异步执行的话,其执行结果应该是先输出its over,再打印danhuang。

以上代码是一个回调逻辑,但不是一个异步代码逻辑,因为其中并没有涉及Node.js的异步调用接口。从如图1-9所示的结果中能看出回调和异步调用的区别,当waitFive()函数执行时,整个代码执行过程都会等待waitFive()函数的执行,而并非如异步调用那样waitFive未结束,还会继续执行console.log("its over")。因此,回调还是一种阻塞式调用。1.3.3 获取异步函数的执行结果

异步函数往往不是直接返回执行结果,而是通过事件驱动方式,将执行结果返回到回调函数中,之后在回调函数中处理相应的逻辑代码。大家可以在官网看到很多的API,都是通过异步回调方式来调用的。

Node.js中很多API的调用模式是异步调用的,因此在学习Node.js过程中理解异步调用、同步调用和回调是非常重要的。例如之前的"Hello World"代码中涉及一个文件的读取,代码中使用的是Node.js中的同步执行的文件读取fs.readFileSync (filename, [encoding]) API,该API是一个同步执行函数,与之对应的异步函数是fs.readFile (filename, [encoding], [callback]),该API携带了一个callback参数,由于其API是一个异步执行函数,需要通过回调函数来处理异步返回结果。同步代码中获取执行结果方法:

而如果getName()函数是一个异步函数,我们用同样的方法来获取name值时,会出现异常,提示name没有定义undefined。如下获取一个异步函数的结果的代码是错误的:

打印出address,可以看到第二个例子结果为null,原因很简单,异步函数dns.resolve4()还未执行结束时,就已经执行到console.log(address),因此最终address为null。既然异步函数出现这个问题,我们就可以使用回调去获取参数。如下代码,通过回调函数获取执行的结果name值:

这样,同样可以实现打印address结果,主要的方法是通过回调函数function(address){}获取resolve4异步执行的结果。

试读结束[说明:试读内容隐藏了图片]

下载完整电子书


相关推荐

最新文章


© 2020 txtepub下载