官术网_书友最值得收藏!

The process object

By now it should be clear as to how Node is structured, in terms of V8, the event loop, and so forth. We are now going to discuss, in detail, how instructions that you write (a JavaScript program) are compiled by V8 into a list of instructions whose execution context is accessible via the native Node process object.

The single thread forming the spine of Node's event loop is V8's event loop. When I/O operations are initiated within this loop they are delegated to libuv, which manages the request using its own (multi-threaded, asynchronous) environment. libuv announces the completion of I/O operations, allowing any callbacks waiting on this event to be re-introduced to the main V8 thread for execution:

The process object

Node's process object provides information on and control over the current running process. It is an instance of EventEmitter, is accessible from any scope, and exposes very useful low-level pointers. Consider the following program:

var size = process.argv[2];
var totl = process.argv[3] || 100;
var buff = [];
for(var i=0; i < totl; i++) {
  buff.push(new Buffer(size));
  process.stdout.write(process.memoryUsage().heapTotal + "\n");
}

Tip

Downloading the example code:

You can download the example code files for all Packt books you have purchased from your account at http://www.packtpub.com. If you purchased this book elsewhere, you can visit http://www.packtpub.com/support and register to have the files e-mailed directly to you.

Assuming the program file is named process.js, it would be executed like so:

> node process.js 1000000 100

This execution context first fetches the two command-line arguments via process.argv, builds a looping construct that grows memory usage depending on these arguments, and emits memory usage data as each new allocation is made. The program sends output to stdout, but could alternatively stream output to other processes, or even a file:

> node process.js 1000000 100 > out.file

In fact, the familiar console.log is implemented in the Node core as a wrapper around process.stdout.write:

 
  console.log = function (d) {
  process.stdout.write(d + '\n');
};

A Node process begins by constructing a single execution stack, with the global context forming the base of the stack. Functions on this stack execute within their own, local, context (sometimes referred to as scope), which remains enclosed within the global context (which you'll hear referred to as closure). Because Node is evented, any given execution context can commit the running thread to handling an eventual execution context. This is the purpose of callback functions.

Consider the following schematic of a simple interface for accessing the filesystem:

The process object

If we were to instantiate Filesystem and call readDir a nested execution context structure would be created: (global (fileSystem (readDir (anonymous function) ) ) ). The concomitant execution stack is introduced to Node's single process thread. This stack remains in memory until libuv reports that fs.readdir has completed, at which point the registered anonymous callback fires, resolving the sole pending execution context. As no further events are pending, and the maintenance of closures no longer necessary, the entire structure can be safely torn down (in reverse, beginning with anonymous), and the process can exit, freeing any allocated memory. This method of building up and tearing down a single stack is what Node's event loop is ultimately doing.

We'll explore the full suite of commands and attributes contained by the process object as we continue to develop examples and libraries in this book.

主站蜘蛛池模板: 柘城县| 安吉县| 上栗县| 阳山县| 崇州市| 潮州市| 寻乌县| 乌拉特后旗| 淅川县| 东宁县| 隆林| 大竹县| 定陶县| 双城市| 乌鲁木齐县| 景德镇市| 黎川县| 大城县| 盈江县| 文安县| 忻州市| 库尔勒市| 于都县| 河池市| 收藏| 偃师市| 屏边| 福安市| 澜沧| 沁水县| 汕尾市| 虎林市| 禄丰县| 扶余县| 临泉县| 南丹县| 江达县| 青海省| 平度市| 高邑县| 江西省|