-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathindex.js
99 lines (90 loc) · 2.4 KB
/
index.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
var path = require('path'),
fs = require('fs'),
crypto = require('crypto');
function md5(data) {
var sum = crypto.createHash('md5');
sum.update(data);
return sum.digest('hex');
}
Context = function(retry){
this.retry = retry || 50;
};
Context.prototype.tempDirectory = function(filePath, cb){
return cb(null, path.dirname(filePath));
};
Context.prototype.tempFileName = function(filePath, cb){
var prefix = String(Date.now()) + filePath;
var hashedPrefix = md5(prefix);
var name = "." + hashedPrefix + "." + path.basename(filePath);
return cb(null, path.basename(name));
};
Context.prototype.tempFilePath = function(filePath, cb, i){
i = i || 0;
var manager = this;
manager.tempDirectory(filePath, function(err, dirPath){
if(err){
return cb(err);
}
manager.tempFileName(filePath, function(err, filePath){
if(err){
return cb(err);
}
var tempPath = path.join(dirPath, filePath);
fs.exists(tempPath,function(exists){
if(exists){
if (i == manager.retry){
return cb("retry limit " + manager.retry + " reached");
}
manager.tempFilePath(filepath, cb, i++);
}
return cb(null, tempPath);
});
});
});
};
Context.prototype.writeFile = function(filename, data, options, callback){
if(arguments.length < 4){
callback = options;
options = {};
}
var manager = this;
manager.tempFilePath(filename, function(err, tempPath){
if(err){
return callback(err);
}
fs.writeFile(tempPath, data, options, function(err){
if(err){
return callback(err);
}
return fs.rename(tempPath, filename, function(err){
return callback(err);
});
});
});
};
Context.prototype.createWriteStream = function (path, options){
if(arguments.length < 2){
options = {};
}
options.fd = 3; // prevent writestream.open
var stream = fs.createWriteStream(null, options);
stream.fd = null; // reset fd
this.tempFilePath(path, function(err, tempPath){
if(err){
return stream.emit('error', err);
}
stream.path = tempPath;
stream.open();
stream.on('close', function(){
fs.rename(tempPath, path, function(err){
if(err){
return stream.emit('error', err);
}
stream.emit('done');
});
});
});
return stream;
};
Context.prototype.Context = Context;
module.exports = new Context();