-
Notifications
You must be signed in to change notification settings - Fork 9
/
Copy pathhound.js
103 lines (98 loc) · 2.68 KB
/
hound.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
var fs = require('fs')
, util = require('util')
, events = require('events')
, path = require('path')
/**
* Watch one or more files or directories for changes.
*
* Options:
* - watchFn: Specify a custom filesystem watch function (eg: `fs.watchFile`)
*
* @param {string|array} src The file or directory to watch.
* @param {array} options
* @return {Hound}
*/
exports.watch = function(src, options) {
var watcher = new Hound(options)
watcher.watch(src)
return watcher
}
/**
* The Hound class tracks watchers and changes and emits events.
*/
function Hound(options) {
events.EventEmitter.call(this)
this.options = options || {}
}
util.inherits(Hound, events.EventEmitter)
Hound.prototype.watchers = []
/**
* Watch a file or directory tree for changes, and fire events when they happen.
* Fires the following events:
* 'create' (file, stats)
* 'change' (file, stats)
* 'delete' (file)
* @param {string} src
* @return {Hound}
*/
Hound.prototype.watch = function(src) {
var self = this
var stats = fs.statSync(src)
var lastChange = null
var watchFn = self.options.watchFn || fs.watch
if (stats.isDirectory()) {
var files = fs.readdirSync(src)
for (var i = 0, len = files.length; i < len; i++) {
self.watch(src + path.sep + files[i])
}
}
self.watchers[src] = watchFn(src, function(event, filename) {
if (fs.existsSync(src)) {
stats = fs.statSync(src)
if (stats.isFile()) {
if (lastChange === null || stats.mtime.getTime() > lastChange)
self.emit('change', src, stats)
lastChange = stats.mtime.getTime()
} else if (stats.isDirectory()) {
// Check if the dir is new
if (self.watchers[src] === undefined) {
self.emit('create', src, stats)
}
// Check files to see if there are any new files
var dirFiles = fs.readdirSync(src)
for (var i = 0, len = dirFiles.length; i < len; i++) {
var file = src + path.sep + dirFiles[i]
if (self.watchers[file] === undefined) {
self.watch(file)
self.emit('create', file, fs.statSync(file))
}
}
}
} else {
self.unwatch(src)
self.emit('delete', src)
}
})
self.emit('watch', src)
}
/**
* Unwatch a file or directory tree.
* @param {string} src
*/
Hound.prototype.unwatch = function(src) {
var self = this
if (self.watchers[src] !== undefined) {
self.watchers[src].close()
delete self.watchers[src]
}
self.emit('unwatch', src)
}
/**
* Unwatch all currently watched files and directories in this watcher.
*/
Hound.prototype.clear = function() {
var self = this
for (var file in this.watchers) {
self.unwatch(file)
}
}