/
FixedBufferedStream.js
128 lines (108 loc) · 3.31 KB
/
FixedBufferedStream.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
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
// Generated by CoffeeScript 1.4.0
var BufferedStream, stream, util;
stream = require('stream');
util = require('util');
/*
`BufferedStream([size])`
========================
This class implement both the Readable and Writable Stream
API. Data written to it are stored inside a buffer. The buffer
is emited though a "data" event when it is about to
get larger than a defined "size".
The buffer is defined with a fixed size. As a consequence,
this implentation present the advantage of consuming a
constant amount of memory over time.
In the event that the data written is larger than the
defined size, the buffer mechanism is bypassed and the data
is directly emited with the "data" event.
Setting the "size" parameter to 0 will simply bypassed the bufferisation.
Performances
------------
The results presented below are obtained by running `coffee samples/speed.coffee`.
Writting 100000 lines of 100 bytes (about 9.5 Mo)
```
0 b : 2 s 123 ms
64 b : 2 s 17 ms
128 b : 1 s 579 ms
256 b : 1 s 184 ms
512 b : 773 ms
1 Kb : 517 ms
1 Mb : 273 ms
4 Mb : 278 ms
16 Mb : 264 ms
64 Mb : 261 ms
128 Mb : 269 ms
```
Writting 1000000 lines of 100 bytes (about 95 Mo)
```
0 b : 22 s 407 ms
64 b : 21 s 490 ms
128 b : 16 s 796 ms
256 b : 12 s 72 ms
512 b : 7 s 721 ms
1 Kb : 5 s 91 ms
1 Mb : 2 s 460 ms
4 Mb : 2 s 577 ms
16 Mb : 2 s 706 ms
64 Mb : 2 s 706 ms
128 Mb : 2 s 673 ms
```
In this test, we are reading from a custom generator
Readable Stream and writing to the file system. Since we
are writing 100 bytes lines, a buffer of 0 byte or 64 byte
lead to the same internal behavior while a buffer of 128 bytes
use the internal buffer but lead to similar performances. Increasing
the buffer size increase performance until the buffer reach 1 Mo. After
that, performance stale. Notice that in our tests, a file Readable Stream write data
as 1 Mo chunks as well.
*/
BufferedStream = function(size) {
if (size == null) {
size = 1024;
}
this.writable = true;
this.readable = true;
this.size = size;
this.buffer = new Buffer(size);
this.bufferPos = 0;
return stream.call(this);
};
BufferedStream.prototype.__proto__ = stream.prototype;
BufferedStream.prototype.write = function(data) {
var buffer, dataWritten;
if (!Buffer.isBuffer(data)) {
data = new Buffer(data);
}
if (data.length > this.size) {
this.emit('data', data);
return !this.paused;
}
dataWritten = Math.min(this.size - this.bufferPos, data.length);
if (dataWritten !== 0) {
data.copy(this.buffer, this.bufferPos, 0, dataWritten);
}
this.bufferPos += dataWritten;
if (dataWritten !== data.length) {
buffer = new Buffer(this.bufferPos);
this.buffer.copy(buffer, 0, 0, this.bufferPos);
this.emit('data', buffer);
data.copy(this.buffer, 0, dataWritten, data.length);
this.bufferPos = data.length - dataWritten;
return !this.paused;
}
return true;
};
BufferedStream.prototype.pause = function(data) {
return this.paused = true;
};
BufferedStream.prototype.resume = function(data) {
this.paused = false;
return this.emit('drain');
};
BufferedStream.prototype.end = function() {
this.emit('data', this.buffer.slice(0, this.bufferPos));
this.writable = false;
this.readable = false;
return this.emit('end');
};
module.exports = BufferedStream;