在使用node開發過程中很多時候會遇到對文件系統做各種處理操縱
-
文件處理開發中常用的內置模塊
- path:處理文件路徑
- fs:操作文件系統
- child_process:新建子進程
- process: 進程
-
比較好用的第三方模塊
- glob: 使用shell命令的模式匹配文件
- trash: 文件放到回收站
下面通過一個文件遍歷例子 來描述下node處理文件的各種實現方式
1. 遞歸遍歷
很多時候如果不知道其它方式處理的話第一反應就是手寫遞歸處理遍歷文件夾
下面我寫了幾個簡約的列子來看下
我們要處理文件的目錄結構如下:
使用遞歸處理的代碼實現
```
const fs = require('fs');
const path = require('path');
const files = [];
const findDirectory = function (dir) {
const fdList = fs.readdirSync(dir);
fdList.forEach(fd => {
const fdPath = path.resolve(dir, fd);
const stat = fs.statSync(fdPath);
if (stat.isFile()) {
files.push(fdPath)
} else if (stat.isDirectory()) {
findDirectory(fdPath);
}
});
};
const filesDisplay = function (filePath) {
const fdPath = path.resolve(filePath);
const stat = fs.statSync(fdPath);
if (stat.isDirectory()) {
findDirectory(fdPath);
} else if (stat.isFile()) {
files.push(fdPath)
}
return files
};
console.log(filesDisplay('/Users/fengshi/Documents/tix/test'))
運行返回結果:
[ '/Users/fengshi/Documents/tix/test/2.7.7/WARemoteDebug.js', '/Users/fengshi/Documents/tix/test/2.7.7/appservice.js', '/Users/fengshi/Documents/tix/test/2.7.7/base/WAService.js', '/Users/fengshi/Documents/tix/test/2.7.7/base/WAWebview.js', '/Users/fengshi/Documents/tix/test/2.7.7/bridge.js', '/Users/fengshi/Documents/tix/test/2.7.7/context.js', '/Users/fengshi/Documents/tix/test/2.7.7/documentstart.js', '/Users/fengshi/Documents/tix/test/2.7.7/hls.js', '/Users/fengshi/Documents/tix/test/2.7.7/pageframe.js', '/Users/fengshi/Documents/tix/test/2.7.7/virtualdom.js' ]
可以看出使用遞歸操作我們最少需要使用fs path模塊和一些fs模塊的方法
- fs.statSync: 獲取文件信息對象Stats
- stat.isDirectory():判斷是否是文件夾
- stat.isFile():判斷是否是文件
- path.resolve(path):一個路徑或路徑片段解析成一個絕對路徑返回解析後的路徑字符串
- fs.readdirSync(dir): 讀取目錄下面的文件 返回目錄下的文件列表對象
2. 使用glob模塊
glob很方便功能也很強大
因爲他是基於shell命令的模式 如果想深入研究的話可以參考glob
使用glob模塊的話很簡潔實現我們想要的效果
const path = require('path');
const glob = require('glob');
const files = glob.sync(path.resolve('/Users/fengshi/Documents/tix/test/2.7.7', '**'), { nodir: true});
console.log(files)
運行結果: [ '/Users/fengshi/Documents/tix/test/2.7.7/appservice.js', '/Users/fengshi/Documents/tix/test/2.7.7/base/WAService.js', '/Users/fengshi/Documents/tix/test/2.7.7/base/WAWebview.js', '/Users/fengshi/Documents/tix/test/2.7.7/bridge.js', '/Users/fengshi/Documents/tix/test/2.7.7/context.js', '/Users/fengshi/Documents/tix/test/2.7.7/documentstart.js', '/Users/fengshi/Documents/tix/test/2.7.7/hls.js', '/Users/fengshi/Documents/tix/test/2.7.7/pageframe.js', '/Users/fengshi/Documents/tix/test/2.7.7/virtualdom.js', '/Users/fengshi/Documents/tix/test/2.7.7/WARemoteDebug.js' ]
- nodir:不匹配目錄,只匹配文件。(注意:要只匹配目錄,只需在模式末尾加上)
參數對象中比較常用的
- ignore:添加一個模式或一個glob模式數組來排除匹配
const path = require('path');
const glob = require('glob');
const ignore = [];
ignore.push(path.resolve('/Users/fengshi/Documents/tix/test/2.7.7', 'base', '*'));
ignore.push(path.resolve('/Users/fengshi/Documents/tix/test/2.7.7', 'hls.js'));
const files = glob.sync(path.resolve('/Users/fengshi/Documents/tix/test/2.7.7', '**'), {
ignore,
nodir: true
});
console.log(files)
運行結果: [ '/Users/fengshi/Documents/tix/test/2.7.7/appservice.js', '/Users/fengshi/Documents/tix/test/2.7.7/bridge.js', '/Users/fengshi/Documents/tix/test/2.7.7/context.js', '/Users/fengshi/Documents/tix/test/2.7.7/documentstart.js', '/Users/fengshi/Documents/tix/test/2.7.7/pageframe.js', '/Users/fengshi/Documents/tix/test/2.7.7/virtualdom.js', '/Users/fengshi/Documents/tix/test/2.7.7/WARemoteDebug.js' ]
可以看到base文件夾下和hls.js都忽略了 後續我們可以對文件組合過濾等處理都很方便
靈活的使用shell模式匹配操作文件 可以看出讓代碼可讀性和簡約大大提高
3. 使用child_process子進程
child_process模塊非常強大和重要
靈活運用它可以讓你的node水平提高一個水平
child_process 模塊讓我們在一個子進程內運行一些能夠進入操作系統的命令
使我們可以控制子進程的輸入流,操作它的輸出流 就像在linux系統裏面一樣操作
這裏不詳細講解關於child_process的點 主要就是運行各種命令 來實現我們的結果
大致我們使用到的一些方法主要是
-
創建同步的進程(爲了書寫方便這裏採用同步寫法 當然都有對應的異步操作)
- child_process.execFileSync(file[, args][, options])
- child_process.execSync(command[, options])
- child_process.spawnSync(command[, args][, options])
這種方式需要對shell腳本有一定的基礎會方便很多 我們先創建一個shell腳本文件fileHandle
-
#!/bin/bash for file in `ls $1` do if [ -d $1"/"$file ] then read_dir $1"/"$file else echo $1"/"$file fi done
然後在js裏面調用
const childProcess = require('child_process');
const dir = '/Users/fengshi/Documents/tix/test/2.7.7'
const files = childProcess.execFileSync('/Users/fengshi/Documents/tix/test/fileHandle', [dir], {encoding: 'utf8'});
console.log(files)
運行結果: /Users/fengshi/Documents/tix/test/2.7.7/WARemoteDebug.js /Users/fengshi/Documents/tix/test/2.7.7/appservice.js /Users/fengshi/Documents/tix/test/2.7.7/base/WAService.js /Users/fengshi/Documents/tix/test/2.7.7/base/WAWebview.js /Users/fengshi/Documents/tix/test/2.7.7/bridge.js /Users/fengshi/Documents/tix/test/2.7.7/context.js /Users/fengshi/Documents/tix/test/2.7.7/documentstart.js /Users/fengshi/Documents/tix/test/2.7.7/hls.js /Users/fengshi/Documents/tix/test/2.7.7/pageframe.js /Users/fengshi/Documents/tix/test/2.7.7/virtualdom.js
child_process模塊讓我們可以脫離在node環境下 使用shell腳本可以實現我們想做的很多事