• 重拾nodeJs


    不确定为什么要去,正是出发的理由。

    Node.js 工作原理

    Node.js 的主要思路是:使用非阻塞的,事件驱动的 I/O (输入/输出端口)操作来保持在处理跨平台 (across distributed devices) 数据密集型实时应用时的轻巧高效。

    Node 真正的亮点在于建设高性能,高扩展性的互联网应用——因为它能够处理庞大的并且高并发的连接。

    总结:Node是一个可以让JavaScript运行在服务器端的平台,抛弃了传统平台依靠多线程来实现高并发的设计思路,而采用单线程、异步式I/O、事件驱动式的程序设计模型

    工作原理对比:

    传统的网络服务技术:每个新增一个连接(请求)便生成一个新的线程,这个新的线程会占用系统内存,最终会占掉所有的可用内存。

    Node.js :仅仅只运行在一个单线程中,使用非阻塞的异步 I/O 调用,所有连接都由该线程处理,在 libuv 的加分下,可以允许其支持数万并发连接(全部挂在该线程的事件循环中)。

    适用类型:

    Node.js 从来不是用于解决大规模计算问题而创建的。它的出现是为了解决大规模I/O 的问题,并且在这一点上做的非常好。

    如果项目需求中不包含CPU密集型操作,也不需要访问任何阻塞的资源,那么就可以利用的 Node.js 的优点,尽情的享受快速、可扩展的网络应用。

    Node.js快速入门 —— 异步式I/O与事件式编程

    回调函数

    异步式I/O是通过回调函数来实现的

    //用异步的方式读取一个文本内容为“Hello world”的文件fs
    var
    fs = require("fs");
    fs.readFile("test.txt", "utf-8", function(err, data) { console.log(data); });
    console.log("end");
    //运行结果
    Hello world
    end

    同步的方式是阻塞线程等待文件读取完毕后,将文件内容输出,然后才继续执行下一步代码,因此控制台先打印“Hello world”,然后再打印“end”。

    而异步式I/O是通过回调函数来实现的,通过将控制台输出文件内容的函数作为参数传给fs.readFile函数,fs.readFile调用时只是将异步式I/O请求发送给操作系统,然后立即返回并执行后面的语句,当fs接收到I/O请求完成的事件时,才会调用回调函数。因此我们先看到“end”,再看到“Hello world”的内容。

    事件

    Node.js所有的异步I/O操作在完成时都会发送一个事件到事件队列。事件由EventEmitter提供,前面提到的fs.readFile的回调函数就是通过EventEmitter来实现。

    模块和包

    Node提供了require函数来调用其他模块。node中的模块和包并没有本质的区别,包可以理解为某个功能模块的集合。

    什么是模块

    模块是node应用程序的基本组成部分,文件和模块是一一对应的。一个node.js文件就是一个模块,这个文件可能是JavaScript代码、JSON或者编译过的C/C++扩展。

    创建及加载模块

    node提供了exports和require两个对象,其中exports是模块的公开接口,require用于从外部获取一个模块的接口。

    新建一个myModule.js文件,输入如下代码:

    var text;
    
    function setText(myText){
        text = myText;
    }
    
    function printText(){
        console.log(text);
    }
    
    exports.setText = setText;
    exports.printText = printText;

    再新建一个test.js文件: 

    var myModule = require("./myModule");
    
    myModule.setText("Hello world!");
    myModule.printText();
    
    //运行test.js,结果为: Hello world
    !

    单次加载

    模块的调用与创建一个对象不同,require不会重复加载模块。

    修改test.js:

    var myModule1 = require("./myModule");
    myModule1.setText("Hello world!");
    
    var myModule2 = require("./myModule");
    myModule2.setText("Hi baby!");
    
    myModule1.printText();
    myModule2.printText();
    
    //运行结果: Hi bayby
    ! Hi bayby!

     这是因为模块不会重复加载,myModule1和myModule2指向的都是同一个实例,因此myModule1的text值就被myModule2覆盖了。

    exports.hello = function(){
        console.log("Hello world");
    };

    创建包

    包是模块基础上更深一步的抽象,类似于C/C++的函数库或者java/.net的类库。

    node包是一个目录,其中包括一个JSON格式的包说明文件package.json。node对包的要求并不严格,但还是建议制作包时遵循CommonJS规范。

    建立一个名为mypackage的文件夹,在文件夹中新建index.js:

    exports.hello = function(){ console.log("Hello world"); };

     然后在mypackage之外建立test.js:

    var mypackage = require("./mypackage");
    
    mypackage.hello();

    这就是一个简单的包了,通过定制package.json,我们可以创建更复杂的包。

    定制package.json:

    1. 在mypackage文件夹下创建一个package.json文件和一个lib子文件夹。
    2. 将index.js重命名为interface.js并放入lib文件夹。
    3. 打开package.json并输入如下json文本:

      {
      "main": "./lib/interface.js"
      }

    运行test.js,依然可以看到控制台输出“Hello world”。

    node调用某个包时,会首先检查package.json文件的main字段,将其作为包的接口模块,如果package.json或main字段不存在,就会去寻找index.js或index.node作为包的接口。

    node.js包管理器

    本地模式和全局模式

    npm默认为本地模式,会从http://npmjs.org搜索或下载包 ,将包安装到当前目录的node_modules
    子目录下。

    也可以使用全局安装,它会将包安装在系统目录:

    “npm [install/i] -g [package_name]”

    本地模式可以直接通过require使用,但是不会注册环境变量。
    全局模式不能直接通过require使用,但是它会注册环境变量。

    通过npm link命令可以在本地包和全局包之间创建符号链接,使全局包可以通过require使用,例如要require全局模式安装的express,可以在工程目录下运行:

    npm link express

    使用npm link命令还可以将本地包链接到全局,但是npm link命令不支持windows

    调试

    命令行调试

    例如要调试test.js,则在命令行中输入:

    node debug test.js

    以下为基本的调试命令:

    run: 执行脚本,在第一行暂停
    restart: 重新执行脚本
    cont, c: 继续执行,直到遇到下一个断点
    next, n: 单步执行
    step, s: 单步执行并进入函数
    out, o: 从函数中步出
    setBreakpoint(), sb(): 在当前行设置断点
    setBreakpoint(‘f()’), sb(...): 在函数f的第一行设置断点
    setBreakpoint(‘script.js’, 20), sb(...): 在 script.js 的第20行设置断点
    clearBreakpoint, cb(...): 清除所有断点
    backtrace, bt: 显示当前的调用栈
    list(5): 显示当前执行到的前后5行代码
    watch(expr): 把表达式 expr 加入监视列表
    unwatch(expr): 把表达式 expr 从监视列表移除
    watchers: 显示监视列表中所有的表达式和值
    repl: 在当前上下文打开即时求值环境
    kill: 终止当前执行的脚本
    scripts: 显示当前已加载的所有脚本
    version: 显示 V8 的版本

    远程调试

    使用以下语句之一可以打开调试服务器:

    node --debug[=port] test.js //脚本正常执行,调试客户端可以连接到调试服务器。
    node --debug-brk[=port] test.js //脚本暂停执行等待客户端连接。
    //如不指定端口,则默认为5858。
    
    //客户端:
    
    node debug 127.0.0.1:5858
    node-inspector
    
    //安装node-inspector:
    
    npm install -g node-inspector
    //在终端连接调试服务器:
    
    node --debug-brk=5858 test.js
    //启动node-inspector:
    
    node-inspector
    //在浏览器中打开http://127.0.0.1:8080/debug?port=5858。

     未完待续。。。。。。

  • 相关阅读:
    python3--生成器
    python3--列表生成式
    python3--装饰器高级学习版
    python3--嵌套函数
    python3-装饰器
    《Hexo+github搭建个人博客》
    Html网页的代码
    关于内联框架
    性能调优
    Java知识总结
  • 原文地址:https://www.cnblogs.com/shanhaihong/p/7490975.html
Copyright © 2020-2023  润新知