2
2
3
3
const zlib = require ( 'zlib' ) ;
4
4
5
+ const bufferUtil = require ( './BufferUtil' ) ;
6
+
5
7
const AVAILABLE_WINDOW_BITS = [ 8 , 9 , 10 , 11 , 12 , 13 , 14 , 15 ] ;
6
8
const DEFAULT_WINDOW_BITS = 15 ;
7
9
const DEFAULT_MEM_LEVEL = 8 ;
8
10
const TRAILER = Buffer . from ( [ 0x00 , 0x00 , 0xff , 0xff ] ) ;
9
11
const EMPTY_BLOCK = Buffer . from ( [ 0x00 ] ) ;
10
12
11
13
/**
12
- * Per-message Compression Extensions implementation
14
+ * Per-message Deflate implementation.
13
15
*/
14
16
class PerMessageDeflate {
15
17
constructor ( options , isServer , maxPayload ) {
@@ -22,12 +24,15 @@ class PerMessageDeflate {
22
24
this . threshold = this . _options . threshold === undefined ? 1024 : this . _options . threshold ;
23
25
}
24
26
27
+ static get extensionName ( ) {
28
+ return 'permessage-deflate' ;
29
+ }
30
+
25
31
/**
26
32
* Create extension parameters offer
27
33
*
28
- * @api public
34
+ * @public
29
35
*/
30
-
31
36
offer ( ) {
32
37
var params = { } ;
33
38
if ( this . _options . serverNoContextTakeover ) {
@@ -50,7 +55,7 @@ class PerMessageDeflate {
50
55
/**
51
56
* Accept extension offer
52
57
*
53
- * @api public
58
+ * @public
54
59
*/
55
60
accept ( paramsList ) {
56
61
paramsList = this . normalizeParams ( paramsList ) ;
@@ -69,7 +74,7 @@ class PerMessageDeflate {
69
74
/**
70
75
* Releases all resources used by the extension
71
76
*
72
- * @api public
77
+ * @public
73
78
*/
74
79
cleanup ( ) {
75
80
if ( this . _inflate ) {
@@ -93,9 +98,8 @@ class PerMessageDeflate {
93
98
/**
94
99
* Accept extension offer from client
95
100
*
96
- * @api private
101
+ * @private
97
102
*/
98
-
99
103
acceptAsServer ( paramsList ) {
100
104
var accepted = { } ;
101
105
var result = paramsList . some ( ( params ) => {
@@ -147,9 +151,8 @@ class PerMessageDeflate {
147
151
/**
148
152
* Accept extension response from server
149
153
*
150
- * @api privaye
154
+ * @private
151
155
*/
152
-
153
156
acceptAsClient ( paramsList ) {
154
157
var params = paramsList [ 0 ] ;
155
158
if ( this . _options . clientNoContextTakeover != null ) {
@@ -172,9 +175,8 @@ class PerMessageDeflate {
172
175
/**
173
176
* Normalize extensions parameters
174
177
*
175
- * @api private
178
+ * @private
176
179
*/
177
-
178
180
normalizeParams ( paramsList ) {
179
181
return paramsList . map ( ( params ) => {
180
182
Object . keys ( params ) . forEach ( ( key ) => {
@@ -276,26 +278,25 @@ class PerMessageDeflate {
276
278
this . _inflate . flush ( ( ) => {
277
279
cleanup ( ) ;
278
280
if ( err ) callback ( err ) ;
279
- else callback ( null , Buffer . concat ( buffers , totalLength ) ) ;
281
+ else callback ( null , bufferUtil . concat ( buffers , totalLength ) ) ;
280
282
} ) ;
281
283
}
282
284
283
285
/**
284
286
* Compress message
285
287
*
286
- * @api public
288
+ * @public
287
289
*/
288
-
289
290
compress ( data , fin , callback ) {
290
291
if ( ! data || data . length === 0 ) {
291
292
process . nextTick ( callback , null , EMPTY_BLOCK ) ;
292
293
return ;
293
294
}
294
295
295
- var endpoint = this . _isServer ? 'server' : 'client' ;
296
+ const endpoint = this . _isServer ? 'server' : 'client' ;
296
297
297
298
if ( ! this . _deflate ) {
298
- var maxWindowBits = this . params [ endpoint + ' _max_window_bits' ] ;
299
+ const maxWindowBits = this . params [ ` ${ endpoint } _max_window_bits` ] ;
299
300
this . _deflate = zlib . createDeflateRaw ( {
300
301
flush : zlib . Z_SYNC_FLUSH ,
301
302
windowBits : typeof maxWindowBits === 'number' ? maxWindowBits : DEFAULT_WINDOW_BITS ,
@@ -304,19 +305,30 @@ class PerMessageDeflate {
304
305
}
305
306
this . _deflate . writeInProgress = true ;
306
307
308
+ var totalLength = 0 ;
307
309
const buffers = [ ] ;
308
310
309
- const onData = ( data ) => buffers . push ( data ) ;
311
+ const onData = ( data ) => {
312
+ totalLength += data . length ;
313
+ buffers . push ( data ) ;
314
+ } ;
315
+
310
316
const onError = ( err ) => {
311
317
cleanup ( ) ;
312
318
callback ( err ) ;
313
319
} ;
320
+
314
321
const cleanup = ( ) => {
315
322
if ( ! this . _deflate ) return ;
323
+
316
324
this . _deflate . removeListener ( 'error' , onError ) ;
317
325
this . _deflate . removeListener ( 'data' , onData ) ;
318
326
this . _deflate . writeInProgress = false ;
319
- if ( ( fin && this . params [ endpoint + '_no_context_takeover' ] ) || this . _deflate . pendingClose ) {
327
+
328
+ if (
329
+ ( fin && this . params [ `${ endpoint } _no_context_takeover` ] ) ||
330
+ this . _deflate . pendingClose
331
+ ) {
320
332
this . _deflate . close ( ) ;
321
333
this . _deflate = null ;
322
334
}
@@ -326,15 +338,11 @@ class PerMessageDeflate {
326
338
this . _deflate . write ( data ) ;
327
339
this . _deflate . flush ( zlib . Z_SYNC_FLUSH , ( ) => {
328
340
cleanup ( ) ;
329
- var data = Buffer . concat ( buffers ) ;
330
- if ( fin ) {
331
- data = data . slice ( 0 , data . length - 4 ) ;
332
- }
341
+ var data = bufferUtil . concat ( buffers , totalLength ) ;
342
+ if ( fin ) data = data . slice ( 0 , data . length - 4 ) ;
333
343
callback ( null , data ) ;
334
344
} ) ;
335
345
}
336
346
}
337
347
338
- PerMessageDeflate . extensionName = 'permessage-deflate' ;
339
-
340
348
module . exports = PerMessageDeflate ;
0 commit comments