diff --git a/.airtap.yml b/.airtap.yml
new file mode 100644
index 0000000000..38e6f0349e
--- /dev/null
+++ b/.airtap.yml
@@ -0,0 +1,17 @@
+sauce_connect: true
+browsers:
+ - name: chrome
+ version: latest
+ platform: Windows 10
+ - name: internet explorer
+ version: latest
+ platform: Windows 10
+ - name: firefox
+ version: latest
+ platform: Windows 10
+ - name: safari
+ version: latest
+ platform: Mac 10.13
+ - name: microsoftedge
+ version: latest
+ platform: Windows 10
diff --git a/.gitignore b/.gitignore
index f768783ace..27e4893f19 100644
--- a/.gitignore
+++ b/.gitignore
@@ -4,3 +4,4 @@ node_modules/
coverage
package-lock.json
*.tap
+.airtaprc
diff --git a/.travis.yml b/.travis.yml
index 40992555bf..94374dc018 100644
--- a/.travis.yml
+++ b/.travis.yml
@@ -1,55 +1,22 @@
sudo: false
language: node_js
-before_install:
- - npm install -g npm@2
- - test $NPM_LEGACY && npm install -g npm@latest-3 || npm install npm -g
notifications:
email: false
matrix:
fast_finish: true
include:
- - node_js: '0.8'
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: '0.10'
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: '0.11'
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: '0.12'
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: 1
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: 2
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: 3
- env:
- - TASK=test
- - NPM_LEGACY=true
- - node_js: 4
- env: TASK=test
- - node_js: 5
- env: TASK=test
- node_js: 6
- env: TASK=test
- - node_js: 7
- env: TASK=test
+ env: CMD=test
- node_js: 8
- env: TASK=test
+ env: CMD=test
- node_js: 9
- env: TASK=test
-script: "npm run $TASK"
-env:
- global:
- - secure: rE2Vvo7vnjabYNULNyLFxOyt98BoJexDqsiOnfiD6kLYYsiQGfr/sbZkPMOFm9qfQG7pjqx+zZWZjGSswhTt+626C0t/njXqug7Yps4c3dFblzGfreQHp7wNX5TFsvrxd6dAowVasMp61sJcRnB2w8cUzoe3RAYUDHyiHktwqMc=
- - secure: g9YINaKAdMatsJ28G9jCGbSaguXCyxSTy+pBO6Ch0Cf57ZLOTka3HqDj8p3nV28LUIHZ3ut5WO43CeYKwt4AUtLpBS3a0dndHdY6D83uY6b2qh5hXlrcbeQTq2cvw2y95F7hm4D1kwrgZ7ViqaKggRcEupAL69YbJnxeUDKWEdI=
+ env: CMD=test
+ - node_js: 10
+ env: CMD=test
+ - node_js: stable
+ env: CMD=test-browsers
+ addons:
+ sauce_connect: true
+ hosts:
+ - airtap.local
+script: npm run $CMD
diff --git a/README.md b/README.md
index 174ff9d294..1c9c6afe12 100644
--- a/README.md
+++ b/README.md
@@ -1,30 +1,86 @@
# readable-stream
-***Node-core v8.11.1 streams for userland*** [![Build Status](https://travis-ci.org/nodejs/readable-stream.svg?branch=master)](https://travis-ci.org/nodejs/readable-stream)
+***Node.js core streams for userland*** [![Build Status](https://travis-ci.com/nodejs/readable-stream.svg?branch=master)](https://travis-ci.com/nodejs/readable-stream)
[![NPM](https://nodei.co/npm/readable-stream.png?downloads=true&downloadRank=true)](https://nodei.co/npm/readable-stream/)
[![NPM](https://nodei.co/npm-dl/readable-stream.png?&months=6&height=3)](https://nodei.co/npm/readable-stream/)
-[![Sauce Test Status](https://saucelabs.com/browser-matrix/readable-stream.svg)](https://saucelabs.com/u/readable-stream)
+[![Sauce Test Status](https://saucelabs.com/browser-matrix/readabe-stream.svg)](https://saucelabs.com/u/readabe-stream)
```bash
npm install --save readable-stream
```
-***Node-core streams for userland***
+This package is a mirror of the streams implementations in Node.js.
-This package is a mirror of the Streams2 and Streams3 implementations in
-Node-core.
-
-Full documentation may be found on the [Node.js website](https://nodejs.org/dist/v8.11.1/docs/api/stream.html).
+Full documentation may be found on the [Node.js website](https://nodejs.org/dist/v10.8.0/docs/api/stream.html).
If you want to guarantee a stable streams base, regardless of what version of
Node you, or the users of your libraries are using, use **readable-stream** *only* and avoid the *"stream"* module in Node-core, for background see [this blogpost](http://r.va.gg/2014/06/why-i-dont-use-nodes-core-stream-module.html).
As of version 2.0.0 **readable-stream** uses semantic versioning.
+## Version 3.x.x
+
+v3.x.x of `readable-stream` supports Node 6, 8, and 10, as well as
+evergreen browsers, IE 11 and latest Safari. The breaking changes
+introduced by v3 are composed by the combined breaking changes in [Node v9](https://nodejs.org/en/blog/release/v9.0.0/)
+and [Node v10](https://nodejs.org/en/blog/release/v10.0.0/), as follows:
+
+1. Error codes: https://github.com/nodejs/node/pull/13310,
+ https://github.com/nodejs/node/pull/13291,
+ https://github.com/nodejs/node/pull/16589,
+ https://github.com/nodejs/node/pull/15042,
+ https://github.com/nodejs/node/pull/15665,
+ https://github.com/nodejs/readable-stream/pull/344
+2. 'readable' have precedence over flowing
+ https://github.com/nodejs/node/pull/18994
+3. make virtual methods errors consistent
+ https://github.com/nodejs/node/pull/18813
+4. updated streams error handling
+ https://github.com/nodejs/node/pull/18438
+5. writable.end should return this.
+ https://github.com/nodejs/node/pull/18780
+6. readable continues to read when push('')
+ https://github.com/nodejs/node/pull/18211
+7. add custom inspect to BufferList
+ https://github.com/nodejs/node/pull/17907
+8. always defer 'readable' with nextTick
+ https://github.com/nodejs/node/pull/17979
+
+## Version 2.x.x
+
+v2.x.x of `readable-stream` supports all Node.js version from 0.8, as well as
+evergreen browsers and IE 10 & 11.
+
+### Big Thanks
+
+Cross-browser Testing Platform and Open Source <3 Provided by [Sauce Labs][sauce]
+
+# Usage
+
+You can swap your `require('stream')` with `require('readable-stream')`
+without any changes, if you are just using one of the main classes and
+functions.
+
+```js
+const {
+ Readable,
+ Writable,
+ Transform,
+ Duplex,
+ pipeline,
+ finished
+} = require('readable-stream')
+````
+
+Note that `require('stream')` will return `Stream`, while
+`require('readable-stream')` will return `Readable`. We discourage using
+whatever is exported directly, but rather use one of the properties as
+shown in the example above.
+
# Streams Working Group
`readable-stream` is maintained by the Streams Working Group, which
@@ -51,3 +107,5 @@ Node.js. The responsibilities of the Streams Working Group include:
- Release GPG key: 3ABC01543F22DD2239285CDD818674489FBC127E
* **Irina Shestak** ([@lrlna](https://github.com/lrlna)) <shestak.irina@gmail.com>
* **Yoshua Wyuts** ([@yoshuawuyts](https://github.com/yoshuawuyts)) <yoshuawuyts@gmail.com>
+
+[sauce]: https://saucelabs.com
diff --git a/build/build.js b/build/build.js
index 2580303c87..ee363ab3ee 100644
--- a/build/build.js
+++ b/build/build.js
@@ -36,7 +36,7 @@ if (!usageVersionRegex.test(nodeVersion)) {
}
// `inputLoc`: URL or local path.
-function processFile (inputLoc, out, replacements) {
+function processFile (inputLoc, out, replacements, addAtEnd) {
var file = fs.createReadStream(inputLoc, encoding)
file.pipe(bl(function (err, data) {
@@ -55,6 +55,10 @@ function processFile (inputLoc, out, replacements) {
}
data = data.replace(regexp, arg2)
})
+
+ if (addAtEnd) {
+ data += addAtEnd
+ }
if (inputLoc.slice(-3) === '.js') {
try {
const transformed = babel.transform(data, {
@@ -68,7 +72,11 @@ function processFile (inputLoc, out, replacements) {
['transform-es2015-classes', { loose: true }],
'transform-es2015-destructuring',
'transform-es2015-computed-properties',
- 'transform-es2015-spread'
+ 'transform-es2015-spread',
+ 'transform-optional-catch-binding',
+ 'transform-inline-imports-commonjs',
+ 'transform-async-to-generator',
+ 'transform-async-generator-functions'
]
})
data = transformed.code
@@ -113,7 +121,7 @@ function processTestFile (file) {
if (testReplace[file])
replacements = replacements.concat(testReplace[file])
- processFile(url, out, replacements)
+ processFile(url, out, replacements, ';require(\'tap\').pass(\'sync run\');var _list = process.listeners(\'uncaughtException\'); process.removeAllListeners(\'uncaughtException\'); _list.pop(); _list.forEach((e) => process.on(\'uncaughtException\', e));')
}
//--------------------------------------------------------------------
diff --git a/build/files.js b/build/files.js
index 9bf53a6ee4..8fbc8cf20d 100644
--- a/build/files.js
+++ b/build/files.js
@@ -41,8 +41,12 @@ const headRegexp = /(^module.exports = \w+;?)/m
, utilReplacement = [
/^const util = require\('util'\);/m
- , '\n/**/\nconst util = require(\'core-util-is\');\n'
- + 'util.inherits = require(\'inherits\');\n/**/\n'
+ , ''
+ ]
+
+ , inherits = [
+ /^util.inherits/m
+ , 'require(\'inherits\')'
]
, debugLogReplacement = [
@@ -72,16 +76,6 @@ const headRegexp = /(^module.exports = \w+;?)/m
+ '}catch(_){}}());\n'
]
- , isArrayDefine = [
- headRegexp
- , '$1\n\n/**/\nvar isArray = require(\'isarray\');\n/**/\n'
- ]
-
- , isArrayReplacement = [
- /Array\.isArray/g
- , 'isArray'
- ]
-
, objectKeysDefine = require('./common-replacements').objectKeysDefine
, objectKeysReplacement = require('./common-replacements').objectKeysReplacement
@@ -156,13 +150,6 @@ const headRegexp = /(^module.exports = \w+;?)/m
}
`
]
- , safeBufferFix = [
- /(?:var|const) (?:{ )Buffer(?: }) = require\('buffer'\)(?:\.Buffer)?;/,
- `/**/
- var Buffer = require('safe-buffer').Buffer;
-/**/
-`
- ]
, internalDirectory = [
/require\('internal\/streams\/([a-zA-z]+)'\)/g,
'require(\'./internal/streams/$1\')'
@@ -176,9 +163,9 @@ const headRegexp = /(^module.exports = \w+;?)/m
, `function(er) { onwrite(stream, er); }`
]
, addUintStuff = [
- /(?:var|const) Buffer = require\('safe-buffer'\)\.Buffer;/
+ /(?:var|const) (?:{ )Buffer(?: }) = require\('buffer'\)(?:\.Buffer)?;/g
, `
- const Buffer = require('safe-buffer').Buffer
+ const Buffer = require('buffer').Buffer
const OurUint8Array = global.Uint8Array || function () {}
function _uint8ArrayToBuffer(chunk) {
return Buffer.from(chunk);
@@ -230,23 +217,39 @@ function CorkedRequest(state) {
/Buffer\.prototype\.copy\.call\(src, target, offset\);/
, 'src.copy(target, offset);'
]
+ , errorsOneLevel = [
+ /internal\/errors/
+ , '../errors'
+ ]
+ , errorsTwoLevel = [
+ /internal\/errors/
+ , '../../../errors'
+ ]
+ , warnings = [
+ /^const { emitExperimentalWarning } = require\('internal\/util'\);/m,
+ 'const { emitExperimentalWarning } = require(\'../experimentalWarning\');'
+ ]
module.exports['_stream_duplex.js'] = [
requireReplacement
, instanceofReplacement
, utilReplacement
+ , inherits
, stringDecoderReplacement
, objectKeysReplacement
, objectKeysDefine
, processNextTickImport
, processNextTickReplacement
+ , errorsOneLevel
]
module.exports['_stream_passthrough.js'] = [
requireReplacement
, instanceofReplacement
, utilReplacement
+ , inherits
, stringDecoderReplacement
+ , errorsOneLevel
]
module.exports['_stream_readable.js'] = [
@@ -257,10 +260,9 @@ module.exports['_stream_readable.js'] = [
, altIndexOfImplReplacement
, altIndexOfUseReplacement
, stringDecoderReplacement
- , isArrayReplacement
- , isArrayDefine
, debugLogReplacement
, utilReplacement
+ , inherits
, stringDecoderReplacement
, eventEmittterReplacement
, requireStreamReplacement
@@ -269,16 +271,19 @@ module.exports['_stream_readable.js'] = [
, processNextTickReplacement
, eventEmittterListenerCountReplacement
, internalDirectory
- , safeBufferFix
, fixUintStuff
, addUintStuff
+ , errorsOneLevel
+ , warnings
]
module.exports['_stream_transform.js'] = [
requireReplacement
, instanceofReplacement
, utilReplacement
+ , inherits
, stringDecoderReplacement
+ , errorsOneLevel
]
module.exports['_stream_writable.js'] = [
@@ -287,6 +292,7 @@ module.exports['_stream_writable.js'] = [
, requireReplacement
, instanceofReplacement
, utilReplacement
+ , inherits
, stringDecoderReplacement
, debugLogReplacement
, deprecateReplacement
@@ -304,20 +310,20 @@ module.exports['_stream_writable.js'] = [
, fixInstanceCheck
, removeOnWriteBind
, internalDirectory
- , safeBufferFix
, fixUintStuff
, addUintStuff
, fixBufferCheck
, useWriteReq
, useCorkedRequest
, addConstructors
+ , errorsOneLevel
]
-module.exports['internal/streams/BufferList.js'] = [
+module.exports['internal/streams/buffer_list.js'] = [
[
/(?:var|const) (?:{ )Buffer(?: }) = require\('buffer'\)(?:\.Buffer)?;/,
`
-const Buffer = require('safe-buffer').Buffer
+const Buffer = require('buffer').Buffer
const util = require('util')
`
]
@@ -339,4 +345,33 @@ if (util && util.inspect && util.inspect.custom) {
module.exports['internal/streams/destroy.js'] = [
processNextTickImport
, processNextTickReplacement
+ , errorsTwoLevel
+]
+
+module.exports['internal/streams/state.js'] = [
+ processNextTickImport
+ , processNextTickReplacement
+ , errorsTwoLevel
+]
+
+module.exports['internal/streams/async_iterator.js'] = [
+ processNextTickImport
+ , processNextTickReplacement
+ , errorsTwoLevel
+]
+
+module.exports['internal/streams/end-of-stream.js'] = [
+ processNextTickImport
+ , processNextTickReplacement
+ , errorsTwoLevel
+]
+
+module.exports['internal/streams/pipeline.js'] = [
+ processNextTickImport
+ , processNextTickReplacement
+ , errorsTwoLevel
+ , [
+ /require\('internal\/streams\/end-of-stream'\)/,
+ 'require(\'.\/end-of-stream\')'
+ ]
]
diff --git a/build/package.json b/build/package.json
deleted file mode 100644
index cf2a76902f..0000000000
--- a/build/package.json
+++ /dev/null
@@ -1,26 +0,0 @@
-{
- "name": "readable-stream-build",
- "version": "0.0.0",
- "description": "",
- "main": "build.js",
- "dependencies": {
- "babel-core": "^6.26.0",
- "babel-plugin-transform-es2015-arrow-functions": "^6.5.2",
- "babel-plugin-transform-es2015-block-scoping": "^6.26.0",
- "babel-plugin-transform-es2015-classes": "^6.24.1",
- "babel-plugin-transform-es2015-computed-properties": "^6.24.1",
- "babel-plugin-transform-es2015-destructuring": "^6.18.0",
- "babel-plugin-transform-es2015-for-of": "^6.8.0",
- "babel-plugin-transform-es2015-parameters": "^6.24.1",
- "babel-plugin-transform-es2015-shorthand-properties": "^6.24.1",
- "babel-plugin-transform-es2015-spread": "^6.22.0",
- "babel-plugin-transform-es2015-template-literals": "^6.8.0",
- "bl": "^1.2.1",
- "glob": "^7.1.2",
- "gunzip-maybe": "^1.4.1",
- "hyperquest": "^2.1.3",
- "pump": "^3.0.0",
- "rimraf": "^2.6.2",
- "tar-fs": "^1.16.0"
- }
-}
diff --git a/build/test-replacements.js b/build/test-replacements.js
index 61ee998586..265318438e 100644
--- a/build/test-replacements.js
+++ b/build/test-replacements.js
@@ -12,6 +12,23 @@ const altForEachImplReplacement = require('./common-replacements').altForEachImp
require('./common-replacements').bufferStaticMethods
, specialForEachReplacment =
require('./common-replacements').specialForEachReplacment
+ , deepStrictEqual = [
+ /util\.isDeepStrictEqual/,
+ 'require(\'deep-strict-equal\')'
+ ]
+ , tapOk = [
+ /console\.log\('ok'\);/g,
+ 'require(\'tap\').pass();'
+ ]
+ , catchES7 = [
+ /} catch {/,
+ '} catch(_e) {'
+ ]
+ , catchES7OpenClose = [
+ /} catch {}/,
+ '} catch(_e) {}'
+ ]
+
module.exports.all = [
[
@@ -73,32 +90,21 @@ module.exports['test-stream-big-packet.js'] = [
, altIndexOfUseReplacement
]
+module.exports['test-stream-end-paused.js'] = [
+ [
+ /console.log\('ok'\);/,
+ ''
+ ]
+]
+
module.exports['common.js'] = [
objectKeysDefine
, objectKeysReplacement
, altForEachImplReplacement
, altForEachUseReplacement
-
- , [
- /(exports.mustCall[\s\S]*)/m
- , '$1\n'
- + 'if (!util._errnoException) {\n'
- + ' var uv;\n'
- + ' util._errnoException = function(err, syscall) {\n'
- + ' if (util.isUndefined(uv)) try { uv = process.binding(\'uv\'); } catch (e) {}\n'
- + ' var errname = uv ? uv.errname(err) : \'\';\n'
- + ' var e = new Error(syscall + \' \' + errname);\n'
- + ' e.code = errname;\n'
- + ' e.errno = errname;\n'
- + ' e.syscall = syscall;\n'
- + ' return e;\n'
- + ' };\n'
- + '}\n'
- ]
-
- // for streams2 on node 0.11
- // and dtrace in 0.10
- // and coverage in all
+ , deepStrictEqual
+ , catchES7
+ , catchES7OpenClose
, [
/^( for \(var x in global\) \{|function leakedGlobals\(\) \{)$/m
, ' /**/\n'
@@ -110,27 +116,27 @@ module.exports['common.js'] = [
+ ' knownGlobals.push(DTRACE_NET_SOCKET_WRITE);\n'
+ ' if (global.__coverage__)\n'
+ ' knownGlobals.push(__coverage__);\n'
- + '\'core,__core-js_shared__,Promise,Map,Set,WeakMap,WeakSet,Reflect,System,asap,Observable,regeneratorRuntime,_babelPolyfill\'.split(\',\').filter(function (item) { return typeof global[item] !== undefined}).forEach(function (item) {knownGlobals.push(global[item])})'
+ + '\'console,clearImmediate,setImmediate,core,__core-js_shared__,Promise,Map,Set,WeakMap,WeakSet,Reflect,System,asap,Observable,regeneratorRuntime,_babelPolyfill\'.split(\',\').filter(function (item) { return typeof global[item] !== undefined}).forEach(function (item) {knownGlobals.push(global[item])})'
+ ' /**/\n\n$1'
]
- // for node 0.8
, [
- /^/
- , '/**/'
- + '\nif (!global.setImmediate) {\n'
- + ' global.setImmediate = function setImmediate(fn) {\n'
-
- + ' return setTimeout(fn.bind.apply(fn, arguments), 4);\n'
- + ' };\n'
- + '}\n'
- + 'if (!global.clearImmediate) {\n'
- + ' global.clearImmediate = function clearImmediate(i) {\n'
- + ' return clearTimeout(i);\n'
+ /(exports.mustCall[\s\S]*)/m
+ , '$1\n'
+ + 'if (!util._errnoException) {\n'
+ + ' var uv;\n'
+ + ' util._errnoException = function(err, syscall) {\n'
+ + ' if (util.isUndefined(uv)) try { uv = process.binding(\'uv\'); } catch (e) {}\n'
+ + ' var errname = uv ? uv.errname(err) : \'\';\n'
+ + ' var e = new Error(syscall + \' \' + errname);\n'
+ + ' e.code = errname;\n'
+ + ' e.errno = errname;\n'
+ + ' e.syscall = syscall;\n'
+ + ' return e;\n'
+ ' };\n'
+ '}\n'
- + '/**/\n'
]
+
, [
/^if \(global\.ArrayBuffer\) \{([^\}]+)\}$/m
, '/**/if (!process.browser) {'
@@ -193,6 +199,10 @@ module.exports['common.js'] = [
/\}\).enable\(\);/,
'}).enable();*/'
],
+[
+ /const async_hooks = require\('async_hooks'\)/,
+ 'var async_hooks = require(\'async_\' + \'hooks\')'
+],
[
/(?:var|const) async_wrap = process\.binding\('async_wrap'\);\n.*(?:var|const) (?:{ )?kCheck(?: })? = async_wrap\.constants(?:\.kCheck)?;/gm,
'// const async_wrap = process.binding(\'async_wrap\');\n' +
@@ -301,17 +311,56 @@ module.exports['test-stream3-cork-uncork.js'] = module.exports['test-stream3-cor
]
module.exports['test-stream2-readable-from-list.js'] = [
[
- /require\('internal\/streams\/BufferList'\)/,
- 'require(\'../../lib/internal/streams/BufferList\')'
+ /require\('internal\/streams\/buffer_list'\)/,
+ 'require(\'../../lib/internal/streams/buffer_list\')'
]
]
module.exports['test-stream-writev.js'] = [
+ tapOk,
[
- /'latin1'/g,
- `'binary'`
+ /console.log\(`# decode=/,
+ 'require(\'tap\').test(`# decode='
]
]
+
+module.exports['test-stream3-pause-then-read.js'] = [
+ tapOk
+]
+
+module.exports['test-stream-unshift-read-race.js'] = [
+ tapOk
+]
+
+module.exports['test-stream2-unpipe-leak.js'] = [
+ tapOk
+]
+
+module.exports['test-stream2-compatibility.js'] = [
+ tapOk
+]
+
+module.exports['test-stream-push-strings.js'] = [
+ tapOk
+]
+
+module.exports['test-stream-unshift-empty-chunk.js'] = [
+ tapOk
+]
+
+module.exports['test-stream2-pipe-error-once-listener.js'] = [
+ tapOk
+]
+
+module.exports['test-stream-push-order.js'] = [
+ tapOk
+]
+
+module.exports['test-stream2-push.js'] = [
+ tapOk
+]
+
module.exports['test-stream2-readable-empty-buffer-no-eof.js'] = [
+ tapOk,
[
/case 3:\n(\s+)setImmediate\(r\.read\.bind\(r, 0\)\);/,
'case 3:\n$1setTimeout(r.read.bind(r, 0), 50);'
@@ -319,8 +368,8 @@ module.exports['test-stream2-readable-empty-buffer-no-eof.js'] = [
]
module.exports['test-stream-buffer-list.js'] = [
[
- /require\('internal\/streams\/BufferList'\);/,
- 'require(\'../../lib/internal/streams/BufferList\');'
+ /require\('internal\/streams\/buffer_list'\);/,
+ 'require(\'../../lib/internal/streams/buffer_list\');'
]
]
@@ -337,3 +386,53 @@ module.exports['test-stream-unpipe-event.js'] = [
'if (process.version.indexOf(\'v0.8\') === 0) { process.exit(0) }\n'
]
]
+
+module.exports['test-stream-readable-flow-recursion.js'] = [
+ tapOk,
+ deepStrictEqual
+]
+
+module.exports['test-stream-readable-with-unimplemented-_read.js'] = [
+ deepStrictEqual
+]
+
+module.exports['test-stream-writable-needdrain-state.js'] = [
+ deepStrictEqual
+]
+
+module.exports['test-stream-readable-setEncoding-null.js'] = [
+ deepStrictEqual
+]
+
+module.exports['test-stream-pipeline.js'] = [
+ [
+ /require\('http2'\)/g,
+ '{ createServer() { return { listen() {} } } }'
+ ],
+ [
+ /assert\.deepStrictEqual\(err, new Error\('kaboom'\)\);/g,
+ 'assert.strictEqual(err.message, \'kaboom\');'
+ ],
+ [
+ /cb\(new Error\('kaboom'\)\)/g,
+ 'process.nextTick(cb, new Error(\'kaboom\'))'
+ ],
+ [
+ /const \{ promisify \} = require\('util'\);/g,
+ 'const promisify = require(\'util-promisify\');'
+ ]
+]
+
+module.exports['test-stream-finished.js'] = [
+ [
+ /const \{ promisify \} = require\('util'\);/g,
+ 'const promisify = require(\'util-promisify\');'
+ ]
+]
+
+module.exports['test-stream-readable-async-iterators.js'] = [
+ [
+ /assert.rejects\(/g,
+ '(function(f, e) { let success = false; f().then(function() { success = true; throw new Error(\'should not succeeed\') }).catch(function(e2) { if (success) { throw e2; } assert.strictEqual(e.message, e2.message); })})('
+ ]
+]
diff --git a/duplex-browser.js b/duplex-browser.js
deleted file mode 100644
index f8b2db83db..0000000000
--- a/duplex-browser.js
+++ /dev/null
@@ -1 +0,0 @@
-module.exports = require('./lib/_stream_duplex.js');
diff --git a/duplex.js b/duplex.js
deleted file mode 100644
index 46924cbfdf..0000000000
--- a/duplex.js
+++ /dev/null
@@ -1 +0,0 @@
-module.exports = require('./readable').Duplex
diff --git a/errors-browser.js b/errors-browser.js
new file mode 100644
index 0000000000..26c5d2635e
--- /dev/null
+++ b/errors-browser.js
@@ -0,0 +1,61 @@
+'use strict';
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
+
+function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
+
+var codes = {};
+
+function createErrorType(code, message, Base) {
+ if (!Base) {
+ Base = Error;
+ }
+
+ function getMessage(arg1, arg2) {
+ if (typeof message === 'string') {
+ return message;
+ } else {
+ return message(arg1, arg2);
+ }
+ }
+
+ var NodeError = function (_Base) {
+ _inherits(NodeError, _Base);
+
+ function NodeError(arg1, arg2) {
+ _classCallCheck(this, NodeError);
+
+ return _possibleConstructorReturn(this, (NodeError.__proto__ || Object.getPrototypeOf(NodeError)).call(this, getMessage(arg1, arg2)));
+ }
+
+ return NodeError;
+ }(Base);
+
+ NodeError.prototype.name = Base.name;
+ NodeError.prototype.code = code;
+
+ codes[code] = NodeError;
+}
+
+createErrorType('ERR_INVALID_OPT_VALUE', function (name, value) {
+ return 'The value "' + value + '" is invalid for option "' + name + '"';
+}, TypeError);
+createErrorType('ERR_INVALID_ARG_TYPE', 'argument must be of the right type', TypeError);
+createErrorType('ERR_STREAM_PUSH_AFTER_EOF', 'stream.push() after EOF');
+createErrorType('ERR_METHOD_NOT_IMPLEMENTED', function (name) {
+ return 'The ' + name + ' method is not implemented';
+});
+createErrorType('ERR_STREAM_PREMATURE_CLOSE', 'premature close');
+createErrorType('ERR_STREAM_DESTROYED', 'the stream was destroyed');
+createErrorType('ERR_MULTIPLE_CALLBACK', 'Callback called multiple times');
+createErrorType('ERR_STREAM_CANNOT_PIPE', 'Cannot pipe, not readable');
+createErrorType('ERR_STREAM_WRITE_AFTER_END', 'write after end');
+createErrorType('ERR_STREAM_NULL_VALUES', 'May not write null values to stream', TypeError);
+createErrorType('ERR_UNKNOWN_ENCODING', function (arg) {
+ return 'Unknown encoding: ' + arg;
+}, TypeError);
+createErrorType('ERR_STREAM_UNSHIFT_AFTER_END_EVENT', 'stream.unshift() after end event');
+
+module.exports.codes = codes;
diff --git a/errors.js b/errors.js
new file mode 100644
index 0000000000..428398360b
--- /dev/null
+++ b/errors.js
@@ -0,0 +1,49 @@
+'use strict';
+
+const codes = {};
+
+function createErrorType(code, message, Base) {
+ if (!Base) {
+ Base = Error
+ }
+
+ function getMessage (arg1, arg2) {
+ if (typeof message === 'string') {
+ return message
+ } else {
+ return message(arg1, arg2)
+ }
+ }
+
+ class NodeError extends Base {
+ constructor (arg1, arg2) {
+ super(getMessage(arg1, arg2));
+ }
+ }
+
+ NodeError.prototype.name = Base.name;
+ NodeError.prototype.code = code;
+
+ codes[code] = NodeError;
+}
+
+createErrorType('ERR_INVALID_OPT_VALUE', function (name, value) {
+ return 'The value "' + value + '" is invalid for option "' + name + '"'
+}, TypeError);
+createErrorType('ERR_INVALID_ARG_TYPE', 'argument must be of the right type', TypeError);
+createErrorType('ERR_STREAM_PUSH_AFTER_EOF', 'stream.push() after EOF');
+createErrorType('ERR_METHOD_NOT_IMPLEMENTED', function (name) {
+ return 'The ' + name + ' method is not implemented'
+});
+createErrorType('ERR_STREAM_PREMATURE_CLOSE', 'premature close');
+createErrorType('ERR_STREAM_DESTROYED', 'the stream was destroyed');
+createErrorType('ERR_MULTIPLE_CALLBACK', 'Callback called multiple times');
+createErrorType('ERR_STREAM_CANNOT_PIPE', 'Cannot pipe, not readable');
+createErrorType('ERR_STREAM_WRITE_AFTER_END', 'write after end');
+createErrorType('ERR_STREAM_NULL_VALUES', 'May not write null values to stream', TypeError);
+createErrorType('ERR_UNKNOWN_ENCODING', function (arg) {
+ return 'Unknown encoding: ' + arg
+}, TypeError);
+createErrorType('ERR_STREAM_UNSHIFT_AFTER_END_EVENT', 'stream.unshift() after end event');
+
+module.exports.codes = codes;
diff --git a/experimentalWarning.js b/experimentalWarning.js
new file mode 100644
index 0000000000..27003face2
--- /dev/null
+++ b/experimentalWarning.js
@@ -0,0 +1,13 @@
+'use strict'
+
+var experimentalWarnings = new Set();
+
+function emitExperimentalWarning(feature) {
+ if (experimentalWarnings.has(feature)) return;
+ var msg = feature + ' is an experimental feature. This feature could ' +
+ 'change at any time';
+ experimentalWarnings.add(feature);
+ process.emitWarning(msg, 'ExperimentalWarning');
+}
+
+module.exports.emitExperimentalWarning = emitExperimentalWarning;
diff --git a/lib/_stream_duplex.js b/lib/_stream_duplex.js
index a1ca813e5a..e8839b1419 100644
--- a/lib/_stream_duplex.js
+++ b/lib/_stream_duplex.js
@@ -42,18 +42,13 @@ var objectKeys = Object.keys || function (obj) {
module.exports = Duplex;
-/**/
-var util = require('core-util-is');
-util.inherits = require('inherits');
-/**/
-
var Readable = require('./_stream_readable');
var Writable = require('./_stream_writable');
-util.inherits(Duplex, Readable);
+require('inherits')(Duplex, Readable);
{
- // avoid scope creep, the keys array can then be collected
+ // Allow the keys array to be GC'ed.
var keys = objectKeys(Writable.prototype);
for (var v = 0; v < keys.length; v++) {
var method = keys[v];
@@ -66,15 +61,18 @@ function Duplex(options) {
Readable.call(this, options);
Writable.call(this, options);
+ this.allowHalfOpen = true;
- if (options && options.readable === false) this.readable = false;
-
- if (options && options.writable === false) this.writable = false;
+ if (options) {
+ if (options.readable === false) this.readable = false;
- this.allowHalfOpen = true;
- if (options && options.allowHalfOpen === false) this.allowHalfOpen = false;
+ if (options.writable === false) this.writable = false;
- this.once('end', onend);
+ if (options.allowHalfOpen === false) {
+ this.allowHalfOpen = false;
+ this.once('end', onend);
+ }
+ }
}
Object.defineProperty(Duplex.prototype, 'writableHighWaterMark', {
@@ -87,11 +85,30 @@ Object.defineProperty(Duplex.prototype, 'writableHighWaterMark', {
}
});
+Object.defineProperty(Duplex.prototype, 'writableBuffer', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._writableState && this._writableState.getBuffer();
+ }
+});
+
+Object.defineProperty(Duplex.prototype, 'writableLength', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._writableState.length;
+ }
+});
+
// the no-half-open enforcer
function onend() {
- // if we allow half-open state, or if the writable side ended,
- // then we're ok.
- if (this.allowHalfOpen || this._writableState.ended) return;
+ // If the writable side ended, then we're ok.
+ if (this._writableState.ended) return;
// no more data can be written.
// But allow more writes to happen in this tick.
@@ -103,6 +120,10 @@ function onEndNT(self) {
}
Object.defineProperty(Duplex.prototype, 'destroyed', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
get: function () {
if (this._readableState === undefined || this._writableState === undefined) {
return false;
@@ -121,11 +142,4 @@ Object.defineProperty(Duplex.prototype, 'destroyed', {
this._readableState.destroyed = value;
this._writableState.destroyed = value;
}
-});
-
-Duplex.prototype._destroy = function (err, cb) {
- this.push(null);
- this.end();
-
- pna.nextTick(cb, err);
-};
\ No newline at end of file
+});
\ No newline at end of file
diff --git a/lib/_stream_passthrough.js b/lib/_stream_passthrough.js
index a9c8358848..a3ab801b5b 100644
--- a/lib/_stream_passthrough.js
+++ b/lib/_stream_passthrough.js
@@ -29,12 +29,7 @@ module.exports = PassThrough;
var Transform = require('./_stream_transform');
-/**/
-var util = require('core-util-is');
-util.inherits = require('inherits');
-/**/
-
-util.inherits(PassThrough, Transform);
+require('inherits')(PassThrough, Transform);
function PassThrough(options) {
if (!(this instanceof PassThrough)) return new PassThrough(options);
diff --git a/lib/_stream_readable.js b/lib/_stream_readable.js
index bf34ac65e1..fec906e7d5 100644
--- a/lib/_stream_readable.js
+++ b/lib/_stream_readable.js
@@ -28,10 +28,6 @@ var pna = require('process-nextick-args');
module.exports = Readable;
-/**/
-var isArray = require('isarray');
-/**/
-
/**/
var Duplex;
/**/
@@ -50,9 +46,7 @@ var EElistenerCount = function (emitter, type) {
var Stream = require('./internal/streams/stream');
/**/
-/**/
-
-var Buffer = require('safe-buffer').Buffer;
+var Buffer = require('buffer').Buffer;
var OurUint8Array = global.Uint8Array || function () {};
function _uint8ArrayToBuffer(chunk) {
return Buffer.from(chunk);
@@ -61,13 +55,6 @@ function _isUint8Array(obj) {
return Buffer.isBuffer(obj) || obj instanceof OurUint8Array;
}
-/**/
-
-/**/
-var util = require('core-util-is');
-util.inherits = require('inherits');
-/**/
-
/**/
var debugUtil = require('util');
var debug = void 0;
@@ -78,11 +65,28 @@ if (debugUtil && debugUtil.debuglog) {
}
/**/
-var BufferList = require('./internal/streams/BufferList');
+var BufferList = require('./internal/streams/buffer_list');
var destroyImpl = require('./internal/streams/destroy');
-var StringDecoder;
-util.inherits(Readable, Stream);
+var _require = require('./internal/streams/state'),
+ getHighWaterMark = _require.getHighWaterMark;
+
+var _require$codes = require('../errors').codes,
+ ERR_INVALID_ARG_TYPE = _require$codes.ERR_INVALID_ARG_TYPE,
+ ERR_STREAM_PUSH_AFTER_EOF = _require$codes.ERR_STREAM_PUSH_AFTER_EOF,
+ ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED,
+ ERR_STREAM_UNSHIFT_AFTER_END_EVENT = _require$codes.ERR_STREAM_UNSHIFT_AFTER_END_EVENT;
+
+var _require2 = require('../experimentalWarning'),
+ emitExperimentalWarning = _require2.emitExperimentalWarning;
+
+// Lazy loaded to improve the startup performance.
+
+
+var StringDecoder = void 0;
+var ReadableAsyncIterator = void 0;
+
+require('inherits')(Readable, Stream);
var kProxyEvents = ['error', 'close', 'destroy', 'pause', 'resume'];
@@ -95,10 +99,10 @@ function prependListener(emitter, event, fn) {
// userland ones. NEVER DO THIS. This is here only because this code needs
// to continue to work with older versions of Node.js that do not include
// the prependListener() method. The goal is to eventually remove this hack.
- if (!emitter._events || !emitter._events[event]) emitter.on(event, fn);else if (isArray(emitter._events[event])) emitter._events[event].unshift(fn);else emitter._events[event] = [fn, emitter._events[event]];
+ if (!emitter._events || !emitter._events[event]) emitter.on(event, fn);else if (Array.isArray(emitter._events[event])) emitter._events[event].unshift(fn);else emitter._events[event] = [fn, emitter._events[event]];
}
-function ReadableState(options, stream) {
+function ReadableState(options, stream, isDuplex) {
Duplex = Duplex || require('./_stream_duplex');
options = options || {};
@@ -108,7 +112,7 @@ function ReadableState(options, stream) {
// However, some cases require setting options to different
// values for the readable and the writable sides of the duplex stream.
// These options can be provided separately as readableXXX and writableXXX.
- var isDuplex = stream instanceof Duplex;
+ if (typeof isDuplex !== 'boolean') isDuplex = stream instanceof Duplex;
// object stream flag. Used to make read(n) ignore n and to
// make all the buffer merging and length checks go away
@@ -118,14 +122,7 @@ function ReadableState(options, stream) {
// the point at which it stops calling _read() to fill the buffer
// Note: 0 is a valid value, means "don't call _read preemptively ever"
- var hwm = options.highWaterMark;
- var readableHwm = options.readableHighWaterMark;
- var defaultHwm = this.objectMode ? 16 : 16 * 1024;
-
- if (hwm || hwm === 0) this.highWaterMark = hwm;else if (isDuplex && (readableHwm || readableHwm === 0)) this.highWaterMark = readableHwm;else this.highWaterMark = defaultHwm;
-
- // cast to ints.
- this.highWaterMark = Math.floor(this.highWaterMark);
+ this.highWaterMark = getHighWaterMark(this, options, 'readableHighWaterMark', isDuplex);
// A linked list is used to store data chunks instead of an array because the
// linked list can remove elements from the beginning faster than
@@ -152,6 +149,9 @@ function ReadableState(options, stream) {
this.readableListening = false;
this.resumeScheduled = false;
+ // Should close be emitted on destroy. Defaults to true.
+ this.emitClose = options.emitClose !== false;
+
// has it been destroyed
this.destroyed = false;
@@ -180,7 +180,11 @@ function Readable(options) {
if (!(this instanceof Readable)) return new Readable(options);
- this._readableState = new ReadableState(options, this);
+ // Checking for a Stream.Duplex instance is faster here instead of inside
+ // the ReadableState constructor, at least with V8 6.5
+ var isDuplex = this instanceof Duplex;
+
+ this._readableState = new ReadableState(options, this, isDuplex);
// legacy
this.readable = true;
@@ -195,6 +199,10 @@ function Readable(options) {
}
Object.defineProperty(Readable.prototype, 'destroyed', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
get: function () {
if (this._readableState === undefined) {
return false;
@@ -217,7 +225,6 @@ Object.defineProperty(Readable.prototype, 'destroyed', {
Readable.prototype.destroy = destroyImpl.destroy;
Readable.prototype._undestroy = destroyImpl.undestroy;
Readable.prototype._destroy = function (err, cb) {
- this.push(null);
cb(err);
};
@@ -251,6 +258,7 @@ Readable.prototype.unshift = function (chunk) {
};
function readableAddChunk(stream, chunk, encoding, addToFront, skipChunkCheck) {
+ debug('readableAddChunk', chunk);
var state = stream._readableState;
if (chunk === null) {
state.reading = false;
@@ -266,9 +274,11 @@ function readableAddChunk(stream, chunk, encoding, addToFront, skipChunkCheck) {
}
if (addToFront) {
- if (state.endEmitted) stream.emit('error', new Error('stream.unshift() after end event'));else addChunk(stream, state, chunk, true);
+ if (state.endEmitted) stream.emit('error', new ERR_STREAM_UNSHIFT_AFTER_END_EVENT());else addChunk(stream, state, chunk, true);
} else if (state.ended) {
- stream.emit('error', new Error('stream.push() after EOF'));
+ stream.emit('error', new ERR_STREAM_PUSH_AFTER_EOF());
+ } else if (state.destroyed) {
+ return false;
} else {
state.reading = false;
if (state.decoder && !encoding) {
@@ -280,16 +290,20 @@ function readableAddChunk(stream, chunk, encoding, addToFront, skipChunkCheck) {
}
} else if (!addToFront) {
state.reading = false;
+ maybeReadMore(stream, state);
}
}
- return needMoreData(state);
+ // We can push more data if we are below the highWaterMark.
+ // Also, if we have no data yet, we can stand some more bytes.
+ // This is to work around cases where hwm=0, such as the repl.
+ return !state.ended && (state.length < state.highWaterMark || state.length === 0);
}
function addChunk(stream, state, chunk, addToFront) {
if (state.flowing && state.length === 0 && !state.sync) {
+ state.awaitDrain = 0;
stream.emit('data', chunk);
- stream.read(0);
} else {
// update the buffer info.
state.length += state.objectMode ? 1 : chunk.length;
@@ -303,22 +317,11 @@ function addChunk(stream, state, chunk, addToFront) {
function chunkInvalid(state, chunk) {
var er;
if (!_isUint8Array(chunk) && typeof chunk !== 'string' && chunk !== undefined && !state.objectMode) {
- er = new TypeError('Invalid non-string/buffer chunk');
+ er = new ERR_INVALID_ARG_TYPE('chunk', ['string', 'Buffer', 'Uint8Array'], chunk);
}
return er;
}
-// if it's past the high water mark, we can push in some more.
-// Also, if we have no data yet, we can stand some
-// more bytes. This is to work around cases where hwm=0,
-// such as the repl. Also, if the push() triggered a
-// readable event, and the user called read(largeNumber) such that
-// needReadable was set, then we ought to push more, so that another
-// 'readable' event will be triggered.
-function needMoreData(state) {
- return !state.ended && (state.needReadable || state.length < state.highWaterMark || state.length === 0);
-}
-
Readable.prototype.isPaused = function () {
return this._readableState.flowing === false;
};
@@ -327,7 +330,8 @@ Readable.prototype.isPaused = function () {
Readable.prototype.setEncoding = function (enc) {
if (!StringDecoder) StringDecoder = require('string_decoder/').StringDecoder;
this._readableState.decoder = new StringDecoder(enc);
- this._readableState.encoding = enc;
+ // if setEncoding(null), decoder.encoding equals utf8
+ this._readableState.encoding = this._readableState.decoder.encoding;
return this;
};
@@ -355,7 +359,7 @@ function computeNewHighWaterMark(n) {
function howMuchToRead(n, state) {
if (n <= 0 || state.length === 0 && state.ended) return 0;
if (state.objectMode) return 1;
- if (n !== n) {
+ if (Number.isNaN(n)) {
// Only flow one buffer at a time
if (state.flowing && state.length) return state.buffer.head.data.length;else return state.length;
}
@@ -455,6 +459,7 @@ Readable.prototype.read = function (n) {
n = 0;
} else {
state.length -= n;
+ state.awaitDrain = 0;
}
if (state.length === 0) {
@@ -482,8 +487,19 @@ function onEofChunk(stream, state) {
}
state.ended = true;
- // emit 'readable' now to make sure it gets picked up.
- emitReadable(stream);
+ if (state.sync) {
+ // if we are sync, wait until next tick to emit the data.
+ // Otherwise we risk emitting data in the flow()
+ // the readable code triggers during a read() call
+ emitReadable(stream);
+ } else {
+ // emit 'readable' now to make sure it gets picked up.
+ state.needReadable = false;
+ if (!state.emittedReadable) {
+ state.emittedReadable = true;
+ emitReadable_(stream);
+ }
+ }
}
// Don't emit readable right away in sync mode, because this can trigger
@@ -495,13 +511,24 @@ function emitReadable(stream) {
if (!state.emittedReadable) {
debug('emitReadable', state.flowing);
state.emittedReadable = true;
- if (state.sync) pna.nextTick(emitReadable_, stream);else emitReadable_(stream);
+ pna.nextTick(emitReadable_, stream);
}
}
function emitReadable_(stream) {
+ var state = stream._readableState;
debug('emit readable');
- stream.emit('readable');
+ if (!state.destroyed && (state.length || state.ended)) {
+ stream.emit('readable');
+ }
+
+ // The stream needs another readable event if
+ // 1. It is not flowing, as the flow mechanism will take
+ // care of it.
+ // 2. It is not ended.
+ // 3. It is below the highWaterMark, so we can schedule
+ // another readable later.
+ state.needReadable = !state.flowing && !state.ended && state.length <= state.highWaterMark;
flow(stream);
}
@@ -520,7 +547,7 @@ function maybeReadMore(stream, state) {
function maybeReadMore_(stream, state) {
var len = state.length;
- while (!state.reading && !state.flowing && !state.ended && state.length < state.highWaterMark) {
+ while (!state.reading && !state.ended && state.length < state.highWaterMark) {
debug('maybeReadMore read 0');
stream.read(0);
if (len === state.length)
@@ -535,7 +562,7 @@ function maybeReadMore_(stream, state) {
// for virtual (non-string, non-buffer) streams, "length" is somewhat
// arbitrary, and perhaps not very meaningful.
Readable.prototype._read = function (n) {
- this.emit('error', new Error('_read() is not implemented'));
+ this.emit('error', new ERR_METHOD_NOT_IMPLEMENTED('_read()'));
};
Readable.prototype.pipe = function (dest, pipeOpts) {
@@ -607,25 +634,19 @@ Readable.prototype.pipe = function (dest, pipeOpts) {
if (state.awaitDrain && (!dest._writableState || dest._writableState.needDrain)) ondrain();
}
- // If the user pushes more data while we're writing to dest then we'll end up
- // in ondata again. However, we only want to increase awaitDrain once because
- // dest will only emit one 'drain' event for the multiple writes.
- // => Introduce a guard on increasing awaitDrain.
- var increasedAwaitDrain = false;
src.on('data', ondata);
function ondata(chunk) {
debug('ondata');
- increasedAwaitDrain = false;
var ret = dest.write(chunk);
- if (false === ret && !increasedAwaitDrain) {
+ debug('dest.write', ret);
+ if (ret === false) {
// If the user unpiped during `dest.write()`, it is possible
// to get stuck in a permanently paused state if that write
// also returned false.
// => Check whether `dest` is still a piping destination.
if ((state.pipesCount === 1 && state.pipes === dest || state.pipesCount > 1 && indexOf(state.pipes, dest) !== -1) && !cleanedUp) {
- debug('false write response, pause', src._readableState.awaitDrain);
- src._readableState.awaitDrain++;
- increasedAwaitDrain = true;
+ debug('false write response, pause', state.awaitDrain);
+ state.awaitDrain++;
}
src.pause();
}
@@ -674,7 +695,7 @@ Readable.prototype.pipe = function (dest, pipeOpts) {
};
function pipeOnDrain(src) {
- return function () {
+ return function pipeOnDrainFunctionResult() {
var state = src._readableState;
debug('pipeOnDrain', state.awaitDrain);
if (state.awaitDrain) state.awaitDrain--;
@@ -718,7 +739,7 @@ Readable.prototype.unpipe = function (dest) {
state.flowing = false;
for (var i = 0; i < len; i++) {
- dests[i].emit('unpipe', this, unpipeInfo);
+ dests[i].emit('unpipe', this, { hasUnpiped: false });
}return this;
}
@@ -739,19 +760,23 @@ Readable.prototype.unpipe = function (dest) {
// Ensure readable listeners eventually get something
Readable.prototype.on = function (ev, fn) {
var res = Stream.prototype.on.call(this, ev, fn);
+ var state = this._readableState;
if (ev === 'data') {
- // Start flowing on next tick if stream isn't explicitly paused
- if (this._readableState.flowing !== false) this.resume();
+ // update readableListening so that resume() may be a no-op
+ // a few lines down. This is needed to support once('readable').
+ state.readableListening = this.listenerCount('readable') > 0;
+
+ // Try start flowing on next tick if stream isn't explicitly paused
+ if (state.flowing !== false) this.resume();
} else if (ev === 'readable') {
- var state = this._readableState;
if (!state.endEmitted && !state.readableListening) {
state.readableListening = state.needReadable = true;
state.emittedReadable = false;
- if (!state.reading) {
- pna.nextTick(nReadingNextTick, this);
- } else if (state.length) {
+ if (state.length) {
emitReadable(this);
+ } else if (!state.reading) {
+ pna.nextTick(nReadingNextTick, this);
}
}
}
@@ -760,6 +785,42 @@ Readable.prototype.on = function (ev, fn) {
};
Readable.prototype.addListener = Readable.prototype.on;
+Readable.prototype.removeListener = function (ev, fn) {
+ var res = Stream.prototype.removeListener.call(this, ev, fn);
+
+ if (ev === 'readable') {
+ // We need to check if there is someone still listening to
+ // readable and reset the state. However this needs to happen
+ // after readable has been emitted but before I/O (nextTick) to
+ // support once('readable', fn) cycles. This means that calling
+ // resume within the same tick will have no
+ // effect.
+ pna.nextTick(updateReadableListening, this);
+ }
+
+ return res;
+};
+
+Readable.prototype.removeAllListeners = function (ev) {
+ var res = Stream.prototype.removeAllListeners.apply(this, arguments);
+
+ if (ev === 'readable' || ev === undefined) {
+ // We need to check if there is someone still listening to
+ // readable and reset the state. However this needs to happen
+ // after readable has been emitted but before I/O (nextTick) to
+ // support once('readable', fn) cycles. This means that calling
+ // resume within the same tick will have no
+ // effect.
+ pna.nextTick(updateReadableListening, this);
+ }
+
+ return res;
+};
+
+function updateReadableListening(self) {
+ self._readableState.readableListening = self.listenerCount('readable') > 0;
+}
+
function nReadingNextTick(self) {
debug('readable nexttick read 0');
self.read(0);
@@ -771,7 +832,9 @@ Readable.prototype.resume = function () {
var state = this._readableState;
if (!state.flowing) {
debug('resume');
- state.flowing = true;
+ // we flow only if there is no one listening
+ // for readable
+ state.flowing = !state.readableListening;
resume(this, state);
}
return this;
@@ -785,13 +848,12 @@ function resume(stream, state) {
}
function resume_(stream, state) {
+ debug('resume', state.reading);
if (!state.reading) {
- debug('resume read 0');
stream.read(0);
}
state.resumeScheduled = false;
- state.awaitDrain = 0;
stream.emit('resume');
flow(stream);
if (state.flowing && !state.reading) stream.read(0);
@@ -799,7 +861,7 @@ function resume_(stream, state) {
Readable.prototype.pause = function () {
debug('call pause flowing=%j', this._readableState.flowing);
- if (false !== this._readableState.flowing) {
+ if (this._readableState.flowing !== false) {
debug('pause');
this._readableState.flowing = false;
this.emit('pause');
@@ -850,8 +912,8 @@ Readable.prototype.wrap = function (stream) {
// important when wrapping filters and duplexes.
for (var i in stream) {
if (this[i] === undefined && typeof stream[i] === 'function') {
- this[i] = function (method) {
- return function () {
+ this[i] = function methodWrap(method) {
+ return function methodWrapReturnFunction() {
return stream[method].apply(stream, arguments);
};
}(i);
@@ -876,6 +938,12 @@ Readable.prototype.wrap = function (stream) {
return this;
};
+Readable.prototype[Symbol.asyncIterator] = function () {
+ emitExperimentalWarning('Readable[Symbol.asyncIterator]');
+ if (ReadableAsyncIterator === undefined) ReadableAsyncIterator = require('./internal/streams/async_iterator');
+ return new ReadableAsyncIterator(this);
+};
+
Object.defineProperty(Readable.prototype, 'readableHighWaterMark', {
// making it explicit this property is not enumerable
// because otherwise some prototype manipulation in
@@ -886,9 +954,44 @@ Object.defineProperty(Readable.prototype, 'readableHighWaterMark', {
}
});
+Object.defineProperty(Readable.prototype, 'readableBuffer', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._readableState && this._readableState.buffer;
+ }
+});
+
+Object.defineProperty(Readable.prototype, 'readableFlowing', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._readableState.flowing;
+ },
+ set: function (state) {
+ if (this._readableState) {
+ this._readableState.flowing = state;
+ }
+ }
+});
+
// exposed for testing purposes only.
Readable._fromList = fromList;
+Object.defineProperty(Readable.prototype, 'readableLength', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._readableState.length;
+ }
+});
+
// Pluck off n bytes from an array of buffers.
// Length is the combined lengths of all the buffers in the list.
// This function is designed to be inlinable, so please take care when making
@@ -900,102 +1003,20 @@ function fromList(n, state) {
var ret;
if (state.objectMode) ret = state.buffer.shift();else if (!n || n >= state.length) {
// read it all, truncate the list
- if (state.decoder) ret = state.buffer.join('');else if (state.buffer.length === 1) ret = state.buffer.head.data;else ret = state.buffer.concat(state.length);
+ if (state.decoder) ret = state.buffer.join('');else if (state.buffer.length === 1) ret = state.buffer.first();else ret = state.buffer.concat(state.length);
state.buffer.clear();
} else {
// read part of list
- ret = fromListPartial(n, state.buffer, state.decoder);
+ ret = state.buffer.consume(n, state.decoder);
}
return ret;
}
-// Extracts only enough buffered data to satisfy the amount requested.
-// This function is designed to be inlinable, so please take care when making
-// changes to the function body.
-function fromListPartial(n, list, hasStrings) {
- var ret;
- if (n < list.head.data.length) {
- // slice is the same for buffers and strings
- ret = list.head.data.slice(0, n);
- list.head.data = list.head.data.slice(n);
- } else if (n === list.head.data.length) {
- // first chunk is a perfect match
- ret = list.shift();
- } else {
- // result spans more than one buffer
- ret = hasStrings ? copyFromBufferString(n, list) : copyFromBuffer(n, list);
- }
- return ret;
-}
-
-// Copies a specified amount of characters from the list of buffered data
-// chunks.
-// This function is designed to be inlinable, so please take care when making
-// changes to the function body.
-function copyFromBufferString(n, list) {
- var p = list.head;
- var c = 1;
- var ret = p.data;
- n -= ret.length;
- while (p = p.next) {
- var str = p.data;
- var nb = n > str.length ? str.length : n;
- if (nb === str.length) ret += str;else ret += str.slice(0, n);
- n -= nb;
- if (n === 0) {
- if (nb === str.length) {
- ++c;
- if (p.next) list.head = p.next;else list.head = list.tail = null;
- } else {
- list.head = p;
- p.data = str.slice(nb);
- }
- break;
- }
- ++c;
- }
- list.length -= c;
- return ret;
-}
-
-// Copies a specified amount of bytes from the list of buffered data chunks.
-// This function is designed to be inlinable, so please take care when making
-// changes to the function body.
-function copyFromBuffer(n, list) {
- var ret = Buffer.allocUnsafe(n);
- var p = list.head;
- var c = 1;
- p.data.copy(ret);
- n -= p.data.length;
- while (p = p.next) {
- var buf = p.data;
- var nb = n > buf.length ? buf.length : n;
- buf.copy(ret, ret.length - n, 0, nb);
- n -= nb;
- if (n === 0) {
- if (nb === buf.length) {
- ++c;
- if (p.next) list.head = p.next;else list.head = list.tail = null;
- } else {
- list.head = p;
- p.data = buf.slice(nb);
- }
- break;
- }
- ++c;
- }
- list.length -= c;
- return ret;
-}
-
function endReadable(stream) {
var state = stream._readableState;
- // If we get here before consuming all the bytes, then that is a
- // bug in node. Should never happen.
- if (state.length > 0) throw new Error('"endReadable()" called on non-empty stream');
-
+ debug('endReadable', state.endEmitted);
if (!state.endEmitted) {
state.ended = true;
pna.nextTick(endReadableNT, state, stream);
@@ -1003,6 +1024,8 @@ function endReadable(stream) {
}
function endReadableNT(state, stream) {
+ debug('endReadableNT', state.endEmitted, state.length);
+
// Check that we didn't get one last unshift.
if (!state.endEmitted && state.length === 0) {
state.endEmitted = true;
diff --git a/lib/_stream_transform.js b/lib/_stream_transform.js
index 5d1f8b876d..0db25398ab 100644
--- a/lib/_stream_transform.js
+++ b/lib/_stream_transform.js
@@ -65,14 +65,15 @@
module.exports = Transform;
-var Duplex = require('./_stream_duplex');
+var _require$codes = require('../errors').codes,
+ ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED,
+ ERR_MULTIPLE_CALLBACK = _require$codes.ERR_MULTIPLE_CALLBACK,
+ ERR_TRANSFORM_ALREADY_TRANSFORMING = _require$codes.ERR_TRANSFORM_ALREADY_TRANSFORMING,
+ ERR_TRANSFORM_WITH_LENGTH_0 = _require$codes.ERR_TRANSFORM_WITH_LENGTH_0;
-/**/
-var util = require('core-util-is');
-util.inherits = require('inherits');
-/**/
+var Duplex = require('./_stream_duplex');
-util.inherits(Transform, Duplex);
+require('inherits')(Transform, Duplex);
function afterTransform(er, data) {
var ts = this._transformState;
@@ -80,8 +81,8 @@ function afterTransform(er, data) {
var cb = ts.writecb;
- if (!cb) {
- return this.emit('error', new Error('write callback called multiple times'));
+ if (cb === null) {
+ return this.emit('error', new ERR_MULTIPLE_CALLBACK());
}
ts.writechunk = null;
@@ -134,7 +135,7 @@ function Transform(options) {
function prefinish() {
var _this = this;
- if (typeof this._flush === 'function') {
+ if (typeof this._flush === 'function' && !this._readableState.destroyed) {
this._flush(function (er, data) {
done(_this, er, data);
});
@@ -159,7 +160,7 @@ Transform.prototype.push = function (chunk, encoding) {
// an error, then that'll put the hurt on the whole operation. If you
// never call cb(), then you'll never get another chunk.
Transform.prototype._transform = function (chunk, encoding, cb) {
- throw new Error('_transform() is not implemented');
+ cb(new ERR_METHOD_NOT_IMPLEMENTED('_transform()'));
};
Transform.prototype._write = function (chunk, encoding, cb) {
@@ -179,7 +180,7 @@ Transform.prototype._write = function (chunk, encoding, cb) {
Transform.prototype._read = function (n) {
var ts = this._transformState;
- if (ts.writechunk !== null && ts.writecb && !ts.transforming) {
+ if (ts.writechunk !== null && !ts.transforming) {
ts.transforming = true;
this._transform(ts.writechunk, ts.writeencoding, ts.afterTransform);
} else {
@@ -190,11 +191,8 @@ Transform.prototype._read = function (n) {
};
Transform.prototype._destroy = function (err, cb) {
- var _this2 = this;
-
Duplex.prototype._destroy.call(this, err, function (err2) {
cb(err2);
- _this2.emit('close');
});
};
@@ -204,11 +202,11 @@ function done(stream, er, data) {
if (data != null) // single equals check for both `null` and `undefined`
stream.push(data);
+ // TODO(BridgeAR): Write a test for these two error cases
// if there's nothing in the write buffer, then that means
// that nothing more will ever be provided
- if (stream._writableState.length) throw new Error('Calling transform done when ws.length != 0');
-
- if (stream._transformState.transforming) throw new Error('Calling transform done when still transforming');
+ if (stream._writableState.length) throw new ERR_TRANSFORM_WITH_LENGTH_0();
+ if (stream._transformState.transforming) throw new ERR_TRANSFORM_ALREADY_TRANSFORMING();
return stream.push(null);
}
\ No newline at end of file
diff --git a/lib/_stream_writable.js b/lib/_stream_writable.js
index b3f4e85a2f..b332fb0b80 100644
--- a/lib/_stream_writable.js
+++ b/lib/_stream_writable.js
@@ -63,11 +63,6 @@ var Duplex;
Writable.WritableState = WritableState;
-/**/
-var util = require('core-util-is');
-util.inherits = require('inherits');
-/**/
-
/**/
var internalUtil = {
deprecate: require('util-deprecate')
@@ -78,9 +73,7 @@ var internalUtil = {
var Stream = require('./internal/streams/stream');
/**/
-/**/
-
-var Buffer = require('safe-buffer').Buffer;
+var Buffer = require('buffer').Buffer;
var OurUint8Array = global.Uint8Array || function () {};
function _uint8ArrayToBuffer(chunk) {
return Buffer.from(chunk);
@@ -89,15 +82,26 @@ function _isUint8Array(obj) {
return Buffer.isBuffer(obj) || obj instanceof OurUint8Array;
}
-/**/
-
var destroyImpl = require('./internal/streams/destroy');
-util.inherits(Writable, Stream);
+var _require = require('./internal/streams/state'),
+ getHighWaterMark = _require.getHighWaterMark;
+
+var _require$codes = require('../errors').codes,
+ ERR_INVALID_ARG_TYPE = _require$codes.ERR_INVALID_ARG_TYPE,
+ ERR_METHOD_NOT_IMPLEMENTED = _require$codes.ERR_METHOD_NOT_IMPLEMENTED,
+ ERR_MULTIPLE_CALLBACK = _require$codes.ERR_MULTIPLE_CALLBACK,
+ ERR_STREAM_CANNOT_PIPE = _require$codes.ERR_STREAM_CANNOT_PIPE,
+ ERR_STREAM_DESTROYED = _require$codes.ERR_STREAM_DESTROYED,
+ ERR_STREAM_NULL_VALUES = _require$codes.ERR_STREAM_NULL_VALUES,
+ ERR_STREAM_WRITE_AFTER_END = _require$codes.ERR_STREAM_WRITE_AFTER_END,
+ ERR_UNKNOWN_ENCODING = _require$codes.ERR_UNKNOWN_ENCODING;
+
+require('inherits')(Writable, Stream);
function nop() {}
-function WritableState(options, stream) {
+function WritableState(options, stream, isDuplex) {
Duplex = Duplex || require('./_stream_duplex');
options = options || {};
@@ -107,7 +111,7 @@ function WritableState(options, stream) {
// However, some cases require setting options to different
// values for the readable and the writable sides of the duplex stream.
// These options can be provided separately as readableXXX and writableXXX.
- var isDuplex = stream instanceof Duplex;
+ if (typeof isDuplex !== 'boolean') isDuplex = stream instanceof Duplex;
// object stream flag to indicate whether or not this stream
// contains buffers or objects.
@@ -118,14 +122,7 @@ function WritableState(options, stream) {
// the point at which write() starts returning false
// Note: 0 is a valid value, means that we always return false if
// the entire buffer is not flushed immediately on write()
- var hwm = options.highWaterMark;
- var writableHwm = options.writableHighWaterMark;
- var defaultHwm = this.objectMode ? 16 : 16 * 1024;
-
- if (hwm || hwm === 0) this.highWaterMark = hwm;else if (isDuplex && (writableHwm || writableHwm === 0)) this.highWaterMark = writableHwm;else this.highWaterMark = defaultHwm;
-
- // cast to ints.
- this.highWaterMark = Math.floor(this.highWaterMark);
+ this.highWaterMark = getHighWaterMark(this, options, 'writableHighWaterMark', isDuplex);
// if _final has been called
this.finalCalled = false;
@@ -200,6 +197,9 @@ function WritableState(options, stream) {
// True if the error was already emitted and should not be thrown again
this.errorEmitted = false;
+ // Should close be emitted on destroy. Defaults to true.
+ this.emitClose = options.emitClose !== false;
+
// count buffered requests
this.bufferedRequestCount = 0;
@@ -221,7 +221,7 @@ WritableState.prototype.getBuffer = function getBuffer() {
(function () {
try {
Object.defineProperty(WritableState.prototype, 'buffer', {
- get: internalUtil.deprecate(function () {
+ get: internalUtil.deprecate(function writableStateBufferGetter() {
return this.getBuffer();
}, '_writableState.buffer is deprecated. Use _writableState.getBuffer ' + 'instead.', 'DEP0003')
});
@@ -257,11 +257,14 @@ function Writable(options) {
// Trying to use the custom `instanceof` for Writable here will also break the
// Node.js LazyTransform implementation, which has a non-trivial getter for
// `_writableState` that would lead to infinite recursion.
- if (!realHasInstance.call(Writable, this) && !(this instanceof Duplex)) {
- return new Writable(options);
- }
- this._writableState = new WritableState(options, this);
+ // Checking for a Stream.Duplex instance is faster here instead of inside
+ // the WritableState constructor, at least with V8 6.5
+ var isDuplex = this instanceof Duplex;
+
+ if (!isDuplex && !realHasInstance.call(Writable, this)) return new Writable(options);
+
+ this._writableState = new WritableState(options, this, isDuplex);
// legacy.
this.writable = true;
@@ -281,11 +284,11 @@ function Writable(options) {
// Otherwise people can pipe Writable streams, which is just wrong.
Writable.prototype.pipe = function () {
- this.emit('error', new Error('Cannot pipe, not readable'));
+ this.emit('error', new ERR_STREAM_CANNOT_PIPE());
};
function writeAfterEnd(stream, cb) {
- var er = new Error('write after end');
+ var er = new ERR_STREAM_WRITE_AFTER_END();
// TODO: defer error events consistently everywhere, not just the cb
stream.emit('error', er);
pna.nextTick(cb, er);
@@ -295,20 +298,19 @@ function writeAfterEnd(stream, cb) {
// mode the stream is in. Currently this means that `null` is never accepted
// and undefined/non-string values are only allowed in object mode.
function validChunk(stream, state, chunk, cb) {
- var valid = true;
- var er = false;
+ var er;
if (chunk === null) {
- er = new TypeError('May not write null values to stream');
- } else if (typeof chunk !== 'string' && chunk !== undefined && !state.objectMode) {
- er = new TypeError('Invalid non-string/buffer chunk');
+ er = new ERR_STREAM_NULL_VALUES();
+ } else if (typeof chunk !== 'string' && !state.objectMode) {
+ er = new ERR_INVALID_ARG_TYPE('chunk', ['string', 'Buffer'], chunk);
}
if (er) {
stream.emit('error', er);
pna.nextTick(cb, er);
- valid = false;
+ return false;
}
- return valid;
+ return true;
}
Writable.prototype.write = function (chunk, encoding, cb) {
@@ -329,7 +331,7 @@ Writable.prototype.write = function (chunk, encoding, cb) {
if (typeof cb !== 'function') cb = nop;
- if (state.ended) writeAfterEnd(this, cb);else if (isBuf || validChunk(this, state, chunk, cb)) {
+ if (state.ending) writeAfterEnd(this, cb);else if (isBuf || validChunk(this, state, chunk, cb)) {
state.pendingcb++;
ret = writeOrBuffer(this, state, isBuf, chunk, encoding, cb);
}
@@ -338,9 +340,7 @@ Writable.prototype.write = function (chunk, encoding, cb) {
};
Writable.prototype.cork = function () {
- var state = this._writableState;
-
- state.corked++;
+ this._writableState.corked++;
};
Writable.prototype.uncork = function () {
@@ -349,18 +349,28 @@ Writable.prototype.uncork = function () {
if (state.corked) {
state.corked--;
- if (!state.writing && !state.corked && !state.finished && !state.bufferProcessing && state.bufferedRequest) clearBuffer(this, state);
+ if (!state.writing && !state.corked && !state.bufferProcessing && state.bufferedRequest) clearBuffer(this, state);
}
};
Writable.prototype.setDefaultEncoding = function setDefaultEncoding(encoding) {
// node::ParseEncoding() requires lower case.
if (typeof encoding === 'string') encoding = encoding.toLowerCase();
- if (!(['hex', 'utf8', 'utf-8', 'ascii', 'binary', 'base64', 'ucs2', 'ucs-2', 'utf16le', 'utf-16le', 'raw'].indexOf((encoding + '').toLowerCase()) > -1)) throw new TypeError('Unknown encoding: ' + encoding);
+ if (!(['hex', 'utf8', 'utf-8', 'ascii', 'binary', 'base64', 'ucs2', 'ucs-2', 'utf16le', 'utf-16le', 'raw'].indexOf((encoding + '').toLowerCase()) > -1)) throw new ERR_UNKNOWN_ENCODING(encoding);
this._writableState.defaultEncoding = encoding;
return this;
};
+Object.defineProperty(Writable.prototype, 'writableBuffer', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._writableState && this._writableState.getBuffer();
+ }
+});
+
function decodeChunk(state, chunk, encoding) {
if (!state.objectMode && state.decodeStrings !== false && typeof chunk === 'string') {
chunk = Buffer.from(chunk, encoding);
@@ -425,7 +435,7 @@ function doWrite(stream, state, writev, len, chunk, encoding, cb) {
state.writecb = cb;
state.writing = true;
state.sync = true;
- if (writev) stream._writev(chunk, state.onwrite);else stream._write(chunk, encoding, state.onwrite);
+ if (state.destroyed) state.onwrite(new ERR_STREAM_DESTROYED('write'));else if (writev) stream._writev(chunk, state.onwrite);else stream._write(chunk, encoding, state.onwrite);
state.sync = false;
}
@@ -465,6 +475,8 @@ function onwrite(stream, er) {
var sync = state.sync;
var cb = state.writecb;
+ if (typeof cb !== 'function') throw new ERR_MULTIPLE_CALLBACK();
+
onwriteStateUpdate(state);
if (er) onwriteError(stream, state, sync, er, cb);else {
@@ -565,7 +577,7 @@ function clearBuffer(stream, state) {
}
Writable.prototype._write = function (chunk, encoding, cb) {
- cb(new Error('_write() is not implemented'));
+ cb(new ERR_METHOD_NOT_IMPLEMENTED('_write()'));
};
Writable.prototype._writev = null;
@@ -591,9 +603,21 @@ Writable.prototype.end = function (chunk, encoding, cb) {
}
// ignore unnecessary end() calls.
- if (!state.ending && !state.finished) endWritable(this, state, cb);
+ if (!state.ending) endWritable(this, state, cb);
+
+ return this;
};
+Object.defineProperty(Writable.prototype, 'writableLength', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
+ get: function () {
+ return this._writableState.length;
+ }
+});
+
function needFinish(state) {
return state.ending && state.length === 0 && state.bufferedRequest === null && !state.finished && !state.writing;
}
@@ -610,7 +634,7 @@ function callFinal(stream, state) {
}
function prefinish(stream, state) {
if (!state.prefinished && !state.finalCalled) {
- if (typeof stream._final === 'function') {
+ if (typeof stream._final === 'function' && !state.destroyed) {
state.pendingcb++;
state.finalCalled = true;
pna.nextTick(callFinal, stream, state);
@@ -652,14 +676,16 @@ function onCorkedFinish(corkReq, state, err) {
cb(err);
entry = entry.next;
}
- if (state.corkedRequestsFree) {
- state.corkedRequestsFree.next = corkReq;
- } else {
- state.corkedRequestsFree = corkReq;
- }
+
+ // reuse the free corkReq.
+ state.corkedRequestsFree.next = corkReq;
}
Object.defineProperty(Writable.prototype, 'destroyed', {
+ // making it explicit this property is not enumerable
+ // because otherwise some prototype manipulation in
+ // userland will fail
+ enumerable: false,
get: function () {
if (this._writableState === undefined) {
return false;
@@ -682,6 +708,5 @@ Object.defineProperty(Writable.prototype, 'destroyed', {
Writable.prototype.destroy = destroyImpl.destroy;
Writable.prototype._undestroy = destroyImpl.undestroy;
Writable.prototype._destroy = function (err, cb) {
- this.end();
cb(err);
};
\ No newline at end of file
diff --git a/lib/internal/streams/BufferList.js b/lib/internal/streams/BufferList.js
deleted file mode 100644
index aefc68bd90..0000000000
--- a/lib/internal/streams/BufferList.js
+++ /dev/null
@@ -1,79 +0,0 @@
-'use strict';
-
-function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
-
-var Buffer = require('safe-buffer').Buffer;
-var util = require('util');
-
-function copyBuffer(src, target, offset) {
- src.copy(target, offset);
-}
-
-module.exports = function () {
- function BufferList() {
- _classCallCheck(this, BufferList);
-
- this.head = null;
- this.tail = null;
- this.length = 0;
- }
-
- BufferList.prototype.push = function push(v) {
- var entry = { data: v, next: null };
- if (this.length > 0) this.tail.next = entry;else this.head = entry;
- this.tail = entry;
- ++this.length;
- };
-
- BufferList.prototype.unshift = function unshift(v) {
- var entry = { data: v, next: this.head };
- if (this.length === 0) this.tail = entry;
- this.head = entry;
- ++this.length;
- };
-
- BufferList.prototype.shift = function shift() {
- if (this.length === 0) return;
- var ret = this.head.data;
- if (this.length === 1) this.head = this.tail = null;else this.head = this.head.next;
- --this.length;
- return ret;
- };
-
- BufferList.prototype.clear = function clear() {
- this.head = this.tail = null;
- this.length = 0;
- };
-
- BufferList.prototype.join = function join(s) {
- if (this.length === 0) return '';
- var p = this.head;
- var ret = '' + p.data;
- while (p = p.next) {
- ret += s + p.data;
- }return ret;
- };
-
- BufferList.prototype.concat = function concat(n) {
- if (this.length === 0) return Buffer.alloc(0);
- if (this.length === 1) return this.head.data;
- var ret = Buffer.allocUnsafe(n >>> 0);
- var p = this.head;
- var i = 0;
- while (p) {
- copyBuffer(p.data, ret, i);
- i += p.data.length;
- p = p.next;
- }
- return ret;
- };
-
- return BufferList;
-}();
-
-if (util && util.inspect && util.inspect.custom) {
- module.exports.prototype[util.inspect.custom] = function () {
- var obj = util.inspect({ length: this.length });
- return this.constructor.name + ' ' + obj;
- };
-}
\ No newline at end of file
diff --git a/lib/internal/streams/async_iterator.js b/lib/internal/streams/async_iterator.js
new file mode 100644
index 0000000000..4ec9f1ac3d
--- /dev/null
+++ b/lib/internal/streams/async_iterator.js
@@ -0,0 +1,179 @@
+'use strict';
+
+/**/
+
+var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+var pna = require('process-nextick-args');
+/**/
+
+var kLastResolve = Symbol('lastResolve');
+var kLastReject = Symbol('lastReject');
+var kError = Symbol('error');
+var kEnded = Symbol('ended');
+var kLastPromise = Symbol('lastPromise');
+var kHandlePromise = Symbol('handlePromise');
+var kStream = Symbol('stream');
+
+var AsyncIteratorRecord = function AsyncIteratorRecord(value, done) {
+ _classCallCheck(this, AsyncIteratorRecord);
+
+ this.done = done;
+ this.value = value;
+};
+
+function readAndResolve(iter) {
+ var resolve = iter[kLastResolve];
+ if (resolve !== null) {
+ var data = iter[kStream].read();
+ // we defer if data is null
+ // we can be expecting either 'end' or
+ // 'error'
+ if (data !== null) {
+ iter[kLastPromise] = null;
+ iter[kLastResolve] = null;
+ iter[kLastReject] = null;
+ resolve(new AsyncIteratorRecord(data, false));
+ }
+ }
+}
+
+function onReadable(iter) {
+ // we wait for the next tick, because it might
+ // emit an error with process.nextTick
+ pna.nextTick(readAndResolve, iter);
+}
+
+function onEnd(iter) {
+ var resolve = iter[kLastResolve];
+ if (resolve !== null) {
+ iter[kLastPromise] = null;
+ iter[kLastResolve] = null;
+ iter[kLastReject] = null;
+ resolve(new AsyncIteratorRecord(null, true));
+ }
+ iter[kEnded] = true;
+}
+
+function onError(iter, err) {
+ var reject = iter[kLastReject];
+ // reject if we are waiting for data in the Promise
+ // returned by next() and store the error
+ if (reject !== null) {
+ iter[kLastPromise] = null;
+ iter[kLastResolve] = null;
+ iter[kLastReject] = null;
+ reject(err);
+ }
+ iter[kError] = err;
+}
+
+function wrapForNext(lastPromise, iter) {
+ return function (resolve, reject) {
+ lastPromise.then(function () {
+ iter[kHandlePromise](resolve, reject);
+ }, reject);
+ };
+}
+
+var ReadableAsyncIterator = function () {
+ function ReadableAsyncIterator(stream) {
+ var _this = this;
+
+ _classCallCheck(this, ReadableAsyncIterator);
+
+ this[kStream] = stream;
+ this[kLastResolve] = null;
+ this[kLastReject] = null;
+ this[kError] = null;
+ this[kEnded] = false;
+ this[kLastPromise] = null;
+
+ stream.on('readable', onReadable.bind(null, this));
+ stream.on('end', onEnd.bind(null, this));
+ stream.on('error', onError.bind(null, this));
+
+ // the function passed to new Promise
+ // is cached so we avoid allocating a new
+ // closure at every run
+ this[kHandlePromise] = function (resolve, reject) {
+ var data = _this[kStream].read();
+ if (data) {
+ _this[kLastPromise] = null;
+ _this[kLastResolve] = null;
+ _this[kLastReject] = null;
+ resolve(new AsyncIteratorRecord(data, false));
+ } else {
+ _this[kLastResolve] = resolve;
+ _this[kLastReject] = reject;
+ }
+ };
+ }
+
+ ReadableAsyncIterator.prototype.next = function next() {
+ // if we have detected an error in the meanwhile
+ // reject straight away
+ var error = this[kError];
+ if (error !== null) {
+ return Promise.reject(error);
+ }
+
+ if (this[kEnded]) {
+ return Promise.resolve(new AsyncIteratorRecord(null, true));
+ }
+
+ // if we have multiple next() calls
+ // we will wait for the previous Promise to finish
+ // this logic is optimized to support for await loops,
+ // where next() is only called once at a time
+ var lastPromise = this[kLastPromise];
+ var promise = void 0;
+
+ if (lastPromise) {
+ promise = new Promise(wrapForNext(lastPromise, this));
+ } else {
+ // fast path needed to support multiple this.push()
+ // without triggering the next() queue
+ var data = this[kStream].read();
+ if (data !== null) {
+ return Promise.resolve(new AsyncIteratorRecord(data, false));
+ }
+
+ promise = new Promise(this[kHandlePromise]);
+ }
+
+ this[kLastPromise] = promise;
+
+ return promise;
+ };
+
+ ReadableAsyncIterator.prototype.return = function _return() {
+ var _this2 = this;
+
+ // destroy(err, cb) is a private API
+ // we can guarantee we have that here, because we control the
+ // Readable class this is attached to
+ return new Promise(function (resolve, reject) {
+ _this2[kStream].destroy(null, function (err) {
+ if (err) {
+ reject(err);
+ return;
+ }
+ resolve(new AsyncIteratorRecord(null, true));
+ });
+ });
+ };
+
+ _createClass(ReadableAsyncIterator, [{
+ key: 'stream',
+ get: function () {
+ return this[kStream];
+ }
+ }]);
+
+ return ReadableAsyncIterator;
+}();
+
+module.exports = ReadableAsyncIterator;
\ No newline at end of file
diff --git a/lib/internal/streams/buffer_list.js b/lib/internal/streams/buffer_list.js
new file mode 100644
index 0000000000..72463e17ff
--- /dev/null
+++ b/lib/internal/streams/buffer_list.js
@@ -0,0 +1,168 @@
+'use strict';
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+var Buffer = require('buffer').Buffer;
+var util = require('util');
+
+var _require = require('util'),
+ inspect = _require.inspect;
+
+function copyBuffer(src, target, offset) {
+ src.copy(target, offset);
+}
+
+module.exports = function () {
+ function BufferList() {
+ _classCallCheck(this, BufferList);
+
+ this.head = null;
+ this.tail = null;
+ this.length = 0;
+ }
+
+ BufferList.prototype.push = function push(v) {
+ var entry = { data: v, next: null };
+ if (this.length > 0) this.tail.next = entry;else this.head = entry;
+ this.tail = entry;
+ ++this.length;
+ };
+
+ BufferList.prototype.unshift = function unshift(v) {
+ var entry = { data: v, next: this.head };
+ if (this.length === 0) this.tail = entry;
+ this.head = entry;
+ ++this.length;
+ };
+
+ BufferList.prototype.shift = function shift() {
+ if (this.length === 0) return;
+ var ret = this.head.data;
+ if (this.length === 1) this.head = this.tail = null;else this.head = this.head.next;
+ --this.length;
+ return ret;
+ };
+
+ BufferList.prototype.clear = function clear() {
+ this.head = this.tail = null;
+ this.length = 0;
+ };
+
+ BufferList.prototype.join = function join(s) {
+ if (this.length === 0) return '';
+ var p = this.head;
+ var ret = '' + p.data;
+ while (p = p.next) {
+ ret += s + p.data;
+ }return ret;
+ };
+
+ BufferList.prototype.concat = function concat(n) {
+ if (this.length === 0) return Buffer.alloc(0);
+ var ret = Buffer.allocUnsafe(n >>> 0);
+ var p = this.head;
+ var i = 0;
+ while (p) {
+ copyBuffer(p.data, ret, i);
+ i += p.data.length;
+ p = p.next;
+ }
+ return ret;
+ };
+
+ // Consumes a specified amount of bytes or characters from the buffered data.
+
+
+ BufferList.prototype.consume = function consume(n, hasStrings) {
+ var ret;
+ if (n < this.head.data.length) {
+ // `slice` is the same for buffers and strings.
+ ret = this.head.data.slice(0, n);
+ this.head.data = this.head.data.slice(n);
+ } else if (n === this.head.data.length) {
+ // First chunk is a perfect match.
+ ret = this.shift();
+ } else {
+ // Result spans more than one buffer.
+ ret = hasStrings ? this._getString(n) : this._getBuffer(n);
+ }
+ return ret;
+ };
+
+ BufferList.prototype.first = function first() {
+ return this.head.data;
+ };
+
+ // Consumes a specified amount of characters from the buffered data.
+
+
+ BufferList.prototype._getString = function _getString(n) {
+ var p = this.head;
+ var c = 1;
+ var ret = p.data;
+ n -= ret.length;
+ while (p = p.next) {
+ var str = p.data;
+ var nb = n > str.length ? str.length : n;
+ if (nb === str.length) ret += str;else ret += str.slice(0, n);
+ n -= nb;
+ if (n === 0) {
+ if (nb === str.length) {
+ ++c;
+ if (p.next) this.head = p.next;else this.head = this.tail = null;
+ } else {
+ this.head = p;
+ p.data = str.slice(nb);
+ }
+ break;
+ }
+ ++c;
+ }
+ this.length -= c;
+ return ret;
+ };
+
+ // Consumes a specified amount of bytes from the buffered data.
+
+
+ BufferList.prototype._getBuffer = function _getBuffer(n) {
+ var ret = Buffer.allocUnsafe(n);
+ var p = this.head;
+ var c = 1;
+ p.data.copy(ret);
+ n -= p.data.length;
+ while (p = p.next) {
+ var buf = p.data;
+ var nb = n > buf.length ? buf.length : n;
+ buf.copy(ret, ret.length - n, 0, nb);
+ n -= nb;
+ if (n === 0) {
+ if (nb === buf.length) {
+ ++c;
+ if (p.next) this.head = p.next;else this.head = this.tail = null;
+ } else {
+ this.head = p;
+ p.data = buf.slice(nb);
+ }
+ break;
+ }
+ ++c;
+ }
+ this.length -= c;
+ return ret;
+ };
+
+ BufferList.prototype[inspect.custom] = function () {
+ var obj = inspect({ length: this.length });
+ return this.constructor.name + ' ' + obj;
+ };
+
+ return BufferList;
+}();
+
+if (util && util.inspect && util.inspect.custom) {
+ module.exports.prototype[util.inspect.custom] = function () {
+ var obj = util.inspect({ length: this.length });
+ return this.constructor.name + ' ' + obj;
+ };
+}
\ No newline at end of file
diff --git a/lib/internal/streams/destroy.js b/lib/internal/streams/destroy.js
index 5a0a0d88ce..ca929a153c 100644
--- a/lib/internal/streams/destroy.js
+++ b/lib/internal/streams/destroy.js
@@ -35,18 +35,32 @@ function destroy(err, cb) {
this._destroy(err || null, function (err) {
if (!cb && err) {
- pna.nextTick(emitErrorNT, _this, err);
+ pna.nextTick(emitErrorAndCloseNT, _this, err);
if (_this._writableState) {
_this._writableState.errorEmitted = true;
}
} else if (cb) {
+ pna.nextTick(emitCloseNT, _this);
cb(err);
+ } else {
+ pna.nextTick(emitCloseNT, _this);
}
});
return this;
}
+function emitErrorAndCloseNT(self, err) {
+ emitErrorNT(self, err);
+ emitCloseNT(self);
+}
+
+function emitCloseNT(self) {
+ if (self._writableState && !self._writableState.emitClose) return;
+ if (self._readableState && !self._readableState.emitClose) return;
+ self.emit('close');
+}
+
function undestroy() {
if (this._readableState) {
this._readableState.destroyed = false;
@@ -59,6 +73,8 @@ function undestroy() {
this._writableState.destroyed = false;
this._writableState.ended = false;
this._writableState.ending = false;
+ this._writableState.finalCalled = false;
+ this._writableState.prefinished = false;
this._writableState.finished = false;
this._writableState.errorEmitted = false;
}
diff --git a/lib/internal/streams/end-of-stream.js b/lib/internal/streams/end-of-stream.js
new file mode 100644
index 0000000000..b06dabdb93
--- /dev/null
+++ b/lib/internal/streams/end-of-stream.js
@@ -0,0 +1,99 @@
+// Ported from https://github.com/mafintosh/end-of-stream with
+// permission from the author, Mathias Buus (@mafintosh).
+
+'use strict';
+
+/**/
+
+var pna = require('process-nextick-args');
+/**/
+
+var ERR_STREAM_PREMATURE_CLOSE = require('../../../errors').codes.ERR_STREAM_PREMATURE_CLOSE;
+
+function noop() {}
+
+function isRequest(stream) {
+ return stream.setHeader && typeof stream.abort === 'function';
+}
+
+function once(callback) {
+ var called = false;
+ return function (err) {
+ if (called) return;
+ called = true;
+ callback.call(this, err);
+ };
+}
+
+function eos(stream, opts, callback) {
+ if (typeof opts === 'function') return eos(stream, null, opts);
+ if (!opts) opts = {};
+
+ callback = once(callback || noop);
+
+ var ws = stream._writableState;
+ var rs = stream._readableState;
+ var readable = opts.readable || opts.readable !== false && stream.readable;
+ var writable = opts.writable || opts.writable !== false && stream.writable;
+
+ var onlegacyfinish = function () {
+ if (!stream.writable) onfinish();
+ };
+
+ var onfinish = function () {
+ writable = false;
+ if (!readable) callback.call(stream);
+ };
+
+ var onend = function () {
+ readable = false;
+ if (!writable) callback.call(stream);
+ };
+
+ var onerror = function (err) {
+ callback.call(stream, err);
+ };
+
+ var onclose = function () {
+ if (readable && !(rs && rs.ended)) {
+ return callback.call(stream, new ERR_STREAM_PREMATURE_CLOSE());
+ }
+ if (writable && !(ws && ws.ended)) {
+ return callback.call(stream, new ERR_STREAM_PREMATURE_CLOSE());
+ }
+ };
+
+ var onrequest = function () {
+ stream.req.on('finish', onfinish);
+ };
+
+ if (isRequest(stream)) {
+ stream.on('complete', onfinish);
+ stream.on('abort', onclose);
+ if (stream.req) onrequest();else stream.on('request', onrequest);
+ } else if (writable && !ws) {
+ // legacy streams
+ stream.on('end', onlegacyfinish);
+ stream.on('close', onlegacyfinish);
+ }
+
+ stream.on('end', onend);
+ stream.on('finish', onfinish);
+ if (opts.error !== false) stream.on('error', onerror);
+ stream.on('close', onclose);
+
+ return function () {
+ stream.removeListener('complete', onfinish);
+ stream.removeListener('abort', onclose);
+ stream.removeListener('request', onrequest);
+ if (stream.req) stream.req.removeListener('finish', onfinish);
+ stream.removeListener('end', onlegacyfinish);
+ stream.removeListener('close', onlegacyfinish);
+ stream.removeListener('finish', onfinish);
+ stream.removeListener('end', onend);
+ stream.removeListener('error', onerror);
+ stream.removeListener('close', onclose);
+ };
+}
+
+module.exports = eos;
\ No newline at end of file
diff --git a/lib/internal/streams/pipeline.js b/lib/internal/streams/pipeline.js
new file mode 100644
index 0000000000..c23ce4e3a5
--- /dev/null
+++ b/lib/internal/streams/pipeline.js
@@ -0,0 +1,107 @@
+// Ported from https://github.com/mafintosh/pump with
+// permission from the author, Mathias Buus (@mafintosh).
+
+'use strict';
+
+/**/
+
+var pna = require('process-nextick-args');
+/**/
+
+var eos = void 0;
+
+var _require$codes = require('../../../errors').codes,
+ ERR_MISSING_ARGS = _require$codes.ERR_MISSING_ARGS,
+ ERR_STREAM_DESTROYED = _require$codes.ERR_STREAM_DESTROYED;
+
+function once(callback) {
+ var called = false;
+ return function (err) {
+ if (called) return;
+ called = true;
+ callback(err);
+ };
+}
+
+function noop(err) {
+ // Rethrow the error if it exists to avoid swallowing it
+ if (err) throw err;
+}
+
+function isRequest(stream) {
+ return stream.setHeader && typeof stream.abort === 'function';
+}
+
+function destroyer(stream, reading, writing, callback) {
+ callback = once(callback);
+
+ var closed = false;
+ stream.on('close', function () {
+ closed = true;
+ });
+
+ if (eos === undefined) eos = require('./end-of-stream');
+ eos(stream, { readable: reading, writable: writing }, function (err) {
+ if (err) return callback(err);
+ closed = true;
+ callback();
+ });
+
+ var destroyed = false;
+ return function (err) {
+ if (closed) return;
+ if (destroyed) return;
+ destroyed = true;
+
+ // request.destroy just do .end - .abort is what we want
+ if (isRequest(stream)) return stream.abort();
+ if (typeof stream.destroy === 'function') return stream.destroy();
+
+ callback(err || new ERR_STREAM_DESTROYED('pipe'));
+ };
+}
+
+function call(fn) {
+ fn();
+}
+
+function pipe(from, to) {
+ return from.pipe(to);
+}
+
+function popCallback(streams) {
+ if (!streams.length) return noop;
+ if (typeof streams[streams.length - 1] !== 'function') return noop;
+ return streams.pop();
+}
+
+function pipeline() {
+ for (var _len = arguments.length, streams = Array(_len), _key = 0; _key < _len; _key++) {
+ streams[_key] = arguments[_key];
+ }
+
+ var callback = popCallback(streams);
+
+ if (Array.isArray(streams[0])) streams = streams[0];
+
+ if (streams.length < 2) {
+ throw new ERR_MISSING_ARGS('streams');
+ }
+
+ var error = void 0;
+ var destroys = streams.map(function (stream, i) {
+ var reading = i < streams.length - 1;
+ var writing = i > 0;
+ return destroyer(stream, reading, writing, function (err) {
+ if (!error) error = err;
+ if (err) destroys.forEach(call);
+ if (reading) return;
+ destroys.forEach(call);
+ callback(error);
+ });
+ });
+
+ return streams.reduce(pipe);
+}
+
+module.exports = pipeline;
\ No newline at end of file
diff --git a/lib/internal/streams/state.js b/lib/internal/streams/state.js
new file mode 100644
index 0000000000..1632e883f8
--- /dev/null
+++ b/lib/internal/streams/state.js
@@ -0,0 +1,30 @@
+'use strict';
+
+/**/
+
+var pna = require('process-nextick-args');
+/**/
+
+var ERR_INVALID_OPT_VALUE = require('../../../errors').codes.ERR_INVALID_OPT_VALUE;
+
+function highWaterMarkFrom(options, isDuplex, duplexKey) {
+ return options.highWaterMark != null ? options.highWaterMark : isDuplex ? options[duplexKey] : null;
+}
+
+function getHighWaterMark(state, options, duplexKey, isDuplex) {
+ var hwm = highWaterMarkFrom(options, isDuplex, duplexKey);
+ if (hwm != null) {
+ if (!Number.isInteger(hwm) || hwm < 0) {
+ var name = isDuplex ? duplexKey : 'highWaterMark';
+ throw new ERR_INVALID_OPT_VALUE(name, hwm);
+ }
+ return Math.floor(hwm);
+ }
+
+ // Default value
+ return state.objectMode ? 16 : 16 * 1024;
+}
+
+module.exports = {
+ getHighWaterMark: getHighWaterMark
+};
\ No newline at end of file
diff --git a/package.json b/package.json
index dbb1da6be5..cd89cc438e 100644
--- a/package.json
+++ b/package.json
@@ -1,31 +1,57 @@
{
"name": "readable-stream",
- "version": "2.3.6",
+ "version": "3.0.0-rc.3",
"description": "Streams3, a user-land copy of the stream library from Node.js",
"main": "readable.js",
"dependencies": {
- "core-util-is": "~1.0.0",
- "inherits": "~2.0.3",
- "isarray": "~1.0.0",
- "process-nextick-args": "~2.0.0",
- "safe-buffer": "~5.1.1",
- "string_decoder": "~1.1.1",
- "util-deprecate": "~1.0.1"
+ "inherits": "^2.0.3",
+ "process-nextick-args": "^2.0.0",
+ "string_decoder": "^1.1.1",
+ "util-deprecate": "^1.0.1"
},
"devDependencies": {
+ "airtap": "0.0.9",
"assert": "^1.4.0",
+ "babel-cli": "^6.26.0",
+ "babel-core": "^6.26.3",
+ "babel-plugin-transform-async-generator-functions": "^6.24.1",
+ "babel-plugin-transform-async-to-generator": "^6.24.1",
+ "babel-plugin-transform-es2015-arrow-functions": "^6.5.2",
+ "babel-plugin-transform-es2015-block-scoping": "^6.26.0",
+ "babel-plugin-transform-es2015-classes": "^6.24.1",
+ "babel-plugin-transform-es2015-computed-properties": "^6.24.1",
+ "babel-plugin-transform-es2015-destructuring": "^6.18.0",
+ "babel-plugin-transform-es2015-for-of": "^6.8.0",
+ "babel-plugin-transform-es2015-parameters": "^6.24.1",
+ "babel-plugin-transform-es2015-shorthand-properties": "^6.24.1",
+ "babel-plugin-transform-es2015-spread": "^6.22.0",
+ "babel-plugin-transform-es2015-template-literals": "^6.8.0",
+ "babel-plugin-transform-inline-imports-commonjs": "^1.2.0",
"babel-polyfill": "^6.9.1",
- "buffer": "^4.9.0",
- "lolex": "^2.3.2",
- "nyc": "^6.4.0",
- "tap": "^0.7.0",
- "tape": "^4.8.0"
+ "babel-preset-env": "^1.7.0",
+ "bl": "^2.0.0",
+ "buffer": "^5.1.0",
+ "deep-strict-equal": "^0.2.0",
+ "glob": "^7.1.2",
+ "gunzip-maybe": "^1.4.1",
+ "hyperquest": "^2.1.3",
+ "lolex": "^2.6.0",
+ "nyc": "^11.0.0",
+ "pump": "^3.0.0",
+ "rimraf": "^2.6.2",
+ "tap": "^11.0.0",
+ "tape": "^4.9.0",
+ "tar-fs": "^1.16.2",
+ "util-promisify": "^2.1.0"
},
"scripts": {
- "test": "tap test/parallel/*.js test/ours/*.js && node test/verify-dependencies.js",
- "ci": "tap test/parallel/*.js test/ours/*.js --tap | tee test.tap && node test/verify-dependencies.js",
+ "test": "tap -j 4 test/parallel/*.js test/ours/*.js",
+ "ci": "TAP=1 tap test/parallel/*.js test/ours/*.js | tee test.tap",
+ "test-browsers": "airtap --sauce-connect --loopback airtap.local -- test/browser.js",
+ "test-browser-local": "airtap --local -- test/browser.js",
"cover": "nyc npm test",
- "report": "nyc report --reporter=lcov"
+ "report": "nyc report --reporter=lcov",
+ "update-browser-errors": "babel --presets env -o errors-browser.js errors.js"
},
"repository": {
"type": "git",
@@ -38,9 +64,9 @@
],
"browser": {
"util": false,
+ "worker_threads": false,
+ "./errors": "./errors-browser.js",
"./readable.js": "./readable-browser.js",
- "./writable.js": "./writable-browser.js",
- "./duplex.js": "./duplex-browser.js",
"./lib/internal/streams/stream.js": "./lib/internal/streams/stream-browser.js"
},
"nyc": {
diff --git a/passthrough.js b/passthrough.js
deleted file mode 100644
index ffd791d7ff..0000000000
--- a/passthrough.js
+++ /dev/null
@@ -1 +0,0 @@
-module.exports = require('./readable').PassThrough
diff --git a/readable.js b/readable.js
index ec89ec5330..aeec0df5b3 100644
--- a/readable.js
+++ b/readable.js
@@ -16,4 +16,6 @@ if (process.env.READABLE_STREAM === 'disable' && Stream) {
exports.Duplex = require('./lib/_stream_duplex.js');
exports.Transform = require('./lib/_stream_transform.js');
exports.PassThrough = require('./lib/_stream_passthrough.js');
+ exports.finished = require('./lib/internal/streams/end-of-stream.js');
+ exports.pipeline = require('./lib/internal/streams/pipeline.js');
}
diff --git a/test/browser.js b/test/browser.js
index a82c13ae34..a3504d63f7 100644
--- a/test/browser.js
+++ b/test/browser.js
@@ -11,6 +11,27 @@ if (!global.console.info) {
global.console.info = global.console.log;
}
var test = require('tape');
+var util = require('util');
+
+// TODO: add replacements instead
+if (!util.inspect) {
+ util.inspect = function () {};
+ util.inspect.custom = 'custom';
+}
+
+// TODO: add replacements instead
+global.process = {
+ env: {},
+ on: function () {},
+ cwd: function () {
+ return '/';
+ },
+ binding: function () {
+ return {
+ hasTracing: false
+ };
+ }
+};
test('streams', function (t) {
require('./browser/test-stream-big-packet')(t);
@@ -49,8 +70,8 @@ test('streams 2', function (t) {
require('./browser/test-stream2-pipe-error-once-listener')(t);
require('./browser/test-stream2-push')(t);
require('./browser/test-stream2-readable-empty-buffer-no-eof')(t);
- require('./browser/test-stream2-readable-from-list')(t);
- require('./browser/test-stream2-transform')(t);
+ // require('./browser/test-stream2-readable-from-list')(t);
+ // require('./browser/test-stream2-transform')(t);
require('./browser/test-stream2-set-encoding')(t);
require('./browser/test-stream2-readable-legacy-drain')(t);
require('./browser/test-stream2-readable-wrap-empty')(t);
diff --git a/test/common/README.md b/test/common/README.md
index 67e4e4e48f..943700ed71 100644
--- a/test/common/README.md
+++ b/test/common/README.md
@@ -2,19 +2,7 @@
require('babel-polyfill');
var util = require('util');
for (var i in util) exports[i] = util[i];
- /**//**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-# Node.js Core Test Common Modules
+ /**/# Node.js Core Test Common Modules
This directory contains modules used to test the Node.js implementation.
@@ -26,6 +14,10 @@ This directory contains modules used to test the Node.js implementation.
* [DNS module](#dns-module)
* [Duplex pair helper](#duplex-pair-helper)
* [Fixtures module](#fixtures-module)
+* [Heap dump checker module](#heap-dump-checker-module)
+* [HTTP2 module](#http2-module)
+* [Internet module](#internet-module)
+* [tmpdir module](#tmpdir-module)
* [WPT module](#wpt-module)
## Benchmark Module
@@ -34,7 +26,7 @@ The `benchmark` module is used by tests to run benchmarks.
### runBenchmark(name, args, env)
-* `name` [<String>] Name of benchmark suite to be run.
+* `name` [<string>] Name of benchmark suite to be run.
* `args` [<Array>] Array of environment variable key/value pairs (ex:
`n=1`) to be applied via `--set`.
* `env` [<Object>] Environment variables to be applied during the run.
@@ -54,12 +46,12 @@ Takes `whitelist` and concats that with predefined `knownGlobals`.
A stream to push an array into a REPL
### busyLoop(time)
-* `time` [<Number>]
+* `time` [<number>]
Blocks for `time` amount of time.
### canCreateSymLink()
-* return [<Boolean>]
+* return [<boolean>]
Checks whether the current running process can create symlinks. On Windows, this
returns `false` if the process running doesn't have privileges to create
@@ -67,20 +59,21 @@ symlinks
([SeCreateSymbolicLinkPrivilege](https://msdn.microsoft.com/en-us/library/windows/desktop/bb530716(v=vs.85).aspx)).
On non-Windows platforms, this always returns `true`.
-### crashOnUnhandledRejection()
-
-Installs a `process.on('unhandledRejection')` handler that crashes the process
-after a tick. This is useful for tests that use Promises and need to make sure
-no unexpected rejections occur, because currently they result in silent
-failures.
-
### ddCommand(filename, kilobytes)
* return [<Object>]
Platform normalizes the `dd` command
+### disableCrashOnUnhandledRejection()
+
+Removes the `process.on('unhandledRejection')` handler that crashes the process
+after a tick. The handler is useful for tests that use Promises and need to make
+sure no unexpected rejections occur, because currently they result in silent
+failures. However, it is useful in some rare cases to disable it, for example if
+the `unhandledRejection` hook is directly used by the test.
+
### enoughTestMem
-* [<Boolean>]
+* [<boolean>]
Indicates if there is more than 1gb of total memory.
@@ -89,17 +82,19 @@ Indicates if there is more than 1gb of total memory.
* `settings` [<Object>]
that must contain the `code` property plus any of the other following
properties (some properties only apply for `AssertionError`):
- * `code` [<String>]
+ * `code` [<string>]
expected error must have this value for its `code` property.
* `type` [<Function>]
expected error must be an instance of `type` and must be an Error subclass.
- * `message` [<String>] or [<RegExp>]
+ * `message` [<string>] or [<RegExp>]
if a string is provided for `message`, expected error must have it for its
`message` property; if a regular expression is provided for `message`, the
regular expression must match the `message` property of the expected error.
- * `name` [<String>]
+ * `name` [<string>]
expected error must have this value for its `name` property.
- * `generatedMessage` [<String>]
+ * `info` <Object> expected error must have the same `info` property
+ that is deeply equal to this value.
+ * `generatedMessage` [<string>]
(`AssertionError` only) expected error must have this value for its
`generatedMessage` property.
* `actual` <any>
@@ -111,7 +106,7 @@ Indicates if there is more than 1gb of total memory.
* `operator` <any>
(`AssertionError` only) expected error must have this value for its
`operator` property.
-* `exact` [<Number>] default = 1
+* `exact` [<number>] default = 1
* return [<Function>]
If `fn` is provided, it will be passed to `assert.throws` as first argument
@@ -121,15 +116,18 @@ Indicates if there is more than 1gb of total memory.
returned function has not been called exactly `exact` number of times when the
test is complete, then the test will fail.
-### expectWarning(name, expected)
-* `name` [<String>]
-* `expected` [<String>] | [<Array>]
+### expectWarning(name, expected, code)
+* `name` [<string>]
+* `expected` [<string>] | [<Array>]
+* `code` [<string>]
-Tests whether `name` and `expected` are part of a raised warning.
+Tests whether `name`, `expected`, and `code` are part of a raised warning. If
+an expected warning does not have a code then `common.noWarnCode` can be used
+to indicate this.
### fileExists(pathname)
-* pathname [<String>]
-* return [<Boolean>]
+* pathname [<string>]
+* return [<boolean>]
Checks if `pathname` exists
@@ -139,44 +137,52 @@ Checks if `pathname` exists
Returns an instance of all possible `ArrayBufferView`s of the provided Buffer.
+### getBufferSources(buf)
+* `buf` [<Buffer>]
+* return [<BufferSource[]>]
+
+Returns an instance of all possible `BufferSource`s of the provided Buffer,
+consisting of all `ArrayBufferView` and an `ArrayBuffer`.
+
### getCallSite(func)
* `func` [<Function>]
-* return [<String>]
+* return [<string>]
Returns the file name and line number for the provided Function.
-### globalCheck
-* [<Boolean>]
+### getTTYfd()
+
+Attempts to get a valid TTY file descriptor. Returns `-1` if it fails.
-Set to `false` if the test should not check for global leaks.
+The TTY file descriptor is assumed to be capable of being writable.
### hasCrypto
-* [<Boolean>]
+* [<boolean>]
Indicates whether OpenSSL is available.
### hasFipsCrypto
-* [<Boolean>]
+* [<boolean>]
Indicates `hasCrypto` and `crypto` with fips.
### hasIntl
-* [<Boolean>]
+* [<boolean>]
Indicates if [internationalization] is supported.
### hasSmallICU
-* [<Boolean>]
+* [<boolean>]
Indicates `hasIntl` and `small-icu` are supported.
### hasIPv6
-* [<Boolean>]
+* [<boolean>]
Indicates whether `IPv6` is supported on this platform.
### hasMultiLocalhost
-* [<Boolean>]
+* [<boolean>]
Indicates if there are multiple localhosts available.
@@ -199,63 +205,68 @@ be passed to `listener`. What's more, `process.stdout.writeTimes` is a count of
the number of calls.
### inFreeBSDJail
-* [<Boolean>]
+* [<boolean>]
Checks whether free BSD Jail is true or false.
### isAIX
-* [<Boolean>]
+* [<boolean>]
Platform check for Advanced Interactive eXecutive (AIX).
### isAlive(pid)
-* `pid` [<Number>]
-* return [<Boolean>]
+* `pid` [<number>]
+* return [<boolean>]
Attempts to 'kill' `pid`
### isFreeBSD
-* [<Boolean>]
+* [<boolean>]
Platform check for Free BSD.
### isLinux
-* [<Boolean>]
+* [<boolean>]
Platform check for Linux.
### isLinuxPPCBE
-* [<Boolean>]
+* [<boolean>]
Platform check for Linux on PowerPC.
### isOSX
-* [<Boolean>]
+* [<boolean>]
Platform check for macOS.
### isSunOS
-* [<Boolean>]
+* [<boolean>]
Platform check for SunOS.
### isWindows
-* [<Boolean>]
+* [<boolean>]
Platform check for Windows.
### isWOW64
-* [<Boolean>]
+* [<boolean>]
Platform check for Windows 32-bit on Windows 64-bit.
+### isCPPSymbolsNotMapped
+* [<boolean>]
+
+Platform check for C++ symbols are mapped or not.
+
### leakedGlobals()
* return [<Array>]
Indicates whether any globals are not on the `knownGlobals` list.
### localhostIPv4
-* [<String>]
+* [<string>]
IP of `localhost`.
@@ -266,7 +277,7 @@ Array of IPV6 representations for `localhost`.
### mustCall([fn][, exact])
* `fn` [<Function>] default = () => {}
-* `exact` [<Number>] default = 1
+* `exact` [<number>] default = 1
* return [<Function>]
Returns a function that calls `fn`. If the returned function has not been called
@@ -275,9 +286,20 @@ fail.
If `fn` is not provided, an empty function will be used.
+### mustCallAsync([fn][, exact])
+* `fn` [<Function>]
+* `exact` [<number>] default = 1
+* return [<Function>]
+
+The same as `mustCall()`, except that it is also checked that the Promise
+returned by the function is fulfilled for each invocation of the function.
+
+The return value of the wrapped function is the return value of the original
+function, if necessary wrapped as a promise.
+
### mustCallAtLeast([fn][, minimum])
* `fn` [<Function>] default = () => {}
-* `minimum` [<Number>] default = 1
+* `minimum` [<number>] default = 1
* return [<Function>]
Returns a function that calls `fn`. If the returned function has not been called
@@ -287,52 +309,65 @@ fail.
If `fn` is not provided, an empty function will be used.
### mustNotCall([msg])
-* `msg` [<String>] default = 'function should not have been called'
+* `msg` [<string>] default = 'function should not have been called'
* return [<Function>]
Returns a function that triggers an `AssertionError` if it is invoked. `msg` is
used as the error message for the `AssertionError`.
### nodeProcessAborted(exitCode, signal)
-* `exitCode` [<Number>]
-* `signal` [<String>]
-* return [<Boolean>]
+* `exitCode` [<number>]
+* `signal` [<string>]
+* return [<boolean>]
Returns `true` if the exit code `exitCode` and/or signal name `signal` represent
the exit code and/or signal name of a node process that aborted, `false`
otherwise.
+### noWarnCode
+See `common.expectWarning()` for usage.
+
+### onGC(target, listener)
+* `target` [<Object>]
+* `listener` [<Object>]
+ * `ongc` [<Function>]
+
+Installs a GC listener for the collection of `target`.
+
+This uses `async_hooks` for GC tracking. This means that it enables
+`async_hooks` tracking, which may affect the test functionality. It also
+means that between a `global.gc()` call and the listener being invoked
+a full `setImmediate()` invocation passes.
+
+`listener` is an object to make it easier to use a closure; the target object
+should not be in scope when `listener.ongc()` is created.
+
### opensslCli
-* [<Boolean>]
+* [<boolean>]
Indicates whether 'opensslCli' is supported.
### platformTimeout(ms)
-* `ms` [<Number>]
-* return [<Number>]
+* `ms` [<number>]
+* return [<number>]
Platform normalizes timeout.
### PIPE
-* [<String>]
+* [<string>]
Path to the test socket.
### PORT
-* [<Number>]
+* [<number>]
A port number for tests to use if one is needed.
### printSkipMessage(msg)
-* `msg` [<String>]
+* `msg` [<string>]
Logs '1..0 # Skipped: ' + `msg`
-### refreshTmpDir()
-* return [<String>]
-
-Deletes the testing 'tmp' directory and recreates it.
-
### restoreStderr()
Restore the original `process.stderr.write`. Used to restore `stderr` to its
@@ -344,17 +379,20 @@ Restore the original `process.stdout.write`. Used to restore `stdout` to its
original state after calling [`common.hijackStdOut()`][].
### rootDir
-* [<String>]
+* [<string>]
Path to the 'root' directory. either `/` or `c:\\` (windows)
-### projectDir
-* [<String>]
+### runWithInvalidFD(func)
+* `func` [<Function>]
-Path to the project directory.
+Runs `func` with an invalid file descriptor that is an unsigned integer and
+can be used to trigger `EBADF` as the first argument. If no such file
+descriptor could be generated, a skip message will be printed and the `func`
+will not be run.
### skip(msg)
-* `msg` [<String>]
+* `msg` [<string>]
Logs '1..0 # Skipped: ' + `msg` and exits with exit code `0`.
@@ -385,19 +423,14 @@ Platform normalizes the `pwd` command.
Synchronous version of `spawnPwd`.
-### tmpDir
-* [<String>]
-
-The realpath of the 'tmp' directory.
-
## Countdown Module
The `Countdown` module provides a simple countdown mechanism for tests that
require a particular action to be taken after a given number of completed
tasks (for instance, shutting down an HTTP server after a specific number of
-requests).
+requests). The Countdown will fail the test if the remainder did not reach 0.
-
+
```js
const Countdown = require('../common/countdown');
@@ -428,12 +461,30 @@ called before the callback is invoked.
## DNS Module
-The `DNS` module provides a naïve DNS parser/serializer.
+The `DNS` module provides utilities related to the `dns` built-in module.
+
+### errorLookupMock(code, syscall)
+
+* `code` [<string>] Defaults to `dns.mockedErrorCode`.
+* `syscall` [<string>] Defaults to `dns.mockedSysCall`.
+* return [<Function>]
+
+A mock for the `lookup` option of `net.connect()` that would result in an error
+with the `code` and the `syscall` specified. Returns a function that has the
+same signature as `dns.lookup()`.
+
+### mockedErrorCode
+
+The default `code` of errors generated by `errorLookupMock`.
+
+### mockedSysCall
+
+The default `syscall` of errors generated by `errorLookupMock`.
### readDomainFromPacket(buffer, offset)
* `buffer` [<Buffer>]
-* `offset` [<Number>]
+* `offset` [<number>]
* return [<Object>]
Reads the domain string from a packet and returns an object containing the
@@ -449,14 +500,14 @@ the packet depending on the type of packet.
### writeIPv6(ip)
-* `ip` [<String>]
+* `ip` [<string>]
* return [<Buffer>]
Reads an IPv6 String and returns a Buffer containing the parts.
### writeDomainName(domain)
-* `domain` [<String>]
+* `domain` [<string>]
* return [<Buffer>]
Reads a Domain String and returns a Buffer containing the domain.
@@ -484,30 +535,224 @@ files in the `test/fixtures` directory.
### fixtures.fixturesDir
-* [<String>]
+* [<string>]
The absolute path to the `test/fixtures/` directory.
### fixtures.path(...args)
-* `...args` [<String>]
+* `...args` [<string>]
Returns the result of `path.join(fixtures.fixturesDir, ...args)`.
### fixtures.readSync(args[, enc])
-* `args` [<String>] | [<Array>]
+* `args` [<string>] | [<Array>]
Returns the result of
`fs.readFileSync(path.join(fixtures.fixturesDir, ...args), 'enc')`.
### fixtures.readKey(arg[, enc])
-* `arg` [<String>]
+* `arg` [<string>]
Returns the result of
`fs.readFileSync(path.join(fixtures.fixturesDir, 'keys', arg), 'enc')`.
+## Heap dump checker module
+
+This provides utilities for checking the validity of heap dumps.
+This requires the usage of `--expose-internals`.
+
+### heap.recordState()
+
+Create a heap dump and an embedder graph copy for inspection.
+The returned object has a `validateSnapshotNodes` function similar to the
+one listed below. (`heap.validateSnapshotNodes(...)` is a shortcut for
+`heap.recordState().validateSnapshotNodes(...)`.)
+
+### heap.validateSnapshotNodes(name, expected, options)
+
+* `name` [<string>] Look for this string as the name of heap dump nodes.
+* `expected` [<Array>] A list of objects, possibly with an `children`
+ property that points to expected other adjacent nodes.
+* `options` [<Array>]
+ * `loose` [<boolean>] Do not expect an exact listing of occurrences
+ of nodes with name `name` in `expected`.
+
+Create a heap dump and an embedder graph copy and validate occurrences.
+
+
+```js
+validateSnapshotNodes('TLSWRAP', [
+ {
+ children: [
+ { name: 'enc_out' },
+ { name: 'enc_in' },
+ { name: 'TLSWrap' }
+ ]
+ }
+]);
+```
+
+## HTTP/2 Module
+
+The http2.js module provides a handful of utilities for creating mock HTTP/2
+frames for testing of HTTP/2 endpoints
+
+
+```js
+const http2 = require('../common/http2');
+```
+
+### Class: Frame
+
+The `http2.Frame` is a base class that creates a `Buffer` containing a
+serialized HTTP/2 frame header.
+
+
+```js
+// length is a 24-bit unsigned integer
+// type is an 8-bit unsigned integer identifying the frame type
+// flags is an 8-bit unsigned integer containing the flag bits
+// id is the 32-bit stream identifier, if any.
+const frame = new http2.Frame(length, type, flags, id);
+
+// Write the frame data to a socket
+socket.write(frame.data);
+```
+
+The serialized `Buffer` may be retrieved using the `frame.data` property.
+
+### Class: DataFrame extends Frame
+
+The `http2.DataFrame` is a subclass of `http2.Frame` that serializes a `DATA`
+frame.
+
+
+```js
+// id is the 32-bit stream identifier
+// payload is a Buffer containing the DATA payload
+// padlen is an 8-bit integer giving the number of padding bytes to include
+// final is a boolean indicating whether the End-of-stream flag should be set,
+// defaults to false.
+const frame = new http2.DataFrame(id, payload, padlen, final);
+
+socket.write(frame.data);
+```
+
+### Class: HeadersFrame
+
+The `http2.HeadersFrame` is a subclass of `http2.Frame` that serializes a
+`HEADERS` frame.
+
+
+```js
+// id is the 32-bit stream identifier
+// payload is a Buffer containing the HEADERS payload (see either
+// http2.kFakeRequestHeaders or http2.kFakeResponseHeaders).
+// padlen is an 8-bit integer giving the number of padding bytes to include
+// final is a boolean indicating whether the End-of-stream flag should be set,
+// defaults to false.
+const frame = new http2.HeadersFrame(id, payload, padlen, final);
+
+socket.write(frame.data);
+```
+
+### Class: SettingsFrame
+
+The `http2.SettingsFrame` is a subclass of `http2.Frame` that serializes an
+empty `SETTINGS` frame.
+
+
+```js
+// ack is a boolean indicating whether or not to set the ACK flag.
+const frame = new http2.SettingsFrame(ack);
+
+socket.write(frame.data);
+```
+
+### http2.kFakeRequestHeaders
+
+Set to a `Buffer` instance that contains a minimal set of serialized HTTP/2
+request headers to be used as the payload of a `http2.HeadersFrame`.
+
+
+```js
+const frame = new http2.HeadersFrame(1, http2.kFakeRequestHeaders, 0, true);
+
+socket.write(frame.data);
+```
+
+### http2.kFakeResponseHeaders
+
+Set to a `Buffer` instance that contains a minimal set of serialized HTTP/2
+response headers to be used as the payload a `http2.HeadersFrame`.
+
+
+```js
+const frame = new http2.HeadersFrame(1, http2.kFakeResponseHeaders, 0, true);
+
+socket.write(frame.data);
+```
+
+### http2.kClientMagic
+
+Set to a `Buffer` containing the preamble bytes an HTTP/2 client must send
+upon initial establishment of a connection.
+
+
+```js
+socket.write(http2.kClientMagic);
+```
+
+## Internet Module
+
+The `common/internet` module provides utilities for working with
+internet-related tests.
+
+### internet.addresses
+
+* [<Object>]
+ * `INET_HOST` [<string>] A generic host that has registered common
+ DNS records, supports both IPv4 and IPv6, and provides basic HTTP/HTTPS
+ services
+ * `INET4_HOST` [<string>] A host that provides IPv4 services
+ * `INET6_HOST` [<string>] A host that provides IPv6 services
+ * `INET4_IP` [<string>] An accessible IPv4 IP, defaults to the
+ Google Public DNS IPv4 address
+ * `INET6_IP` [<string>] An accessible IPv6 IP, defaults to the
+ Google Public DNS IPv6 address
+ * `INVALID_HOST` [<string>] An invalid host that cannot be resolved
+ * `MX_HOST` [<string>] A host with MX records registered
+ * `SRV_HOST` [<string>] A host with SRV records registered
+ * `PTR_HOST` [<string>] A host with PTR records registered
+ * `NAPTR_HOST` [<string>] A host with NAPTR records registered
+ * `SOA_HOST` [<string>] A host with SOA records registered
+ * `CNAME_HOST` [<string>] A host with CNAME records registered
+ * `NS_HOST` [<string>] A host with NS records registered
+ * `TXT_HOST` [<string>] A host with TXT records registered
+ * `DNS4_SERVER` [<string>] An accessible IPv4 DNS server
+ * `DNS6_SERVER` [<string>] An accessible IPv6 DNS server
+
+A set of addresses for internet-related tests. All properties are configurable
+via `NODE_TEST_*` environment variables. For example, to configure
+`internet.addresses.INET_HOST`, set the environment
+variable `NODE_TEST_INET_HOST` to a specified host.
+
+## tmpdir Module
+
+The `tmpdir` module supports the use of a temporary directory for testing.
+
+### path
+* [<string>]
+
+The realpath of the testing temporary directory.
+
+### refresh()
+
+Deletes and recreates the testing temporary directory.
+
## WPT Module
The wpt.js module is a port of parts of
@@ -517,15 +762,16 @@ Node.js
implementation with tests from
[W3C Web Platform Tests](https://github.com/w3c/web-platform-tests).
+
[<Array>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array
[<ArrayBufferView[]>]: https://developer.mozilla.org/en-US/docs/Web/API/ArrayBufferView
-[<Boolean>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#Boolean_type
[<Buffer>]: https://nodejs.org/api/buffer.html#buffer_class_buffer
[<Function>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function
-[<Number>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#Number_type
[<Object>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Object
[<RegExp>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp
-[<String>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#String_type
+[<boolean>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#Boolean_type
+[<number>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#Number_type
+[<string>]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Data_structures#String_type
[`common.hijackStdErr()`]: #hijackstderrlistener
[`common.hijackStdOut()`]: #hijackstdoutlistener
[internationalization]: https://github.com/nodejs/node/wiki/Intl
diff --git a/test/common/benchmark.js b/test/common/benchmark.js
index 555dc620f4..56ee8e5719 100644
--- a/test/common/benchmark.js
+++ b/test/common/benchmark.js
@@ -1,21 +1,11 @@
+'use strict';
+
/**/
require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
'use strict';
@@ -46,10 +36,24 @@ function runBenchmark(name, args, env) {
var mergedEnv = Object.assign({}, process.env, env);
- var child = fork(runjs, argv, { env: mergedEnv });
+ var child = fork(runjs, argv, { env: mergedEnv, stdio: 'pipe' });
+ child.stdout.setEncoding('utf8');
+
+ var stdout = '';
+ child.stdout.on('data', function (line) {
+ stdout += line;
+ });
+
child.on('exit', function (code, signal) {
assert.strictEqual(code, 0);
assert.strictEqual(signal, null);
+ // This bit makes sure that each benchmark file is being sent settings such
+ // that the benchmark file runs just one set of options. This helps keep the
+ // benchmark tests from taking a long time to run. Therefore, each benchmark
+ // file should result in three lines of output: a blank line, a line with
+ // the name of the benchmark file, and a line with the only results that we
+ // get from testing the benchmark file.
+ assert.ok(/^(?:\n.+?\n.+?\n)+$/.test(stdout), 'benchmark file not running exactly one configuration in test: ' + stdout);
});
}
diff --git a/test/common/countdown.js b/test/common/countdown.js
index 411fb69d2e..f09c35be1e 100644
--- a/test/common/countdown.js
+++ b/test/common/countdown.js
@@ -1,3 +1,5 @@
+'use strict';
+
var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
@@ -7,19 +9,8 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
+
'use strict';
/**/
@@ -34,6 +25,7 @@ var objectKeys = objectKeys || function (obj) {
var assert = require('assert');
var kLimit = Symbol('limit');
var kCallback = Symbol('callback');
+var common = require('./');
var Countdown = function () {
function Countdown(limit, cb) {
@@ -42,7 +34,7 @@ var Countdown = function () {
assert.strictEqual(typeof limit, 'number');
assert.strictEqual(typeof cb, 'function');
this[kLimit] = limit;
- this[kCallback] = cb;
+ this[kCallback] = common.mustCall(cb);
}
Countdown.prototype.dec = function dec() {
diff --git a/test/common/dns.js b/test/common/dns.js
index 388c8df83d..25aa816a6c 100644
--- a/test/common/dns.js
+++ b/test/common/dns.js
@@ -1,3 +1,5 @@
+'use strict';
+
var _slicedToArray = function () { function sliceIterator(arr, i) { var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"]) _i["return"](); } finally { if (_d) throw _e; } } return _arr; } return function (arr, i) { if (Array.isArray(arr)) { return arr; } else if (Symbol.iterator in Object(arr)) { return sliceIterator(arr, i); } else { throw new TypeError("Invalid attempt to destructure non-iterable instance"); } }; }();
/**/
@@ -5,19 +7,7 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
'use strict';
/**/
@@ -29,8 +19,6 @@ var objectKeys = objectKeys || function (obj) {
};
/**/
-// Naïve DNS parser/serializer.
-
var assert = require('assert');
var os = require('os');
@@ -50,6 +38,8 @@ var classes = {
IN: 1
};
+// Naïve DNS parser/serializer.
+
function readDomainFromPacket(buffer, offset) {
assert.ok(offset < buffer.length);
var length = buffer[offset];
@@ -409,7 +399,32 @@ function writeDNSPacket(parsed) {
}));
}
-module.exports = { types: types, classes: classes, writeDNSPacket: writeDNSPacket, parseDNSPacket: parseDNSPacket };
+var mockedErrorCode = 'ENOTFOUND';
+var mockedSysCall = 'getaddrinfo';
+
+function errorLookupMock() {
+ var code = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : mockedErrorCode;
+ var syscall = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : mockedSysCall;
+
+ return function lookupWithError(host, dnsopts, cb) {
+ var err = new Error(syscall + ' ' + code + ' ' + host);
+ err.code = code;
+ err.errno = code;
+ err.syscall = syscall;
+ err.hostname = host;
+ cb(err);
+ };
+}
+
+module.exports = {
+ types: types,
+ classes: classes,
+ writeDNSPacket: writeDNSPacket,
+ parseDNSPacket: parseDNSPacket,
+ errorLookupMock: errorLookupMock,
+ mockedErrorCode: mockedErrorCode,
+ mockedSysCall: mockedSysCall
+};
function forEach(xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
diff --git a/test/common/duplexpair.js b/test/common/duplexpair.js
index b4b9577e9c..bcd219274d 100644
--- a/test/common/duplexpair.js
+++ b/test/common/duplexpair.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -9,19 +11,7 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
'use strict';
/**/
diff --git a/test/common/fixtures.js b/test/common/fixtures.js
index 75f170d8c1..390bf20ba3 100644
--- a/test/common/fixtures.js
+++ b/test/common/fixtures.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
/**/
@@ -5,19 +7,7 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
'use strict';
/**/
diff --git a/test/common/heap.js b/test/common/heap.js
new file mode 100644
index 0000000000..5d7c8f4be1
--- /dev/null
+++ b/test/common/heap.js
@@ -0,0 +1,206 @@
+'use strict';
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/ /* eslint-disable node-core/required-modules */
+'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+var assert = require('assert');
+
+/**/
+var util = require('core-util-is');
+util.inherits = require('inherits');
+/**/
+
+var internalTestHeap = void 0;
+try {
+ internalTestHeap = require('internal/test/heap');
+} catch (e) {
+ console.log('using `test/common/heap.js` requires `--expose-internals`');
+ throw e;
+}
+var _internalTestHeap = internalTestHeap,
+ createJSHeapDump = _internalTestHeap.createJSHeapDump,
+ buildEmbedderGraph = _internalTestHeap.buildEmbedderGraph;
+
+var State = function () {
+ function State() {
+ _classCallCheck(this, State);
+
+ this.snapshot = createJSHeapDump();
+ this.embedderGraph = buildEmbedderGraph();
+ }
+
+ State.prototype.validateSnapshotNodes = function validateSnapshotNodes(name, expected) {
+ var _ref = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : {},
+ _ref$loose = _ref.loose,
+ loose = _ref$loose === undefined ? false : _ref$loose;
+
+ var snapshot = this.snapshot.filter(function (node) {
+ return node.name === 'Node / ' + name && node.type !== 'string';
+ });
+ if (loose) assert(snapshot.length >= expected.length);else assert.strictEqual(snapshot.length, expected.length);
+ var _iteratorNormalCompletion = true;
+ var _didIteratorError = false;
+ var _iteratorError = undefined;
+
+ try {
+ for (var _iterator = expected[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
+ var expectedNode = _step.value;
+
+ if (expectedNode.children) {
+ var _loop = function (expectedChild) {
+ var check = typeof expectedChild === 'function' ? expectedChild : function (node) {
+ return [expectedChild.name, 'Node / ' + expectedChild.name].includes(node.name);
+ };
+
+ assert(snapshot.some(function (node) {
+ return node.outgoingEdges.map(function (edge) {
+ return edge.toNode;
+ }).some(check);
+ }), 'expected to find child ' + util.inspect(expectedChild) + ' ' + ('in ' + util.inspect(snapshot)));
+ };
+
+ var _iteratorNormalCompletion3 = true;
+ var _didIteratorError3 = false;
+ var _iteratorError3 = undefined;
+
+ try {
+ for (var _iterator3 = expectedNode.children[Symbol.iterator](), _step3; !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
+ var expectedChild = _step3.value;
+
+ _loop(expectedChild);
+ }
+ } catch (err) {
+ _didIteratorError3 = true;
+ _iteratorError3 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion3 && _iterator3.return) {
+ _iterator3.return();
+ }
+ } finally {
+ if (_didIteratorError3) {
+ throw _iteratorError3;
+ }
+ }
+ }
+ }
+ }
+ } catch (err) {
+ _didIteratorError = true;
+ _iteratorError = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion && _iterator.return) {
+ _iterator.return();
+ }
+ } finally {
+ if (_didIteratorError) {
+ throw _iteratorError;
+ }
+ }
+ }
+
+ var graph = this.embedderGraph.filter(function (node) {
+ return node.name === name;
+ });
+ if (loose) assert(graph.length >= expected.length);else assert.strictEqual(graph.length, expected.length);
+ var _iteratorNormalCompletion2 = true;
+ var _didIteratorError2 = false;
+ var _iteratorError2 = undefined;
+
+ try {
+ for (var _iterator2 = expected[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
+ var _expectedNode = _step2.value;
+
+ if (_expectedNode.edges) {
+ var _loop2 = function (_expectedChild) {
+ var check = typeof _expectedChild === 'function' ? _expectedChild : function (node) {
+ return node.name === _expectedChild.name || node.value && node.value.constructor && node.value.constructor.name === _expectedChild.name;
+ };
+
+ assert(graph.some(function (node) {
+ return node.edges.some(check);
+ }), 'expected to find child ' + util.inspect(_expectedChild) + ' ' + ('in ' + util.inspect(snapshot)));
+ };
+
+ var _iteratorNormalCompletion4 = true;
+ var _didIteratorError4 = false;
+ var _iteratorError4 = undefined;
+
+ try {
+ for (var _iterator4 = _expectedNode.children[Symbol.iterator](), _step4; !(_iteratorNormalCompletion4 = (_step4 = _iterator4.next()).done); _iteratorNormalCompletion4 = true) {
+ var _expectedChild = _step4.value;
+
+ _loop2(_expectedChild);
+ }
+ } catch (err) {
+ _didIteratorError4 = true;
+ _iteratorError4 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion4 && _iterator4.return) {
+ _iterator4.return();
+ }
+ } finally {
+ if (_didIteratorError4) {
+ throw _iteratorError4;
+ }
+ }
+ }
+ }
+ }
+ } catch (err) {
+ _didIteratorError2 = true;
+ _iteratorError2 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion2 && _iterator2.return) {
+ _iterator2.return();
+ }
+ } finally {
+ if (_didIteratorError2) {
+ throw _iteratorError2;
+ }
+ }
+ }
+ };
+
+ return State;
+}();
+
+function recordState() {
+ return new State();
+}
+
+function validateSnapshotNodes() {
+ var _recordState;
+
+ return (_recordState = recordState()).validateSnapshotNodes.apply(_recordState, arguments);
+}
+
+module.exports = {
+ recordState: recordState,
+ validateSnapshotNodes: validateSnapshotNodes
+};
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/http2.js b/test/common/http2.js
new file mode 100644
index 0000000000..1327800fdf
--- /dev/null
+++ b/test/common/http2.js
@@ -0,0 +1,227 @@
+'use strict';
+
+var _createClass = function () { function defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } } return function (Constructor, protoProps, staticProps) { if (protoProps) defineProperties(Constructor.prototype, protoProps); if (staticProps) defineProperties(Constructor, staticProps); return Constructor; }; }();
+
+function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
+
+function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/ /* eslint-disable node-core/required-modules */
+'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+// An HTTP/2 testing tool used to create mock frames for direct testing
+// of HTTP/2 endpoints.
+
+var kFrameData = Symbol('frame-data');
+var FLAG_EOS = 0x1;
+var FLAG_ACK = 0x1;
+var FLAG_EOH = 0x4;
+var FLAG_PADDED = 0x8;
+var PADDING = Buffer.alloc(255);
+
+var kClientMagic = Buffer.from('505249202a20485454502f322' + 'e300d0a0d0a534d0d0a0d0a', 'hex');
+
+var kFakeRequestHeaders = Buffer.from('828684410f7777772e65' + '78616d706c652e636f6d', 'hex');
+
+var kFakeResponseHeaders = Buffer.from('4803333032580770726976617465611d' + '4d6f6e2c203231204f63742032303133' + '2032303a31333a323120474d546e1768' + '747470733a2f2f7777772e6578616d70' + '6c652e636f6d', 'hex');
+
+function isUint32(val) {
+ return val >>> 0 === val;
+}
+
+function isUint24(val) {
+ return val >>> 0 === val && val <= 0xFFFFFF;
+}
+
+function isUint8(val) {
+ return val >>> 0 === val && val <= 0xFF;
+}
+
+function write32BE(array, pos, val) {
+ if (!isUint32(val)) throw new RangeError('val is not a 32-bit number');
+ array[pos++] = val >> 24 & 0xff;
+ array[pos++] = val >> 16 & 0xff;
+ array[pos++] = val >> 8 & 0xff;
+ array[pos++] = val & 0xff;
+}
+
+function write24BE(array, pos, val) {
+ if (!isUint24(val)) throw new RangeError('val is not a 24-bit number');
+ array[pos++] = val >> 16 & 0xff;
+ array[pos++] = val >> 8 & 0xff;
+ array[pos++] = val & 0xff;
+}
+
+function write8(array, pos, val) {
+ if (!isUint8(val)) throw new RangeError('val is not an 8-bit number');
+ array[pos] = val;
+}
+
+var Frame = function () {
+ function Frame(length, type, flags, id) {
+ _classCallCheck(this, Frame);
+
+ this[kFrameData] = Buffer.alloc(9);
+ write24BE(this[kFrameData], 0, length);
+ write8(this[kFrameData], 3, type);
+ write8(this[kFrameData], 4, flags);
+ write32BE(this[kFrameData], 5, id);
+ }
+
+ _createClass(Frame, [{
+ key: 'data',
+ get: function () {
+ return this[kFrameData];
+ }
+ }]);
+
+ return Frame;
+}();
+
+var SettingsFrame = function (_Frame) {
+ _inherits(SettingsFrame, _Frame);
+
+ function SettingsFrame() {
+ var ack = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;
+
+ _classCallCheck(this, SettingsFrame);
+
+ var flags = 0;
+ if (ack) flags |= FLAG_ACK;
+ return _possibleConstructorReturn(this, _Frame.call(this, 0, 4, flags, 0));
+ }
+
+ return SettingsFrame;
+}(Frame);
+
+var DataFrame = function (_Frame2) {
+ _inherits(DataFrame, _Frame2);
+
+ function DataFrame(id, payload) {
+ var padlen = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
+ var final = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : false;
+
+ _classCallCheck(this, DataFrame);
+
+ var len = payload.length;
+ var flags = 0;
+ if (final) flags |= FLAG_EOS;
+ var buffers = [payload];
+ if (padlen > 0) {
+ buffers.unshift(Buffer.from([padlen]));
+ buffers.push(PADDING.slice(0, padlen));
+ len += padlen + 1;
+ flags |= FLAG_PADDED;
+ }
+
+ var _this2 = _possibleConstructorReturn(this, _Frame2.call(this, len, 0, flags, id));
+
+ buffers.unshift(_this2[kFrameData]);
+ _this2[kFrameData] = Buffer.concat(buffers);
+ return _this2;
+ }
+
+ return DataFrame;
+}(Frame);
+
+var HeadersFrame = function (_Frame3) {
+ _inherits(HeadersFrame, _Frame3);
+
+ function HeadersFrame(id, payload) {
+ var padlen = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
+ var final = arguments.length > 3 && arguments[3] !== undefined ? arguments[3] : false;
+
+ _classCallCheck(this, HeadersFrame);
+
+ var len = payload.length;
+ var flags = FLAG_EOH;
+ if (final) flags |= FLAG_EOS;
+ var buffers = [payload];
+ if (padlen > 0) {
+ buffers.unshift(Buffer.from([padlen]));
+ buffers.push(PADDING.slice(0, padlen));
+ len += padlen + 1;
+ flags |= FLAG_PADDED;
+ }
+
+ var _this3 = _possibleConstructorReturn(this, _Frame3.call(this, len, 1, flags, id));
+
+ buffers.unshift(_this3[kFrameData]);
+ _this3[kFrameData] = Buffer.concat(buffers);
+ return _this3;
+ }
+
+ return HeadersFrame;
+}(Frame);
+
+var PingFrame = function (_Frame4) {
+ _inherits(PingFrame, _Frame4);
+
+ function PingFrame() {
+ var ack = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : false;
+
+ _classCallCheck(this, PingFrame);
+
+ var buffers = [Buffer.alloc(8)];
+
+ var _this4 = _possibleConstructorReturn(this, _Frame4.call(this, 8, 6, ack ? 1 : 0, 0));
+
+ buffers.unshift(_this4[kFrameData]);
+ _this4[kFrameData] = Buffer.concat(buffers);
+ return _this4;
+ }
+
+ return PingFrame;
+}(Frame);
+
+var AltSvcFrame = function (_Frame5) {
+ _inherits(AltSvcFrame, _Frame5);
+
+ function AltSvcFrame(size) {
+ _classCallCheck(this, AltSvcFrame);
+
+ var buffers = [Buffer.alloc(size)];
+
+ var _this5 = _possibleConstructorReturn(this, _Frame5.call(this, size, 10, 0, 0));
+
+ buffers.unshift(_this5[kFrameData]);
+ _this5[kFrameData] = Buffer.concat(buffers);
+ return _this5;
+ }
+
+ return AltSvcFrame;
+}(Frame);
+
+module.exports = {
+ Frame: Frame,
+ AltSvcFrame: AltSvcFrame,
+ DataFrame: DataFrame,
+ HeadersFrame: HeadersFrame,
+ SettingsFrame: SettingsFrame,
+ PingFrame: PingFrame,
+ kFakeRequestHeaders: kFakeRequestHeaders,
+ kFakeResponseHeaders: kFakeResponseHeaders,
+ kClientMagic: kClientMagic
+};
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/index.js b/test/common/index.js
index 33fa11e8d6..67d596414c 100644
--- a/test/common/index.js
+++ b/test/common/index.js
@@ -1,3 +1,7 @@
+'use strict';
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
function _defineProperty(obj, key, value) { if (key in obj) { Object.defineProperty(obj, key, { value: value, enumerable: true, configurable: true, writable: true }); } else { obj[key] = value; } return obj; }
function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
@@ -7,19 +11,7 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-// Copyright Joyent, Inc. and other Node contributors.
+} /**/ // Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
// copy of this software and associated documentation files (the
@@ -40,7 +32,7 @@ if (!global.clearImmediate) {
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
// USE OR OTHER DEALINGS IN THE SOFTWARE.
-/* eslint-disable required-modules, crypto-check */
+/* eslint-disable node-core/required-modules, node-core/crypto-check */
'use strict';
/**/
@@ -52,6 +44,7 @@ var objectKeys = objectKeys || function (obj) {
};
/**/
+var process = global.process; // Some tests tamper with the process global.
var path = require('path');
var fs = require('fs');
var assert = require('assert');
@@ -72,64 +65,89 @@ util.inherits = require('inherits');
var Timer = { now: function () {} };
+var _process$binding = process.binding('config'),
+ hasTracing = _process$binding.hasTracing;
+
var _require2 = require('./fixtures'),
fixturesDir = _require2.fixturesDir;
-var testRoot = process.env.NODE_TEST_DIR ? fs.realpathSync(process.env.NODE_TEST_DIR) : path.resolve(__dirname, '..');
+var tmpdir = require('./tmpdir');
var noop = function () {};
-// Using a `.` prefixed name, which is the convention for "hidden" on POSIX,
-// gets tools to ignore it by default or by simple rules, especially eslint.
-var tmpDirName = '.tmp';
-// PORT should match the definition in test/testpy/__init__.py.
-exports.PORT = +process.env.NODE_COMMON_PORT || 12346;
+/**/if (!process.browser) {
+ Object.defineProperty(exports, 'PORT', {
+ get: function () {
+ if (+process.env.TEST_PARALLEL) {
+ throw new Error('common.PORT cannot be used in a parallelized test');
+ }
+ return +process.env.NODE_COMMON_PORT || 12346;
+ },
+ enumerable: true
+ });
+} /**/
+
+exports.isMainThread = function () {
+ try {
+ return require('worker_threads').isMainThread;
+ } catch (_e) {
+ // Worker module not enabled → only a single main thread exists.
+ return true;
+ }
+}();
+
exports.isWindows = process.platform === 'win32';
exports.isWOW64 = exports.isWindows && process.env.PROCESSOR_ARCHITEW6432 !== undefined;
exports.isAIX = process.platform === 'aix';
exports.isLinuxPPCBE = process.platform === 'linux' && process.arch === 'ppc64' && os.endianness() === 'BE';
exports.isSunOS = process.platform === 'sunos';
exports.isFreeBSD = process.platform === 'freebsd';
+exports.isOpenBSD = process.platform === 'openbsd';
exports.isLinux = process.platform === 'linux';
exports.isOSX = process.platform === 'darwin';
+var isGlibc = void 0;
+exports.isGlibc = function () {
+ if (isGlibc !== undefined) return isGlibc;
+ try {
+ var lddOut = spawnSync('ldd', [process.execPath]).stdout;
+ var libcInfo = lddOut.toString().split('\n').map(function (line) {
+ return line.match(/libc\.so.+=>\s*(\S+)\s/);
+ }).filter(function (info) {
+ return info;
+ });
+ if (libcInfo.length === 0) return isGlibc = false;
+ var nmOut = spawnSync('nm', ['-D', libcInfo[0][1]]).stdout;
+ if (/gnu_get_libc_version/.test(nmOut)) return isGlibc = true;
+ } catch (_e) {}
+ return isGlibc = false;
+};
+
exports.enoughTestMem = os.totalmem() > 0x70000000; /* 1.75 Gb */
var cpus = os.cpus();
/*exports.enoughTestCpu = Array.isArray(cpus) &&
(cpus.length > 1 || cpus[0].speed > 999);*/
exports.rootDir = exports.isWindows ? 'c:\\' : '/';
-exports.projectDir = path.resolve(__dirname, '..', '..');
//exports.buildType = process.config.target_defaults.default_configuration;
-// Always enable async_hooks checks in tests
-{
- // const async_wrap = process.binding('async_wrap');
- // const kCheck = async_wrap.constants.kCheck;
- // async_wrap.async_hook_fields[kCheck] += 1;
-
- exports.revert_force_async_hooks_checks = function () {
- async_wrap.async_hook_fields[kCheck] -= 1;
- };
-}
-
// If env var is set then enable async_hook hooks for all tests.
if (process.env.NODE_TEST_WITH_ASYNC_HOOKS) {
var destroydIdsList = {};
var destroyListList = {};
var initHandles = {};
- var _async_wrap = process.binding('async_wrap');
+ var async_wrap = process.binding('async_wrap');
process.on('exit', function () {
- // itterate through handles to make sure nothing crashes
+ // iterate through handles to make sure nothing crashes
for (var k in initHandles) {
util.inspect(initHandles[k]);
}
});
- var _queueDestroyAsyncId = _async_wrap.queueDestroyAsyncId;
- _async_wrap.queueDestroyAsyncId = function queueDestroyAsyncId(id) {
+ var _queueDestroyAsyncId = async_wrap.queueDestroyAsyncId;
+ async_wrap.queueDestroyAsyncId = function queueDestroyAsyncId(id) {
if (destroyListList[id] !== undefined) {
process._rawDebug(destroyListList[id]);
process._rawDebug();
@@ -162,55 +180,6 @@ if (process.env.NODE_TEST_WITH_ASYNC_HOOKS) {
}).enable();*/
}
-function rimrafSync(p) {
- var st = void 0;
- try {
- st = fs.lstatSync(p);
- } catch (e) {
- if (e.code === 'ENOENT') return;
- }
-
- try {
- if (st && st.isDirectory()) rmdirSync(p, null);else fs.unlinkSync(p);
- } catch (e) {
- if (e.code === 'ENOENT') return;
- if (e.code === 'EPERM') return rmdirSync(p, e);
- if (e.code !== 'EISDIR') throw e;
- rmdirSync(p, e);
- }
-}
-
-function rmdirSync(p, originalEr) {
- try {
- fs.rmdirSync(p);
- } catch (e) {
- if (e.code === 'ENOTDIR') throw originalEr;
- if (e.code === 'ENOTEMPTY' || e.code === 'EEXIST' || e.code === 'EPERM') {
- var enc = exports.isLinux ? 'buffer' : 'utf8';
- forEach(fs.readdirSync(p, enc), function (f) {
- if (f instanceof Buffer) {
- var buf = Buffer.concat([Buffer.from(p), Buffer.from(path.sep), f]);
- rimrafSync(buf);
- } else {
- rimrafSync(path.join(p, f));
- }
- });
- fs.rmdirSync(p);
- }
- }
-}
-
-exports.refreshTmpDir = function () {
- rimrafSync(exports.tmpDir);
- fs.mkdirSync(exports.tmpDir);
-};
-
-if (process.env.TEST_THREAD_ID) {
- exports.PORT += process.env.TEST_THREAD_ID * 100;
- tmpDirName += '.' + process.env.TEST_THREAD_ID;
-}
-exports.tmpDir = path.join(testRoot, tmpDirName);
-
var opensslCli = null;
var inFreeBSDJail = null;
var localhostIPv4 = null;
@@ -298,6 +267,14 @@ if (exports.isLinux) {
});
} /**/
+/**/if (!process.browser) {
+ Object.defineProperty(exports, 'hasTracing', {
+ get: function () {
+ return Boolean(hasTracing);
+ }
+ });
+} /**/
+
/**/if (!process.browser) {
Object.defineProperty(exports, 'hasFipsCrypto', {
get: function () {
@@ -307,7 +284,7 @@ if (exports.isLinux) {
} /**/
{
- var localRelative = path.relative(process.cwd(), exports.tmpDir + '/');
+ var localRelative = path.relative(process.cwd(), tmpdir.path + '/');
var pipePrefix = exports.isWindows ? '\\\\.\\pipe\\' : localRelative;
var pipeName = 'node-test.' + process.pid + '.sock';
exports.PIPE = path.join(pipePrefix, pipeName);
@@ -387,8 +364,7 @@ exports.platformTimeout = function (ms) {
return ms; // ARMv8+
};
-var knownGlobals = [Buffer, clearImmediate, clearInterval, clearTimeout, console, constructor, // Enumerable in V8 3.21.
-global, process, setImmediate, setInterval, setTimeout];
+var knownGlobals = [Buffer, clearImmediate, clearInterval, clearTimeout, global, process, setImmediate, setInterval, setTimeout];
if (global.gc) {
knownGlobals.push(global.gc);
@@ -412,40 +388,6 @@ if (global.COUNTER_NET_SERVER_CONNECTION) {
knownGlobals.push(COUNTER_HTTP_CLIENT_RESPONSE);
}
-if (global.LTTNG_HTTP_SERVER_RESPONSE) {
- knownGlobals.push(LTTNG_HTTP_SERVER_RESPONSE);
- knownGlobals.push(LTTNG_HTTP_SERVER_REQUEST);
- knownGlobals.push(LTTNG_HTTP_CLIENT_RESPONSE);
- knownGlobals.push(LTTNG_HTTP_CLIENT_REQUEST);
- knownGlobals.push(LTTNG_NET_STREAM_END);
- knownGlobals.push(LTTNG_NET_SERVER_CONNECTION);
-}
-
-/**/if (!process.browser) {
- if (global.ArrayBuffer) {
- knownGlobals.push(ArrayBuffer);
- knownGlobals.push(Int8Array);
- knownGlobals.push(Uint8Array);
- knownGlobals.push(Uint8ClampedArray);
- knownGlobals.push(Int16Array);
- knownGlobals.push(Uint16Array);
- knownGlobals.push(Int32Array);
- knownGlobals.push(Uint32Array);
- knownGlobals.push(Float32Array);
- knownGlobals.push(Float64Array);
- knownGlobals.push(DataView);
- }
-} /**/
-
-// Harmony features.
-if (global.Proxy) {
- knownGlobals.push(Proxy);
-}
-
-if (global.Symbol) {
- knownGlobals.push(Symbol);
-}
-
if (process.env.NODE_TEST_KNOWN_GLOBALS) {
var knownFromEnv = process.env.NODE_TEST_KNOWN_GLOBALS.split(',');
allowGlobals.apply(undefined, _toConsumableArray(knownFromEnv));
@@ -465,7 +407,7 @@ if (typeof constructor == 'function') knownGlobals.push(constructor);
if (typeof DTRACE_NET_SOCKET_READ == 'function') knownGlobals.push(DTRACE_NET_SOCKET_READ);
if (typeof DTRACE_NET_SOCKET_WRITE == 'function') knownGlobals.push(DTRACE_NET_SOCKET_WRITE);
if (global.__coverage__) knownGlobals.push(__coverage__);
-'core,__core-js_shared__,Promise,Map,Set,WeakMap,WeakSet,Reflect,System,asap,Observable,regeneratorRuntime,_babelPolyfill'.split(',').filter(function (item) {
+'console,clearImmediate,setImmediate,core,__core-js_shared__,Promise,Map,Set,WeakMap,WeakSet,Reflect,System,asap,Observable,regeneratorRuntime,_babelPolyfill'.split(',').filter(function (item) {
return typeof global[item] !== undefined;
}).forEach(function (item) {
knownGlobals.push(global[item]);
@@ -490,11 +432,7 @@ function leakedGlobals() {
}
exports.leakedGlobals = leakedGlobals;
-// Turn this off if the test should not check for global leaks.
-exports.globalCheck = true;
-
process.on('exit', function () {
- if (!exports.globalCheck) return;
var leaked = leakedGlobals();
if (leaked.length > 0) {
assert.fail('Unexpected global(s) found: ' + leaked.join(', '));
@@ -532,6 +470,14 @@ exports.mustCallAtLeast = function (fn, minimum) {
return _mustCallInner(fn, minimum, 'minimum');
};
+exports.mustCallAsync = function (fn, exact) {
+ return exports.mustCall(function () {
+ return Promise.resolve(fn.apply(undefined, arguments)).then(exports.mustCall(function (val) {
+ return val;
+ }));
+ }, exact);
+};
+
function _mustCallInner(fn) {
var _context;
@@ -562,9 +508,9 @@ function _mustCallInner(fn) {
}
exports.hasMultiLocalhost = function hasMultiLocalhost() {
- var _process$binding = process.binding('tcp_wrap'),
- TCP = _process$binding.TCP,
- TCPConstants = _process$binding.constants;
+ var _process$binding2 = process.binding('tcp_wrap'),
+ TCP = _process$binding2.TCP,
+ TCPConstants = _process$binding2.constants;
var t = new TCP(TCPConstants.SOCKET);
var ret = t.bind('127.0.0.2', 0);
@@ -582,7 +528,7 @@ exports.fileExists = function (pathname) {
};
exports.skipIfEslintMissing = function () {
- if (!exports.fileExists(path.join('..', '..', 'tools', 'node_modules', 'eslint'))) {
+ if (!exports.fileExists(path.join(__dirname, '..', '..', 'tools', 'node_modules', 'eslint'))) {
exports.skip('missing ESLint');
}
};
@@ -595,22 +541,16 @@ exports.canCreateSymLink = function () {
// whoami.exe needs to be the one from System32
// If unix tools are in the path, they can shadow the one we want,
// so use the full path while executing whoami
- var whoamiPath = path.join(process.env['SystemRoot'], 'System32', 'whoami.exe');
-
- var err = false;
- var output = '';
+ var whoamiPath = path.join(process.env.SystemRoot, 'System32', 'whoami.exe');
try {
- output = execSync(whoamiPath + ' /priv', { timout: 1000 });
+ var output = execSync(whoamiPath + ' /priv', { timout: 1000 });
+ return output.includes('SeCreateSymbolicLinkPrivilege');
} catch (e) {
- err = true;
- } finally {
- if (err || !output.includes('SeCreateSymbolicLinkPrivilege')) {
- return false;
- }
+ return false;
}
}
-
+ // On non-Windows platforms, this always returns `true`
return true;
};
@@ -680,9 +620,9 @@ exports.nodeProcessAborted = function nodeProcessAborted(exitCode, signal) {
// On Windows, 'aborts' are of 2 types, depending on the context:
// (i) Forced access violation, if --abort-on-uncaught-exception is on
// which corresponds to exit code 3221225477 (0xC0000005)
- // (ii) raise(SIGABRT) or abort(), which lands up in CRT library calls
- // which corresponds to exit code 3.
- if (exports.isWindows) expectedExitCodes = [3221225477, 3];
+ // (ii) Otherwise, _exit(134) which is called in place of abort() due to
+ // raising SIGABRT exiting with ambiguous exit code '3' by default
+ if (exports.isWindows) expectedExitCodes = [0xC0000005, 134];
// When using --abort-on-uncaught-exception, V8 will use
// base::OS::Abort to terminate the process.
@@ -713,19 +653,24 @@ exports.isAlive = function isAlive(pid) {
}
};
-function expectWarning(name, expectedMessages) {
+exports.noWarnCode = undefined;
+
+function expectWarning(name, expected) {
+ var map = new Map(expected);
return exports.mustCall(function (warning) {
assert.strictEqual(warning.name, name);
- assert.ok(expectedMessages.includes(warning.message), 'unexpected error message: "' + warning.message + '"');
+ assert.ok(map.has(warning.message), 'unexpected error message: "' + warning.message + '"');
+ var code = map.get(warning.message);
+ assert.strictEqual(warning.code, code);
// Remove a warning message after it is seen so that we guarantee that we
// get each message only once.
- expectedMessages.splice(expectedMessages.indexOf(warning.message), 1);
- }, expectedMessages.length);
+ map.delete(expected);
+ }, expected.length);
}
-function expectWarningByName(name, expected) {
+function expectWarningByName(name, expected, code) {
if (typeof expected === 'string') {
- expected = [expected];
+ expected = [[expected, code]];
}
process.on('warning', expectWarning(name, expected));
}
@@ -734,8 +679,14 @@ function expectWarningByMap(warningMap) {
var catchWarning = {};
forEach(objectKeys(warningMap), function (name) {
var expected = warningMap[name];
- if (typeof expected === 'string') {
- expected = [expected];
+ if (!Array.isArray(expected)) {
+ throw new Error('warningMap entries must be arrays consisting of two ' + 'entries: [message, warningCode]');
+ }
+ if (!Array.isArray(expected[0])) {
+ if (expected.length === 0) {
+ return;
+ }
+ expected = [[expected[0], expected[1]]];
}
catchWarning[name] = expectWarning(name, expected);
});
@@ -747,9 +698,9 @@ function expectWarningByMap(warningMap) {
// accepts a warning name and description or array of descriptions or a map
// of warning names to description(s)
// ensures a warning is generated for each name/description pair
-exports.expectWarning = function (nameOrMap, expected) {
+exports.expectWarning = function (nameOrMap, expected, code) {
if (typeof nameOrMap === 'string') {
- expectWarningByName(nameOrMap, expected);
+ expectWarningByName(nameOrMap, expected, code);
} else {
expectWarningByMap(nameOrMap);
}
@@ -771,42 +722,123 @@ exports.expectWarning = function (nameOrMap, expected) {
});
} /**/
+var Comparison = function Comparison(obj, keys) {
+ _classCallCheck(this, Comparison);
+
+ var _iteratorNormalCompletion = true;
+ var _didIteratorError = false;
+ var _iteratorError = undefined;
+
+ try {
+ for (var _iterator = keys[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
+ var key = _step.value;
+
+ if (key in obj) this[key] = obj[key];
+ }
+ } catch (err) {
+ _didIteratorError = true;
+ _iteratorError = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion && _iterator.return) {
+ _iterator.return();
+ }
+ } finally {
+ if (_didIteratorError) {
+ throw _iteratorError;
+ }
+ }
+ }
+};
+
// Useful for testing expected internal/error objects
+
+
exports.expectsError = function expectsError(fn, settings, exact) {
if (typeof fn !== 'function') {
exact = settings;
settings = fn;
fn = undefined;
}
+
function innerFn(error) {
- assert.strictEqual(error.code, settings.code);
+ if (arguments.length !== 1) {
+ // Do not use `assert.strictEqual()` to prevent `util.inspect` from
+ // always being called.
+ assert.fail('Expected one argument, got ' + util.inspect(arguments));
+ }
+ var descriptor = Object.getOwnPropertyDescriptor(error, 'message');
+ assert.strictEqual(descriptor.enumerable, false, 'The error message should be non-enumerable');
+
+ var innerSettings = settings;
if ('type' in settings) {
var type = settings.type;
if (type !== Error && !Error.isPrototypeOf(type)) {
throw new TypeError('`settings.type` must inherit from `Error`');
}
- assert(error instanceof type, error.name + ' is not instance of ' + type.name);
- }
- if ('message' in settings) {
- var message = settings.message;
- if (typeof message === 'string') {
- assert.strictEqual(error.message, message);
- } else {
- assert(message.test(error.message), error.message + ' does not match ' + message);
+ var _constructor = error.constructor;
+ if (_constructor.name === 'NodeError' && type.name !== 'NodeError') {
+ _constructor = Object.getPrototypeOf(error.constructor);
}
+ // Add the `type` to the error to properly compare and visualize it.
+ if (!('type' in error)) error.type = _constructor;
}
- if ('name' in settings) {
- assert.strictEqual(error.name, settings.name);
+
+ if ('message' in settings && typeof settings.message === 'object' && settings.message.test(error.message)) {
+ // Make a copy so we are able to modify the settings.
+ innerSettings = Object.create(settings, Object.getOwnPropertyDescriptors(settings));
+ // Visualize the message as identical in case of other errors.
+ innerSettings.message = error.message;
}
- if (error.constructor.name === 'AssertionError') {
- forEach(['generatedMessage', 'actual', 'expected', 'operator'], function (key) {
- if (key in settings) {
- var actual = error[key];
- var expected = settings[key];
- assert.strictEqual(actual, expected, key + ': expected ' + expected + ', not ' + actual);
+
+ // Check all error properties.
+ var keys = objectKeys(settings);
+ var _iteratorNormalCompletion2 = true;
+ var _didIteratorError2 = false;
+ var _iteratorError2 = undefined;
+
+ try {
+ for (var _iterator2 = keys[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
+ var key = _step2.value;
+
+ if (!require('deep-strict-equal')(error[key], innerSettings[key])) {
+ // Create placeholder objects to create a nice output.
+ var a = new Comparison(error, keys);
+ var b = new Comparison(innerSettings, keys);
+
+ var tmpLimit = Error.stackTraceLimit;
+ Error.stackTraceLimit = 0;
+ var err = new assert.AssertionError({
+ actual: a,
+ expected: b,
+ operator: 'strictEqual',
+ stackStartFn: assert.throws
+ });
+ Error.stackTraceLimit = tmpLimit;
+
+ throw new assert.AssertionError({
+ actual: error,
+ expected: settings,
+ operator: 'common.expectsError',
+ message: err.message
+ });
}
- });
+ }
+ } catch (err) {
+ _didIteratorError2 = true;
+ _iteratorError2 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion2 && _iterator2.return) {
+ _iterator2.return();
+ }
+ } finally {
+ if (_didIteratorError2) {
+ throw _iteratorError2;
+ }
+ }
}
+
return true;
}
if (fn) {
@@ -820,6 +852,10 @@ exports.skipIfInspectorDisabled = function skipIfInspectorDisabled() {
if (process.config.variables.v8_enable_inspector === 0) {
exports.skip('V8 inspector is disabled');
}
+ if (!exports.isMainThread) {
+ // TODO(addaleax): Fix me.
+ exports.skip('V8 inspector is not available in Workers');
+ }
};
exports.skipIf32Bits = function skipIf32Bits() {
@@ -838,13 +874,13 @@ exports.getArrayBufferViews = function getArrayBufferViews(buf) {
var arrayBufferViews = [Int8Array, Uint8Array, Uint8ClampedArray, Int16Array, Uint16Array, Int32Array, Uint32Array, Float32Array, Float64Array, DataView];
- var _iteratorNormalCompletion = true;
- var _didIteratorError = false;
- var _iteratorError = undefined;
+ var _iteratorNormalCompletion3 = true;
+ var _didIteratorError3 = false;
+ var _iteratorError3 = undefined;
try {
- for (var _iterator = arrayBufferViews[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
- var type = _step.value;
+ for (var _iterator3 = arrayBufferViews[Symbol.iterator](), _step3; !(_iteratorNormalCompletion3 = (_step3 = _iterator3.next()).done); _iteratorNormalCompletion3 = true) {
+ var type = _step3.value;
var _type$BYTES_PER_ELEME = type.BYTES_PER_ELEMENT,
BYTES_PER_ELEMENT = _type$BYTES_PER_ELEME === undefined ? 1 : _type$BYTES_PER_ELEME;
@@ -853,16 +889,16 @@ exports.getArrayBufferViews = function getArrayBufferViews(buf) {
}
}
} catch (err) {
- _didIteratorError = true;
- _iteratorError = err;
+ _didIteratorError3 = true;
+ _iteratorError3 = err;
} finally {
try {
- if (!_iteratorNormalCompletion && _iterator.return) {
- _iterator.return();
+ if (!_iteratorNormalCompletion3 && _iterator3.return) {
+ _iterator3.return();
}
} finally {
- if (_didIteratorError) {
- throw _iteratorError;
+ if (_didIteratorError3) {
+ throw _iteratorError3;
}
}
}
@@ -870,27 +906,34 @@ exports.getArrayBufferViews = function getArrayBufferViews(buf) {
return out;
};
+exports.getBufferSources = function getBufferSources(buf) {
+ return [].concat(_toConsumableArray(exports.getArrayBufferViews(buf)), [new Uint8Array(buf).buffer]);
+};
+
// Crash the process on unhandled rejections.
-exports.crashOnUnhandledRejection = function () {
- process.on('unhandledRejection', function (err) {
- return process.nextTick(function () {
- throw err;
- });
- });
+var crashOnUnhandledRejection = function (err) {
+ throw err;
+};
+process.on('unhandledRejection', crashOnUnhandledRejection);
+exports.disableCrashOnUnhandledRejection = function () {
+ process.removeListener('unhandledRejection', crashOnUnhandledRejection);
};
exports.getTTYfd = function getTTYfd() {
+ // Do our best to grab a tty fd.
var tty = require('tty');
- var tty_fd = 0;
- if (!tty.isatty(tty_fd)) tty_fd++;else if (!tty.isatty(tty_fd)) tty_fd++;else if (!tty.isatty(tty_fd)) tty_fd++;else {
+ // Don't attempt fd 0 as it is not writable on Windows.
+ // Ref: ef2861961c3d9e9ed6972e1e84d969683b25cf95
+ var ttyFd = [1, 2, 4, 5].find(tty.isatty);
+ if (ttyFd === undefined) {
try {
- tty_fd = fs.openSync('/dev/tty');
+ return fs.openSync('/dev/tty');
} catch (e) {
// There aren't any tty fd's available to use.
return -1;
}
}
- return tty_fd;
+ return ttyFd;
};
// Hijack stdout and stderr
@@ -919,18 +962,50 @@ function restoreWritable(name) {
delete process[name].writeTimes;
}
+exports.runWithInvalidFD = function (func) {
+ var fd = 1 << 30;
+ // Get first known bad file descriptor. 1 << 30 is usually unlikely to
+ // be an valid one.
+ try {
+ while (fs.fstatSync(fd--) && fd > 0) {}
+ } catch (e) {
+ return func(fd);
+ }
+
+ exports.printSkipMessage('Could not generate an invalid fd');
+};
+
exports.hijackStdout = hijackStdWritable.bind(null, 'stdout');
exports.hijackStderr = hijackStdWritable.bind(null, 'stderr');
exports.restoreStdout = restoreWritable.bind(null, 'stdout');
exports.restoreStderr = restoreWritable.bind(null, 'stderr');
+exports.isCPPSymbolsNotMapped = exports.isWindows || exports.isSunOS || exports.isAIX || exports.isLinuxPPCBE || exports.isFreeBSD;
-var fd = 2;
-exports.firstInvalidFD = function firstInvalidFD() {
- // Get first known bad file descriptor.
- try {
- while (fs.fstatSync(++fd)) {}
- } catch (e) {}
- return fd;
+var gcTrackerMap = new WeakMap();
+var gcTrackerTag = 'NODE_TEST_COMMON_GC_TRACKER';
+
+exports.onGC = function (obj, gcListener) {
+ var async_hooks = require('async_' + 'hooks');
+
+ var onGcAsyncHook = async_hooks.createHook({
+ init: exports.mustCallAtLeast(function (id, type, trigger, resource) {
+ if (this.trackedId === undefined) {
+ assert.strictEqual(type, gcTrackerTag);
+ this.trackedId = id;
+ }
+ }),
+ destroy: function (id) {
+ assert.notStrictEqual(this.trackedId, -1);
+ if (id === this.trackedId) {
+ this.gcListener.ongc();
+ onGcAsyncHook.disable();
+ }
+ }
+ }).enable();
+ onGcAsyncHook.gcListener = gcListener;
+
+ gcTrackerMap.set(obj, new async_hooks.AsyncResource(gcTrackerTag));
+ obj = null;
};
function forEach(xs, f) {
diff --git a/test/common/index.mjs b/test/common/index.mjs
index ad89e9dc7d..d6e9f31fe3 100644
--- a/test/common/index.mjs
+++ b/test/common/index.mjs
@@ -2,127 +2,129 @@
require('babel-polyfill');
var util = require('util');
for (var i in util) exports[i] = util[i];
- /**//**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-// Flags: --experimental-modules
-/* eslint-disable required-modules */
-
-import assert from 'assert';
-
-let knownGlobals = [
- Buffer,
- clearImmediate,
- clearInterval,
- clearTimeout,
- console,
- constructor, // Enumerable in V8 3.21.
- global,
- process,
- setImmediate,
- setInterval,
- setTimeout
-];
-
-if (process.env.NODE_TEST_KNOWN_GLOBALS) {
- const knownFromEnv = process.env.NODE_TEST_KNOWN_GLOBALS.split(',');
- allowGlobals(...knownFromEnv);
-}
-
-export function allowGlobals(...whitelist) {
- knownGlobals = knownGlobals.concat(whitelist);
-}
-
-export function leakedGlobals() {
- //add possible expected globals
- if (global.gc) {
- knownGlobals.push(global.gc);
- }
-
- if (global.DTRACE_HTTP_SERVER_RESPONSE) {
- knownGlobals.push(DTRACE_HTTP_SERVER_RESPONSE);
- knownGlobals.push(DTRACE_HTTP_SERVER_REQUEST);
- knownGlobals.push(DTRACE_HTTP_CLIENT_RESPONSE);
- knownGlobals.push(DTRACE_HTTP_CLIENT_REQUEST);
- knownGlobals.push(DTRACE_NET_STREAM_END);
- knownGlobals.push(DTRACE_NET_SERVER_CONNECTION);
- }
-
- if (global.COUNTER_NET_SERVER_CONNECTION) {
- knownGlobals.push(COUNTER_NET_SERVER_CONNECTION);
- knownGlobals.push(COUNTER_NET_SERVER_CONNECTION_CLOSE);
- knownGlobals.push(COUNTER_HTTP_SERVER_REQUEST);
- knownGlobals.push(COUNTER_HTTP_SERVER_RESPONSE);
- knownGlobals.push(COUNTER_HTTP_CLIENT_REQUEST);
- knownGlobals.push(COUNTER_HTTP_CLIENT_RESPONSE);
- }
-
- if (global.LTTNG_HTTP_SERVER_RESPONSE) {
- knownGlobals.push(LTTNG_HTTP_SERVER_RESPONSE);
- knownGlobals.push(LTTNG_HTTP_SERVER_REQUEST);
- knownGlobals.push(LTTNG_HTTP_CLIENT_RESPONSE);
- knownGlobals.push(LTTNG_HTTP_CLIENT_REQUEST);
- knownGlobals.push(LTTNG_NET_STREAM_END);
- knownGlobals.push(LTTNG_NET_SERVER_CONNECTION);
- }
-
- if (global.ArrayBuffer) {
- knownGlobals.push(ArrayBuffer);
- knownGlobals.push(Int8Array);
- knownGlobals.push(Uint8Array);
- knownGlobals.push(Uint8ClampedArray);
- knownGlobals.push(Int16Array);
- knownGlobals.push(Uint16Array);
- knownGlobals.push(Int32Array);
- knownGlobals.push(Uint32Array);
- knownGlobals.push(Float32Array);
- knownGlobals.push(Float64Array);
- knownGlobals.push(DataView);
- }
-
- // Harmony features.
- if (global.Proxy) {
- knownGlobals.push(Proxy);
- }
-
- if (global.Symbol) {
- knownGlobals.push(Symbol);
- }
-
- const leaked = [];
-
- for (const val in global) {
- if (!knownGlobals.includes(global[val])) {
- leaked.push(val);
- }
- }
-
- if (global.__coverage__) {
- return leaked.filter((varname) => !/^(?:cov_|__cov)/.test(varname));
- } else {
- return leaked;
- }
-}
-
-// Turn this off if the test should not check for global leaks.
-export let globalCheck = true; // eslint-disable-line
-
-process.on('exit', function() {
- if (!globalCheck) return;
- const leaked = leakedGlobals();
- if (leaked.length > 0) {
- assert.fail(`Unexpected global(s) found: ${leaked.join(', ')}`);
- }
-});
+ /**/// Flags: --experimental-modules
+/* eslint-disable node-core/required-modules */
+import common from './index.js';
+
+const {
+ PORT,
+ isMainThread,
+ isWindows,
+ isWOW64,
+ isAIX,
+ isLinuxPPCBE,
+ isSunOS,
+ isFreeBSD,
+ isOpenBSD,
+ isLinux,
+ isOSX,
+ isGlibc,
+ enoughTestMem,
+ enoughTestCpu,
+ rootDir,
+ buildType,
+ localIPv6Hosts,
+ opensslCli,
+ PIPE,
+ hasIPv6,
+ childShouldThrowAndAbort,
+ ddCommand,
+ spawnPwd,
+ spawnSyncPwd,
+ platformTimeout,
+ allowGlobals,
+ leakedGlobals,
+ mustCall,
+ mustCallAtLeast,
+ mustCallAsync,
+ hasMultiLocalhost,
+ fileExists,
+ skipIfEslintMissing,
+ canCreateSymLink,
+ getCallSite,
+ mustNotCall,
+ printSkipMessage,
+ skip,
+ ArrayStream,
+ nodeProcessAborted,
+ busyLoop,
+ isAlive,
+ noWarnCode,
+ expectWarning,
+ expectsError,
+ skipIfInspectorDisabled,
+ skipIf32Bits,
+ getArrayBufferViews,
+ getBufferSources,
+ disableCrashOnUnhandledRejection,
+ getTTYfd,
+ runWithInvalidFD,
+ hijackStdout,
+ hijackStderr,
+ restoreStdout,
+ restoreStderr,
+ isCPPSymbolsNotMapped
+} = common;
+
+export {
+ PORT,
+ isMainThread,
+ isWindows,
+ isWOW64,
+ isAIX,
+ isLinuxPPCBE,
+ isSunOS,
+ isFreeBSD,
+ isOpenBSD,
+ isLinux,
+ isOSX,
+ isGlibc,
+ enoughTestMem,
+ enoughTestCpu,
+ rootDir,
+ buildType,
+ localIPv6Hosts,
+ opensslCli,
+ PIPE,
+ hasIPv6,
+ childShouldThrowAndAbort,
+ ddCommand,
+ spawnPwd,
+ spawnSyncPwd,
+ platformTimeout,
+ allowGlobals,
+ leakedGlobals,
+ mustCall,
+ mustCallAtLeast,
+ mustCallAsync,
+ hasMultiLocalhost,
+ fileExists,
+ skipIfEslintMissing,
+ canCreateSymLink,
+ getCallSite,
+ mustNotCall,
+ printSkipMessage,
+ skip,
+ ArrayStream,
+ nodeProcessAborted,
+ busyLoop,
+ isAlive,
+ noWarnCode,
+ expectWarning,
+ expectsError,
+ skipIfInspectorDisabled,
+ skipIf32Bits,
+ getArrayBufferViews,
+ getBufferSources,
+ disableCrashOnUnhandledRejection,
+ getTTYfd,
+ runWithInvalidFD,
+ hijackStdout,
+ hijackStderr,
+ restoreStdout,
+ restoreStderr,
+ isCPPSymbolsNotMapped
+};
function forEach (xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
diff --git a/test/common/inspector-helper.js b/test/common/inspector-helper.js
index 3e4f16573a..67cb54f6ce 100644
--- a/test/common/inspector-helper.js
+++ b/test/common/inspector-helper.js
@@ -1,3 +1,11 @@
+'use strict';
+
+function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
+
+function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
+
+function _asyncToGenerator(fn) { return function () { var gen = fn.apply(this, arguments); return new Promise(function (resolve, reject) { function step(key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { return Promise.resolve(value).then(function (value) { step("next", value); }, function (err) { step("throw", err); }); } } return step("next"); }); }; }
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
/**/
@@ -5,19 +13,7 @@ require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-'use strict';
+} /**/'use strict';
/**/
var objectKeys = objectKeys || function (obj) {
@@ -37,7 +33,14 @@ var fixtures = require('../common/fixtures');
var _require = require('child_process'),
spawn = _require.spawn;
-var url = require('url');
+var _require2 = require('url'),
+ parseURL = _require2.parse;
+
+var _require3 = require('internal/url'),
+ getURLFromFilePath = _require3.getURLFromFilePath;
+
+var _require4 = require('events'),
+ EventEmitter = _require4.EventEmitter;
var _MAINSCRIPT = fixtures.path('loop.js');
var DEBUG = false;
@@ -55,6 +58,7 @@ function spawnChildProcess(inspectorFlags, scriptContents, scriptFile) {
var handler = tearDown.bind(null, child);
process.on('exit', handler);
process.on('uncaughtException', handler);
+ common.disableCrashOnUnhandledRejection();
process.on('unhandledRejection', handler);
process.on('SIGINT', handler);
@@ -204,9 +208,18 @@ var InspectorSession = function () {
return this._terminationPromise;
};
- InspectorSession.prototype.disconnect = function disconnect() {
- this._socket.destroy();
- };
+ InspectorSession.prototype.disconnect = function () {
+ var _ref = _asyncToGenerator(function* () {
+ this._socket.destroy();
+ return this.waitForServerDisconnect();
+ });
+
+ function disconnect() {
+ return _ref.apply(this, arguments);
+ }
+
+ return disconnect;
+ }();
InspectorSession.prototype._onMessage = function _onMessage(message) {
if (message.id) {
@@ -218,11 +231,15 @@ var InspectorSession = function () {
if (message.result) resolve(message.result);else reject(message.error);
} else {
if (message.method === 'Debugger.scriptParsed') {
- var script = message['params'];
- var scriptId = script['scriptId'];
- var _url = script['url'];
- this._scriptsIdsByUrl.set(scriptId, _url);
- if (_url === _MAINSCRIPT) this.mainScriptId = scriptId;
+ var _message$params = message.params,
+ scriptId = _message$params.scriptId,
+ url = _message$params.url;
+
+ this._scriptsIdsByUrl.set(scriptId, url);
+ var fileUrl = url.startsWith('file:') ? url : getURLFromFilePath(url).toString();
+ if (fileUrl === this.scriptURL().toString()) {
+ this.mainScriptId = scriptId;
+ }
}
if (this._notificationCallback) {
@@ -240,11 +257,11 @@ var InspectorSession = function () {
var _this2 = this;
var msg = JSON.parse(JSON.stringify(message)); // Clone!
- msg['id'] = this._nextId++;
+ msg.id = this._nextId++;
if (DEBUG) console.log('[sent]', JSON.stringify(msg));
var responsePromise = new Promise(function (resolve, reject) {
- _this2._commandResponsePromises.set(msg['id'], { resolve: resolve, reject: reject });
+ _this2._commandResponsePromises.set(msg.id, { resolve: resolve, reject: reject });
});
return new Promise(function (resolve) {
@@ -274,32 +291,41 @@ var InspectorSession = function () {
return fires(this._asyncWaitForNotification(methodOrPredicate), message, TIMEOUT);
};
- InspectorSession.prototype._asyncWaitForNotification = async function _asyncWaitForNotification(methodOrPredicate) {
- var _this4 = this;
+ InspectorSession.prototype._asyncWaitForNotification = function () {
+ var _ref2 = _asyncToGenerator(function* (methodOrPredicate) {
+ var _this4 = this;
- function matchMethod(notification) {
- return notification.method === methodOrPredicate;
- }
- var predicate = typeof methodOrPredicate === 'string' ? matchMethod : methodOrPredicate;
- var notification = null;
- do {
- if (this._unprocessedNotifications.length) {
- notification = this._unprocessedNotifications.shift();
- } else {
- notification = await new Promise(function (resolve) {
- return _this4._notificationCallback = resolve;
- });
+ function matchMethod(notification) {
+ return notification.method === methodOrPredicate;
}
- } while (!predicate(notification));
- return notification;
- };
+ var predicate = typeof methodOrPredicate === 'string' ? matchMethod : methodOrPredicate;
+ var notification = null;
+ do {
+ if (this._unprocessedNotifications.length) {
+ notification = this._unprocessedNotifications.shift();
+ } else {
+ notification = yield new Promise(function (resolve) {
+ return _this4._notificationCallback = resolve;
+ });
+ }
+ } while (!predicate(notification));
+ return notification;
+ });
+
+ function _asyncWaitForNotification(_x) {
+ return _ref2.apply(this, arguments);
+ }
- InspectorSession.prototype._isBreakOnLineNotification = function _isBreakOnLineNotification(message, line, url) {
- if ('Debugger.paused' === message['method']) {
- var callFrame = message['params']['callFrames'][0];
- var location = callFrame['location'];
- assert.strictEqual(url, this._scriptsIdsByUrl.get(location['scriptId']));
- assert.strictEqual(line, location['lineNumber']);
+ return _asyncWaitForNotification;
+ }();
+
+ InspectorSession.prototype._isBreakOnLineNotification = function _isBreakOnLineNotification(message, line, expectedScriptPath) {
+ if (message.method === 'Debugger.paused') {
+ var callFrame = message.params.callFrames[0];
+ var location = callFrame.location;
+ var scriptPath = this._scriptsIdsByUrl.get(location.scriptId);
+ assert.strictEqual(scriptPath.toString(), expectedScriptPath.toString(), scriptPath + ' !== ' + expectedScriptPath);
+ assert.strictEqual(line, location.lineNumber);
return true;
}
};
@@ -314,19 +340,19 @@ var InspectorSession = function () {
InspectorSession.prototype._matchesConsoleOutputNotification = function _matchesConsoleOutputNotification(notification, type, values) {
if (!Array.isArray(values)) values = [values];
- if ('Runtime.consoleAPICalled' === notification['method']) {
- var params = notification['params'];
- if (params['type'] === type) {
+ if (notification.method === 'Runtime.consoleAPICalled') {
+ var params = notification.params;
+ if (params.type === type) {
var _i2 = 0;
var _iteratorNormalCompletion2 = true;
var _didIteratorError2 = false;
var _iteratorError2 = undefined;
try {
- for (var _iterator2 = params['args'][Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
+ for (var _iterator2 = params.args[Symbol.iterator](), _step2; !(_iteratorNormalCompletion2 = (_step2 = _iterator2.next()).done); _iteratorNormalCompletion2 = true) {
var value = _step2.value;
- if (value['value'] !== values[_i2++]) return false;
+ if (value.value !== values[_i2++]) return false;
}
} catch (err) {
_didIteratorError2 = true;
@@ -357,62 +383,95 @@ var InspectorSession = function () {
}, desc);
};
- InspectorSession.prototype.runToCompletion = async function runToCompletion() {
- console.log('[test]', 'Verify node waits for the frontend to disconnect');
- await this.send({ 'method': 'Debugger.resume' });
- await this.waitForNotification(function (notification) {
- return notification.method === 'Runtime.executionContextDestroyed' && notification.params.executionContextId === 1;
+ InspectorSession.prototype.runToCompletion = function () {
+ var _ref3 = _asyncToGenerator(function* () {
+ console.log('[test]', 'Verify node waits for the frontend to disconnect');
+ yield this.send({ 'method': 'Debugger.resume' });
+ yield this.waitForNotification(function (notification) {
+ return notification.method === 'Runtime.executionContextDestroyed' && notification.params.executionContextId === 1;
+ });
+ while ((yield this._instance.nextStderrString()) !== 'Waiting for the debugger to disconnect...') {}
+ yield this.disconnect();
});
- while ((await this._instance.nextStderrString()) !== 'Waiting for the debugger to disconnect...') {}
- await this.disconnect();
+
+ function runToCompletion() {
+ return _ref3.apply(this, arguments);
+ }
+
+ return runToCompletion;
+ }();
+
+ InspectorSession.prototype.scriptPath = function scriptPath() {
+ return this._instance.scriptPath();
+ };
+
+ InspectorSession.prototype.script = function script() {
+ return this._instance.script();
+ };
+
+ InspectorSession.prototype.scriptURL = function scriptURL() {
+ return getURLFromFilePath(this.scriptPath());
};
return InspectorSession;
}();
-var NodeInstance = function () {
+var NodeInstance = function (_EventEmitter) {
+ _inherits(NodeInstance, _EventEmitter);
+
function NodeInstance() {
var inspectorFlags = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : ['--inspect-brk=0'];
-
- var _this7 = this;
-
var scriptContents = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : '';
var scriptFile = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : _MAINSCRIPT;
_classCallCheck(this, NodeInstance);
- this._portCallback = null;
- this.portPromise = new Promise(function (resolve) {
+ var _this7 = _possibleConstructorReturn(this, _EventEmitter.call(this));
+
+ _this7._scriptPath = scriptFile;
+ _this7._script = scriptFile ? null : scriptContents;
+ _this7._portCallback = null;
+ _this7.portPromise = new Promise(function (resolve) {
return _this7._portCallback = resolve;
});
- this._process = spawnChildProcess(inspectorFlags, scriptContents, scriptFile);
- this._running = true;
- this._stderrLineCallback = null;
- this._unprocessedStderrLines = [];
-
- this._process.stdout.on('data', makeBufferingDataCallback(function (line) {
- return console.log('[out]', line);
+ _this7._process = spawnChildProcess(inspectorFlags, scriptContents, scriptFile);
+ _this7._running = true;
+ _this7._stderrLineCallback = null;
+ _this7._unprocessedStderrLines = [];
+
+ _this7._process.stdout.on('data', makeBufferingDataCallback(function (line) {
+ _this7.emit('stdout', line);
+ console.log('[out]', line);
}));
- this._process.stderr.on('data', makeBufferingDataCallback(function (message) {
+ _this7._process.stderr.on('data', makeBufferingDataCallback(function (message) {
return _this7.onStderrLine(message);
}));
- this._shutdownPromise = new Promise(function (resolve) {
+ _this7._shutdownPromise = new Promise(function (resolve) {
_this7._process.once('exit', function (exitCode, signal) {
resolve({ exitCode: exitCode, signal: signal });
_this7._running = false;
});
});
+ return _this7;
}
- NodeInstance.startViaSignal = async function startViaSignal(scriptContents) {
- var instance = new NodeInstance([], scriptContents + '\nprocess._rawDebug(\'started\');', undefined);
- var msg = 'Timed out waiting for process to start';
- while ((await fires(instance.nextStderrString(), msg, TIMEOUT)) !== 'started') {}
- process._debugProcess(instance._process.pid);
- return instance;
- };
+ NodeInstance.startViaSignal = function () {
+ var _ref4 = _asyncToGenerator(function* (scriptContents) {
+ var instance = new NodeInstance([], scriptContents + '\nprocess._rawDebug(\'started\');', undefined);
+ var msg = 'Timed out waiting for process to start';
+ while ((yield fires(instance.nextStderrString(), msg, TIMEOUT)) !== 'started') {}
+ process._debugProcess(instance._process.pid);
+ return instance;
+ });
+
+ function startViaSignal(_x5) {
+ return _ref4.apply(this, arguments);
+ }
+
+ return startViaSignal;
+ }();
NodeInstance.prototype.onStderrLine = function onStderrLine(line) {
console.log('[err]', line);
@@ -431,11 +490,12 @@ var NodeInstance = function () {
}
};
- NodeInstance.prototype.httpGet = function httpGet(host, path) {
+ NodeInstance.prototype.httpGet = function httpGet(host, path, hostHeaderValue) {
console.log('[test]', 'Testing ' + path);
+ var headers = hostHeaderValue ? { 'Host': hostHeaderValue } : null;
return this.portPromise.then(function (port) {
return new Promise(function (resolve, reject) {
- var req = http.get({ host: host, port: port, path: path }, function (res) {
+ var req = http.get({ host: host, port: port, path: path, headers: headers }, function (res) {
var response = '';
res.setEncoding('utf8');
res.on('data', function (data) {
@@ -456,33 +516,69 @@ var NodeInstance = function () {
});
};
- NodeInstance.prototype.wsHandshake = function wsHandshake(devtoolsUrl) {
- var _this8 = this;
+ NodeInstance.prototype.sendUpgradeRequest = function () {
+ var _ref5 = _asyncToGenerator(function* () {
+ var response = yield this.httpGet(null, '/json/list');
+ var devtoolsUrl = response[0].webSocketDebuggerUrl;
+ var port = yield this.portPromise;
+ return http.get({
+ port: port,
+ path: parseURL(devtoolsUrl).path,
+ headers: {
+ 'Connection': 'Upgrade',
+ 'Upgrade': 'websocket',
+ 'Sec-WebSocket-Version': 13,
+ 'Sec-WebSocket-Key': 'key=='
+ }
+ });
+ });
+
+ function sendUpgradeRequest() {
+ return _ref5.apply(this, arguments);
+ }
- return this.portPromise.then(function (port) {
- return new Promise(function (resolve) {
- http.get({
- port: port,
- path: url.parse(devtoolsUrl).path,
- headers: {
- 'Connection': 'Upgrade',
- 'Upgrade': 'websocket',
- 'Sec-WebSocket-Version': 13,
- 'Sec-WebSocket-Key': 'key=='
- }
- }).on('upgrade', function (message, socket) {
- resolve(new InspectorSession(socket, _this8));
+ return sendUpgradeRequest;
+ }();
+
+ NodeInstance.prototype.connectInspectorSession = function () {
+ var _ref6 = _asyncToGenerator(function* () {
+ var _this8 = this;
+
+ console.log('[test]', 'Connecting to a child Node process');
+ var upgradeRequest = yield this.sendUpgradeRequest();
+ return new Promise(function (resolve, reject) {
+ upgradeRequest.on('upgrade', function (message, socket) {
+ return resolve(new InspectorSession(socket, _this8));
}).on('response', common.mustNotCall('Upgrade was not received'));
});
});
- };
- NodeInstance.prototype.connectInspectorSession = async function connectInspectorSession() {
- console.log('[test]', 'Connecting to a child Node process');
- var response = await this.httpGet(null, '/json/list');
- var url = response[0]['webSocketDebuggerUrl'];
- return this.wsHandshake(url);
- };
+ function connectInspectorSession() {
+ return _ref6.apply(this, arguments);
+ }
+
+ return connectInspectorSession;
+ }();
+
+ NodeInstance.prototype.expectConnectionDeclined = function () {
+ var _ref7 = _asyncToGenerator(function* () {
+ console.log('[test]', 'Checking upgrade is not possible');
+ var upgradeRequest = yield this.sendUpgradeRequest();
+ return new Promise(function (resolve, reject) {
+ upgradeRequest.on('upgrade', common.mustNotCall('Upgrade was received')).on('response', function (response) {
+ return response.on('data', function () {}).on('end', function () {
+ return resolve(response.statusCode);
+ });
+ });
+ });
+ });
+
+ function expectConnectionDeclined() {
+ return _ref7.apply(this, arguments);
+ }
+
+ return expectConnectionDeclined;
+ }();
NodeInstance.prototype.expectShutdown = function expectShutdown() {
return this._shutdownPromise;
@@ -497,16 +593,26 @@ var NodeInstance = function () {
});
};
+ NodeInstance.prototype.write = function write(message) {
+ this._process.stdin.write(message);
+ };
+
NodeInstance.prototype.kill = function kill() {
this._process.kill();
+ return this.expectShutdown();
};
- return NodeInstance;
-}();
+ NodeInstance.prototype.scriptPath = function scriptPath() {
+ return this._scriptPath;
+ };
-function readMainScriptSource() {
- return fs.readFileSync(_MAINSCRIPT, 'utf8');
-}
+ NodeInstance.prototype.script = function script() {
+ if (this._script === null) this._script = fs.readFileSync(this.scriptPath(), 'utf8');
+ return this._script;
+ };
+
+ return NodeInstance;
+}(EventEmitter);
function onResolvedOrRejected(promise, callback) {
return promise.then(function (result) {
@@ -548,8 +654,6 @@ function fires(promise, error, timeoutMs) {
}
module.exports = {
- mainScriptPath: _MAINSCRIPT,
- readMainScriptSource: readMainScriptSource,
NodeInstance: NodeInstance
};
diff --git a/test/common/internet.js b/test/common/internet.js
new file mode 100644
index 0000000000..7e596a185b
--- /dev/null
+++ b/test/common/internet.js
@@ -0,0 +1,97 @@
+'use strict';
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/ /* eslint-disable node-core/required-modules */
+'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+// Utilities for internet-related tests
+
+var addresses = {
+ // A generic host that has registered common DNS records,
+ // supports both IPv4 and IPv6, and provides basic HTTP/HTTPS services
+ INET_HOST: 'nodejs.org',
+ // A host that provides IPv4 services
+ INET4_HOST: 'nodejs.org',
+ // A host that provides IPv6 services
+ INET6_HOST: 'nodejs.org',
+ // An accessible IPv4 IP,
+ // defaults to the Google Public DNS IPv4 address
+ INET4_IP: '8.8.8.8',
+ // An accessible IPv6 IP,
+ // defaults to the Google Public DNS IPv6 address
+ INET6_IP: '2001:4860:4860::8888',
+ // An invalid host that cannot be resolved
+ // See https://tools.ietf.org/html/rfc2606#section-2
+ INVALID_HOST: 'something.invalid',
+ // A host with MX records registered
+ MX_HOST: 'nodejs.org',
+ // A host with SRV records registered
+ SRV_HOST: '_jabber._tcp.google.com',
+ // A host with PTR records registered
+ PTR_HOST: '8.8.8.8.in-addr.arpa',
+ // A host with NAPTR records registered
+ NAPTR_HOST: 'sip2sip.info',
+ // A host with SOA records registered
+ SOA_HOST: 'nodejs.org',
+ // A host with CNAME records registered
+ CNAME_HOST: 'blog.nodejs.org',
+ // A host with NS records registered
+ NS_HOST: 'nodejs.org',
+ // A host with TXT records registered
+ TXT_HOST: 'nodejs.org',
+ // An accessible IPv4 DNS server
+ DNS4_SERVER: '8.8.8.8',
+ // An accessible IPv4 DNS server
+ DNS6_SERVER: '2001:4860:4860::8888'
+};
+
+var _iteratorNormalCompletion = true;
+var _didIteratorError = false;
+var _iteratorError = undefined;
+
+try {
+ for (var _iterator = objectKeys(addresses)[Symbol.iterator](), _step; !(_iteratorNormalCompletion = (_step = _iterator.next()).done); _iteratorNormalCompletion = true) {
+ var key = _step.value;
+
+ var envName = 'NODE_TEST_' + key;
+ if (process.env[envName]) {
+ addresses[key] = process.env[envName];
+ }
+ }
+} catch (err) {
+ _didIteratorError = true;
+ _iteratorError = err;
+} finally {
+ try {
+ if (!_iteratorNormalCompletion && _iterator.return) {
+ _iterator.return();
+ }
+ } finally {
+ if (_didIteratorError) {
+ throw _iteratorError;
+ }
+ }
+}
+
+module.exports = {
+ addresses: addresses
+};
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/shared-lib-util.js b/test/common/shared-lib-util.js
new file mode 100644
index 0000000000..399b9bdf50
--- /dev/null
+++ b/test/common/shared-lib-util.js
@@ -0,0 +1,60 @@
+'use strict';
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+var common = require('../common');
+var path = require('path');
+
+// If node executable is linked to shared lib, need to take care about the
+// shared lib path.
+exports.addLibraryPath = function (env) {
+ if (!process.config.variables.node_shared) {
+ return;
+ }
+
+ env = env || process.env;
+
+ env.LD_LIBRARY_PATH = (env.LD_LIBRARY_PATH ? env.LD_LIBRARY_PATH + path.delimiter : '') + path.join(path.dirname(process.execPath), 'lib.target');
+ // For AIX.
+ env.LIBPATH = (env.LIBPATH ? env.LIBPATH + path.delimiter : '') + path.join(path.dirname(process.execPath), 'lib.target');
+ // For Mac OSX.
+ env.DYLD_LIBRARY_PATH = (env.DYLD_LIBRARY_PATH ? env.DYLD_LIBRARY_PATH + path.delimiter : '') + path.dirname(process.execPath);
+ // For Windows.
+ env.PATH = (env.PATH ? env.PATH + path.delimiter : '') + path.dirname(process.execPath);
+};
+
+// Get the full path of shared lib.
+exports.getSharedLibPath = function () {
+ if (common.isWindows) {
+ return path.join(path.dirname(process.execPath), 'node.dll');
+ } else if (common.isOSX) {
+ return path.join(path.dirname(process.execPath), 'libnode.' + process.config.variables.shlib_suffix);
+ } else {
+ return path.join(path.dirname(process.execPath), 'lib.target', 'libnode.' + process.config.variables.shlib_suffix);
+ }
+};
+
+// Get the binary path of stack frames.
+exports.getBinaryPath = function () {
+ return process.config.variables.node_shared ? exports.getSharedLibPath() : process.execPath;
+};
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/tls.js b/test/common/tls.js
new file mode 100644
index 0000000000..577dc4cc73
--- /dev/null
+++ b/test/common/tls.js
@@ -0,0 +1,200 @@
+'use strict';
+
+function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
+
+function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
+
+function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function, not " + typeof superClass); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, enumerable: false, writable: true, configurable: true } }); if (superClass) Object.setPrototypeOf ? Object.setPrototypeOf(subClass, superClass) : subClass.__proto__ = superClass; }
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/ /* eslint-disable node-core/required-modules, node-core/crypto-check */
+
+'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+var crypto = require('crypto');
+var net = require('net');
+
+exports.ccs = Buffer.from('140303000101', 'hex');
+
+var TestTLSSocket = function (_net$Socket) {
+ _inherits(TestTLSSocket, _net$Socket);
+
+ function TestTLSSocket(server_cert) {
+ _classCallCheck(this, TestTLSSocket);
+
+ var _this = _possibleConstructorReturn(this, _net$Socket.call(this));
+
+ _this.server_cert = server_cert;
+ _this.version = Buffer.from('0303', 'hex');
+ _this.handshake_list = [];
+ // AES128-GCM-SHA256
+ _this.ciphers = Buffer.from('000002009c0', 'hex');
+ _this.pre_master_secret = Buffer.concat([_this.version, crypto.randomBytes(46)]);
+ _this.master_secret = null;
+ _this.write_seq = 0;
+ _this.client_random = crypto.randomBytes(32);
+
+ _this.on('handshake', function (msg) {
+ _this.handshake_list.push(msg);
+ });
+
+ _this.on('server_random', function (server_random) {
+ _this.master_secret = PRF12('sha256', _this.pre_master_secret, 'master secret', Buffer.concat([_this.client_random, server_random]), 48);
+ var key_block = PRF12('sha256', _this.master_secret, 'key expansion', Buffer.concat([server_random, _this.client_random]), 40);
+ _this.client_writeKey = key_block.slice(0, 16);
+ _this.client_writeIV = key_block.slice(32, 36);
+ });
+ return _this;
+ }
+
+ TestTLSSocket.prototype.createClientHello = function createClientHello() {
+ var compressions = Buffer.from('0100', 'hex'); // null
+ var msg = addHandshakeHeader(0x01, Buffer.concat([this.version, this.client_random, this.ciphers, compressions]));
+ this.emit('handshake', msg);
+ return addRecordHeader(0x16, msg);
+ };
+
+ TestTLSSocket.prototype.createClientKeyExchange = function createClientKeyExchange() {
+ var encrypted_pre_master_secret = crypto.publicEncrypt({
+ key: this.server_cert,
+ padding: crypto.constants.RSA_PKCS1_PADDING
+ }, this.pre_master_secret);
+ var length = Buffer.alloc(2);
+ length.writeUIntBE(encrypted_pre_master_secret.length, 0, 2);
+ var msg = addHandshakeHeader(0x10, Buffer.concat([length, encrypted_pre_master_secret]));
+ this.emit('handshake', msg);
+ return addRecordHeader(0x16, msg);
+ };
+
+ TestTLSSocket.prototype.createFinished = function createFinished() {
+ var shasum = crypto.createHash('sha256');
+ shasum.update(Buffer.concat(this.handshake_list));
+ var message_hash = shasum.digest();
+ var r = PRF12('sha256', this.master_secret, 'client finished', message_hash, 12);
+ var msg = addHandshakeHeader(0x14, r);
+ this.emit('handshake', msg);
+ return addRecordHeader(0x16, msg);
+ };
+
+ TestTLSSocket.prototype.createIllegalHandshake = function createIllegalHandshake() {
+ var illegal_handshake = Buffer.alloc(5);
+ return addRecordHeader(0x16, illegal_handshake);
+ };
+
+ TestTLSSocket.prototype.parseTLSFrame = function parseTLSFrame(buf) {
+ var offset = 0;
+ var record = buf.slice(offset, 5);
+ var type = record[0];
+ var length = record.slice(3, 5).readUInt16BE(0);
+ offset += 5;
+ var remaining = buf.slice(offset, offset + length);
+ if (type === 0x16) {
+ do {
+ remaining = this.parseTLSHandshake(remaining);
+ } while (remaining.length > 0);
+ }
+ offset += length;
+ return buf.slice(offset);
+ };
+
+ TestTLSSocket.prototype.parseTLSHandshake = function parseTLSHandshake(buf) {
+ var offset = 0;
+ var handshake_type = buf[offset];
+ if (handshake_type === 0x02) {
+ var server_random = buf.slice(6, 6 + 32);
+ this.emit('server_random', server_random);
+ }
+ offset += 1;
+ var length = buf.readUIntBE(offset, 3);
+ offset += 3;
+ var handshake = buf.slice(0, offset + length);
+ this.emit('handshake', handshake);
+ offset += length;
+ var remaining = buf.slice(offset);
+ return remaining;
+ };
+
+ TestTLSSocket.prototype.encrypt = function encrypt(plain) {
+ var type = plain.slice(0, 1);
+ var version = plain.slice(1, 3);
+ var nonce = crypto.randomBytes(8);
+ var iv = Buffer.concat([this.client_writeIV.slice(0, 4), nonce]);
+ var bob = crypto.createCipheriv('aes-128-gcm', this.client_writeKey, iv);
+ var write_seq = Buffer.alloc(8);
+ write_seq.writeUInt32BE(this.write_seq++, 4);
+ var aad = Buffer.concat([write_seq, plain.slice(0, 5)]);
+ bob.setAAD(aad);
+ var encrypted1 = bob.update(plain.slice(5));
+ var encrypted = Buffer.concat([encrypted1, bob.final()]);
+ var tag = bob.getAuthTag();
+ var length = Buffer.alloc(2);
+ length.writeUInt16BE(nonce.length + encrypted.length + tag.length, 0);
+ return Buffer.concat([type, version, length, nonce, encrypted, tag]);
+ };
+
+ return TestTLSSocket;
+}(net.Socket);
+
+function addRecordHeader(type, frame) {
+ var record_layer = Buffer.from('0003030000', 'hex');
+ record_layer[0] = type;
+ record_layer.writeUInt16BE(frame.length, 3);
+ return Buffer.concat([record_layer, frame]);
+}
+
+function addHandshakeHeader(type, msg) {
+ var handshake_header = Buffer.alloc(4);
+ handshake_header[0] = type;
+ handshake_header.writeUIntBE(msg.length, 1, 3);
+ return Buffer.concat([handshake_header, msg]);
+}
+
+function PRF12(algo, secret, label, seed, size) {
+ var newSeed = Buffer.concat([Buffer.from(label, 'utf8'), seed]);
+ return P_hash(algo, secret, newSeed, size);
+}
+
+function P_hash(algo, secret, seed, size) {
+ var result = Buffer.alloc(size);
+ var hmac = crypto.createHmac(algo, secret);
+ hmac.update(seed);
+ var a = hmac.digest();
+ var j = 0;
+ while (j < size) {
+ hmac = crypto.createHmac(algo, secret);
+ hmac.update(a);
+ hmac.update(seed);
+ var b = hmac.digest();
+ var todo = b.length;
+ if (j + todo > size) {
+ todo = size - j;
+ }
+ b.copy(result, j, 0, todo);
+ j += todo;
+ hmac = crypto.createHmac(algo, secret);
+ hmac.update(a);
+ a = hmac.digest();
+ }
+ return result;
+}
+
+exports.TestTLSSocket = TestTLSSocket;
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/tmpdir.js b/test/common/tmpdir.js
new file mode 100644
index 0000000000..eb17dbbcc4
--- /dev/null
+++ b/test/common/tmpdir.js
@@ -0,0 +1,80 @@
+'use strict';
+
+/**/
+require('babel-polyfill');
+var util = require('util');
+for (var i in util) {
+ exports[i] = util[i];
+} /**/ /* eslint-disable node-core/required-modules */
+'use strict';
+
+/**/
+var objectKeys = objectKeys || function (obj) {
+ var keys = [];
+ for (var key in obj) {
+ keys.push(key);
+ }return keys;
+};
+/**/
+
+var fs = require('fs');
+var path = require('path');
+
+function rimrafSync(p) {
+ var st = void 0;
+ try {
+ st = fs.lstatSync(p);
+ } catch (e) {
+ if (e.code === 'ENOENT') return;
+ }
+
+ try {
+ if (st && st.isDirectory()) rmdirSync(p, null);else fs.unlinkSync(p);
+ } catch (e) {
+ if (e.code === 'ENOENT') return;
+ if (e.code === 'EPERM') return rmdirSync(p, e);
+ if (e.code !== 'EISDIR') throw e;
+ rmdirSync(p, e);
+ }
+}
+
+function rmdirSync(p, originalEr) {
+ try {
+ fs.rmdirSync(p);
+ } catch (e) {
+ if (e.code === 'ENOTDIR') throw originalEr;
+ if (e.code === 'ENOTEMPTY' || e.code === 'EEXIST' || e.code === 'EPERM') {
+ var enc = process.platform === 'linux' ? 'buffer' : 'utf8';
+ forEach(fs.readdirSync(p, enc), function (f) {
+ if (f instanceof Buffer) {
+ var buf = Buffer.concat([Buffer.from(p), Buffer.from(path.sep), f]);
+ rimrafSync(buf);
+ } else {
+ rimrafSync(path.join(p, f));
+ }
+ });
+ fs.rmdirSync(p);
+ }
+ }
+}
+
+var testRoot = process.env.NODE_TEST_DIR ? fs.realpathSync(process.env.NODE_TEST_DIR) : path.resolve(__dirname, '..');
+
+// Using a `.` prefixed name, which is the convention for "hidden" on POSIX,
+// gets tools to ignore it by default or by simple rules, especially eslint.
+var tmpdirName = '.tmp';
+if (process.env.TEST_THREAD_ID) {
+ tmpdirName += '.' + process.env.TEST_THREAD_ID;
+}
+exports.path = path.join(testRoot, tmpdirName);
+
+exports.refresh = function () {
+ rimrafSync(exports.path);
+ fs.mkdirSync(exports.path);
+};
+
+function forEach(xs, f) {
+ for (var i = 0, l = xs.length; i < l; i++) {
+ f(xs[i], i);
+ }
+}
\ No newline at end of file
diff --git a/test/common/wpt.js b/test/common/wpt.js
index 22a5c89709..0e45ab7e32 100644
--- a/test/common/wpt.js
+++ b/test/common/wpt.js
@@ -1,21 +1,11 @@
+'use strict';
+
/**/
require('babel-polyfill');
var util = require('util');
for (var i in util) {
exports[i] = util[i];
-} /**/ /**/
-if (!global.setImmediate) {
- global.setImmediate = function setImmediate(fn) {
- return setTimeout(fn.bind.apply(fn, arguments), 4);
- };
-}
-if (!global.clearImmediate) {
- global.clearImmediate = function clearImmediate(i) {
- return clearTimeout(i);
- };
-}
-/**/
-/* eslint-disable required-modules */
+} /**/ /* eslint-disable node-core/required-modules */
'use strict';
/**/
diff --git a/test/ours/lolex-fake-timers.js b/test/ours/lolex-fake-timers.js
index c1b883d4b7..59af1328ea 100644
--- a/test/ours/lolex-fake-timers.js
+++ b/test/ours/lolex-fake-timers.js
@@ -1,4 +1,5 @@
require('../common');
+var tap = require('tap');
var util = require('util');
var assert = require('assert');
var lolex = require('lolex');
@@ -37,3 +38,4 @@ stream.emit('data');
clock.runAll()
clock.uninstall();
assert(stream2DataCalled);
+tap.pass('ok');
diff --git a/test/ours/test-stream-sync-write.js b/test/ours/test-stream-sync-write.js
index f0a08f53e8..bfa7be9410 100644
--- a/test/ours/test-stream-sync-write.js
+++ b/test/ours/test-stream-sync-write.js
@@ -34,3 +34,5 @@ var externalStream = new ExternalStream(internalStream);
for (var i = 0; i < 2000; i++) {
externalStream.write(i.toString());
}
+
+require('tap').pass('sync done');
diff --git a/test/parallel/test-stream-backpressure.js b/test/parallel/test-stream-backpressure.js
new file mode 100644
index 0000000000..14e12bc1ba
--- /dev/null
+++ b/test/parallel/test-stream-backpressure.js
@@ -0,0 +1,46 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+var assert = require('assert/');
+var stream = require('../../');
+
+var pushes = 0;
+var total = 65500 + 40 * 1024;
+var rs = new stream.Readable({
+ read: common.mustCall(function () {
+ if (pushes++ === 10) {
+ this.push(null);
+ return;
+ }
+
+ var length = this._readableState.length;
+
+ // We are at most doing two full runs of _reads
+ // before stopping, because Readable is greedy
+ // to keep its buffer full
+ assert(length <= total);
+
+ this.push(bufferShim.alloc(65500));
+ for (var i = 0; i < 40; i++) {
+ this.push(bufferShim.alloc(1024));
+ }
+
+ // We will be over highWaterMark at this point
+ // but a new call to _read is scheduled anyway.
+ }, 11)
+});
+
+var ws = stream.Writable({
+ write: common.mustCall(function (data, enc, cb) {
+ setImmediate(cb);
+ }, 41 * 10)
+});
+
+rs.pipe(ws);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-big-packet.js b/test/parallel/test-stream-big-packet.js
index 85de251100..9480fdf5c4 100644
--- a/test/parallel/test-stream-big-packet.js
+++ b/test/parallel/test-stream-big-packet.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -83,4 +85,7 @@ function indexOf(xs, x) {
if (xs[i] === x) return i;
}
return -1;
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-big-push.js b/test/parallel/test-stream-big-push.js
index 68835fe5fb..81baa7ba47 100644
--- a/test/parallel/test-stream-big-push.js
+++ b/test/parallel/test-stream-big-push.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -73,4 +75,7 @@ r.once('readable', function () {
chunk = r.read();
assert.strictEqual(chunk, null);
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-buffer-list.js b/test/parallel/test-stream-buffer-list.js
index 531658e81e..393de025d2 100644
--- a/test/parallel/test-stream-buffer-list.js
+++ b/test/parallel/test-stream-buffer-list.js
@@ -1,10 +1,12 @@
+'use strict';
+
// Flags: --expose_internals
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
require('../common');
var assert = require('assert/');
-var BufferList = require('../../lib/internal/streams/BufferList');
+var BufferList = require('../../lib/internal/streams/buffer_list');
// Test empty buffer list.
var emptyList = new BufferList();
@@ -16,14 +18,22 @@ assert.strictEqual(emptyList.join(','), '');
assert.deepStrictEqual(emptyList.concat(0), bufferShim.alloc(0));
+var buf = bufferShim.from('foo');
+
// Test buffer list with one element.
var list = new BufferList();
-list.push('foo');
+list.push(buf);
+
+var copy = list.concat(3);
-assert.strictEqual(list.concat(1), 'foo');
+assert.notStrictEqual(copy, buf);
+assert.deepStrictEqual(copy, buf);
assert.strictEqual(list.join(','), 'foo');
var shifted = list.shift();
-assert.strictEqual(shifted, 'foo');
-assert.deepStrictEqual(list, new BufferList());
\ No newline at end of file
+assert.strictEqual(shifted, buf);
+assert.deepStrictEqual(list, new BufferList());
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-decoder-objectmode.js b/test/parallel/test-stream-decoder-objectmode.js
index b875a0f07d..b10de29754 100644
--- a/test/parallel/test-stream-decoder-objectmode.js
+++ b/test/parallel/test-stream-decoder-objectmode.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -19,4 +21,7 @@ readable.push(null);
// Without object mode, these would be concatenated into a single chunk.
assert.strictEqual(readable.read(), 'abc');
assert.strictEqual(readable.read(), 'def');
-assert.strictEqual(readable.read(), null);
\ No newline at end of file
+assert.strictEqual(readable.read(), null);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-destroy-event-order.js b/test/parallel/test-stream-destroy-event-order.js
new file mode 100644
index 0000000000..133703b47b
--- /dev/null
+++ b/test/parallel/test-stream-destroy-event-order.js
@@ -0,0 +1,33 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+var assert = require('assert/');
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+var rs = new Readable({
+ read: function () {}
+});
+
+var closed = false;
+var errored = false;
+
+rs.on('close', common.mustCall(function () {
+ closed = true;
+ assert(errored);
+}));
+
+rs.on('error', common.mustCall(function (err) {
+ errored = true;
+ assert(!closed);
+}));
+
+rs.destroy(new Error('kaboom'));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-duplex-destroy.js b/test/parallel/test-stream-duplex-destroy.js
index 2ac6fcba27..71187bd1ac 100644
--- a/test/parallel/test-stream-duplex-destroy.js
+++ b/test/parallel/test-stream-duplex-destroy.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -22,8 +24,9 @@ var _require2 = require('util'),
duplex.resume();
- duplex.on('end', common.mustCall());
- duplex.on('finish', common.mustCall());
+ duplex.on('end', common.mustNotCall());
+ duplex.on('finish', common.mustNotCall());
+ duplex.on('close', common.mustCall());
duplex.destroy();
assert.strictEqual(duplex.destroyed, true);
@@ -40,8 +43,8 @@ var _require2 = require('util'),
var expected = new Error('kaboom');
- _duplex.on('end', common.mustCall());
- _duplex.on('finish', common.mustCall());
+ _duplex.on('end', common.mustNotCall());
+ _duplex.on('finish', common.mustNotCall());
_duplex.on('error', common.mustCall(function (err) {
assert.strictEqual(err, expected);
}));
@@ -94,6 +97,7 @@ var _require2 = require('util'),
// error is swallowed by the custom _destroy
_duplex3.on('error', common.mustNotCall('no error event'));
+ _duplex3.on('close', common.mustCall());
_duplex3.destroy(_expected2);
assert.strictEqual(_duplex3.destroyed, true);
@@ -186,8 +190,8 @@ var _require2 = require('util'),
});
_duplex7.resume();
- _duplex7.on('finish', common.mustCall());
- _duplex7.on('end', common.mustCall());
+ _duplex7.on('finish', common.mustNotCall());
+ _duplex7.on('end', common.mustNotCall());
_duplex7.destroy();
assert.strictEqual(_duplex7.destroyed, true);
@@ -220,4 +224,7 @@ var _require2 = require('util'),
inherits(MyDuplex, Duplex);
new MyDuplex();
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-duplex-end.js b/test/parallel/test-stream-duplex-end.js
new file mode 100644
index 0000000000..95754b424d
--- /dev/null
+++ b/test/parallel/test-stream-duplex-end.js
@@ -0,0 +1,50 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+var assert = require('assert/');
+var Duplex = require('../../').Duplex;
+
+{
+ var stream = new Duplex({
+ read: function () {}
+ });
+ assert.strictEqual(stream.allowHalfOpen, true);
+ stream.on('finish', common.mustNotCall());
+ assert.strictEqual(stream.listenerCount('end'), 0);
+ stream.resume();
+ stream.push(null);
+}
+
+{
+ var _stream = new Duplex({
+ read: function () {},
+
+ allowHalfOpen: false
+ });
+ assert.strictEqual(_stream.allowHalfOpen, false);
+ _stream.on('finish', common.mustCall());
+ assert.strictEqual(_stream.listenerCount('end'), 1);
+ _stream.resume();
+ _stream.push(null);
+}
+
+{
+ var _stream2 = new Duplex({
+ read: function () {},
+
+ allowHalfOpen: false
+ });
+ assert.strictEqual(_stream2.allowHalfOpen, false);
+ _stream2._writableState.ended = true;
+ _stream2.on('finish', common.mustNotCall());
+ assert.strictEqual(_stream2.listenerCount('end'), 1);
+ _stream2.resume();
+ _stream2.push(null);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-duplex.js b/test/parallel/test-stream-duplex.js
index 9b121ca2ac..4e54d7d38c 100644
--- a/test/parallel/test-stream-duplex.js
+++ b/test/parallel/test-stream-duplex.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -31,6 +33,8 @@ var stream = new Duplex({ objectMode: true });
assert(Duplex() instanceof Duplex);
assert(stream._readableState.objectMode);
assert(stream._writableState.objectMode);
+assert(stream.allowHalfOpen);
+assert.strictEqual(stream.listenerCount('end'), 0);
var written = void 0;
var read = void 0;
@@ -52,4 +56,7 @@ stream.end({ val: 2 });
process.on('exit', function () {
assert.strictEqual(read.val, 1);
assert.strictEqual(written.val, 2);
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-end-paused.js b/test/parallel/test-stream-end-paused.js
index eeea575920..f9c4584da2 100644
--- a/test/parallel/test-stream-end-paused.js
+++ b/test/parallel/test-stream-end-paused.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -48,5 +50,7 @@ setTimeout(common.mustCall(function () {
process.on('exit', function () {
assert(calledRead);
- console.log('ok');
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-events-prepend.js b/test/parallel/test-stream-events-prepend.js
index b6d36d219f..7cdb62d096 100644
--- a/test/parallel/test-stream-events-prepend.js
+++ b/test/parallel/test-stream-events-prepend.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -49,4 +51,7 @@ var w = new Writable();
w.on('pipe', common.mustCall());
var r = new Readable();
-r.pipe(w);
\ No newline at end of file
+r.pipe(w);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-finished.js b/test/parallel/test-stream-finished.js
new file mode 100644
index 0000000000..90a375b40b
--- /dev/null
+++ b/test/parallel/test-stream-finished.js
@@ -0,0 +1,142 @@
+'use strict';
+
+function _asyncToGenerator(fn) { return function () { var gen = fn.apply(this, arguments); return new Promise(function (resolve, reject) { function step(key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { return Promise.resolve(value).then(function (value) { step("next", value); }, function (err) { step("throw", err); }); } } return step("next"); }); }; }
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+
+var _require = require('../../'),
+ Writable = _require.Writable,
+ Readable = _require.Readable,
+ Transform = _require.Transform,
+ finished = _require.finished;
+
+var assert = require('assert/');
+var fs = require('fs');
+var promisify = require('util-promisify');
+
+{
+ var rs = new Readable({
+ read: function () {}
+ });
+
+ finished(rs, common.mustCall(function (err) {
+ assert(!err, 'no error');
+ }));
+
+ rs.push(null);
+ rs.resume();
+}
+
+{
+ var ws = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ finished(ws, common.mustCall(function (err) {
+ assert(!err, 'no error');
+ }));
+
+ ws.end();
+}
+
+{
+ var tr = new Transform({
+ transform: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ var finish = false;
+ var ended = false;
+
+ tr.on('end', function () {
+ ended = true;
+ });
+
+ tr.on('finish', function () {
+ finish = true;
+ });
+
+ finished(tr, common.mustCall(function (err) {
+ assert(!err, 'no error');
+ assert(finish);
+ assert(ended);
+ }));
+
+ tr.end();
+ tr.resume();
+}
+
+{
+ var _rs = fs.createReadStream(__filename);
+
+ _rs.resume();
+ finished(_rs, common.mustCall());
+}
+
+{
+ var run = function () {
+ var _ref = _asyncToGenerator(function* () {
+ var rs = fs.createReadStream(__filename);
+ var done = common.mustCall();
+
+ var ended = false;
+ rs.resume();
+ rs.on('end', function () {
+ ended = true;
+ });
+ yield finishedPromise(rs);
+ assert(ended);
+ done();
+ });
+
+ return function run() {
+ return _ref.apply(this, arguments);
+ };
+ }();
+
+ var finishedPromise = promisify(finished);
+
+ run();
+}
+
+{
+ var _rs2 = fs.createReadStream('file-does-not-exist');
+
+ finished(_rs2, common.mustCall(function (err) {
+ assert.strictEqual(err.code, 'ENOENT');
+ }));
+}
+
+{
+ var _rs3 = new Readable();
+
+ finished(_rs3, common.mustCall(function (err) {
+ assert(!err, 'no error');
+ }));
+
+ _rs3.push(null);
+ _rs3.emit('close'); // should not trigger an error
+ _rs3.resume();
+}
+
+{
+ var _rs4 = new Readable();
+
+ finished(_rs4, common.mustCall(function (err) {
+ assert(err, 'premature close error');
+ }));
+
+ _rs4.emit('close'); // should trigger error
+ _rs4.push(null);
+ _rs4.resume();
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-ispaused.js b/test/parallel/test-stream-ispaused.js
index 6abb10fc13..4ecf700a4e 100644
--- a/test/parallel/test-stream-ispaused.js
+++ b/test/parallel/test-stream-ispaused.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -43,4 +45,7 @@ assert.ok(!readable.isPaused());
readable.pause();
assert.ok(readable.isPaused());
readable.resume();
-assert.ok(!readable.isPaused());
\ No newline at end of file
+assert.ok(!readable.isPaused());
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-objectmode-undefined.js b/test/parallel/test-stream-objectmode-undefined.js
index d1f5a0c700..72e34c0757 100644
--- a/test/parallel/test-stream-objectmode-undefined.js
+++ b/test/parallel/test-stream-objectmode-undefined.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -47,4 +49,7 @@ var _require = require('../../'),
}));
_stream2.write(undefined);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-after-end.js b/test/parallel/test-stream-pipe-after-end.js
index c9ed1aa721..6a289c9457 100644
--- a/test/parallel/test-stream-pipe-after-end.js
+++ b/test/parallel/test-stream-pipe-after-end.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -92,4 +94,7 @@ setTimeout(common.mustCall(function () {
var w = new TestWritable();
w.on('finish', common.mustCall());
piper.pipe(w);
-}), 1);
\ No newline at end of file
+}), 1);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-await-drain-manual-resume.js b/test/parallel/test-stream-pipe-await-drain-manual-resume.js
index 3475d3528e..5d605a4a1a 100644
--- a/test/parallel/test-stream-pipe-await-drain-manual-resume.js
+++ b/test/parallel/test-stream-pipe-await-drain-manual-resume.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -77,4 +79,7 @@ readable.push(null);
writable.on('finish', common.mustCall(function () {
assert.strictEqual(readable._readableState.awaitDrain, 0, 'awaitDrain should equal 0 after all chunks are written but instead got' + ('' + readable._readableState.awaitDrain));
// Everything okay, all chunks were written.
-}));
\ No newline at end of file
+}));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-await-drain-push-while-write.js b/test/parallel/test-stream-pipe-await-drain-push-while-write.js
index 7dc8de43a6..2ee2ce1afb 100644
--- a/test/parallel/test-stream-pipe-await-drain-push-while-write.js
+++ b/test/parallel/test-stream-pipe-await-drain-push-while-write.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -5,27 +7,20 @@ var common = require('../common');
var stream = require('../../');
var assert = require('assert/');
-var awaitDrainStates = [1, // after first chunk before callback
-1, // after second chunk before callback
-0 // resolving chunk pushed after first chunk, awaitDrain is decreased
-];
-
-// A writable stream which pushes data onto the stream which pipes into it,
-// but only the first time it's written to. Since it's not paused at this time,
-// a second write will occur. If the pipe increases awaitDrain twice, we'll
-// never get subsequent chunks because 'drain' is only emitted once.
var writable = new stream.Writable({
write: common.mustCall(function (chunk, encoding, cb) {
+ assert.strictEqual(readable._readableState.awaitDrain, 0);
+
if (chunk.length === 32 * 1024) {
// first chunk
- var beforePush = readable._readableState.awaitDrain;
readable.push(bufferShim.alloc(34 * 1024)); // above hwm
- // We should check if awaitDrain counter is increased.
- var afterPush = readable._readableState.awaitDrain;
- assert.strictEqual(afterPush - beforePush, 1, 'Counter is not increased for awaitDrain');
+ // We should check if awaitDrain counter is increased in the next
+ // tick, because awaitDrain is incremented after this method finished
+ process.nextTick(function () {
+ assert.strictEqual(readable._readableState.awaitDrain, 1);
+ });
}
- assert.strictEqual(awaitDrainStates.shift(), readable._readableState.awaitDrain, 'State variable awaitDrain is not correct.');
cb();
}, 3)
});
@@ -40,4 +35,7 @@ var readable = new stream.Readable({
}
});
-readable.pipe(writable);
\ No newline at end of file
+readable.pipe(writable);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-await-drain.js b/test/parallel/test-stream-pipe-await-drain.js
index 55cc714489..35bf348888 100644
--- a/test/parallel/test-stream-pipe-await-drain.js
+++ b/test/parallel/test-stream-pipe-await-drain.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -25,7 +27,7 @@ writer1._write = common.mustCall(function (chunk, encoding, cb) {
}, 1);
writer1.once('chunk-received', function () {
- assert.strictEqual(reader._readableState.awaitDrain, 0, 'initial value is not 0');
+ assert.strictEqual(reader._readableState.awaitDrain, 0, 'awaitDrain initial value should be 0, actual is ' + reader._readableState.awaitDrain);
setImmediate(function () {
// This one should *not* get through to writer1 because writer2 is not
// "done" processing.
@@ -35,14 +37,14 @@ writer1.once('chunk-received', function () {
// A "slow" consumer:
writer2._write = common.mustCall(function (chunk, encoding, cb) {
- assert.strictEqual(reader._readableState.awaitDrain, 1, 'awaitDrain isn\'t 1 after first push');
+ assert.strictEqual(reader._readableState.awaitDrain, 1, 'awaitDrain should be 1 after first push, actual is ' + reader._readableState.awaitDrain);
// Not calling cb here to "simulate" slow stream.
// This should be called exactly once, since the first .write() call
// will return false.
}, 1);
writer3._write = common.mustCall(function (chunk, encoding, cb) {
- assert.strictEqual(reader._readableState.awaitDrain, 2, 'awaitDrain isn\'t 2 after second push');
+ assert.strictEqual(reader._readableState.awaitDrain, 2, 'awaitDrain should be 2 after second push, actual is ' + reader._readableState.awaitDrain);
// Not calling cb here to "simulate" slow stream.
// This should be called exactly once, since the first .write() call
// will return false.
@@ -51,4 +53,7 @@ writer3._write = common.mustCall(function (chunk, encoding, cb) {
reader.pipe(writer1);
reader.pipe(writer2);
reader.pipe(writer3);
-reader.push(buffer);
\ No newline at end of file
+reader.push(buffer);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-cleanup-pause.js b/test/parallel/test-stream-pipe-cleanup-pause.js
index 6aad21ed15..8e1cbc02ff 100644
--- a/test/parallel/test-stream-pipe-cleanup-pause.js
+++ b/test/parallel/test-stream-pipe-cleanup-pause.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -36,4 +38,7 @@ writer2._write = common.mustCall(function (chunk, encoding, cb) {
}, 3);
reader.pipe(writer1);
-reader.push(buffer);
\ No newline at end of file
+reader.push(buffer);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-cleanup.js b/test/parallel/test-stream-pipe-cleanup.js
index e7151796f4..c16f1c629a 100644
--- a/test/parallel/test-stream-pipe-cleanup.js
+++ b/test/parallel/test-stream-pipe-cleanup.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -126,4 +128,6 @@ var util = require('util');
assert.strictEqual(d.listeners('close').length, 0);
assert.strictEqual(w.listeners('end').length, 0);
assert.strictEqual(w.listeners('close').length, 0);
-})();
\ No newline at end of file
+})();require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-error-handling.js b/test/parallel/test-stream-pipe-error-handling.js
index f6040812c9..de2b824fb6 100644
--- a/test/parallel/test-stream-pipe-error-handling.js
+++ b/test/parallel/test-stream-pipe-error-handling.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -109,4 +111,7 @@ var Stream = require('stream').Stream;
// Removing some OTHER random listener should not do anything
_w.removeListener('error', function () {});
_removed = true;
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-event.js b/test/parallel/test-stream-pipe-event.js
index ebe373e7d6..ac761c86b4 100644
--- a/test/parallel/test-stream-pipe-event.js
+++ b/test/parallel/test-stream-pipe-event.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -49,4 +51,7 @@ w.on('pipe', function (src) {
var r = new Readable();
r.pipe(w);
-assert.ok(passed);
\ No newline at end of file
+assert.ok(passed);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-flow-after-unpipe.js b/test/parallel/test-stream-pipe-flow-after-unpipe.js
new file mode 100644
index 0000000000..9c7fa184af
--- /dev/null
+++ b/test/parallel/test-stream-pipe-flow-after-unpipe.js
@@ -0,0 +1,42 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+var common = require('../common');
+
+var _require = require('../../'),
+ Readable = _require.Readable,
+ Writable = _require.Writable;
+
+// Tests that calling .unpipe() un-blocks a stream that is paused because
+// it is waiting on the writable side to finish a write().
+
+var rs = new Readable({
+ highWaterMark: 1,
+ // That this gets called at least 20 times is the real test here.
+ read: common.mustCallAtLeast(function () {
+ return rs.push('foo');
+ }, 20)
+});
+
+var ws = new Writable({
+ highWaterMark: 1,
+ write: common.mustCall(function () {
+ // Ignore the callback, this write() simply never finishes.
+ setImmediate(function () {
+ return rs.unpipe(ws);
+ });
+ })
+});
+
+var chunks = 0;
+rs.on('data', common.mustCallAtLeast(function () {
+ chunks++;
+ if (chunks >= 20) rs.pause(); // Finish this test.
+}));
+
+rs.pipe(ws);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-flow.js b/test/parallel/test-stream-pipe-flow.js
new file mode 100644
index 0000000000..b651f3902b
--- /dev/null
+++ b/test/parallel/test-stream-pipe-flow.js
@@ -0,0 +1,78 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+var common = require('../common');
+
+var _require = require('../../'),
+ Readable = _require.Readable,
+ Writable = _require.Writable,
+ PassThrough = _require.PassThrough;
+
+{
+ var ticks = 17;
+
+ var rs = new Readable({
+ objectMode: true,
+ read: function () {
+ if (ticks-- > 0) return process.nextTick(function () {
+ return rs.push({});
+ });
+ rs.push({});
+ rs.push(null);
+ }
+ });
+
+ var ws = new Writable({
+ highWaterMark: 0,
+ objectMode: true,
+ write: function (data, end, cb) {
+ return setImmediate(cb);
+ }
+ });
+
+ rs.on('end', common.mustCall());
+ ws.on('finish', common.mustCall());
+ rs.pipe(ws);
+}
+
+{
+ var missing = 8;
+
+ var _rs = new Readable({
+ objectMode: true,
+ read: function () {
+ if (missing--) _rs.push({});else _rs.push(null);
+ }
+ });
+
+ var pt = _rs.pipe(new PassThrough({ objectMode: true, highWaterMark: 2 })).pipe(new PassThrough({ objectMode: true, highWaterMark: 2 }));
+
+ pt.on('end', function () {
+ wrapper.push(null);
+ });
+
+ var wrapper = new Readable({
+ objectMode: true,
+ read: function () {
+ process.nextTick(function () {
+ var data = pt.read();
+ if (data === null) {
+ pt.once('readable', function () {
+ data = pt.read();
+ if (data !== null) wrapper.push(data);
+ });
+ } else {
+ wrapper.push(data);
+ }
+ });
+ }
+ });
+
+ wrapper.resume();
+ wrapper.on('end', common.mustCall());
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-manual-resume.js b/test/parallel/test-stream-pipe-manual-resume.js
new file mode 100644
index 0000000000..d6d7051fc7
--- /dev/null
+++ b/test/parallel/test-stream-pipe-manual-resume.js
@@ -0,0 +1,47 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+var common = require('../common');
+var stream = require('../../');
+
+function test(throwCodeInbetween) {
+ // Check that a pipe does not stall if .read() is called unexpectedly
+ // (i.e. the stream is not resumed by the pipe).
+
+ var n = 1000;
+ var counter = n;
+ var rs = stream.Readable({
+ objectMode: true,
+ read: common.mustCallAtLeast(function () {
+ if (--counter >= 0) rs.push({ counter: counter });else rs.push(null);
+ }, n)
+ });
+
+ var ws = stream.Writable({
+ objectMode: true,
+ write: common.mustCall(function (data, enc, cb) {
+ setImmediate(cb);
+ }, n)
+ });
+
+ setImmediate(function () {
+ return throwCodeInbetween(rs, ws);
+ });
+
+ rs.pipe(ws);
+}
+
+test(function (rs) {
+ return rs.read();
+});
+test(function (rs) {
+ return rs.resume();
+});
+test(function () {
+ return 0;
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-multiple-pipes.js b/test/parallel/test-stream-pipe-multiple-pipes.js
index 21abfcf18e..71952b4575 100644
--- a/test/parallel/test-stream-pipe-multiple-pipes.js
+++ b/test/parallel/test-stream-pipe-multiple-pipes.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -95,4 +97,7 @@ readable.on('end', common.mustCall(function () {
}
}
}
-}));
\ No newline at end of file
+}));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-same-destination-twice.js b/test/parallel/test-stream-pipe-same-destination-twice.js
index f3c0c895b3..9f77baf20b 100644
--- a/test/parallel/test-stream-pipe-same-destination-twice.js
+++ b/test/parallel/test-stream-pipe-same-destination-twice.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -80,4 +82,7 @@ var _require = require('../../'),
assert.strictEqual(_passThrough2._readableState.pipesCount, 0);
_passThrough2.write('foobar');
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-unpipe-streams.js b/test/parallel/test-stream-pipe-unpipe-streams.js
index 6cc3a10491..72ab9ea851 100644
--- a/test/parallel/test-stream-pipe-unpipe-streams.js
+++ b/test/parallel/test-stream-pipe-unpipe-streams.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -34,4 +36,49 @@ source.unpipe(dest2);
source.unpipe(dest1);
-assert.strictEqual(source._readableState.pipes, null);
\ No newline at end of file
+assert.strictEqual(source._readableState.pipes, null);
+
+{
+ // test `cleanup()` if we unpipe all streams.
+ var _source = Readable({ read: function () {} });
+ var _dest = Writable({ write: function () {} });
+ var _dest2 = Writable({ write: function () {} });
+
+ var destCount = 0;
+ var srcCheckEventNames = ['end', 'data'];
+ var destCheckEventNames = ['close', 'finish', 'drain', 'error', 'unpipe'];
+
+ var checkSrcCleanup = common.mustCall(function () {
+ assert.strictEqual(_source._readableState.pipes, null);
+ assert.strictEqual(_source._readableState.pipesCount, 0);
+ assert.strictEqual(_source._readableState.flowing, false);
+
+ srcCheckEventNames.forEach(function (eventName) {
+ assert.strictEqual(_source.listenerCount(eventName), 0, 'source\'s \'' + eventName + '\' event listeners not removed');
+ });
+ });
+
+ function checkDestCleanup(dest) {
+ var currentDestId = ++destCount;
+ _source.pipe(dest);
+
+ var unpipeChecker = common.mustCall(function () {
+ assert.deepStrictEqual(dest.listeners('unpipe'), [unpipeChecker], 'destination{' + currentDestId + '} should have a \'unpipe\' event ' + 'listener which is `unpipeChecker`');
+ dest.removeListener('unpipe', unpipeChecker);
+ destCheckEventNames.forEach(function (eventName) {
+ assert.strictEqual(dest.listenerCount(eventName), 0, 'destination{' + currentDestId + '}\'s \'' + eventName + '\' event ' + 'listeners not removed');
+ });
+
+ if (--destCount === 0) checkSrcCleanup();
+ });
+
+ dest.on('unpipe', unpipeChecker);
+ }
+
+ checkDestCleanup(_dest);
+ checkDestCleanup(_dest2);
+ _source.unpipe();
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipe-without-listenerCount.js b/test/parallel/test-stream-pipe-without-listenerCount.js
index 3bb5a9e4ef..8e4b437879 100644
--- a/test/parallel/test-stream-pipe-without-listenerCount.js
+++ b/test/parallel/test-stream-pipe-without-listenerCount.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -16,4 +18,7 @@ w.on('pipe', function () {
});
r.on('error', common.mustCall());
w.on('error', common.mustCall());
-r.pipe(w);
\ No newline at end of file
+r.pipe(w);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-pipeline.js b/test/parallel/test-stream-pipeline.js
new file mode 100644
index 0000000000..d8021fc0b4
--- /dev/null
+++ b/test/parallel/test-stream-pipeline.js
@@ -0,0 +1,510 @@
+'use strict';
+
+function _asyncToGenerator(fn) { return function () { var gen = fn.apply(this, arguments); return new Promise(function (resolve, reject) { function step(key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { return Promise.resolve(value).then(function (value) { step("next", value); }, function (err) { step("throw", err); }); } } return step("next"); }); }; }
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+if (!common.hasCrypto) common.skip('missing crypto');
+
+var _require = require('../../'),
+ Stream = _require.Stream,
+ Writable = _require.Writable,
+ Readable = _require.Readable,
+ Transform = _require.Transform,
+ pipeline = _require.pipeline;
+
+var assert = require('assert/');
+var http = require('http');
+var http2 = {
+ createServer: function () {
+ return {
+ listen: function () {}
+ };
+ }
+};
+var promisify = require('util-promisify');
+
+{
+ var finished = false;
+ var processed = [];
+ var expected = [bufferShim.from('a'), bufferShim.from('b'), bufferShim.from('c')];
+
+ var read = new Readable({
+ read: function () {}
+ });
+
+ var write = new Writable({
+ write: function (data, enc, cb) {
+ processed.push(data);
+ cb();
+ }
+ });
+
+ write.on('finish', function () {
+ finished = true;
+ });
+
+ for (var i = 0; i < expected.length; i++) {
+ read.push(expected[i]);
+ }
+ read.push(null);
+
+ pipeline(read, write, common.mustCall(function (err) {
+ assert.ok(!err, 'no error');
+ assert.ok(finished);
+ assert.deepStrictEqual(processed, expected);
+ }));
+}
+
+{
+ var _read = new Readable({
+ read: function () {}
+ });
+
+ assert.throws(function () {
+ pipeline(_read, function () {});
+ }, /ERR_MISSING_ARGS/);
+ assert.throws(function () {
+ pipeline(function () {});
+ }, /ERR_MISSING_ARGS/);
+ assert.throws(function () {
+ pipeline();
+ }, /ERR_MISSING_ARGS/);
+}
+
+{
+ var _read2 = new Readable({
+ read: function () {}
+ });
+
+ var _write = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ _read2.push('data');
+ setImmediate(function () {
+ return _read2.destroy();
+ });
+
+ pipeline(_read2, _write, common.mustCall(function (err) {
+ assert.ok(err, 'should have an error');
+ }));
+}
+
+{
+ var _read3 = new Readable({
+ read: function () {}
+ });
+
+ var _write2 = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ _read3.push('data');
+ setImmediate(function () {
+ return _read3.destroy(new Error('kaboom'));
+ });
+
+ var dst = pipeline(_read3, _write2, common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ }));
+
+ assert.strictEqual(dst, _write2);
+}
+
+{
+ var _read4 = new Readable({
+ read: function () {}
+ });
+
+ var transform = new Transform({
+ transform: function (data, enc, cb) {
+ process.nextTick(cb, new Error('kaboom'));
+ }
+ });
+
+ var _write3 = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ _read4.on('close', common.mustCall());
+ transform.on('close', common.mustCall());
+ _write3.on('close', common.mustCall());
+
+ var _dst = pipeline(_read4, transform, _write3, common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ }));
+
+ assert.strictEqual(_dst, _write3);
+
+ _read4.push('hello');
+}
+
+{
+ var server = http.createServer(function (req, res) {
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ rs.push(null);
+ }
+ });
+
+ pipeline(rs, res, function () {});
+ });
+
+ server.listen(0, function () {
+ var req = http.request({
+ port: server.address().port
+ });
+
+ req.end();
+ req.on('response', function (res) {
+ var buf = [];
+ res.on('data', function (data) {
+ return buf.push(data);
+ });
+ res.on('end', common.mustCall(function () {
+ assert.deepStrictEqual(Buffer.concat(buf), bufferShim.from('hello'));
+ server.close();
+ }));
+ });
+ });
+}
+
+{
+ var _server = http.createServer(function (req, res) {
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ },
+
+ destroy: common.mustCall(function (err, cb) {
+ // prevents fd leaks by destroying http pipelines
+ cb();
+ })
+ });
+
+ pipeline(rs, res, function () {});
+ });
+
+ _server.listen(0, function () {
+ var req = http.request({
+ port: _server.address().port
+ });
+
+ req.end();
+ req.on('response', function (res) {
+ setImmediate(function () {
+ res.destroy();
+ _server.close();
+ });
+ });
+ });
+}
+
+{
+ var _server2 = http.createServer(function (req, res) {
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ },
+
+ destroy: common.mustCall(function (err, cb) {
+ cb();
+ })
+ });
+
+ pipeline(rs, res, function () {});
+ });
+
+ var cnt = 10;
+
+ var badSink = new Writable({
+ write: function (data, enc, cb) {
+ cnt--;
+ if (cnt === 0) process.nextTick(cb, new Error('kaboom'));else cb();
+ }
+ });
+
+ _server2.listen(0, function () {
+ var req = http.request({
+ port: _server2.address().port
+ });
+
+ req.end();
+ req.on('response', function (res) {
+ pipeline(res, badSink, common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ _server2.close();
+ }));
+ });
+ });
+}
+
+{
+ var _server3 = http.createServer(function (req, res) {
+ pipeline(req, res, common.mustCall());
+ });
+
+ _server3.listen(0, function () {
+ var req = http.request({
+ port: _server3.address().port
+ });
+
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ }
+ });
+
+ pipeline(rs, req, common.mustCall(function () {
+ _server3.close();
+ }));
+
+ req.on('response', function (res) {
+ var cnt = 10;
+ res.on('data', function () {
+ cnt--;
+ if (cnt === 0) rs.destroy();
+ });
+ });
+ });
+}
+
+{
+ var _server4 = http2.createServer(function (req, res) {
+ pipeline(req, res, common.mustCall());
+ });
+
+ _server4.listen(0, function () {
+ var url = 'http://localhost:' + _server4.address().port;
+ var client = http2.connect(url);
+ var req = client.request({ ':method': 'POST' });
+
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ }
+ });
+
+ pipeline(rs, req, common.mustCall(function (err) {
+ _server4.close();
+ client.close();
+ }));
+
+ var cnt = 10;
+ req.on('data', function (data) {
+ cnt--;
+ if (cnt === 0) rs.destroy();
+ });
+ });
+}
+
+{
+ var makeTransform = function () {
+ var tr = new Transform({
+ transform: function (data, enc, cb) {
+ cb(null, data);
+ }
+ });
+
+ tr.on('close', common.mustCall());
+ return tr;
+ };
+
+ var rs = new Readable({
+ read: function () {
+ rs.push('hello');
+ }
+ });
+
+ var _cnt = 10;
+
+ var ws = new Writable({
+ write: function (data, enc, cb) {
+ _cnt--;
+ if (_cnt === 0) return process.nextTick(cb, new Error('kaboom'));
+ cb();
+ }
+ });
+
+ rs.on('close', common.mustCall());
+ ws.on('close', common.mustCall());
+
+ pipeline(rs, makeTransform(), makeTransform(), makeTransform(), makeTransform(), makeTransform(), makeTransform(), ws, common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ }));
+}
+
+{
+ var oldStream = new Stream();
+
+ oldStream.pause = oldStream.resume = function () {};
+ oldStream.write = function (data) {
+ oldStream.emit('data', data);
+ return true;
+ };
+ oldStream.end = function () {
+ oldStream.emit('end');
+ };
+
+ var _expected = [bufferShim.from('hello'), bufferShim.from('world')];
+
+ var _rs = new Readable({
+ read: function () {
+ for (var _i = 0; _i < _expected.length; _i++) {
+ _rs.push(_expected[_i]);
+ }
+ _rs.push(null);
+ }
+ });
+
+ var _ws = new Writable({
+ write: function (data, enc, cb) {
+ assert.deepStrictEqual(data, _expected.shift());
+ cb();
+ }
+ });
+
+ var _finished = false;
+
+ _ws.on('finish', function () {
+ _finished = true;
+ });
+
+ pipeline(_rs, oldStream, _ws, common.mustCall(function (err) {
+ assert(!err, 'no error');
+ assert(_finished, 'last stream finished');
+ }));
+}
+
+{
+ var _oldStream = new Stream();
+
+ _oldStream.pause = _oldStream.resume = function () {};
+ _oldStream.write = function (data) {
+ _oldStream.emit('data', data);
+ return true;
+ };
+ _oldStream.end = function () {
+ _oldStream.emit('end');
+ };
+
+ var destroyableOldStream = new Stream();
+
+ destroyableOldStream.pause = destroyableOldStream.resume = function () {};
+ destroyableOldStream.destroy = common.mustCall(function () {
+ destroyableOldStream.emit('close');
+ });
+ destroyableOldStream.write = function (data) {
+ destroyableOldStream.emit('data', data);
+ return true;
+ };
+ destroyableOldStream.end = function () {
+ destroyableOldStream.emit('end');
+ };
+
+ var _rs2 = new Readable({
+ read: function () {
+ _rs2.destroy(new Error('stop'));
+ }
+ });
+
+ var _ws2 = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ var _finished2 = false;
+
+ _ws2.on('finish', function () {
+ _finished2 = true;
+ });
+
+ pipeline(_rs2, _oldStream, destroyableOldStream, _ws2, common.mustCall(function (err) {
+ assert.deepStrictEqual(err, new Error('stop'));
+ assert(!_finished2, 'should not finish');
+ }));
+}
+
+{
+ var run = function () {
+ var _ref = _asyncToGenerator(function* () {
+ var read = new Readable({
+ read: function () {}
+ });
+
+ var write = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ read.push('data');
+ read.push(null);
+
+ var finished = false;
+
+ write.on('finish', function () {
+ finished = true;
+ });
+
+ yield pipelinePromise(read, write);
+
+ assert(finished);
+ });
+
+ return function run() {
+ return _ref.apply(this, arguments);
+ };
+ }();
+
+ var pipelinePromise = promisify(pipeline);
+
+ run();
+}
+
+{
+ var _read5 = new Readable({
+ read: function () {}
+ });
+
+ var _transform = new Transform({
+ transform: function (data, enc, cb) {
+ process.nextTick(cb, new Error('kaboom'));
+ }
+ });
+
+ var _write4 = new Writable({
+ write: function (data, enc, cb) {
+ cb();
+ }
+ });
+
+ _read5.on('close', common.mustCall());
+ _transform.on('close', common.mustCall());
+ _write4.on('close', common.mustCall());
+
+ process.on('uncaughtException', common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ }));
+
+ var _dst2 = pipeline(_read5, _transform, _write4);
+
+ assert.strictEqual(_dst2, _write4);
+
+ _read5.push('hello');
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-push-order.js b/test/parallel/test-stream-push-order.js
index 166d51d6b9..55b7f7d238 100644
--- a/test/parallel/test-stream-push-order.js
+++ b/test/parallel/test-stream-push-order.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -49,6 +51,9 @@ s.read(0);
// ACTUALLY [1, 3, 5, 6, 4, 2]
process.on('exit', function () {
- assert.deepStrictEqual(s._readableState.buffer.join(','), '1,2,3,4,5,6');
- console.log('ok');
+ assert.deepStrictEqual(s.readableBuffer.join(','), '1,2,3,4,5,6');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-push-strings.js b/test/parallel/test-stream-push-strings.js
index 00a6e8354c..60d4fd2e60 100644
--- a/test/parallel/test-stream-push-strings.js
+++ b/test/parallel/test-stream-push-strings.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -82,5 +84,8 @@ var expect = ['first chunksecond to last chunk', 'last chunk'];
process.on('exit', function () {
assert.strictEqual(ms._chunks, -1);
assert.deepStrictEqual(results, expect);
- console.log('ok');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-async-iterators.js b/test/parallel/test-stream-readable-async-iterators.js
new file mode 100644
index 0000000000..a3feea6aae
--- /dev/null
+++ b/test/parallel/test-stream-readable-async-iterators.js
@@ -0,0 +1,495 @@
+'use strict';
+
+var tests = function () {
+ var _ref = _asyncToGenerator(function* () {
+ yield _asyncToGenerator(function* () {
+ console.log('read without for..await');
+ var max = 5;
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {}
+ });
+
+ var iter = readable[Symbol.asyncIterator]();
+ assert.strictEqual(iter.stream, readable);
+ var values = [];
+ for (var i = 0; i < max; i++) {
+ values.push(iter.next());
+ }
+ Promise.all(values).then(common.mustCall(function (values) {
+ values.forEach(common.mustCall(function (item, i) {
+ return assert.strictEqual(item.value, 'hello-' + i);
+ }, 5));
+ }));
+
+ readable.push('hello-0');
+ readable.push('hello-1');
+ readable.push('hello-2');
+ readable.push('hello-3');
+ readable.push('hello-4');
+ readable.push(null);
+
+ var last = yield iter.next();
+ assert.strictEqual(last.done, true);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('read without for..await deferred');
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {}
+ });
+
+ var iter = readable[Symbol.asyncIterator]();
+ assert.strictEqual(iter.stream, readable);
+ var values = [];
+ for (var i = 0; i < 3; i++) {
+ values.push(iter.next());
+ }
+
+ readable.push('hello-0');
+ readable.push('hello-1');
+ readable.push('hello-2');
+
+ var k = 0;
+ var results1 = yield Promise.all(values);
+ results1.forEach(common.mustCall(function (item) {
+ return assert.strictEqual(item.value, 'hello-' + k++);
+ }, 3));
+
+ values = [];
+ for (var _i = 0; _i < 2; _i++) {
+ values.push(iter.next());
+ }
+
+ readable.push('hello-3');
+ readable.push('hello-4');
+ readable.push(null);
+
+ var results2 = yield Promise.all(values);
+ results2.forEach(common.mustCall(function (item) {
+ return assert.strictEqual(item.value, 'hello-' + k++);
+ }, 2));
+
+ var last = yield iter.next();
+ assert.strictEqual(last.done, true);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('read without for..await with errors');
+ var max = 3;
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {}
+ });
+
+ var iter = readable[Symbol.asyncIterator]();
+ assert.strictEqual(iter.stream, readable);
+ var values = [];
+ var errors = [];
+ var i = void 0;
+ for (i = 0; i < max; i++) {
+ values.push(iter.next());
+ }
+ for (i = 0; i < 2; i++) {
+ errors.push(iter.next());
+ }
+
+ readable.push('hello-0');
+ readable.push('hello-1');
+ readable.push('hello-2');
+
+ var resolved = yield Promise.all(values);
+
+ resolved.forEach(common.mustCall(function (item, i) {
+ return assert.strictEqual(item.value, 'hello-' + i);
+ }, max));
+
+ errors.forEach(function (promise) {
+ promise.catch(common.mustCall(function (err) {
+ assert.strictEqual(err.message, 'kaboom');
+ }));
+ });
+
+ readable.destroy(new Error('kaboom'));
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('call next() after error');
+ var readable = new Readable({
+ read: function () {}
+ });
+ var iterator = readable[Symbol.asyncIterator]();
+
+ var err = new Error('kaboom');
+ readable.destroy(new Error('kaboom'));
+ yield function (f, e) {
+ var success = false;f().then(function () {
+ success = true;throw new Error('should not succeeed');
+ }).catch(function (e2) {
+ if (success) {
+ throw e2;
+ }assert.strictEqual(e.message, e2.message);
+ });
+ }(iterator.next.bind(iterator), err);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('read object mode');
+ var max = 42;
+ var readed = 0;
+ var received = 0;
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ this.push('hello');
+ if (++readed === max) {
+ this.push(null);
+ }
+ }
+ });
+
+ var _iteratorNormalCompletion = true;
+ var _didIteratorError = false;
+ var _iteratorError = undefined;
+
+ try {
+ for (var _iterator = _asyncIterator(readable), _step, _value; _step = yield _iterator.next(), _iteratorNormalCompletion = _step.done, _value = yield _step.value, !_iteratorNormalCompletion; _iteratorNormalCompletion = true) {
+ var k = _value;
+
+ received++;
+ assert.strictEqual(k, 'hello');
+ }
+ } catch (err) {
+ _didIteratorError = true;
+ _iteratorError = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion && _iterator.return) {
+ yield _iterator.return();
+ }
+ } finally {
+ if (_didIteratorError) {
+ throw _iteratorError;
+ }
+ }
+ }
+
+ assert.strictEqual(readed, received);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('destroy sync');
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ this.destroy(new Error('kaboom from read'));
+ }
+ });
+
+ var err = void 0;
+ try {
+ // eslint-disable-next-line no-unused-vars
+ var _iteratorNormalCompletion2 = true;
+ var _didIteratorError2 = false;
+ var _iteratorError2 = undefined;
+
+ try {
+ for (var _iterator2 = _asyncIterator(readable), _step2, _value2; _step2 = yield _iterator2.next(), _iteratorNormalCompletion2 = _step2.done, _value2 = yield _step2.value, !_iteratorNormalCompletion2; _iteratorNormalCompletion2 = true) {
+ var k = _value2;
+ }
+ } catch (err) {
+ _didIteratorError2 = true;
+ _iteratorError2 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion2 && _iterator2.return) {
+ yield _iterator2.return();
+ }
+ } finally {
+ if (_didIteratorError2) {
+ throw _iteratorError2;
+ }
+ }
+ }
+ } catch (e) {
+ err = e;
+ }
+ assert.strictEqual(err.message, 'kaboom from read');
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('destroy async');
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ var _this = this;
+
+ if (!this.pushed) {
+ this.push('hello');
+ this.pushed = true;
+
+ setImmediate(function () {
+ _this.destroy(new Error('kaboom'));
+ });
+ }
+ }
+ });
+
+ var received = 0;
+
+ var err = null;
+ try {
+ // eslint-disable-next-line no-unused-vars
+ var _iteratorNormalCompletion3 = true;
+ var _didIteratorError3 = false;
+ var _iteratorError3 = undefined;
+
+ try {
+ for (var _iterator3 = _asyncIterator(readable), _step3, _value3; _step3 = yield _iterator3.next(), _iteratorNormalCompletion3 = _step3.done, _value3 = yield _step3.value, !_iteratorNormalCompletion3; _iteratorNormalCompletion3 = true) {
+ var k = _value3;
+
+ received++;
+ }
+ } catch (err) {
+ _didIteratorError3 = true;
+ _iteratorError3 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion3 && _iterator3.return) {
+ yield _iterator3.return();
+ }
+ } finally {
+ if (_didIteratorError3) {
+ throw _iteratorError3;
+ }
+ }
+ }
+ } catch (e) {
+ err = e;
+ }
+
+ assert.strictEqual(err.message, 'kaboom');
+ assert.strictEqual(received, 1);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('destroyed by throw');
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ this.push('hello');
+ }
+ });
+
+ var err = null;
+ try {
+ var _iteratorNormalCompletion4 = true;
+ var _didIteratorError4 = false;
+ var _iteratorError4 = undefined;
+
+ try {
+ for (var _iterator4 = _asyncIterator(readable), _step4, _value4; _step4 = yield _iterator4.next(), _iteratorNormalCompletion4 = _step4.done, _value4 = yield _step4.value, !_iteratorNormalCompletion4; _iteratorNormalCompletion4 = true) {
+ var k = _value4;
+
+ assert.strictEqual(k, 'hello');
+ throw new Error('kaboom');
+ }
+ } catch (err) {
+ _didIteratorError4 = true;
+ _iteratorError4 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion4 && _iterator4.return) {
+ yield _iterator4.return();
+ }
+ } finally {
+ if (_didIteratorError4) {
+ throw _iteratorError4;
+ }
+ }
+ }
+ } catch (e) {
+ err = e;
+ }
+
+ assert.strictEqual(err.message, 'kaboom');
+ assert.strictEqual(readable.destroyed, true);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('destroyed sync after push');
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ this.push('hello');
+ this.destroy(new Error('kaboom'));
+ }
+ });
+
+ var received = 0;
+
+ var err = null;
+ try {
+ var _iteratorNormalCompletion5 = true;
+ var _didIteratorError5 = false;
+ var _iteratorError5 = undefined;
+
+ try {
+ for (var _iterator5 = _asyncIterator(readable), _step5, _value5; _step5 = yield _iterator5.next(), _iteratorNormalCompletion5 = _step5.done, _value5 = yield _step5.value, !_iteratorNormalCompletion5; _iteratorNormalCompletion5 = true) {
+ var k = _value5;
+
+ assert.strictEqual(k, 'hello');
+ received++;
+ }
+ } catch (err) {
+ _didIteratorError5 = true;
+ _iteratorError5 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion5 && _iterator5.return) {
+ yield _iterator5.return();
+ }
+ } finally {
+ if (_didIteratorError5) {
+ throw _iteratorError5;
+ }
+ }
+ }
+ } catch (e) {
+ err = e;
+ }
+
+ assert.strictEqual(err.message, 'kaboom');
+ assert.strictEqual(received, 1);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('push async');
+ var max = 42;
+ var readed = 0;
+ var received = 0;
+ var readable = new Readable({
+ objectMode: true,
+ read: function () {
+ var _this2 = this;
+
+ setImmediate(function () {
+ _this2.push('hello');
+ if (++readed === max) {
+ _this2.push(null);
+ }
+ });
+ }
+ });
+
+ var _iteratorNormalCompletion6 = true;
+ var _didIteratorError6 = false;
+ var _iteratorError6 = undefined;
+
+ try {
+ for (var _iterator6 = _asyncIterator(readable), _step6, _value6; _step6 = yield _iterator6.next(), _iteratorNormalCompletion6 = _step6.done, _value6 = yield _step6.value, !_iteratorNormalCompletion6; _iteratorNormalCompletion6 = true) {
+ var k = _value6;
+
+ received++;
+ assert.strictEqual(k, 'hello');
+ }
+ } catch (err) {
+ _didIteratorError6 = true;
+ _iteratorError6 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion6 && _iterator6.return) {
+ yield _iterator6.return();
+ }
+ } finally {
+ if (_didIteratorError6) {
+ throw _iteratorError6;
+ }
+ }
+ }
+
+ assert.strictEqual(readed, received);
+ })();
+
+ yield _asyncToGenerator(function* () {
+ console.log('push binary async');
+ var max = 42;
+ var readed = 0;
+ var readable = new Readable({
+ read: function () {
+ var _this3 = this;
+
+ setImmediate(function () {
+ _this3.push('hello');
+ if (++readed === max) {
+ _this3.push(null);
+ }
+ });
+ }
+ });
+
+ var expected = '';
+ readable.setEncoding('utf8');
+ readable.pause();
+ readable.on('data', function (chunk) {
+ expected += chunk;
+ });
+
+ var data = '';
+ var _iteratorNormalCompletion7 = true;
+ var _didIteratorError7 = false;
+ var _iteratorError7 = undefined;
+
+ try {
+ for (var _iterator7 = _asyncIterator(readable), _step7, _value7; _step7 = yield _iterator7.next(), _iteratorNormalCompletion7 = _step7.done, _value7 = yield _step7.value, !_iteratorNormalCompletion7; _iteratorNormalCompletion7 = true) {
+ var k = _value7;
+
+ data += k;
+ }
+ } catch (err) {
+ _didIteratorError7 = true;
+ _iteratorError7 = err;
+ } finally {
+ try {
+ if (!_iteratorNormalCompletion7 && _iterator7.return) {
+ yield _iterator7.return();
+ }
+ } finally {
+ if (_didIteratorError7) {
+ throw _iteratorError7;
+ }
+ }
+ }
+
+ assert.strictEqual(data, expected);
+ })();
+ });
+
+ return function tests() {
+ return _ref.apply(this, arguments);
+ };
+}();
+
+// to avoid missing some tests if a promise does not resolve
+
+
+function _asyncIterator(iterable) { if (typeof Symbol === "function") { if (Symbol.asyncIterator) { var method = iterable[Symbol.asyncIterator]; if (method != null) return method.call(iterable); } if (Symbol.iterator) { return iterable[Symbol.iterator](); } } throw new TypeError("Object is not async iterable"); }
+
+function _asyncToGenerator(fn) { return function () { var gen = fn.apply(this, arguments); return new Promise(function (resolve, reject) { function step(key, arg) { try { var info = gen[key](arg); var value = info.value; } catch (error) { reject(error); return; } if (info.done) { resolve(value); } else { return Promise.resolve(value).then(function (value) { step("next", value); }, function (err) { step("throw", err); }); } } return step("next"); }); }; }
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+var assert = require('assert/');
+
+tests().then(common.mustCall());
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-constructor-set-methods.js b/test/parallel/test-stream-readable-constructor-set-methods.js
index 7974f9c290..15302105d0 100644
--- a/test/parallel/test-stream-readable-constructor-set-methods.js
+++ b/test/parallel/test-stream-readable-constructor-set-methods.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -10,4 +12,7 @@ var _read = common.mustCall(function _read(n) {
});
var r = new Readable({ read: _read });
-r.resume();
\ No newline at end of file
+r.resume();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-destroy.js b/test/parallel/test-stream-readable-destroy.js
index 3df1e2a180..e5a73d36dd 100644
--- a/test/parallel/test-stream-readable-destroy.js
+++ b/test/parallel/test-stream-readable-destroy.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -18,7 +20,7 @@ var _require2 = require('util'),
});
read.resume();
- read.on('end', common.mustCall());
+ read.on('close', common.mustCall());
read.destroy();
assert.strictEqual(read.destroyed, true);
@@ -32,7 +34,8 @@ var _require2 = require('util'),
var expected = new Error('kaboom');
- _read.on('end', common.mustCall());
+ _read.on('end', common.mustNotCall('no end event'));
+ _read.on('close', common.mustCall());
_read.on('error', common.mustCall(function (err) {
assert.strictEqual(err, expected);
}));
@@ -54,6 +57,7 @@ var _require2 = require('util'),
var _expected = new Error('kaboom');
_read2.on('end', common.mustNotCall('no end event'));
+ _read2.on('close', common.mustCall());
_read2.on('error', common.mustCall(function (err) {
assert.strictEqual(err, _expected);
}));
@@ -78,6 +82,7 @@ var _require2 = require('util'),
// error is swallowed by the custom _destroy
_read3.on('error', common.mustNotCall('no error event'));
+ _read3.on('close', common.mustCall());
_read3.destroy(_expected2);
assert.strictEqual(_read3.destroyed, true);
@@ -116,6 +121,7 @@ var _require2 = require('util'),
var fail = common.mustNotCall('no end event');
_read5.on('end', fail);
+ _read5.on('close', common.mustCall());
_read5.destroy();
@@ -180,7 +186,21 @@ var _require2 = require('util'),
var _expected4 = new Error('kaboom');
+ _read8.on('close', common.mustCall());
_read8.destroy(_expected4, common.mustCall(function (err) {
assert.strictEqual(_expected4, err);
}));
-}
\ No newline at end of file
+}
+
+{
+ var _read9 = new Readable({
+ read: function () {}
+ });
+
+ _read9.destroy();
+ _read9.push('hi');
+ _read9.on('data', common.mustNotCall());
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-emittedReadable.js b/test/parallel/test-stream-readable-emittedReadable.js
index 13695547f7..4812dcb4ab 100644
--- a/test/parallel/test-stream-readable-emittedReadable.js
+++ b/test/parallel/test-stream-readable-emittedReadable.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -12,30 +14,33 @@ var readable = new Readable({
// Initialized to false.
assert.strictEqual(readable._readableState.emittedReadable, false);
+var expected = [bufferShim.from('foobar'), bufferShim.from('quo'), null];
readable.on('readable', common.mustCall(function () {
// emittedReadable should be true when the readable event is emitted
assert.strictEqual(readable._readableState.emittedReadable, true);
- readable.read();
+ assert.deepStrictEqual(readable.read(), expected.shift());
// emittedReadable is reset to false during read()
assert.strictEqual(readable._readableState.emittedReadable, false);
-}, 4));
+}, 3));
// When the first readable listener is just attached,
// emittedReadable should be false
assert.strictEqual(readable._readableState.emittedReadable, false);
-// Each one of these should trigger a readable event.
+// These trigger a single 'readable', as things are batched up
process.nextTick(common.mustCall(function () {
readable.push('foo');
}));
process.nextTick(common.mustCall(function () {
readable.push('bar');
}));
-process.nextTick(common.mustCall(function () {
+
+// these triggers two readable events
+setImmediate(common.mustCall(function () {
readable.push('quo');
-}));
-process.nextTick(common.mustCall(function () {
- readable.push(null);
+ process.nextTick(common.mustCall(function () {
+ readable.push(null);
+ }));
}));
var noRead = new Readable({
@@ -69,4 +74,7 @@ flowing.push('bar');
flowing.push('quo');
process.nextTick(common.mustCall(function () {
flowing.push(null);
-}));
\ No newline at end of file
+}));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-event.js b/test/parallel/test-stream-readable-event.js
index 587f1acbef..62f39ef40f 100644
--- a/test/parallel/test-stream-readable-event.js
+++ b/test/parallel/test-stream-readable-event.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -84,4 +86,54 @@ var Readable = require('../../').Readable;
assert(!_r2._readableState.reading);
_r2.on('readable', common.mustCall());
}, 1);
-}
\ No newline at end of file
+}
+
+{
+ // pushing a empty string in non-objectMode should
+ // trigger next `read()`.
+ var underlyingData = ['', 'x', 'y', '', 'z'];
+ var expected = underlyingData.filter(function (data) {
+ return data;
+ });
+ var result = [];
+
+ var _r3 = new Readable({
+ encoding: 'utf8'
+ });
+ _r3._read = function () {
+ var _this = this;
+
+ process.nextTick(function () {
+ if (!underlyingData.length) {
+ _this.push(null);
+ } else {
+ _this.push(underlyingData.shift());
+ }
+ });
+ };
+
+ _r3.on('readable', function () {
+ var data = _r3.read();
+ if (data !== null) result.push(data);
+ });
+
+ _r3.on('end', common.mustCall(function () {
+ assert.deepStrictEqual(result, expected);
+ }));
+}
+
+{
+ // #20923
+ var _r4 = new Readable();
+ _r4._read = function () {
+ // actually doing thing here
+ };
+ _r4.on('data', function () {});
+
+ _r4.removeAllListeners();
+
+ assert.strictEqual(_r4.eventNames().length, 0);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-flow-recursion.js b/test/parallel/test-stream-readable-flow-recursion.js
index 0b6704a212..1e81189c16 100644
--- a/test/parallel/test-stream-readable-flow-recursion.js
+++ b/test/parallel/test-stream-readable-flow-recursion.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -66,8 +68,11 @@ process.on('exit', function (code) {
// we pushed up the high water mark
assert.strictEqual(stream.readableHighWaterMark, 8192);
// length is 0 right now, because we pulled it all out.
- assert.strictEqual(stream._readableState.length, 0);
+ assert.strictEqual(stream.readableLength, 0);
assert(!code);
assert.strictEqual(depth, 0);
- console.log('ok');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-invalid-chunk.js b/test/parallel/test-stream-readable-invalid-chunk.js
index 81f0eed852..c756875a8e 100644
--- a/test/parallel/test-stream-readable-invalid-chunk.js
+++ b/test/parallel/test-stream-readable-invalid-chunk.js
@@ -1,22 +1,32 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
+var common = require('../common');
var stream = require('../../');
-var assert = require('assert/');
var readable = new stream.Readable({
read: function () {}
});
-var errMessage = /Invalid non-string\/buffer chunk/;
-assert.throws(function () {
+function checkError(fn) {
+ common.expectsError(fn, {
+ code: 'ERR_INVALID_ARG_TYPE',
+ type: TypeError
+ });
+}
+
+checkError(function () {
return readable.push([]);
-}, errMessage);
-assert.throws(function () {
+});
+checkError(function () {
return readable.push({});
-}, errMessage);
-assert.throws(function () {
+});
+checkError(function () {
return readable.push(0);
-}, errMessage);
\ No newline at end of file
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-needReadable.js b/test/parallel/test-stream-readable-needReadable.js
index b7e1d5ec7f..fa1a793b6f 100644
--- a/test/parallel/test-stream-readable-needReadable.js
+++ b/test/parallel/test-stream-readable-needReadable.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -40,7 +42,7 @@ asyncReadable.on('readable', common.mustCall(function () {
// then we need to notify the reader on future changes.
assert.strictEqual(asyncReadable._readableState.needReadable, true);
}
-}, 3));
+}, 2));
process.nextTick(common.mustCall(function () {
asyncReadable.push('foooo');
@@ -48,8 +50,9 @@ process.nextTick(common.mustCall(function () {
process.nextTick(common.mustCall(function () {
asyncReadable.push('bar');
}));
-process.nextTick(common.mustCall(function () {
+setImmediate(common.mustCall(function () {
asyncReadable.push(null);
+ assert.strictEqual(asyncReadable._readableState.needReadable, false);
}));
var flowing = new Readable({
@@ -86,13 +89,16 @@ slowProducer.on('readable', common.mustCall(function () {
process.nextTick(common.mustCall(function () {
slowProducer.push('foo');
+ process.nextTick(common.mustCall(function () {
+ slowProducer.push('foo');
+ process.nextTick(common.mustCall(function () {
+ slowProducer.push('foo');
+ process.nextTick(common.mustCall(function () {
+ slowProducer.push(null);
+ }));
+ }));
+ }));
}));
-process.nextTick(common.mustCall(function () {
- slowProducer.push('foo');
-}));
-process.nextTick(common.mustCall(function () {
- slowProducer.push('foo');
-}));
-process.nextTick(common.mustCall(function () {
- slowProducer.push(null);
-}));
\ No newline at end of file
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-no-unneeded-readable.js b/test/parallel/test-stream-readable-no-unneeded-readable.js
new file mode 100644
index 0000000000..d7d9b1ed1a
--- /dev/null
+++ b/test/parallel/test-stream-readable-no-unneeded-readable.js
@@ -0,0 +1,74 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+var common = require('../common');
+
+var _require = require('../../'),
+ Readable = _require.Readable,
+ PassThrough = _require.PassThrough;
+
+function test(r) {
+ var wrapper = new Readable({
+ read: function () {
+ var data = r.read();
+
+ if (data) {
+ wrapper.push(data);
+ return;
+ }
+
+ r.once('readable', function () {
+ data = r.read();
+ if (data) {
+ wrapper.push(data);
+ }
+ // else the end event should fire
+ });
+ }
+ });
+
+ r.once('end', function () {
+ wrapper.push(null);
+ });
+
+ wrapper.resume();
+ wrapper.once('end', common.mustCall());
+}
+
+{
+ var source = new Readable({
+ read: function () {}
+ });
+ source.push('foo');
+ source.push('bar');
+ source.push(null);
+
+ var pt = source.pipe(new PassThrough());
+ test(pt);
+}
+
+{
+ // This is the underlying cause of the above test case.
+ var pushChunks = ['foo', 'bar'];
+ var r = new Readable({
+ read: function () {
+ var chunk = pushChunks.shift();
+ if (chunk) {
+ // synchronous call
+ r.push(chunk);
+ } else {
+ // asynchronous call
+ process.nextTick(function () {
+ return r.push(null);
+ });
+ }
+ }
+ });
+
+ test(r);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-object-multi-push-async.js b/test/parallel/test-stream-readable-object-multi-push-async.js
new file mode 100644
index 0000000000..4c987c069a
--- /dev/null
+++ b/test/parallel/test-stream-readable-object-multi-push-async.js
@@ -0,0 +1,204 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var common = require('../common');
+var assert = require('assert/');
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+var MAX = 42;
+var BATCH = 10;
+
+{
+ var readable = new Readable({
+ objectMode: true,
+ read: common.mustCall(function () {
+ var _this = this;
+
+ console.log('>> READ');
+ fetchData(function (err, data) {
+ if (err) {
+ _this.destroy(err);
+ return;
+ }
+
+ if (data.length === 0) {
+ console.log('pushing null');
+ _this.push(null);
+ return;
+ }
+
+ console.log('pushing');
+ data.forEach(function (d) {
+ return _this.push(d);
+ });
+ });
+ }, Math.floor(MAX / BATCH) + 2)
+ });
+
+ var i = 0;
+ function fetchData(cb) {
+ if (i > MAX) {
+ setTimeout(cb, 10, null, []);
+ } else {
+ var array = [];
+ var max = i + BATCH;
+ for (; i < max; i++) {
+ array.push(i);
+ }
+ setTimeout(cb, 10, null, array);
+ }
+ }
+
+ readable.on('readable', function () {
+ var data = void 0;
+ console.log('readable emitted');
+ while (data = readable.read()) {
+ console.log(data);
+ }
+ });
+
+ readable.on('end', common.mustCall(function () {
+ assert.strictEqual(i, (Math.floor(MAX / BATCH) + 1) * BATCH);
+ }));
+}
+
+{
+ var _readable = new Readable({
+ objectMode: true,
+ read: common.mustCall(function () {
+ var _this2 = this;
+
+ console.log('>> READ');
+ fetchData(function (err, data) {
+ if (err) {
+ _this2.destroy(err);
+ return;
+ }
+
+ if (data.length === 0) {
+ console.log('pushing null');
+ _this2.push(null);
+ return;
+ }
+
+ console.log('pushing');
+ data.forEach(function (d) {
+ return _this2.push(d);
+ });
+ });
+ }, Math.floor(MAX / BATCH) + 2)
+ });
+
+ var _i = 0;
+ function fetchData(cb) {
+ if (_i > MAX) {
+ setTimeout(cb, 10, null, []);
+ } else {
+ var array = [];
+ var max = _i + BATCH;
+ for (; _i < max; _i++) {
+ array.push(_i);
+ }
+ setTimeout(cb, 10, null, array);
+ }
+ }
+
+ _readable.on('data', function (data) {
+ console.log('data emitted', data);
+ });
+
+ _readable.on('end', common.mustCall(function () {
+ assert.strictEqual(_i, (Math.floor(MAX / BATCH) + 1) * BATCH);
+ }));
+}
+
+{
+ var _readable2 = new Readable({
+ objectMode: true,
+ read: common.mustCall(function () {
+ var _this3 = this;
+
+ console.log('>> READ');
+ fetchData(function (err, data) {
+ if (err) {
+ _this3.destroy(err);
+ return;
+ }
+
+ console.log('pushing');
+ data.forEach(function (d) {
+ return _this3.push(d);
+ });
+
+ if (data[BATCH - 1] >= MAX) {
+ console.log('pushing null');
+ _this3.push(null);
+ }
+ });
+ }, Math.floor(MAX / BATCH) + 1)
+ });
+
+ var _i2 = 0;
+ function fetchData(cb) {
+ var array = [];
+ var max = _i2 + BATCH;
+ for (; _i2 < max; _i2++) {
+ array.push(_i2);
+ }
+ setTimeout(cb, 10, null, array);
+ }
+
+ _readable2.on('data', function (data) {
+ console.log('data emitted', data);
+ });
+
+ _readable2.on('end', common.mustCall(function () {
+ assert.strictEqual(_i2, (Math.floor(MAX / BATCH) + 1) * BATCH);
+ }));
+}
+
+{
+ var _readable3 = new Readable({
+ objectMode: true,
+ read: common.mustNotCall()
+ });
+
+ _readable3.on('data', common.mustNotCall());
+
+ _readable3.push(null);
+
+ var nextTickPassed = false;
+ process.nextTick(function () {
+ nextTickPassed = true;
+ });
+
+ _readable3.on('end', common.mustCall(function () {
+ assert.strictEqual(nextTickPassed, true);
+ }));
+}
+
+{
+ var _readable4 = new Readable({
+ objectMode: true,
+ read: common.mustCall()
+ });
+
+ _readable4.on('data', function (data) {
+ console.log('data emitted', data);
+ });
+
+ _readable4.on('end', common.mustCall());
+
+ setImmediate(function () {
+ _readable4.push('aaa');
+ _readable4.push(null);
+ });
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-pause-and-resume.js b/test/parallel/test-stream-readable-pause-and-resume.js
new file mode 100644
index 0000000000..b43d8bb6c4
--- /dev/null
+++ b/test/parallel/test-stream-readable-pause-and-resume.js
@@ -0,0 +1,49 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+var common = require('../common');
+
+var ticks = 18;
+var expectedData = 19;
+
+var rs = new Readable({
+ objectMode: true,
+ read: function () {
+ if (ticks-- > 0) return process.nextTick(function () {
+ return rs.push({});
+ });
+ rs.push({});
+ rs.push(null);
+ }
+});
+
+rs.on('end', common.mustCall());
+readAndPause();
+
+function readAndPause() {
+ // Does a on(data) -> pause -> wait -> resume -> on(data) ... loop.
+ // Expects on(data) to never fire if the stream is paused.
+ var ondata = common.mustCall(function (data) {
+ rs.pause();
+
+ expectedData--;
+ if (expectedData <= 0) return;
+
+ setImmediate(function () {
+ rs.removeListener('data', ondata);
+ readAndPause();
+ rs.resume();
+ });
+ }, 1); // only call ondata once
+
+ rs.on('data', ondata);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-reading-readingMore.js b/test/parallel/test-stream-readable-reading-readingMore.js
index 8512dcf7ee..5d383247bb 100644
--- a/test/parallel/test-stream-readable-reading-readingMore.js
+++ b/test/parallel/test-stream-readable-reading-readingMore.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -5,62 +7,167 @@ var common = require('../common');
var assert = require('assert/');
var Readable = require('../../').Readable;
-var readable = new Readable({
- read: function (size) {}
-});
+{
+ var readable = new Readable({
+ read: function (size) {}
+ });
-var state = readable._readableState;
+ var state = readable._readableState;
-// Starting off with false initially.
-assert.strictEqual(state.reading, false);
-assert.strictEqual(state.readingMore, false);
+ // Starting off with false initially.
+ assert.strictEqual(state.reading, false);
+ assert.strictEqual(state.readingMore, false);
-readable.on('data', common.mustCall(function (data) {
- // while in a flowing state, should try to read more.
- if (state.flowing) assert.strictEqual(state.readingMore, true);
+ readable.on('data', common.mustCall(function (data) {
+ // while in a flowing state with a 'readable' listener
+ // we should not be reading more
+ if (readable.readableFlowing) assert.strictEqual(state.readingMore, true);
- // reading as long as we've not ended
- assert.strictEqual(state.reading, !state.ended);
-}, 2));
+ // reading as long as we've not ended
+ assert.strictEqual(state.reading, !state.ended);
+ }, 2));
-function onStreamEnd() {
- // End of stream; state.reading is false
- // And so should be readingMore.
- assert.strictEqual(state.readingMore, false);
- assert.strictEqual(state.reading, false);
-}
+ function onStreamEnd() {
+ // End of stream; state.reading is false
+ // And so should be readingMore.
+ assert.strictEqual(state.readingMore, false);
+ assert.strictEqual(state.reading, false);
+ }
+
+ readable.on('readable', common.mustCall(function () {
+ // 'readable' always gets called before 'end'
+ // since 'end' hasn't been emitted, more data could be incoming
+ assert.strictEqual(state.readingMore, true);
+
+ // if the stream has ended, we shouldn't be reading
+ assert.strictEqual(state.ended, !state.reading);
+
+ var data = readable.read();
+ if (data === null) // reached end of stream
+ process.nextTick(common.mustCall(onStreamEnd, 1));
+ }, 2));
-readable.on('readable', common.mustCall(function () {
- // 'readable' always gets called before 'end'
- // since 'end' hasn't been emitted, more data could be incoming
+ readable.on('end', common.mustCall(onStreamEnd));
+ readable.push('pushed');
+
+ readable.read(6);
+
+ // reading
+ assert.strictEqual(state.reading, true);
assert.strictEqual(state.readingMore, true);
- // if the stream has ended, we shouldn't be reading
- assert.strictEqual(state.ended, !state.reading);
+ // add chunk to front
+ readable.unshift('unshifted');
+
+ // end
+ readable.push(null);
+}
+
+{
+ var _readable = new Readable({
+ read: function (size) {}
+ });
+
+ var _state = _readable._readableState;
+
+ // Starting off with false initially.
+ assert.strictEqual(_state.reading, false);
+ assert.strictEqual(_state.readingMore, false);
+
+ _readable.on('data', common.mustCall(function (data) {
+ // while in a flowing state without a 'readable' listener
+ // we should be reading more
+ if (_readable.readableFlowing) assert.strictEqual(_state.readingMore, true);
- if (readable.read() === null) // reached end of stream
- process.nextTick(common.mustCall(onStreamEnd, 1));
-}, 2));
+ // reading as long as we've not ended
+ assert.strictEqual(_state.reading, !_state.ended);
+ }, 2));
-readable.on('end', common.mustCall(onStreamEnd));
+ function onStreamEnd() {
+ // End of stream; state.reading is false
+ // And so should be readingMore.
+ assert.strictEqual(_state.readingMore, false);
+ assert.strictEqual(_state.reading, false);
+ }
-readable.push('pushed');
+ _readable.on('end', common.mustCall(onStreamEnd));
+ _readable.push('pushed');
-// stop emitting 'data' events
-readable.pause();
+ // stop emitting 'data' events
+ assert.strictEqual(_state.flowing, true);
+ _readable.pause();
-// read() should only be called while operating in paused mode
-readable.read(6);
+ // paused
+ assert.strictEqual(_state.reading, false);
+ assert.strictEqual(_state.flowing, false);
-// reading
-assert.strictEqual(state.reading, true);
-assert.strictEqual(state.readingMore, true);
+ _readable.resume();
+ assert.strictEqual(_state.reading, false);
+ assert.strictEqual(_state.flowing, true);
-// resume emitting 'data' events
-readable.resume();
+ // add chunk to front
+ _readable.unshift('unshifted');
-// add chunk to front
-readable.unshift('unshifted');
+ // end
+ _readable.push(null);
+}
+
+{
+ var _readable2 = new Readable({
+ read: function (size) {}
+ });
+
+ var _state2 = _readable2._readableState;
+
+ // Starting off with false initially.
+ assert.strictEqual(_state2.reading, false);
+ assert.strictEqual(_state2.readingMore, false);
+
+ var onReadable = common.mustNotCall;
+
+ _readable2.on('readable', onReadable);
+
+ _readable2.on('data', common.mustCall(function (data) {
+ // reading as long as we've not ended
+ assert.strictEqual(_state2.reading, !_state2.ended);
+ }, 2));
+
+ _readable2.removeListener('readable', onReadable);
+
+ function onStreamEnd() {
+ // End of stream; state.reading is false
+ // And so should be readingMore.
+ assert.strictEqual(_state2.readingMore, false);
+ assert.strictEqual(_state2.reading, false);
+ }
-// end
-readable.push(null);
\ No newline at end of file
+ _readable2.on('end', common.mustCall(onStreamEnd));
+ _readable2.push('pushed');
+
+ // we are still not flowing, we will be resuming in the next tick
+ assert.strictEqual(_state2.flowing, false);
+
+ // wait for nextTick, so the readableListener flag resets
+ process.nextTick(function () {
+ _readable2.resume();
+
+ // stop emitting 'data' events
+ assert.strictEqual(_state2.flowing, true);
+ _readable2.pause();
+
+ // paused
+ assert.strictEqual(_state2.flowing, false);
+
+ _readable2.resume();
+ assert.strictEqual(_state2.flowing, true);
+
+ // add chunk to front
+ _readable2.unshift('unshifted');
+
+ // end
+ _readable2.push(null);
+ });
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-resumeScheduled.js b/test/parallel/test-stream-readable-resumeScheduled.js
index c32fb35df8..c3e6cc7219 100644
--- a/test/parallel/test-stream-readable-resumeScheduled.js
+++ b/test/parallel/test-stream-readable-resumeScheduled.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -73,4 +75,7 @@ var _require = require('../../'),
process.nextTick(common.mustCall(function () {
assert.strictEqual(_r2._readableState.resumeScheduled, false);
}));
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-setEncoding-null.js b/test/parallel/test-stream-readable-setEncoding-null.js
new file mode 100644
index 0000000000..4c3b1d91d9
--- /dev/null
+++ b/test/parallel/test-stream-readable-setEncoding-null.js
@@ -0,0 +1,23 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+
+require('../common');
+var assert = require('assert/');
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+{
+ var readable = new Readable({ encoding: 'hex' });
+ assert.strictEqual(readable._readableState.encoding, 'hex');
+
+ readable.setEncoding(null);
+
+ assert.strictEqual(readable._readableState.encoding, 'utf8');
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readable-with-unimplemented-_read.js b/test/parallel/test-stream-readable-with-unimplemented-_read.js
index 92bfbc030a..19a588ab79 100644
--- a/test/parallel/test-stream-readable-with-unimplemented-_read.js
+++ b/test/parallel/test-stream-readable-with-unimplemented-_read.js
@@ -1,12 +1,22 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
-var stream = require('../../');
-var assert = require('assert/');
+var common = require('../common');
+
+var _require = require('../../'),
+ Readable = _require.Readable;
+
+var readable = new Readable();
-var readable = new stream.Readable();
+readable.on('error', common.expectsError({
+ code: 'ERR_METHOD_NOT_IMPLEMENTED',
+ type: Error,
+ message: 'The _read() method is not implemented'
+}));
-assert.throws(function () {
- return readable.read();
-}, /not implemented/);
\ No newline at end of file
+readable.read();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-readableListening-state.js b/test/parallel/test-stream-readableListening-state.js
index 08e552145f..91fa25358b 100644
--- a/test/parallel/test-stream-readableListening-state.js
+++ b/test/parallel/test-stream-readableListening-state.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -33,4 +35,7 @@ r2.on('data', common.mustCall(function (chunk) {
assert.strictEqual(r2._readableState.readableListening, false);
}));
-r2.push(bufferShim.from('Testing readableListening state'));
\ No newline at end of file
+r2.push(bufferShim.from('Testing readableListening state'));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-callback-twice.js b/test/parallel/test-stream-transform-callback-twice.js
index cd8cdc668c..4ae1f61630 100644
--- a/test/parallel/test-stream-transform-callback-twice.js
+++ b/test/parallel/test-stream-transform-callback-twice.js
@@ -1,8 +1,9 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
var common = require('../common');
-var assert = require('assert/');
var _require = require('../../'),
Transform = _require.Transform;
@@ -13,8 +14,13 @@ var stream = new Transform({
}
});
-stream.on('error', common.mustCall(function (err) {
- assert.strictEqual(err.toString(), 'Error: write callback called multiple times');
+stream.on('error', common.expectsError({
+ type: Error,
+ message: 'Callback called multiple times',
+ code: 'ERR_MULTIPLE_CALLBACK'
}));
-stream.write('foo');
\ No newline at end of file
+stream.write('foo');
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-constructor-set-methods.js b/test/parallel/test-stream-transform-constructor-set-methods.js
index ed4858b3cd..1944f3606b 100644
--- a/test/parallel/test-stream-transform-constructor-set-methods.js
+++ b/test/parallel/test-stream-transform-constructor-set-methods.js
@@ -1,40 +1,50 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
var common = require('../common');
-var assert = require('assert/');
-var Transform = require('../../').Transform;
+var _require = require('assert/'),
+ strictEqual = _require.strictEqual;
+
+var _require2 = require('../../'),
+ Transform = _require2.Transform;
+
+var t = new Transform();
-var _transform = common.mustCall(function _transform(d, e, n) {
- n();
+t.on('error', common.expectsError({
+ type: Error,
+ code: 'ERR_METHOD_NOT_IMPLEMENTED',
+ message: 'The _transform() method is not implemented'
+}));
+
+t.end(bufferShim.from('blerg'));
+
+var _transform = common.mustCall(function (chunk, _, next) {
+ next();
});
-var _final = common.mustCall(function _final(n) {
- n();
+var _final = common.mustCall(function (next) {
+ next();
});
-var _flush = common.mustCall(function _flush(n) {
- n();
+var _flush = common.mustCall(function (next) {
+ next();
});
-var t = new Transform({
+var t2 = new Transform({
transform: _transform,
flush: _flush,
final: _final
});
-var t2 = new Transform({});
-
-t.end(bufferShim.from('blerg'));
-t.resume();
-
-assert.throws(function () {
- t2.end(bufferShim.from('blerg'));
-}, /^Error: .*[Nn]ot implemented$/);
+strictEqual(t2._transform, _transform);
+strictEqual(t2._flush, _flush);
+strictEqual(t2._final, _final);
-process.on('exit', function () {
- assert.strictEqual(t._transform, _transform);
- assert.strictEqual(t._flush, _flush);
- assert.strictEqual(t._final, _final);
+t2.end(bufferShim.from('blerg'));
+t2.resume();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-destroy.js b/test/parallel/test-stream-transform-destroy.js
index 1d30d6f512..670c567fea 100644
--- a/test/parallel/test-stream-transform-destroy.js
+++ b/test/parallel/test-stream-transform-destroy.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -16,9 +18,9 @@ var assert = require('assert/');
transform.resume();
- transform.on('end', common.mustCall());
+ transform.on('end', common.mustNotCall());
transform.on('close', common.mustCall());
- transform.on('finish', common.mustCall());
+ transform.on('finish', common.mustNotCall());
transform.destroy();
}
@@ -31,8 +33,8 @@ var assert = require('assert/');
var expected = new Error('kaboom');
- _transform.on('end', common.mustCall());
- _transform.on('finish', common.mustCall());
+ _transform.on('end', common.mustNotCall());
+ _transform.on('finish', common.mustNotCall());
_transform.on('close', common.mustCall());
_transform.on('error', common.mustCall(function (err) {
assert.strictEqual(err, expected);
@@ -54,7 +56,7 @@ var assert = require('assert/');
var _expected = new Error('kaboom');
_transform2.on('finish', common.mustNotCall('no finish event'));
- _transform2.on('close', common.mustNotCall('no close event'));
+ _transform2.on('close', common.mustCall());
_transform2.on('error', common.mustCall(function (err) {
assert.strictEqual(err, _expected);
}));
@@ -75,7 +77,7 @@ var assert = require('assert/');
_transform3.resume();
_transform3.on('end', common.mustNotCall('no end event'));
- _transform3.on('close', common.mustNotCall('no close event'));
+ _transform3.on('close', common.mustCall());
_transform3.on('finish', common.mustNotCall('no finish event'));
// error is swallowed by the custom _destroy
@@ -118,7 +120,7 @@ var assert = require('assert/');
_transform5.on('finish', fail);
_transform5.on('end', fail);
- _transform5.on('close', fail);
+ _transform5.on('close', common.mustCall());
_transform5.destroy();
@@ -140,7 +142,7 @@ var assert = require('assert/');
cb(_expected3);
}, 1);
- _transform6.on('close', common.mustNotCall('no close event'));
+ _transform6.on('close', common.mustCall());
_transform6.on('finish', common.mustNotCall('no finish event'));
_transform6.on('end', common.mustNotCall('no end event'));
_transform6.on('error', common.mustCall(function (err) {
@@ -148,4 +150,7 @@ var assert = require('assert/');
}));
_transform6.destroy();
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-final-sync.js b/test/parallel/test-stream-transform-final-sync.js
index 8667612bca..7fbf906bcc 100644
--- a/test/parallel/test-stream-transform-final-sync.js
+++ b/test/parallel/test-stream-transform-final-sync.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -9,7 +11,7 @@ var state = 0;
/*
What you do
-var stream = new tream.Transform({
+var stream = new stream.Transform({
transform: function transformCallback(chunk, _, next) {
// part 1
this.push(chunk);
@@ -61,42 +63,55 @@ The order things are called
var t = new stream.Transform({
objectMode: true,
transform: common.mustCall(function (chunk, _, next) {
- assert.strictEqual(++state, chunk, 'transformCallback part 1');
+ // transformCallback part 1
+ assert.strictEqual(++state, chunk);
this.push(state);
- assert.strictEqual(++state, chunk + 2, 'transformCallback part 2');
+ // transformCallback part 2
+ assert.strictEqual(++state, chunk + 2);
process.nextTick(next);
}, 3),
final: common.mustCall(function (done) {
state++;
- assert.strictEqual(state, 10, 'finalCallback part 1');
+ // finalCallback part 1
+ assert.strictEqual(state, 10);
state++;
- assert.strictEqual(state, 11, 'finalCallback part 2');
+ // finalCallback part 2
+ assert.strictEqual(state, 11);
done();
}, 1),
flush: common.mustCall(function (done) {
state++;
- assert.strictEqual(state, 12, 'flushCallback part 1');
+ // fluchCallback part 1
+ assert.strictEqual(state, 12);
process.nextTick(function () {
state++;
- assert.strictEqual(state, 15, 'flushCallback part 2');
+ // fluchCallback part 2
+ assert.strictEqual(state, 15);
done();
});
}, 1)
});
t.on('finish', common.mustCall(function () {
state++;
- assert.strictEqual(state, 13, 'finishListener');
+ // finishListener
+ assert.strictEqual(state, 13);
}, 1));
t.on('end', common.mustCall(function () {
state++;
- assert.strictEqual(state, 16, 'end event');
+ // endEvent
+ assert.strictEqual(state, 16);
}, 1));
t.on('data', common.mustCall(function (d) {
- assert.strictEqual(++state, d + 1, 'dataListener');
+ // dataListener
+ assert.strictEqual(++state, d + 1);
}, 3));
t.write(1);
t.write(4);
t.end(7, common.mustCall(function () {
state++;
- assert.strictEqual(state, 14, 'endMethodCallback');
-}, 1));
\ No newline at end of file
+ // endMethodCallback
+ assert.strictEqual(state, 14);
+}, 1));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-final.js b/test/parallel/test-stream-transform-final.js
index 50e0ce8a1d..bdd2f05faa 100644
--- a/test/parallel/test-stream-transform-final.js
+++ b/test/parallel/test-stream-transform-final.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -9,7 +11,7 @@ var state = 0;
/*
What you do
-var stream = new tream.Transform({
+var stream = new stream.Transform({
transform: function transformCallback(chunk, _, next) {
// part 1
this.push(chunk);
@@ -101,4 +103,7 @@ t.write(4);
t.end(7, common.mustCall(function () {
state++;
assert.strictEqual(state, 14, 'endMethodCallback');
-}, 1));
\ No newline at end of file
+}, 1));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-flush-data.js b/test/parallel/test-stream-transform-flush-data.js
index 2dd4ffc64c..0680630f88 100644
--- a/test/parallel/test-stream-transform-flush-data.js
+++ b/test/parallel/test-stream-transform-flush-data.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -24,4 +26,7 @@ var t = new Transform({
t.end(bufferShim.from('blerg'));
t.on('data', function (data) {
assert.strictEqual(data.toString(), expected);
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-objectmode-falsey-value.js b/test/parallel/test-stream-transform-objectmode-falsey-value.js
index 0e95c48d0e..4d21263c82 100644
--- a/test/parallel/test-stream-transform-objectmode-falsey-value.js
+++ b/test/parallel/test-stream-transform-objectmode-falsey-value.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -50,4 +52,7 @@ var int = setInterval(common.mustCall(function () {
} else {
src.write(i++);
}
-}, expect.length + 1), 1);
\ No newline at end of file
+}, expect.length + 1), 1);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-split-highwatermark.js b/test/parallel/test-stream-transform-split-highwatermark.js
index 2c3b034a81..6306557c63 100644
--- a/test/parallel/test-stream-transform-split-highwatermark.js
+++ b/test/parallel/test-stream-transform-split-highwatermark.js
@@ -1,7 +1,9 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
+var common = require('../common');
var assert = require('assert/');
var _require = require('../../'),
@@ -59,18 +61,40 @@ testTransform(0, 0, {
writableHighWaterMark: 777
});
-// test undefined, null, NaN
-[undefined, null, NaN].forEach(function (v) {
+// test undefined, null
+[undefined, null].forEach(function (v) {
testTransform(DEFAULT, DEFAULT, { readableHighWaterMark: v });
testTransform(DEFAULT, DEFAULT, { writableHighWaterMark: v });
testTransform(666, DEFAULT, { highWaterMark: v, readableHighWaterMark: 666 });
testTransform(DEFAULT, 777, { highWaterMark: v, writableHighWaterMark: 777 });
});
+// test NaN
+{
+ common.expectsError(function () {
+ new Transform({ readableHighWaterMark: NaN });
+ }, {
+ type: TypeError,
+ code: 'ERR_INVALID_OPT_VALUE',
+ message: 'The value "NaN" is invalid for option "readableHighWaterMark"'
+ });
+
+ common.expectsError(function () {
+ new Transform({ writableHighWaterMark: NaN });
+ }, {
+ type: TypeError,
+ code: 'ERR_INVALID_OPT_VALUE',
+ message: 'The value "NaN" is invalid for option "writableHighWaterMark"'
+ });
+}
+
// test non Duplex streams ignore the options
{
var r = new Readable({ readableHighWaterMark: 666 });
assert.strictEqual(r._readableState.highWaterMark, DEFAULT);
var w = new Writable({ writableHighWaterMark: 777 });
assert.strictEqual(w._writableState.highWaterMark, DEFAULT);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-transform-split-objectmode.js b/test/parallel/test-stream-transform-split-objectmode.js
index 097c3d789f..ef61a3a4de 100644
--- a/test/parallel/test-stream-transform-split-objectmode.js
+++ b/test/parallel/test-stream-transform-split-objectmode.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -75,4 +77,7 @@ serializer.write({ val: 42 });
process.on('exit', function () {
assert.strictEqual(serialized[0], 42);
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-uint8array.js b/test/parallel/test-stream-uint8array.js
index def15cd61a..463cc82fc6 100644
--- a/test/parallel/test-stream-uint8array.js
+++ b/test/parallel/test-stream-uint8array.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _toConsumableArray(arr) { if (Array.isArray(arr)) { for (var i = 0, arr2 = Array(arr.length); i < arr.length; i++) { arr2[i] = arr[i]; } return arr2; } else { return Array.from(arr); } }
/**/
@@ -104,4 +106,7 @@ var GHI = new Uint8Array([0x47, 0x48, 0x49]);
var out = _readable.read();
assert.strictEqual(out, 'ABCDEF');
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-unpipe-event.js b/test/parallel/test-stream-unpipe-event.js
index 2f7ef2567b..441de4b3c4 100644
--- a/test/parallel/test-stream-unpipe-event.js
+++ b/test/parallel/test-stream-unpipe-event.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -129,4 +131,7 @@ var NeverEndReadable = function (_Readable2) {
setImmediate(function () {
assert.strictEqual(_src5._readableState.pipesCount, 0);
});
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-unshift-empty-chunk.js b/test/parallel/test-stream-unshift-empty-chunk.js
index fcc5457ddd..41b19e001d 100644
--- a/test/parallel/test-stream-unshift-empty-chunk.js
+++ b/test/parallel/test-stream-unshift-empty-chunk.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -60,5 +62,8 @@ var expect = ['xxxxxxxxxx', 'yyyyy', 'xxxxxxxxxx', 'yyyyy', 'xxxxxxxxxx', 'yyyyy
r.on('end', function () {
assert.deepStrictEqual(seen, expect);
- console.log('ok');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-unshift-read-race.js b/test/parallel/test-stream-unshift-read-race.js
index 0e615db95d..c5db217a86 100644
--- a/test/parallel/test-stream-unshift-read-race.js
+++ b/test/parallel/test-stream-unshift-read-race.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -53,7 +55,7 @@ r._read = function (n) {
function push(fast) {
assert(!pushedNull, 'push() after null push');
- var c = pos >= data.length ? null : data.slice(pos, Math.min(pos + n, data.length));
+ var c = pos >= data.length ? null : data.slice(pos, pos + n);
pushedNull = c === null;
if (fast) {
pos += n;
@@ -70,9 +72,13 @@ r._read = function (n) {
};
function pushError() {
- assert.throws(function () {
+ common.expectsError(function () {
r.push(bufferShim.allocUnsafe(1));
- }, /^Error: stream\.push\(\) after EOF$/);
+ }, {
+ code: 'ERR_STREAM_PUSH_AFTER_EOF',
+ type: Error,
+ message: 'stream.push() after EOF'
+ });
}
var w = stream.Writable();
@@ -83,9 +89,13 @@ w._write = function (chunk, encoding, cb) {
};
r.on('end', common.mustCall(function () {
- assert.throws(function () {
+ common.expectsError(function () {
r.unshift(bufferShim.allocUnsafe(1));
- }, /^Error: stream\.unshift\(\) after end event$/);
+ }, {
+ code: 'ERR_STREAM_UNSHIFT_AFTER_END_EVENT',
+ type: Error,
+ message: 'stream.unshift() after end event'
+ });
w.end();
}));
@@ -126,5 +136,8 @@ w.on('finish', common.mustCall(function () {
process.on('exit', function () {
assert.strictEqual(written.length, 18);
- console.log('ok');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-change-default-encoding.js b/test/parallel/test-stream-writable-change-default-encoding.js
index 05f37cc014..86ef2f3f59 100644
--- a/test/parallel/test-stream-writable-change-default-encoding.js
+++ b/test/parallel/test-stream-writable-change-default-encoding.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -28,7 +30,7 @@ function _inherits(subClass, superClass) { if (typeof superClass !== "function"
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
+var common = require('../common');
var assert = require('assert/');
var stream = require('../../');
@@ -70,12 +72,16 @@ var MyWritable = function (_stream$Writable) {
m.end();
})();
-assert.throws(function changeDefaultEncodingToInvalidValue() {
+common.expectsError(function changeDefaultEncodingToInvalidValue() {
var m = new MyWritable(function (isBuffer, type, enc) {}, { decodeStrings: false });
m.setDefaultEncoding({});
m.write('bar');
m.end();
-}, /^TypeError: Unknown encoding: \[object Object\]$/);
+}, {
+ type: TypeError,
+ code: 'ERR_UNKNOWN_ENCODING',
+ message: 'Unknown encoding: [object Object]'
+});
(function checkVairableCaseEncoding() {
var m = new MyWritable(function (isBuffer, type, enc) {
@@ -84,4 +90,7 @@ assert.throws(function changeDefaultEncodingToInvalidValue() {
m.setDefaultEncoding('AsCii');
m.write('bar');
m.end();
-})();
\ No newline at end of file
+})();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-constructor-set-methods.js b/test/parallel/test-stream-writable-constructor-set-methods.js
index aa88674714..8b66ea35f8 100644
--- a/test/parallel/test-stream-writable-constructor-set-methods.js
+++ b/test/parallel/test-stream-writable-constructor-set-methods.js
@@ -1,37 +1,47 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
-var assert = require('assert/');
+var common = require('../common');
+
+var _require = require('assert/'),
+ strictEqual = _require.strictEqual;
+
+var _require2 = require('../../'),
+ Writable = _require2.Writable;
-var Writable = require('../../').Writable;
+var w = new Writable();
-var _writeCalled = false;
-function _write(d, e, n) {
- _writeCalled = true;
-}
+w.on('error', common.expectsError({
+ type: Error,
+ code: 'ERR_METHOD_NOT_IMPLEMENTED',
+ message: 'The _write() method is not implemented'
+}));
-var w = new Writable({ write: _write });
w.end(bufferShim.from('blerg'));
-var _writevCalled = false;
-var dLength = 0;
-function _writev(d, n) {
- dLength = d.length;
- _writevCalled = true;
-}
+var _write = common.mustCall(function (chunk, _, next) {
+ next();
+});
-var w2 = new Writable({ writev: _writev });
-w2.cork();
+var _writev = common.mustCall(function (chunks, next) {
+ strictEqual(chunks.length, 2);
+ next();
+});
+
+var w2 = new Writable({ write: _write, writev: _writev });
+
+strictEqual(w2._write, _write);
+strictEqual(w2._writev, _writev);
+w2.write(bufferShim.from('blerg'));
+
+w2.cork();
w2.write(bufferShim.from('blerg'));
w2.write(bufferShim.from('blerg'));
-w2.end();
-process.on('exit', function () {
- assert.strictEqual(w._write, _write);
- assert(_writeCalled);
- assert.strictEqual(w2._writev, _writev);
- assert.strictEqual(dLength, 2);
- assert(_writevCalled);
+w2.end();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-decoded-encoding.js b/test/parallel/test-stream-writable-decoded-encoding.js
index e9c71ffa39..0a44a3be32 100644
--- a/test/parallel/test-stream-writable-decoded-encoding.js
+++ b/test/parallel/test-stream-writable-decoded-encoding.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -71,4 +73,7 @@ var MyWritable = function (_stream$Writable) {
}, { decodeStrings: false });
_m.write('some-text', 'utf8');
_m.end();
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-destroy.js b/test/parallel/test-stream-writable-destroy.js
index 3aeff6c445..333134d289 100644
--- a/test/parallel/test-stream-writable-destroy.js
+++ b/test/parallel/test-stream-writable-destroy.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -19,7 +21,8 @@ var _require2 = require('util'),
}
});
- write.on('finish', common.mustCall());
+ write.on('finish', common.mustNotCall());
+ write.on('close', common.mustCall());
write.destroy();
assert.strictEqual(write.destroyed, true);
@@ -34,7 +37,8 @@ var _require2 = require('util'),
var expected = new Error('kaboom');
- _write.on('finish', common.mustCall());
+ _write.on('finish', common.mustNotCall());
+ _write.on('close', common.mustCall());
_write.on('error', common.mustCall(function (err) {
assert.strictEqual(err, expected);
}));
@@ -58,6 +62,7 @@ var _require2 = require('util'),
var _expected = new Error('kaboom');
_write2.on('finish', common.mustNotCall('no finish event'));
+ _write2.on('close', common.mustCall());
_write2.on('error', common.mustCall(function (err) {
assert.strictEqual(err, _expected);
}));
@@ -81,6 +86,7 @@ var _require2 = require('util'),
var _expected2 = new Error('kaboom');
_write3.on('finish', common.mustNotCall('no finish event'));
+ _write3.on('close', common.mustCall());
// error is swallowed by the custom _destroy
_write3.on('error', common.mustNotCall('no error event'));
@@ -125,6 +131,7 @@ var _require2 = require('util'),
var fail = common.mustNotCall('no finish event');
_write5.on('finish', fail);
+ _write5.on('close', common.mustCall());
_write5.destroy();
@@ -147,6 +154,7 @@ var _require2 = require('util'),
cb(_expected3);
});
+ _write6.on('close', common.mustCall());
_write6.on('finish', common.mustNotCall('no finish event'));
_write6.on('error', common.mustCall(function (err) {
assert.strictEqual(err, _expected3);
@@ -164,6 +172,7 @@ var _require2 = require('util'),
}
});
+ _write7.on('close', common.mustCall());
_write7.on('error', common.mustCall());
_write7.destroy(new Error('kaboom 1'));
@@ -183,7 +192,7 @@ var _require2 = require('util'),
assert.strictEqual(_write8.destroyed, true);
// the internal destroy() mechanism should not be triggered
- _write8.on('finish', common.mustNotCall());
+ _write8.on('close', common.mustNotCall());
_write8.destroy();
}
@@ -214,4 +223,23 @@ var _require2 = require('util'),
_write9.destroy(_expected4, common.mustCall(function (err) {
assert.strictEqual(_expected4, err);
}));
-}
\ No newline at end of file
+}
+
+{
+ // Checks that `._undestroy()` restores the state so that `final` will be
+ // called again.
+ var _write10 = new Writable({
+ write: common.mustNotCall(),
+ final: common.mustCall(function (cb) {
+ return cb();
+ }, 2)
+ });
+
+ _write10.end();
+ _write10.destroy();
+ _write10._undestroy();
+ _write10.end();
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-ended-state.js b/test/parallel/test-stream-writable-ended-state.js
index dd2e332d02..f871205874 100644
--- a/test/parallel/test-stream-writable-ended-state.js
+++ b/test/parallel/test-stream-writable-ended-state.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -20,4 +22,7 @@ writable.end('testing ended state', common.mustCall(function () {
assert.strictEqual(writable._writableState.ended, true);
}));
-assert.strictEqual(writable._writableState.ended, true);
\ No newline at end of file
+assert.strictEqual(writable._writableState.ended, true);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-finished-state.js b/test/parallel/test-stream-writable-finished-state.js
index 88566cfd85..e3a61127ea 100644
--- a/test/parallel/test-stream-writable-finished-state.js
+++ b/test/parallel/test-stream-writable-finished-state.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -21,4 +23,7 @@ writable.on('finish', common.mustCall(function () {
writable.end('testing finished state', common.mustCall(function () {
assert.strictEqual(writable._writableState.finished, true);
-}));
\ No newline at end of file
+}));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-needdrain-state.js b/test/parallel/test-stream-writable-needdrain-state.js
index adca330e48..b01ee50a0d 100644
--- a/test/parallel/test-stream-writable-needdrain-state.js
+++ b/test/parallel/test-stream-writable-needdrain-state.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -22,4 +24,7 @@ transform.write('asdasd', common.mustCall(function () {
assert.strictEqual(transform._writableState.needDrain, false);
}));
-assert.strictEqual(transform._writableState.needDrain, true);
\ No newline at end of file
+assert.strictEqual(transform._writableState.needDrain, true);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-null.js b/test/parallel/test-stream-writable-null.js
index bfafc7ff55..ab2dfcbffa 100644
--- a/test/parallel/test-stream-writable-null.js
+++ b/test/parallel/test-stream-writable-null.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -7,7 +9,7 @@ function _inherits(subClass, superClass) { if (typeof superClass !== "function"
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
+var common = require('../common');
var assert = require('assert/');
var stream = require('../../');
@@ -29,47 +31,52 @@ var MyWritable = function (_stream$Writable) {
return MyWritable;
}(stream.Writable);
-assert.throws(function () {
+common.expectsError(function () {
var m = new MyWritable({ objectMode: true });
m.write(null, function (err) {
return assert.ok(err);
});
-}, /^TypeError: May not write null values to stream$/);
-assert.doesNotThrow(function () {
- var m = new MyWritable({ objectMode: true }).on('error', function (e) {
- assert.ok(e);
- });
- m.write(null, function (err) {
- assert.ok(err);
- });
+}, {
+ code: 'ERR_STREAM_NULL_VALUES',
+ type: TypeError,
+ message: 'May not write null values to stream'
});
-assert.throws(function () {
+{
+ // Should not throw.
+ var m = new MyWritable({ objectMode: true }).on('error', assert);
+ m.write(null, assert);
+}
+
+common.expectsError(function () {
var m = new MyWritable();
m.write(false, function (err) {
return assert.ok(err);
});
-}, /^TypeError: Invalid non-string\/buffer chunk$/);
-assert.doesNotThrow(function () {
- var m = new MyWritable().on('error', function (e) {
- assert.ok(e);
- });
- m.write(false, function (err) {
- assert.ok(err);
- });
+}, {
+ code: 'ERR_INVALID_ARG_TYPE',
+ type: TypeError
});
-assert.doesNotThrow(function () {
- var m = new MyWritable({ objectMode: true });
- m.write(false, function (err) {
- return assert.ifError(err);
- });
-});
-assert.doesNotThrow(function () {
- var m = new MyWritable({ objectMode: true }).on('error', function (e) {
+{
+ // Should not throw.
+ var _m = new MyWritable().on('error', assert);
+ _m.write(false, assert);
+}
+
+{
+ // Should not throw.
+ var _m2 = new MyWritable({ objectMode: true });
+ _m2.write(false, assert.ifError);
+}
+
+{
+ // Should not throw.
+ var _m3 = new MyWritable({ objectMode: true }).on('error', function (e) {
assert.ifError(e || new Error('should not get here'));
});
- m.write(false, function (err) {
- assert.ifError(err);
- });
+ _m3.write(false, assert.ifError);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-write-cb-twice.js b/test/parallel/test-stream-writable-write-cb-twice.js
new file mode 100644
index 0000000000..582f8264c3
--- /dev/null
+++ b/test/parallel/test-stream-writable-write-cb-twice.js
@@ -0,0 +1,58 @@
+'use strict';
+
+/**/
+var bufferShim = require('safe-buffer').Buffer;
+/**/
+var common = require('../common');
+
+var _require = require('../../'),
+ Writable = _require.Writable;
+
+{
+ // Sync + Sync
+ var writable = new Writable({
+ write: common.mustCall(function (buf, enc, cb) {
+ cb();
+ common.expectsError(cb, {
+ code: 'ERR_MULTIPLE_CALLBACK',
+ type: Error
+ });
+ })
+ });
+ writable.write('hi');
+}
+
+{
+ // Sync + Async
+ var _writable = new Writable({
+ write: common.mustCall(function (buf, enc, cb) {
+ cb();
+ process.nextTick(function () {
+ common.expectsError(cb, {
+ code: 'ERR_MULTIPLE_CALLBACK',
+ type: Error
+ });
+ });
+ })
+ });
+ _writable.write('hi');
+}
+
+{
+ // Async + Async
+ var _writable2 = new Writable({
+ write: common.mustCall(function (buf, enc, cb) {
+ process.nextTick(cb);
+ process.nextTick(function () {
+ common.expectsError(cb, {
+ code: 'ERR_MULTIPLE_CALLBACK',
+ type: Error
+ });
+ });
+ })
+ });
+ _writable2.write('hi');
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writable-write-writev-finish.js b/test/parallel/test-stream-writable-write-writev-finish.js
index e5a8f65a9e..8adc5a4d1c 100644
--- a/test/parallel/test-stream-writable-write-writev-finish.js
+++ b/test/parallel/test-stream-writable-write-writev-finish.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -155,4 +157,31 @@ var stream = require('../../');
done(new Error());
};
_rs.pipe(_ws);
-}
\ No newline at end of file
+}
+
+{
+ var w = new stream.Writable();
+ w._write = function (chunk, encoding, cb) {
+ process.nextTick(cb);
+ };
+ w.on('error', common.mustCall());
+ w.on('prefinish', function () {
+ w.write("shouldn't write in prefinish listener");
+ });
+ w.end();
+}
+
+{
+ var _w = new stream.Writable();
+ _w._write = function (chunk, encoding, cb) {
+ process.nextTick(cb);
+ };
+ _w.on('error', common.mustCall());
+ _w.on('finish', function () {
+ _w.write("should't write in finish listener");
+ });
+ _w.end();
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writableState-ending.js b/test/parallel/test-stream-writableState-ending.js
index fd423b0d44..44b8d0b586 100644
--- a/test/parallel/test-stream-writableState-ending.js
+++ b/test/parallel/test-stream-writableState-ending.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -26,11 +28,17 @@ writable.on('finish', function () {
testStates(true, true, true);
});
-writable.end('testing function end()', function () {
+var result = writable.end('testing function end()', function () {
// ending, finished, ended = true.
testStates(true, true, true);
});
+// end returns the writable instance
+assert.strictEqual(result, writable);
+
// ending, ended = true.
// finished = false.
-testStates(true, false, true);
\ No newline at end of file
+testStates(true, false, true);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writableState-uncorked-bufferedRequestCount.js b/test/parallel/test-stream-writableState-uncorked-bufferedRequestCount.js
index 376bf7c673..6d6f5b649d 100644
--- a/test/parallel/test-stream-writableState-uncorked-bufferedRequestCount.js
+++ b/test/parallel/test-stream-writableState-uncorked-bufferedRequestCount.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -9,7 +11,7 @@ var stream = require('../../');
var writable = new stream.Writable();
writable._writev = common.mustCall(function (chunks, cb) {
- assert.strictEqual(chunks.length, 2, 'two chunks to write');
+ assert.strictEqual(chunks.length, 2);
cb();
}, 1);
@@ -56,4 +58,7 @@ function uncork() {
// end causes an uncork() as well
assert.strictEqual(writable._writableState.corked, 0);
assert.strictEqual(writable._writableState.bufferedRequestCount, 0);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-write-final.js b/test/parallel/test-stream-write-final.js
index bd3dafecfb..1264389242 100644
--- a/test/parallel/test-stream-write-final.js
+++ b/test/parallel/test-stream-write-final.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -23,4 +25,7 @@ w.on('finish', common.mustCall(function () {
assert(shutdown);
}));
w.write(bufferShim.allocUnsafe(1));
-w.end(bufferShim.allocUnsafe(0));
\ No newline at end of file
+w.end(bufferShim.allocUnsafe(0));
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream-writev.js b/test/parallel/test-stream-writev.js
index 478121e880..9fe98fc592 100644
--- a/test/parallel/test-stream-writev.js
+++ b/test/parallel/test-stream-writev.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -40,11 +42,11 @@ run();
function run() {
var t = queue.pop();
- if (t) test(t[0], t[1], t[2], run);else console.log('ok');
+ if (t) test(t[0], t[1], t[2], run);else require('tap').pass();
}
function test(decode, uncork, multi, next) {
- console.log('# decode=' + decode + ' uncork=' + uncork + ' multi=' + multi);
+ require('tap').test('# decode=' + decode + ' uncork=' + uncork + ' multi=' + multi);
var counter = 0;
var expectCount = 0;
function cnt(msg) {
@@ -65,7 +67,7 @@ function test(decode, uncork, multi, next) {
chunk: [119, 111, 114, 108, 100] }, { encoding: 'buffer',
chunk: [33] }, { encoding: 'buffer',
chunk: [10, 97, 110, 100, 32, 116, 104, 101, 110, 46, 46, 46] }, { encoding: 'buffer',
- chunk: [250, 206, 190, 167, 222, 173, 190, 239, 222, 202, 251, 173] }] : [{ encoding: 'ascii', chunk: 'hello, ' }, { encoding: 'utf8', chunk: 'world' }, { encoding: 'buffer', chunk: [33] }, { encoding: 'binary', chunk: '\nand then...' }, { encoding: 'hex', chunk: 'facebea7deadbeefdecafbad' }];
+ chunk: [250, 206, 190, 167, 222, 173, 190, 239, 222, 202, 251, 173] }] : [{ encoding: 'ascii', chunk: 'hello, ' }, { encoding: 'utf8', chunk: 'world' }, { encoding: 'buffer', chunk: [33] }, { encoding: 'latin1', chunk: '\nand then...' }, { encoding: 'hex', chunk: 'facebea7deadbeefdecafbad' }];
var actualChunks = void 0;
w._writev = function (chunks, cb) {
@@ -85,7 +87,7 @@ function test(decode, uncork, multi, next) {
if (multi) w.cork();
w.write(bufferShim.from('!'), 'buffer', cnt('!'));
- w.write('\nand then...', 'binary', cnt('and then'));
+ w.write('\nand then...', 'latin1', cnt('and then'));
if (multi) w.uncork();
@@ -101,4 +103,7 @@ function test(decode, uncork, multi, next) {
assert.deepStrictEqual(expectChunks, actualChunks);
next();
});
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-base64-single-char-read-end.js b/test/parallel/test-stream2-base64-single-char-read-end.js
index cde122d3be..e526bb1ac0 100644
--- a/test/parallel/test-stream2-base64-single-char-read-end.js
+++ b/test/parallel/test-stream2-base64-single-char-read-end.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -56,4 +58,7 @@ src.pipe(dst);
var timeout = setTimeout(function () {
assert.fail('timed out waiting for _write');
-}, 100);
\ No newline at end of file
+}, 100);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-basic.js b/test/parallel/test-stream2-basic.js
index 0a0b364ed3..9e8f0bec27 100644
--- a/test/parallel/test-stream2-basic.js
+++ b/test/parallel/test-stream2-basic.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -82,8 +84,6 @@ var TestReader = function (_R) {
return TestReader;
}(R);
-/////
-
var TestWriter = function (_EE) {
_inherits(TestWriter, _EE);
@@ -195,10 +195,10 @@ forEach([1, 2, 3, 4, 5, 6, 7, 8, 9], function (SPLIT) {
var _expect2 = ['xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx', 'xxxxx'];
_w[0].on('end', common.mustCall(function (received) {
- assert.deepStrictEqual(received, _expect2, 'first');
+ assert.deepStrictEqual(received, _expect2);
}));
_w[1].on('end', common.mustCall(function (received) {
- assert.deepStrictEqual(received, _expect2, 'second');
+ assert.deepStrictEqual(received, _expect2);
}));
_r2.pipe(_w[0]);
@@ -395,4 +395,7 @@ function forEach(xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
f(xs[i], i);
}
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-compatibility.js b/test/parallel/test-stream2-compatibility.js
index 4737f9a282..58ed5d7e93 100644
--- a/test/parallel/test-stream2-compatibility.js
+++ b/test/parallel/test-stream2-compatibility.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -62,7 +64,7 @@ var TestReader = function (_R) {
var reader = new TestReader();
setImmediate(function () {
assert.strictEqual(ondataCalled, 1);
- console.log('ok');
+ require('tap').pass();
reader.push(null);
});
@@ -91,5 +93,8 @@ var writer = new TestWriter();
process.on('exit', function () {
assert.strictEqual(reader.readable, false);
assert.strictEqual(writer.writable, false);
- console.log('ok');
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-decode-partial.js b/test/parallel/test-stream2-decode-partial.js
index a9a5c55942..4a96aabce4 100644
--- a/test/parallel/test-stream2-decode-partial.js
+++ b/test/parallel/test-stream2-decode-partial.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -22,4 +24,7 @@ readable.on('data', function (data) {
process.on('exit', function () {
assert.strictEqual(buf, '€¢');
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-finish-pipe.js b/test/parallel/test-stream2-finish-pipe.js
index 1566ee3652..2a343dcbb5 100644
--- a/test/parallel/test-stream2-finish-pipe.js
+++ b/test/parallel/test-stream2-finish-pipe.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -40,4 +42,7 @@ r.pipe(w);
// This might sound unrealistic, but it happens in net.js. When
// `socket.allowHalfOpen === false`, EOF will cause `.destroySoon()` call which
// ends the writable side of net.Socket.
-w.end();
\ No newline at end of file
+w.end();
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-large-read-stall.js b/test/parallel/test-stream2-large-read-stall.js
index deabcf1b9c..72623b87e5 100644
--- a/test/parallel/test-stream2-large-read-stall.js
+++ b/test/parallel/test-stream2-large-read-stall.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -68,4 +70,7 @@ function push() {
;false && console.error(' push #' + pushes);
if (r.push(bufferShim.allocUnsafe(PUSHSIZE))) setTimeout(push, 1);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-objects.js b/test/parallel/test-stream2-objects.js
index 5665f5e8ef..8196b10a38 100644
--- a/test/parallel/test-stream2-objects.js
+++ b/test/parallel/test-stream2-objects.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -100,9 +102,9 @@ function fromArray(list) {
{
// Verify that objects can be asynchronously read
var _r4 = new Readable({ objectMode: true });
- var _list = [{ one: '1' }, { two: '2' }];
+ var _list2 = [{ one: '1' }, { two: '2' }];
_r4._read = function (n) {
- var item = _list.shift();
+ var item = _list2.shift();
process.nextTick(function () {
_r4.push(item || null);
});
@@ -119,14 +121,14 @@ function fromArray(list) {
objectMode: true
});
_r5._read = common.mustNotCall();
- var _list2 = ['one', 'two', 'three'];
- forEach(_list2, function (str) {
+ var _list3 = ['one', 'two', 'three'];
+ forEach(_list3, function (str) {
_r5.push(str);
});
_r5.push(null);
_r5.pipe(toArray(common.mustCall(function (array) {
- assert.deepStrictEqual(array, _list2);
+ assert.deepStrictEqual(array, _list3);
})));
}
@@ -169,13 +171,13 @@ function fromArray(list) {
objectMode: true
});
var calls = 0;
- var _list3 = ['1', '2', '3', '4', '5', '6', '7', '8'];
+ var _list4 = ['1', '2', '3', '4', '5', '6', '7', '8'];
_r8._read = function (n) {
calls++;
};
- forEach(_list3, function (c) {
+ forEach(_list4, function (c) {
_r8.push(c);
});
@@ -223,15 +225,15 @@ function fromArray(list) {
{
// Verify that multiple objects can be written to stream
var _w = new Writable({ objectMode: true });
- var _list4 = [];
+ var _list5 = [];
_w._write = function (chunk, encoding, cb) {
- _list4.push(chunk);
+ _list5.push(chunk);
cb();
};
_w.on('finish', common.mustCall(function () {
- assert.deepStrictEqual(_list4, [0, 1, 2, 3, 4]);
+ assert.deepStrictEqual(_list5, [0, 1, 2, 3, 4]);
}));
_w.write(0);
@@ -247,15 +249,15 @@ function fromArray(list) {
var _w2 = new Writable({
objectMode: true
});
- var _list5 = [];
+ var _list6 = [];
_w2._write = function (chunk, encoding, cb) {
- _list5.push(chunk);
+ _list6.push(chunk);
process.nextTick(cb);
};
_w2.on('finish', common.mustCall(function () {
- assert.deepStrictEqual(_list5, ['0', '1', '2', '3', '4']);
+ assert.deepStrictEqual(_list6, ['0', '1', '2', '3', '4']);
}));
_w2.write('0');
@@ -294,4 +296,7 @@ function forEach(xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
f(xs[i], i);
}
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-pipe-error-handling.js b/test/parallel/test-stream2-pipe-error-handling.js
index 4ccad3dfe2..d2eae1faea 100644
--- a/test/parallel/test-stream2-pipe-error-handling.js
+++ b/test/parallel/test-stream2-pipe-error-handling.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -105,4 +107,7 @@ var stream = require('../../');
assert.strictEqual(_gotErr, _err);
assert.strictEqual(_unpipedSource, _source);
assert.strictEqual(_unpipedDest, _dest);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-pipe-error-once-listener.js b/test/parallel/test-stream2-pipe-error-once-listener.js
index 2b8e467cf3..a52ef2cfd0 100644
--- a/test/parallel/test-stream2-pipe-error-once-listener.js
+++ b/test/parallel/test-stream2-pipe-error-once-listener.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -71,11 +73,14 @@ var write = new Write();
write.once('error', function () {});
write.once('alldone', function (err) {
- console.log('ok');
+ require('tap').pass();
});
process.on('exit', function (c) {
console.error('error thrown even with listener');
});
-read.pipe(write);
\ No newline at end of file
+read.pipe(write);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-push.js b/test/parallel/test-stream2-push.js
index 358e57a7a5..efc84a1846 100644
--- a/test/parallel/test-stream2-push.js
+++ b/test/parallel/test-stream2-push.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -52,7 +54,7 @@ stream.on('end', function () {
source.on('data', function (chunk) {
var ret = stream.push(chunk);
- console.error('data', stream._readableState.length);
+ console.error('data', stream.readableLength);
if (!ret) readStop();
});
@@ -115,7 +117,7 @@ function data() {
function finish() {
console.error('finish');
assert.deepStrictEqual(written, expectWritten);
- console.log('ok');
+ require('tap').pass();
}
function end() {
@@ -125,4 +127,7 @@ function end() {
setImmediate(function () {
assert(ended);
});
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-read-sync-stack.js b/test/parallel/test-stream2-read-sync-stack.js
index d0400d52d3..0afe19954d 100644
--- a/test/parallel/test-stream2-read-sync-stack.js
+++ b/test/parallel/test-stream2-read-sync-stack.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -38,10 +40,13 @@ r._read = function (n) {
};
r.on('readable', function onReadable() {
- if (!(r._readableState.length % 256)) console.error('readable', r._readableState.length);
+ if (!(r.readableLength % 256)) console.error('readable', r.readableLength);
r.read(N * 2);
});
r.on('end', common.mustCall());
-r.read(0);
\ No newline at end of file
+r.read(0);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-readable-empty-buffer-no-eof.js b/test/parallel/test-stream2-readable-empty-buffer-no-eof.js
index 8371ac1133..177d7ad64e 100644
--- a/test/parallel/test-stream2-readable-empty-buffer-no-eof.js
+++ b/test/parallel/test-stream2-readable-empty-buffer-no-eof.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -88,7 +90,7 @@ function test1() {
process.on('exit', function () {
assert.deepStrictEqual(results, ['xxxxx', 'xxxxx', 'EOF']);
- console.log('ok');
+ require('tap').pass();
});
}
@@ -115,6 +117,9 @@ function test2() {
process.on('exit', function () {
assert.deepStrictEqual(results, ['eHh4', 'eHg=', 'EOF']);
- console.log('ok');
+ require('tap').pass();
});
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-readable-from-list.js b/test/parallel/test-stream2-readable-from-list.js
index 169d8f8168..cd357992d5 100644
--- a/test/parallel/test-stream2-readable-from-list.js
+++ b/test/parallel/test-stream2-readable-from-list.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -26,7 +28,7 @@ var bufferShim = require('safe-buffer').Buffer;
require('../common');
var assert = require('assert/');
var fromList = require('../../lib/_stream_readable')._fromList;
-var BufferList = require('../../lib/internal/streams/BufferList');
+var BufferList = require('../../lib/internal/streams/buffer_list');
function bufferListFromArray(arr) {
var bl = new BufferList();
@@ -62,25 +64,28 @@ function bufferListFromArray(arr) {
{
// Verify behavior with strings
- var _list = ['foog', 'bark', 'bazy', 'kuel'];
- _list = bufferListFromArray(_list);
+ var _list2 = ['foog', 'bark', 'bazy', 'kuel'];
+ _list2 = bufferListFromArray(_list2);
// read more than the first element.
- var _ret = fromList(6, { buffer: _list, length: 16, decoder: true });
+ var _ret = fromList(6, { buffer: _list2, length: 16, decoder: true });
assert.strictEqual(_ret, 'foogba');
// read exactly the first element.
- _ret = fromList(2, { buffer: _list, length: 10, decoder: true });
+ _ret = fromList(2, { buffer: _list2, length: 10, decoder: true });
assert.strictEqual(_ret, 'rk');
// read less than the first element.
- _ret = fromList(2, { buffer: _list, length: 8, decoder: true });
+ _ret = fromList(2, { buffer: _list2, length: 8, decoder: true });
assert.strictEqual(_ret, 'ba');
// read more than we have.
- _ret = fromList(100, { buffer: _list, length: 6, decoder: true });
+ _ret = fromList(100, { buffer: _list2, length: 6, decoder: true });
assert.strictEqual(_ret, 'zykuel');
// all consumed.
- assert.deepStrictEqual(_list, new BufferList());
-}
\ No newline at end of file
+ assert.deepStrictEqual(_list2, new BufferList());
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-readable-legacy-drain.js b/test/parallel/test-stream2-readable-legacy-drain.js
index 8c249c1f3a..59fdc73113 100644
--- a/test/parallel/test-stream2-readable-legacy-drain.js
+++ b/test/parallel/test-stream2-readable-legacy-drain.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -61,4 +63,7 @@ r.on('readable', function () {
w.emit('drain');
});
-r.pipe(w);
\ No newline at end of file
+r.pipe(w);
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-readable-non-empty-end.js b/test/parallel/test-stream2-readable-non-empty-end.js
index f9045ae513..4a70c8c42a 100644
--- a/test/parallel/test-stream2-readable-non-empty-end.js
+++ b/test/parallel/test-stream2-readable-non-empty-end.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -71,4 +73,7 @@ function next() {
assert.strictEqual(r.length, 1);
r = test.read();
assert.strictEqual(r, null);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-readable-wrap-empty.js b/test/parallel/test-stream2-readable-wrap-empty.js
index 165af42be5..15474eb989 100644
--- a/test/parallel/test-stream2-readable-wrap-empty.js
+++ b/test/parallel/test-stream2-readable-wrap-empty.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -35,4 +37,7 @@ var newStream = new Readable().wrap(oldStream);
newStream.on('readable', function () {}).on('end', common.mustCall());
-oldStream.emit('end');
\ No newline at end of file
+oldStream.emit('end');
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-set-encoding.js b/test/parallel/test-stream2-set-encoding.js
index ebf1fd3f0e..b6027ed866 100644
--- a/test/parallel/test-stream2-set-encoding.js
+++ b/test/parallel/test-stream2-set-encoding.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -224,4 +226,7 @@ var TestReader = function (_R) {
// Verify chaining behavior
var _tr8 = new TestReader(100);
assert.deepStrictEqual(_tr8.setEncoding('utf8'), _tr8);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-transform.js b/test/parallel/test-stream2-transform.js
index 62aa1d2bdb..580a34292d 100644
--- a/test/parallel/test-stream2-transform.js
+++ b/test/parallel/test-stream2-transform.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -45,10 +47,10 @@ var Transform = require('../../lib/_stream_transform');
}
tx.end();
- assert.strictEqual(tx._readableState.length, 10);
+ assert.strictEqual(tx.readableLength, 10);
assert.strictEqual(transformed, 10);
assert.strictEqual(tx._transformState.writechunk.length, 5);
- assert.deepStrictEqual(tx._writableState.getBuffer().map(function (c) {
+ assert.deepStrictEqual(tx.writableBuffer.map(function (c) {
return c.chunk.length;
}), [6, 7, 8, 9, 10]);
}
@@ -177,7 +179,7 @@ var Transform = require('../../lib/_stream_transform');
}
{
- // Verify assymetric transform (expand)
+ // Verify asymmetric transform (expand)
var _pt7 = new Transform();
// emit each chunk 2 times.
@@ -209,7 +211,7 @@ var Transform = require('../../lib/_stream_transform');
}
{
- // Verify assymetric trasform (compress)
+ // Verify asymmetric transform (compress)
var _pt8 = new Transform();
// each output is the first char of 3 consecutive chunks,
@@ -265,7 +267,7 @@ var Transform = require('../../lib/_stream_transform');
// this tests for a stall when data is written to a full stream
// that has empty transforms.
{
- // Verify compex transform behavior
+ // Verify complex transform behavior
var count = 0;
var saved = null;
var _pt9 = new Transform({ highWaterMark: 3 });
@@ -306,25 +308,26 @@ var Transform = require('../../lib/_stream_transform');
_pt10.write(bufferShim.from('foog'));
_pt10.write(bufferShim.from('bark'));
- assert.strictEqual(emits, 1);
+ assert.strictEqual(emits, 0);
assert.strictEqual(_pt10.read(5).toString(), 'foogb');
assert.strictEqual(String(_pt10.read(5)), 'null');
+ assert.strictEqual(emits, 0);
_pt10.write(bufferShim.from('bazy'));
_pt10.write(bufferShim.from('kuel'));
- assert.strictEqual(emits, 2);
+ assert.strictEqual(emits, 0);
assert.strictEqual(_pt10.read(5).toString(), 'arkba');
assert.strictEqual(_pt10.read(5).toString(), 'zykue');
assert.strictEqual(_pt10.read(5), null);
_pt10.end();
- assert.strictEqual(emits, 3);
+ assert.strictEqual(emits, 1);
assert.strictEqual(_pt10.read(5).toString(), 'l');
assert.strictEqual(_pt10.read(5), null);
- assert.strictEqual(emits, 3);
+ assert.strictEqual(emits, 1);
}
{
@@ -338,7 +341,7 @@ var Transform = require('../../lib/_stream_transform');
_pt11.write(bufferShim.from('foog'));
_pt11.write(bufferShim.from('bark'));
- assert.strictEqual(_emits, 1);
+ assert.strictEqual(_emits, 0);
assert.strictEqual(_pt11.read(5).toString(), 'foogb');
assert.strictEqual(_pt11.read(5), null);
@@ -352,7 +355,7 @@ var Transform = require('../../lib/_stream_transform');
_pt11.once('readable', common.mustCall(function () {
assert.strictEqual(_pt11.read(5).toString(), 'l');
assert.strictEqual(_pt11.read(5), null);
- assert.strictEqual(_emits, 4);
+ assert.strictEqual(_emits, 3);
}));
_pt11.end();
}));
@@ -465,4 +468,7 @@ function forEach(xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
f(xs[i], i);
}
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-unpipe-drain.js b/test/parallel/test-stream2-unpipe-drain.js
index 160ded4f06..afa334f204 100644
--- a/test/parallel/test-stream2-unpipe-drain.js
+++ b/test/parallel/test-stream2-unpipe-drain.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -96,4 +98,6 @@ function _inherits(subClass, superClass) { if (typeof superClass !== "function"
assert.strictEqual(src1.reads, 2);
assert.strictEqual(src2.reads, 2);
});
-})();
\ No newline at end of file
+})();require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-unpipe-leak.js b/test/parallel/test-stream2-unpipe-leak.js
index e77e939ed1..dcc3aed100 100644
--- a/test/parallel/test-stream2-unpipe-leak.js
+++ b/test/parallel/test-stream2-unpipe-leak.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -91,8 +93,11 @@ assert.strictEqual(dest.listeners('finish').length, 0);
console.error(src._readableState);
process.on('exit', function () {
- src._readableState.buffer.length = 0;
+ src.readableBuffer.length = 0;
console.error(src._readableState);
- assert(src._readableState.length >= src.readableHighWaterMark);
- console.log('ok');
+ assert(src.readableLength >= src.readableHighWaterMark);
+ require('tap').pass();
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream2-writable.js b/test/parallel/test-stream2-writable.js
index d5d23d28bb..43b173b784 100644
--- a/test/parallel/test-stream2-writable.js
+++ b/test/parallel/test-stream2-writable.js
@@ -1,3 +1,5 @@
+'use strict';
+
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _possibleConstructorReturn(self, call) { if (!self) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return call && (typeof call === "object" || typeof call === "function") ? call : self; }
@@ -125,7 +127,7 @@ for (var i = 0; i < chunks.length; i++) {
} while (ret !== false && _i2 < chunks.length);
if (_i2 < chunks.length) {
- assert(_tw2._writableState.length >= 50);
+ assert(_tw2.writableLength >= 50);
_tw2.once('drain', W);
} else {
_tw2.end();
@@ -388,4 +390,7 @@ function forEach(xs, f) {
for (var i = 0, l = xs.length; i < l; i++) {
f(xs[i], i);
}
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-stream3-cork-end.js b/test/parallel/test-stream3-cork-end.js
index 8e3605ccfa..8e306f2732 100644
--- a/test/parallel/test-stream3-cork-end.js
+++ b/test/parallel/test-stream3-cork-end.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -6,7 +8,7 @@ var assert = require('assert/');
var stream = require('../../');
var Writable = stream.Writable;
-// Test the buffering behaviour of Writable streams.
+// Test the buffering behavior of Writable streams.
//
// The call to cork() triggers storing chunks which are flushed
// on calling end() and the stream subsequently ended.
@@ -90,4 +92,7 @@ writeChunks(inputChunks, function () {
// stream should have ended in next tick
assert.ok(seenEnd);
});
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream3-cork-uncork.js b/test/parallel/test-stream3-cork-uncork.js
index d80e7645e1..779773d5b3 100644
--- a/test/parallel/test-stream3-cork-uncork.js
+++ b/test/parallel/test-stream3-cork-uncork.js
@@ -1,3 +1,5 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
@@ -6,7 +8,7 @@ var assert = require('assert/');
var stream = require('../../');
var Writable = stream.Writable;
-// Test the buffering behaviour of Writable streams.
+// Test the buffering behavior of Writable streams.
//
// The call to cork() triggers storing chunks which are flushed
// on calling uncork() in the same tick.
@@ -67,7 +69,7 @@ writeChunks(inputChunks, function () {
// trigger writing out the buffer
w.uncork();
- // buffered bytes shoud be seen in current tick
+ // buffered bytes should be seen in current tick
assert.strictEqual(seenChunks.length, 4);
// did the chunks match
@@ -85,4 +87,7 @@ writeChunks(inputChunks, function () {
// the stream should not have been ended
assert.ok(!seenEnd);
});
+});
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
});
\ No newline at end of file
diff --git a/test/parallel/test-stream3-pause-then-read.js b/test/parallel/test-stream3-pause-then-read.js
index a0269492e4..ed480b2163 100644
--- a/test/parallel/test-stream3-pause-then-read.js
+++ b/test/parallel/test-stream3-pause-then-read.js
@@ -1,3 +1,5 @@
+'use strict';
+
// Copyright Joyent, Inc. and other Node contributors.
//
// Permission is hereby granted, free of charge, to any person obtaining a
@@ -37,6 +39,7 @@ var expectEndingData = expectTotalData;
var r = new Readable({ highWaterMark: 1000 });
var chunks = totalChunks;
r._read = function (n) {
+ console.log('_read called', chunks);
if (!(chunks % 2)) setImmediate(push);else if (!(chunks % 3)) process.nextTick(push);else push();
};
@@ -46,6 +49,7 @@ function push() {
if (chunk) {
totalPushed += chunk.length;
}
+ console.log('chunks', chunks);
r.push(chunk);
}
@@ -61,9 +65,10 @@ function readn(n, then) {
expectEndingData -= n;
(function read() {
var c = r.read(n);
+ console.error('c', c);
if (!c) r.once('readable', read);else {
assert.strictEqual(c.length, n);
- assert(!r._readableState.flowing);
+ assert(!r.readableFlowing);
then();
}
})();
@@ -155,7 +160,10 @@ function pipe() {
console.error('written', written, totalPushed);
assert.strictEqual(written, expectEndingData);
assert.strictEqual(totalPushed, expectTotalData);
- console.log('ok');
+ require('tap').pass();
});
r.pipe(w);
-}
\ No newline at end of file
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/parallel/test-streams-highwatermark.js b/test/parallel/test-streams-highwatermark.js
index 789af9448b..f3d8a4ed1e 100644
--- a/test/parallel/test-streams-highwatermark.js
+++ b/test/parallel/test-streams-highwatermark.js
@@ -1,20 +1,77 @@
+'use strict';
+
/**/
var bufferShim = require('safe-buffer').Buffer;
/**/
-require('../common');
-
-// This test ensures that the stream implementation correctly handles values
-// for highWaterMark which exceed the range of signed 32 bit integers.
+var common = require('../common');
var assert = require('assert/');
var stream = require('../../');
-// This number exceeds the range of 32 bit integer arithmetic but should still
-// be handled correctly.
-var ovfl = Number.MAX_SAFE_INTEGER;
+{
+ // This test ensures that the stream implementation correctly handles values
+ // for highWaterMark which exceed the range of signed 32 bit integers and
+ // rejects invalid values.
+
+ // This number exceeds the range of 32 bit integer arithmetic but should still
+ // be handled correctly.
+ var ovfl = Number.MAX_SAFE_INTEGER;
+
+ var readable = stream.Readable({ highWaterMark: ovfl });
+ assert.strictEqual(readable._readableState.highWaterMark, ovfl);
+
+ var writable = stream.Writable({ highWaterMark: ovfl });
+ assert.strictEqual(writable._writableState.highWaterMark, ovfl);
+
+ var _loop = function (invalidHwm) {
+ var _loop2 = function (type) {
+ common.expectsError(function () {
+ type({ highWaterMark: invalidHwm });
+ }, {
+ type: TypeError,
+ code: 'ERR_INVALID_OPT_VALUE',
+ message: 'The value "' + invalidHwm + '" is invalid for option "highWaterMark"'
+ });
+ };
+
+ var _arr2 = [stream.Readable, stream.Writable];
+
+ for (var _i2 = 0; _i2 < _arr2.length; _i2++) {
+ var type = _arr2[_i2];
+ _loop2(type);
+ }
+ };
+
+ var _arr = [true, false, '5', {}, -5, NaN];
+ for (var _i = 0; _i < _arr.length; _i++) {
+ var invalidHwm = _arr[_i];
+ _loop(invalidHwm);
+ }
+}
+
+{
+ // This test ensures that the push method's implementation
+ // correctly handles the edge case where the highWaterMark and
+ // the state.length are both zero
+
+ var _readable = stream.Readable({ highWaterMark: 0 });
+
+ for (var i = 0; i < 3; i++) {
+ var needMoreData = _readable.push();
+ assert.strictEqual(needMoreData, true);
+ }
+}
+
+{
+ // This test ensures that the read(n) method's implementation
+ // correctly handles the edge case where the highWaterMark, state.length
+ // and n are all zero
-var readable = stream.Readable({ highWaterMark: ovfl });
-assert.strictEqual(readable._readableState.highWaterMark, ovfl);
+ var _readable2 = stream.Readable({ highWaterMark: 0 });
-var writable = stream.Writable({ highWaterMark: ovfl });
-assert.strictEqual(writable._writableState.highWaterMark, ovfl);
\ No newline at end of file
+ _readable2._read = common.mustCall();
+ _readable2.read(0);
+}
+;require('tap').pass('sync run');var _list = process.listeners('uncaughtException');process.removeAllListeners('uncaughtException');_list.pop();_list.forEach(function (e) {
+ return process.on('uncaughtException', e);
+});
\ No newline at end of file
diff --git a/test/verify-dependencies.js b/test/verify-dependencies.js
deleted file mode 100644
index e7fba50f1f..0000000000
--- a/test/verify-dependencies.js
+++ /dev/null
@@ -1,13 +0,0 @@
-'use strict'
-
-var pack = require('../package.json');
-var assert = require('assert');
-
-function verifyNoCaret(deps) {
- var keys = Object.keys(deps);
- for (var i = 0; i < keys.length; i++) {
- assert(deps[keys[i]][0] !== '^', keys[i] + ' must not be depended on using ^')
- }
-}
-
-verifyNoCaret(pack.dependencies)
diff --git a/transform.js b/transform.js
deleted file mode 100644
index b1baba26da..0000000000
--- a/transform.js
+++ /dev/null
@@ -1 +0,0 @@
-module.exports = require('./readable').Transform
diff --git a/writable-browser.js b/writable-browser.js
deleted file mode 100644
index ebdde6a85d..0000000000
--- a/writable-browser.js
+++ /dev/null
@@ -1 +0,0 @@
-module.exports = require('./lib/_stream_writable.js');
diff --git a/writable.js b/writable.js
deleted file mode 100644
index 3211a6f80d..0000000000
--- a/writable.js
+++ /dev/null
@@ -1,8 +0,0 @@
-var Stream = require("stream")
-var Writable = require("./lib/_stream_writable.js")
-
-if (process.env.READABLE_STREAM === 'disable') {
- module.exports = Stream && Stream.Writable || Writable
-} else {
- module.exports = Writable
-}