node.js 如何监视文件变化


Posted in Javascript onSeptember 01, 2020

fs.FSWatcher

fs.FSWatcher类 继承了 EventEmitter,用于监视文件变化,调用 fs.watch 后返回一个 fs.FSWatcher 实例,每当指定监视的文件被修改时,实例会触发事件调用回调函数

fs.watch('./tmp', (eventType, filename) => {
 if (filename) {
  console.log(filename);
 }
});

fs.watch()

fs.watch(filename[, options][, listener]) 监视文件变化,返回 fs.FSWatcher 实例

1.filename:文件或文件夹路径

2.options

  • encoding
  • recursive:默认值 false,应该监视所有子目录,还是仅监视当前目录,仅在 macOS 和 Windows 上支持
  • persistent:默认值 true,指示如果文件已正被监视,进程是否应继续运行
  • listener(eventType, filename):文件变化回调函数

eventType 主要是 renamechange ,在大多数平台上,文件在目录中出现或消失时触发 'rename' 事件,在 Windows 上,如果监视的目录被移动或重命名,则不会触发任何事件,当监视的目录被删除时,则报告 EPERM 错误

fs.watch('./', { recursive: true }, (eventType, filename) => {
 console.log(eventType, filename);
});

fs.watchFile()

fs.watchFile(filename[, options], listener) 用于监视文件变化

1.filename

2.options

  • biginit:默认值 false,指定回调 stat 中的数值是否为 biginit 类型
  • persistent:默认值 true,当文件正在被监视时,进程是否应该继续运行
  • interval:默认值 5007,用来指定轮询频率(ms)

3.listener(currentStats, previousStats):listener 有两个参数,当前的 stat 对象和之前的 stat 对象
要在修改文件时收到通知,则需要比较 curr.mtime prev.mtime

const fs = require('fs');

fs.watchFile('./test.txt', { interval: 100 }, (curr, prev) => {
 console.log('当前的最近修改时间是: ' + curr.mtime);
 console.log('之前的最近修改时间是: ' + prev.mtime);
});

const tid = setInterval(() => {
 fs.appendFile('./test.txt', 'Hello, world!\n', err => {
  if (err) throw err;
  console.log('文件修改完成');
 });
}, 300);

setTimeout(() => {
 clearInterval(tid);
 fs.unwatchFile('./test.txt');
}, 2000);

fs.watch() 与 fs.watchFile()

因为 fs.watchFile() 使用轮训方式检测文件变化,如果不设置 interval 或者设置较高的值会发现文件变化的监视有延迟
而 fs.watch() 监听操作系统提供的事件,而且可以监视目录变化,使用 fs.watch() 比 fs.watchFile() 更高效,平常应尽可能使用 fs.watch() 代替 fs.watchFile()

当然 fs.watch() 依赖操作系统的实现,在不同平台上表现会有差异

  • Linux 操作系统使用 inotify
  • 在 macOS 系统使用 FSEvents
  • 在 windows 系统使用 ReadDirectoryChangesW

fs.unwatchFile

fs.unwatchFile(filename[, listener]) 停止监视 filename 的变化,如果指定了 listener,则仅移除此特定监听器,否则将移除所有监听器,从而停止监视 filename

fs.unwatchFile('./test.txt');

社区选择

fs.watchFile() 性能问题,fs.watch() 平台不一致等两个方法都有不尽如人意的地方

Node.js fs.watch:

MacOS 有时候不提供 filename
在部分场景不触发修改事件(MacOS Sublime)
经常一次修改两次触发事件
大部分文件变化 eventType 都是 rename.
未提供简单的监视文件树方式

Node.js fs.watchFile:

事件处理问题和 fs.watch 一样烂
没有嵌套监听
CPU 消耗大

https://www.npmjs.com/package/chokidar

日常在监视文件变化可以选择社区的优秀方案

  1. node-watch
  2. chokidar
const chokidar = require('chokidar');
 
// One-liner for current directory
chokidar.watch('.').on('all', (event, path) => {
 console.log(event, path);
});
// Initialize watcher.
const watcher = chokidar.watch('file, dir, glob, or array', {
 ignored: /(^|[\/\\])\../, // ignore dotfiles
 persistent: true
});
 
// Something to use when events are received.
const log = console.log.bind(console);
// Add event listeners.
watcher
 .on('add', path => log(`File ${path} has been added`))
 .on('change', path => log(`File ${path} has been changed`))
 .on('unlink', path => log(`File ${path} has been removed`));
 
// More possible events.
watcher
 .on('addDir', path => log(`Directory ${path} has been added`))
 .on('unlinkDir', path => log(`Directory ${path} has been removed`))
 .on('error', error => log(`Watcher error: ${error}`))
 .on('ready', () => log('Initial scan complete. Ready for changes'))
 .on('raw', (event, path, details) => { // internal
  log('Raw event info:', event, path, details);
 });

以上就是node.js 如何监视文件变化的详细内容,更多关于node.js 监视文件的资料请关注三水点靠木其它相关文章!

Javascript 相关文章推荐
使用Javascript和DOM Interfaces来处理HTML
Oct 09 Javascript
javascript 图片裁剪技巧解读
Nov 15 Javascript
JavaScript DOM节点添加示例
Jul 16 Javascript
分享20款美化网站的 jQuery Lightbox 灯箱插件
Oct 10 Javascript
在JavaScript中操作时间之getUTCDate()方法的使用
Jun 10 Javascript
手动初始化Angular的模块与控制器
Dec 26 Javascript
详解VueJs异步动态加载块
Mar 09 Javascript
Angular.js中上传指令ng-upload的基本使用教程
Jul 30 Javascript
jQuery 实时保存页面动态添加的数据的示例
Aug 14 jQuery
layui实现数据表格隐藏列的示例
Oct 25 Javascript
JS如何定义用字符串拼接的变量
Jul 11 Javascript
Javascript实现打鼓效果
Jan 29 Javascript
JS JQuery获取data-*属性值方法解析
Sep 01 #jQuery
谈谈node.js中的模块系统
Sep 01 #Javascript
JavaScript浅层克隆与深度克隆示例详解
Sep 01 #Javascript
VUE子组件向父组件传值详解(含传多值及添加额外参数场景)
Sep 01 #Javascript
vue离开当前页面触发的函数代码
Sep 01 #Javascript
Vue 实现监听窗口关闭事件,并在窗口关闭前发送请求
Sep 01 #Javascript
Node.js web 应用如何封装到Docker容器中
Sep 01 #Javascript
You might like
最简单的PHP程序--记数器
2006/10/09 PHP
在PHP里得到前天和昨天的日期的代码
2007/08/16 PHP
PHP CURL 内存泄露问题解决方法
2015/02/12 PHP
PHP人民币金额转大写实例代码
2015/10/02 PHP
用jscript实现新建word文档
2007/06/15 Javascript
ExtJS 2.2.1的grid控件在ie6中的显示问题
2009/05/04 Javascript
防止动态加载JavaScript引起的内存泄漏问题
2009/10/08 Javascript
Javascript 通过json自动生成Dom的代码
2010/04/01 Javascript
JQuery与JSon实现的无刷新分页代码
2011/09/13 Javascript
疯狂Jquery第一天(Jquery学习笔记)
2012/05/11 Javascript
基于jquery自定义图片热区效果
2012/07/21 Javascript
JavaScript异步加载浅析
2014/12/28 Javascript
jquery及js实现动态加载js文件的方法
2016/01/21 Javascript
一个超简单的jQuery回调函数例子(分享)
2016/08/08 Javascript
Vue.js使用v-show和v-if的注意事项
2016/12/13 Javascript
vue.js树形组件之删除双击增加分支实例代码
2017/02/28 Javascript
jQuery Validate格式验证功能实例代码(包括重名验证)
2017/07/18 jQuery
JS实现登录页密码的显示和隐藏功能
2017/12/06 Javascript
zTree树形菜单交互选项卡效果的实现方法
2017/12/25 Javascript
JavaScript 中使用 Generator的方法
2017/12/29 Javascript
详解使用VueJS开发项目中的兼容问题
2018/08/02 Javascript
vue.js响应式原理解析与实现
2020/06/22 Javascript
fetch 如何实现请求数据
2018/12/20 Javascript
原生js实现商品筛选功能
2019/10/28 Javascript
js的Object.assign用法示例分析
2020/03/05 Javascript
Python 基于FIR实现Hilbert滤波器求信号包络详解
2020/02/26 Python
python 字符串的驻留机制及优缺点
2020/06/19 Python
css3进阶之less实现星空动画的示例代码
2019/09/10 HTML / CSS
AmazeUI底部导航栏与分享按钮的示例代码
2020/08/18 HTML / CSS
Right-on官方网站:日本知名的休闲服装品牌
2019/07/12 全球购物
教堂婚礼主持词
2014/03/14 职场文书
交通事故协议书范文
2014/04/16 职场文书
人事专员岗位职责说明书
2014/07/30 职场文书
优秀班组事迹材料
2014/12/24 职场文书
初中教务主任竞聘演讲稿(范文)
2019/08/20 职场文书
如何利用python实现Simhash算法
2022/06/28 Python