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 相关文章推荐
用js实现预览待上传的本地图片
Mar 15 Javascript
怎样在JavaScript里写一个swing把数据插入数据库
Dec 10 Javascript
JS生成不重复随机数组的函数代码
Jun 10 Javascript
牛叉的Jquery——Jquery与DOM对象的互相转换及DOM的三种操作
Oct 29 Javascript
理解javascript定时器中的setTimeout与setInterval
Feb 23 Javascript
BootStrap智能表单demo示例详解
Jun 13 Javascript
使用bootstrapValidator插件进行动态添加表单元素并校验
Sep 28 Javascript
JavaScript数组操作详解
Feb 04 Javascript
从parcel.js打包出错到选择nvm的全部过程
Jan 23 Javascript
JQuery样式操作、click事件以及索引值-选项卡应用示例
May 14 jQuery
微信小程序按钮点击动画效果的实现
Sep 04 Javascript
JavaScript图片旋转效果实现方法详解
Jun 28 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
AM/FM收音机的安装与调试
2021/03/02 无线电
非洲第一个咖啡超凡杯大赛承办国—卢旺达的咖啡怎么样
2021/03/03 咖啡文化
Smarty分页实现方法完整实例
2016/05/11 PHP
PHP编写简单的App接口
2016/08/28 PHP
php脚本守护进程原理与实现方法详解
2017/07/20 PHP
浅析PHP 中move_uploaded_file 上传中文文件名失败
2019/04/17 PHP
flexigrid 参数说明
2010/11/23 Javascript
js实现的map方法示例代码
2014/01/13 Javascript
JS自调用匿名函数具体实现
2014/02/11 Javascript
js浏览器本地存储store.js介绍及应用
2014/05/13 Javascript
javascript基于HTML5 canvas制作画箭头组件
2014/06/25 Javascript
JavaScript日期类型的一些用法介绍
2015/03/02 Javascript
javascript格式化日期时间方法汇总
2015/06/19 Javascript
在html中引入外部js文件,并调用带参函数的方法
2016/10/31 Javascript
基于jQuery和CSS3实现APPLE TV海报视差效果
2017/06/16 jQuery
详解vue引入子组件方法
2019/02/12 Javascript
解决ie11 SCRIPT5011:不能执行已释放Script的代码问题
2019/05/05 Javascript
微信小程序 image组件遇到的问题
2019/05/28 Javascript
vue使用showdown并实现代码区域高亮的示例代码
2019/10/17 Javascript
js实现列表向上无限滚动
2020/01/13 Javascript
vue学习笔记之slot插槽用法实例分析
2020/02/29 Javascript
ES5新增数组的实现方法
2020/05/12 Javascript
vue实现前端分页完整代码
2020/06/17 Javascript
Python+Django在windows下的开发环境配置图解
2009/11/11 Python
Python模块学习 filecmp 文件比较
2012/08/27 Python
将Django框架和遗留的Web应用集成的方法
2015/07/24 Python
Python编程产生非均匀随机数的几种方法代码分享
2017/12/13 Python
Python解析多帧dicom数据详解
2020/01/13 Python
Pycharm配置PyQt5环境的教程
2020/04/02 Python
Keras实现DenseNet结构操作
2020/07/06 Python
机械专业毕业生推荐信范文
2013/11/25 职场文书
搞笑婚礼主持词
2014/03/13 职场文书
平面设计师岗位职责
2014/09/18 职场文书
产品调价通知函
2015/04/20 职场文书
暗恋桃花源观后感
2015/06/12 职场文书
Python时间操作之pytz模块使用详解
2022/06/14 Python