Home Web Front-end JS Tutorial Node.js local file operation method of file copy and directory traversal_node.js

Node.js local file operation method of file copy and directory traversal_node.js

May 16, 2016 pm 03:15 PM
javascript node node.js Copy files document Table of contents Traverse directory

File copy
NodeJS provides basic file operation API, but advanced functions such as file copying are not provided, so let’s practice with the file copying program first. Similar to the copy command, our program needs to be able to accept two parameters: the source file path and the target file path.

Small file copy
We use the built-in fs module of NodeJS to simply implement this program as follows.

var fs = require('fs');

function copy(src, dst) {
  fs.writeFileSync(dst, fs.readFileSync(src));
}

function main(argv) {
  copy(argv[0], argv[1]);
}

main(process.argv.slice(2));

Copy after login

The above program uses fs.readFileSync to read the file content from the source path, and uses fs.writeFileSync to write the file content to the target path.

Bean knowledge: process is a global variable and command line parameters can be obtained through process.argv. Since argv[0] is fixedly equal to the absolute path of the NodeJS executable program, and argv[1] is fixedly equal to the absolute path of the main module, the first command line parameter starts from the position argv[2].

Large file copy
The above program has no problem copying some small files, but this method of reading all the file contents into the memory at one time and then writing them to the disk at once is not suitable for copying large files, and the memory will be exhausted. For large files, we can only read a little and write a little until the copy is completed. Therefore, the above program needs to be modified as follows.

var fs = require('fs');

function copy(src, dst) {
  fs.createReadStream(src).pipe(fs.createWriteStream(dst));
}

function main(argv) {
  copy(argv[0], argv[1]);
}

main(process.argv.slice(2));

Copy after login

The above program uses fs.createReadStream to create a read-only data stream for the source file, and uses fs.createWriteStream to create a write-only data stream for the target file, and uses the pipe method to connect the two data streams. What happens after the connection is made, to put it more abstractly, is that water flows from one bucket to another along the pipe.

Traverse directories

Traversing directories is a common requirement when manipulating files. For example, when writing a program that needs to find and process all JS files in a specified directory, it needs to traverse the entire directory.

Recursive Algorithm
Recursive algorithms are generally used when traversing directories, otherwise it will be difficult to write concise code. Recursive algorithms are similar to mathematical induction in that they solve problems by continuously reducing their size. The following example illustrates this approach.

function factorial(n) {
  if (n === 1) {
    return 1;
  } else {
    return n * factorial(n - 1);
  }
}
Copy after login

The above function is used to calculate the factorial of N (N!). As you can see, when N is greater than 1, the problem reduces to computing the factorial of N times N-1. When N equals 1, the problem reaches its minimum size and no further simplification is needed, so 1 is returned directly.

Trap: Although the code written using the recursive algorithm is concise, since each recursion generates a function call, when performance needs to be prioritized, the recursive algorithm needs to be converted into a loop algorithm to reduce the number of function calls.

Traversal Algorithm
The directory is a tree structure, and the depth-first + pre-order traversal algorithm is generally used when traversing. Depth first means that after reaching a node, traverse the child nodes first instead of the neighbor nodes. Preorder traversal means that the traversal is completed when a node is reached for the first time, rather than the last time it returns to a node. Therefore, when using this traversal method, the traversal order of the tree below is A > B > D > E > C > F.

     A
     / \
    B  C
    / \  \
   D  E  F
Copy after login

Synchronous traversal
After understanding the necessary algorithms, we can simply implement the following directory traversal function.

function travel(dir, callback) {
  fs.readdirSync(dir).forEach(function (file) {
    var pathname = path.join(dir, file);

    if (fs.statSync(pathname).isDirectory()) {
      travel(pathname, callback);
    } else {
      callback(pathname);
    }
  });
}

Copy after login

As you can see, this function uses a directory as the starting point for traversal. When a subdirectory is encountered, the subdirectory is traversed first. When a file is encountered, the absolute path to the file is passed to the callback function. After the callback function gets the file path, it can make various judgments and processes. So let's say we have the following directory:

- /home/user/
  - foo/
    x.js
  - bar/
    y.js
  z.css
Copy after login

When traversing the directory using the following code, the input obtained is as follows.

travel('/home/user', function (pathname) {
  console.log(pathname);
});

Copy after login
/home/user/foo/x.js
/home/user/bar/y.js
/home/user/z.css
Copy after login

Asynchronous traversal
If an asynchronous API is used to read the directory or read the file status, the directory traversal function will be a little complicated to implement, but the principle is exactly the same. The asynchronous version of the travel function is as follows.

function travel(dir, callback, finish) {
  fs.readdir(dir, function (err, files) {
    (function next(i) {
      if (i < files.length) {
        var pathname = path.join(dir, files[i]);

        fs.stat(pathname, function (err, stats) {
          if (stats.isDirectory()) {
            travel(pathname, callback, function () {
              next(i + 1);
            });
          } else {
            callback(pathname, function () {
              next(i + 1);
            });
          }
        });
      } else {
        finish && finish();
      }
    }(0));
  });
}

Copy after login

The techniques for writing asynchronous traversal functions will not be introduced in detail here. This will be introduced in detail in subsequent chapters. In short, we can see that asynchronous programming is quite complicated.

Statement of this Website
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn

Hot Article Tags

Notepad++7.3.1

Notepad++7.3.1

Easy-to-use and free code editor

SublimeText3 Chinese version

SublimeText3 Chinese version

Chinese version, very easy to use

Zend Studio 13.0.1

Zend Studio 13.0.1

Powerful PHP integrated development environment

Dreamweaver CS6

Dreamweaver CS6

Visual web development tools

SublimeText3 Mac version

SublimeText3 Mac version

God-level code editing software (SublimeText3)

How to transfer files from Quark Cloud Disk to Baidu Cloud Disk? How to transfer files from Quark Cloud Disk to Baidu Cloud Disk? Mar 14, 2024 pm 02:07 PM

How to transfer files from Quark Cloud Disk to Baidu Cloud Disk?

What to do if the 0x80004005 error code appears. The editor will teach you how to solve the 0x80004005 error code. What to do if the 0x80004005 error code appears. The editor will teach you how to solve the 0x80004005 error code. Mar 21, 2024 pm 09:17 PM

What to do if the 0x80004005 error code appears. The editor will teach you how to solve the 0x80004005 error code.

What is hiberfil.sys file? Can hiberfil.sys be deleted? What is hiberfil.sys file? Can hiberfil.sys be deleted? Mar 15, 2024 am 09:49 AM

What is hiberfil.sys file? Can hiberfil.sys be deleted?

Different uses of slashes and backslashes in file paths Different uses of slashes and backslashes in file paths Feb 26, 2024 pm 04:36 PM

Different uses of slashes and backslashes in file paths

Pi Node Teaching: What is a Pi Node? How to install and set up Pi Node? Pi Node Teaching: What is a Pi Node? How to install and set up Pi Node? Mar 05, 2025 pm 05:57 PM

Pi Node Teaching: What is a Pi Node? How to install and set up Pi Node?

Detailed explanation of log viewing command in Linux system! Detailed explanation of log viewing command in Linux system! Mar 06, 2024 pm 03:55 PM

Detailed explanation of log viewing command in Linux system!

Detailed explanation of the role of .ibd files in MySQL and related precautions Detailed explanation of the role of .ibd files in MySQL and related precautions Mar 15, 2024 am 08:00 AM

Detailed explanation of the role of .ibd files in MySQL and related precautions

Create and run Linux ".a" files Create and run Linux ".a" files Mar 20, 2024 pm 04:46 PM

Create and run Linux ".a" files

See all articles