| Index: tools/vulcanize/node_modules/vulcanize/node_modules/cheerio/node_modules/htmlparser2/node_modules/readable-stream/README.md
|
| diff --git a/tools/vulcanize/node_modules/vulcanize/node_modules/cheerio/node_modules/htmlparser2/node_modules/readable-stream/README.md b/tools/vulcanize/node_modules/vulcanize/node_modules/cheerio/node_modules/htmlparser2/node_modules/readable-stream/README.md
|
| new file mode 100644
|
| index 0000000000000000000000000000000000000000..be976683e44974d48380a6a235dd16faad69ab7c
|
| --- /dev/null
|
| +++ b/tools/vulcanize/node_modules/vulcanize/node_modules/cheerio/node_modules/htmlparser2/node_modules/readable-stream/README.md
|
| @@ -0,0 +1,768 @@
|
| +# readable-stream
|
| +
|
| +A new class of streams for Node.js
|
| +
|
| +This module provides the new Stream base classes introduced in Node
|
| +v0.10, for use in Node v0.8. You can use it to have programs that
|
| +have to work with node v0.8, while being forward-compatible for v0.10
|
| +and beyond. When you drop support for v0.8, you can remove this
|
| +module, and only use the native streams.
|
| +
|
| +This is almost exactly the same codebase as appears in Node v0.10.
|
| +However:
|
| +
|
| +1. The exported object is actually the Readable class. Decorating the
|
| + native `stream` module would be global pollution.
|
| +2. In v0.10, you can safely use `base64` as an argument to
|
| + `setEncoding` in Readable streams. However, in v0.8, the
|
| + StringDecoder class has no `end()` method, which is problematic for
|
| + Base64. So, don't use that, because it'll break and be weird.
|
| +
|
| +Other than that, the API is the same as `require('stream')` in v0.10,
|
| +so the API docs are reproduced below.
|
| +
|
| +----------
|
| +
|
| + Stability: 2 - Unstable
|
| +
|
| +A stream is an abstract interface implemented by various objects in
|
| +Node. For example a request to an HTTP server is a stream, as is
|
| +stdout. Streams are readable, writable, or both. All streams are
|
| +instances of [EventEmitter][]
|
| +
|
| +You can load the Stream base classes by doing `require('stream')`.
|
| +There are base classes provided for Readable streams, Writable
|
| +streams, Duplex streams, and Transform streams.
|
| +
|
| +## Compatibility
|
| +
|
| +In earlier versions of Node, the Readable stream interface was
|
| +simpler, but also less powerful and less useful.
|
| +
|
| +* Rather than waiting for you to call the `read()` method, `'data'`
|
| + events would start emitting immediately. If you needed to do some
|
| + I/O to decide how to handle data, then you had to store the chunks
|
| + in some kind of buffer so that they would not be lost.
|
| +* The `pause()` method was advisory, rather than guaranteed. This
|
| + meant that you still had to be prepared to receive `'data'` events
|
| + even when the stream was in a paused state.
|
| +
|
| +In Node v0.10, the Readable class described below was added. For
|
| +backwards compatibility with older Node programs, Readable streams
|
| +switch into "old mode" when a `'data'` event handler is added, or when
|
| +the `pause()` or `resume()` methods are called. The effect is that,
|
| +even if you are not using the new `read()` method and `'readable'`
|
| +event, you no longer have to worry about losing `'data'` chunks.
|
| +
|
| +Most programs will continue to function normally. However, this
|
| +introduces an edge case in the following conditions:
|
| +
|
| +* No `'data'` event handler is added.
|
| +* The `pause()` and `resume()` methods are never called.
|
| +
|
| +For example, consider the following code:
|
| +
|
| +```javascript
|
| +// WARNING! BROKEN!
|
| +net.createServer(function(socket) {
|
| +
|
| + // we add an 'end' method, but never consume the data
|
| + socket.on('end', function() {
|
| + // It will never get here.
|
| + socket.end('I got your message (but didnt read it)\n');
|
| + });
|
| +
|
| +}).listen(1337);
|
| +```
|
| +
|
| +In versions of node prior to v0.10, the incoming message data would be
|
| +simply discarded. However, in Node v0.10 and beyond, the socket will
|
| +remain paused forever.
|
| +
|
| +The workaround in this situation is to call the `resume()` method to
|
| +trigger "old mode" behavior:
|
| +
|
| +```javascript
|
| +// Workaround
|
| +net.createServer(function(socket) {
|
| +
|
| + socket.on('end', function() {
|
| + socket.end('I got your message (but didnt read it)\n');
|
| + });
|
| +
|
| + // start the flow of data, discarding it.
|
| + socket.resume();
|
| +
|
| +}).listen(1337);
|
| +```
|
| +
|
| +In addition to new Readable streams switching into old-mode, pre-v0.10
|
| +style streams can be wrapped in a Readable class using the `wrap()`
|
| +method.
|
| +
|
| +## Class: stream.Readable
|
| +
|
| +<!--type=class-->
|
| +
|
| +A `Readable Stream` has the following methods, members, and events.
|
| +
|
| +Note that `stream.Readable` is an abstract class designed to be
|
| +extended with an underlying implementation of the `_read(size)`
|
| +method. (See below.)
|
| +
|
| +### new stream.Readable([options])
|
| +
|
| +* `options` {Object}
|
| + * `highWaterMark` {Number} The maximum number of bytes to store in
|
| + the internal buffer before ceasing to read from the underlying
|
| + resource. Default=16kb
|
| + * `encoding` {String} If specified, then buffers will be decoded to
|
| + strings using the specified encoding. Default=null
|
| + * `objectMode` {Boolean} Whether this stream should behave
|
| + as a stream of objects. Meaning that stream.read(n) returns
|
| + a single value instead of a Buffer of size n
|
| +
|
| +In classes that extend the Readable class, make sure to call the
|
| +constructor so that the buffering settings can be properly
|
| +initialized.
|
| +
|
| +### readable.\_read(size)
|
| +
|
| +* `size` {Number} Number of bytes to read asynchronously
|
| +
|
| +Note: **This function should NOT be called directly.** It should be
|
| +implemented by child classes, and called by the internal Readable
|
| +class methods only.
|
| +
|
| +All Readable stream implementations must provide a `_read` method
|
| +to fetch data from the underlying resource.
|
| +
|
| +This method is prefixed with an underscore because it is internal to
|
| +the class that defines it, and should not be called directly by user
|
| +programs. However, you **are** expected to override this method in
|
| +your own extension classes.
|
| +
|
| +When data is available, put it into the read queue by calling
|
| +`readable.push(chunk)`. If `push` returns false, then you should stop
|
| +reading. When `_read` is called again, you should start pushing more
|
| +data.
|
| +
|
| +The `size` argument is advisory. Implementations where a "read" is a
|
| +single call that returns data can use this to know how much data to
|
| +fetch. Implementations where that is not relevant, such as TCP or
|
| +TLS, may ignore this argument, and simply provide data whenever it
|
| +becomes available. There is no need, for example to "wait" until
|
| +`size` bytes are available before calling `stream.push(chunk)`.
|
| +
|
| +### readable.push(chunk)
|
| +
|
| +* `chunk` {Buffer | null | String} Chunk of data to push into the read queue
|
| +* return {Boolean} Whether or not more pushes should be performed
|
| +
|
| +Note: **This function should be called by Readable implementors, NOT
|
| +by consumers of Readable subclasses.** The `_read()` function will not
|
| +be called again until at least one `push(chunk)` call is made. If no
|
| +data is available, then you MAY call `push('')` (an empty string) to
|
| +allow a future `_read` call, without adding any data to the queue.
|
| +
|
| +The `Readable` class works by putting data into a read queue to be
|
| +pulled out later by calling the `read()` method when the `'readable'`
|
| +event fires.
|
| +
|
| +The `push()` method will explicitly insert some data into the read
|
| +queue. If it is called with `null` then it will signal the end of the
|
| +data.
|
| +
|
| +In some cases, you may be wrapping a lower-level source which has some
|
| +sort of pause/resume mechanism, and a data callback. In those cases,
|
| +you could wrap the low-level source object by doing something like
|
| +this:
|
| +
|
| +```javascript
|
| +// source is an object with readStop() and readStart() methods,
|
| +// and an `ondata` member that gets called when it has data, and
|
| +// an `onend` member that gets called when the data is over.
|
| +
|
| +var stream = new Readable();
|
| +
|
| +source.ondata = function(chunk) {
|
| + // if push() returns false, then we need to stop reading from source
|
| + if (!stream.push(chunk))
|
| + source.readStop();
|
| +};
|
| +
|
| +source.onend = function() {
|
| + stream.push(null);
|
| +};
|
| +
|
| +// _read will be called when the stream wants to pull more data in
|
| +// the advisory size argument is ignored in this case.
|
| +stream._read = function(n) {
|
| + source.readStart();
|
| +};
|
| +```
|
| +
|
| +### readable.unshift(chunk)
|
| +
|
| +* `chunk` {Buffer | null | String} Chunk of data to unshift onto the read queue
|
| +* return {Boolean} Whether or not more pushes should be performed
|
| +
|
| +This is the corollary of `readable.push(chunk)`. Rather than putting
|
| +the data at the *end* of the read queue, it puts it at the *front* of
|
| +the read queue.
|
| +
|
| +This is useful in certain use-cases where a stream is being consumed
|
| +by a parser, which needs to "un-consume" some data that it has
|
| +optimistically pulled out of the source.
|
| +
|
| +```javascript
|
| +// A parser for a simple data protocol.
|
| +// The "header" is a JSON object, followed by 2 \n characters, and
|
| +// then a message body.
|
| +//
|
| +// Note: This can be done more simply as a Transform stream. See below.
|
| +
|
| +function SimpleProtocol(source, options) {
|
| + if (!(this instanceof SimpleProtocol))
|
| + return new SimpleProtocol(options);
|
| +
|
| + Readable.call(this, options);
|
| + this._inBody = false;
|
| + this._sawFirstCr = false;
|
| +
|
| + // source is a readable stream, such as a socket or file
|
| + this._source = source;
|
| +
|
| + var self = this;
|
| + source.on('end', function() {
|
| + self.push(null);
|
| + });
|
| +
|
| + // give it a kick whenever the source is readable
|
| + // read(0) will not consume any bytes
|
| + source.on('readable', function() {
|
| + self.read(0);
|
| + });
|
| +
|
| + this._rawHeader = [];
|
| + this.header = null;
|
| +}
|
| +
|
| +SimpleProtocol.prototype = Object.create(
|
| + Readable.prototype, { constructor: { value: SimpleProtocol }});
|
| +
|
| +SimpleProtocol.prototype._read = function(n) {
|
| + if (!this._inBody) {
|
| + var chunk = this._source.read();
|
| +
|
| + // if the source doesn't have data, we don't have data yet.
|
| + if (chunk === null)
|
| + return this.push('');
|
| +
|
| + // check if the chunk has a \n\n
|
| + var split = -1;
|
| + for (var i = 0; i < chunk.length; i++) {
|
| + if (chunk[i] === 10) { // '\n'
|
| + if (this._sawFirstCr) {
|
| + split = i;
|
| + break;
|
| + } else {
|
| + this._sawFirstCr = true;
|
| + }
|
| + } else {
|
| + this._sawFirstCr = false;
|
| + }
|
| + }
|
| +
|
| + if (split === -1) {
|
| + // still waiting for the \n\n
|
| + // stash the chunk, and try again.
|
| + this._rawHeader.push(chunk);
|
| + this.push('');
|
| + } else {
|
| + this._inBody = true;
|
| + var h = chunk.slice(0, split);
|
| + this._rawHeader.push(h);
|
| + var header = Buffer.concat(this._rawHeader).toString();
|
| + try {
|
| + this.header = JSON.parse(header);
|
| + } catch (er) {
|
| + this.emit('error', new Error('invalid simple protocol data'));
|
| + return;
|
| + }
|
| + // now, because we got some extra data, unshift the rest
|
| + // back into the read queue so that our consumer will see it.
|
| + var b = chunk.slice(split);
|
| + this.unshift(b);
|
| +
|
| + // and let them know that we are done parsing the header.
|
| + this.emit('header', this.header);
|
| + }
|
| + } else {
|
| + // from there on, just provide the data to our consumer.
|
| + // careful not to push(null), since that would indicate EOF.
|
| + var chunk = this._source.read();
|
| + if (chunk) this.push(chunk);
|
| + }
|
| +};
|
| +
|
| +// Usage:
|
| +var parser = new SimpleProtocol(source);
|
| +// Now parser is a readable stream that will emit 'header'
|
| +// with the parsed header data.
|
| +```
|
| +
|
| +### readable.wrap(stream)
|
| +
|
| +* `stream` {Stream} An "old style" readable stream
|
| +
|
| +If you are using an older Node library that emits `'data'` events and
|
| +has a `pause()` method that is advisory only, then you can use the
|
| +`wrap()` method to create a Readable stream that uses the old stream
|
| +as its data source.
|
| +
|
| +For example:
|
| +
|
| +```javascript
|
| +var OldReader = require('./old-api-module.js').OldReader;
|
| +var oreader = new OldReader;
|
| +var Readable = require('stream').Readable;
|
| +var myReader = new Readable().wrap(oreader);
|
| +
|
| +myReader.on('readable', function() {
|
| + myReader.read(); // etc.
|
| +});
|
| +```
|
| +
|
| +### Event: 'readable'
|
| +
|
| +When there is data ready to be consumed, this event will fire.
|
| +
|
| +When this event emits, call the `read()` method to consume the data.
|
| +
|
| +### Event: 'end'
|
| +
|
| +Emitted when the stream has received an EOF (FIN in TCP terminology).
|
| +Indicates that no more `'data'` events will happen. If the stream is
|
| +also writable, it may be possible to continue writing.
|
| +
|
| +### Event: 'data'
|
| +
|
| +The `'data'` event emits either a `Buffer` (by default) or a string if
|
| +`setEncoding()` was used.
|
| +
|
| +Note that adding a `'data'` event listener will switch the Readable
|
| +stream into "old mode", where data is emitted as soon as it is
|
| +available, rather than waiting for you to call `read()` to consume it.
|
| +
|
| +### Event: 'error'
|
| +
|
| +Emitted if there was an error receiving data.
|
| +
|
| +### Event: 'close'
|
| +
|
| +Emitted when the underlying resource (for example, the backing file
|
| +descriptor) has been closed. Not all streams will emit this.
|
| +
|
| +### readable.setEncoding(encoding)
|
| +
|
| +Makes the `'data'` event emit a string instead of a `Buffer`. `encoding`
|
| +can be `'utf8'`, `'utf16le'` (`'ucs2'`), `'ascii'`, or `'hex'`.
|
| +
|
| +The encoding can also be set by specifying an `encoding` field to the
|
| +constructor.
|
| +
|
| +### readable.read([size])
|
| +
|
| +* `size` {Number | null} Optional number of bytes to read.
|
| +* Return: {Buffer | String | null}
|
| +
|
| +Note: **This function SHOULD be called by Readable stream users.**
|
| +
|
| +Call this method to consume data once the `'readable'` event is
|
| +emitted.
|
| +
|
| +The `size` argument will set a minimum number of bytes that you are
|
| +interested in. If not set, then the entire content of the internal
|
| +buffer is returned.
|
| +
|
| +If there is no data to consume, or if there are fewer bytes in the
|
| +internal buffer than the `size` argument, then `null` is returned, and
|
| +a future `'readable'` event will be emitted when more is available.
|
| +
|
| +Calling `stream.read(0)` will always return `null`, and will trigger a
|
| +refresh of the internal buffer, but otherwise be a no-op.
|
| +
|
| +### readable.pipe(destination, [options])
|
| +
|
| +* `destination` {Writable Stream}
|
| +* `options` {Object} Optional
|
| + * `end` {Boolean} Default=true
|
| +
|
| +Connects this readable stream to `destination` WriteStream. Incoming
|
| +data on this stream gets written to `destination`. Properly manages
|
| +back-pressure so that a slow destination will not be overwhelmed by a
|
| +fast readable stream.
|
| +
|
| +This function returns the `destination` stream.
|
| +
|
| +For example, emulating the Unix `cat` command:
|
| +
|
| + process.stdin.pipe(process.stdout);
|
| +
|
| +By default `end()` is called on the destination when the source stream
|
| +emits `end`, so that `destination` is no longer writable. Pass `{ end:
|
| +false }` as `options` to keep the destination stream open.
|
| +
|
| +This keeps `writer` open so that "Goodbye" can be written at the
|
| +end.
|
| +
|
| + reader.pipe(writer, { end: false });
|
| + reader.on("end", function() {
|
| + writer.end("Goodbye\n");
|
| + });
|
| +
|
| +Note that `process.stderr` and `process.stdout` are never closed until
|
| +the process exits, regardless of the specified options.
|
| +
|
| +### readable.unpipe([destination])
|
| +
|
| +* `destination` {Writable Stream} Optional
|
| +
|
| +Undo a previously established `pipe()`. If no destination is
|
| +provided, then all previously established pipes are removed.
|
| +
|
| +### readable.pause()
|
| +
|
| +Switches the readable stream into "old mode", where data is emitted
|
| +using a `'data'` event rather than being buffered for consumption via
|
| +the `read()` method.
|
| +
|
| +Ceases the flow of data. No `'data'` events are emitted while the
|
| +stream is in a paused state.
|
| +
|
| +### readable.resume()
|
| +
|
| +Switches the readable stream into "old mode", where data is emitted
|
| +using a `'data'` event rather than being buffered for consumption via
|
| +the `read()` method.
|
| +
|
| +Resumes the incoming `'data'` events after a `pause()`.
|
| +
|
| +
|
| +## Class: stream.Writable
|
| +
|
| +<!--type=class-->
|
| +
|
| +A `Writable` Stream has the following methods, members, and events.
|
| +
|
| +Note that `stream.Writable` is an abstract class designed to be
|
| +extended with an underlying implementation of the
|
| +`_write(chunk, encoding, cb)` method. (See below.)
|
| +
|
| +### new stream.Writable([options])
|
| +
|
| +* `options` {Object}
|
| + * `highWaterMark` {Number} Buffer level when `write()` starts
|
| + returning false. Default=16kb
|
| + * `decodeStrings` {Boolean} Whether or not to decode strings into
|
| + Buffers before passing them to `_write()`. Default=true
|
| +
|
| +In classes that extend the Writable class, make sure to call the
|
| +constructor so that the buffering settings can be properly
|
| +initialized.
|
| +
|
| +### writable.\_write(chunk, encoding, callback)
|
| +
|
| +* `chunk` {Buffer | String} The chunk to be written. Will always
|
| + be a buffer unless the `decodeStrings` option was set to `false`.
|
| +* `encoding` {String} If the chunk is a string, then this is the
|
| + encoding type. Ignore chunk is a buffer. Note that chunk will
|
| + **always** be a buffer unless the `decodeStrings` option is
|
| + explicitly set to `false`.
|
| +* `callback` {Function} Call this function (optionally with an error
|
| + argument) when you are done processing the supplied chunk.
|
| +
|
| +All Writable stream implementations must provide a `_write` method to
|
| +send data to the underlying resource.
|
| +
|
| +Note: **This function MUST NOT be called directly.** It should be
|
| +implemented by child classes, and called by the internal Writable
|
| +class methods only.
|
| +
|
| +Call the callback using the standard `callback(error)` pattern to
|
| +signal that the write completed successfully or with an error.
|
| +
|
| +If the `decodeStrings` flag is set in the constructor options, then
|
| +`chunk` may be a string rather than a Buffer, and `encoding` will
|
| +indicate the sort of string that it is. This is to support
|
| +implementations that have an optimized handling for certain string
|
| +data encodings. If you do not explicitly set the `decodeStrings`
|
| +option to `false`, then you can safely ignore the `encoding` argument,
|
| +and assume that `chunk` will always be a Buffer.
|
| +
|
| +This method is prefixed with an underscore because it is internal to
|
| +the class that defines it, and should not be called directly by user
|
| +programs. However, you **are** expected to override this method in
|
| +your own extension classes.
|
| +
|
| +
|
| +### writable.write(chunk, [encoding], [callback])
|
| +
|
| +* `chunk` {Buffer | String} Data to be written
|
| +* `encoding` {String} Optional. If `chunk` is a string, then encoding
|
| + defaults to `'utf8'`
|
| +* `callback` {Function} Optional. Called when this chunk is
|
| + successfully written.
|
| +* Returns {Boolean}
|
| +
|
| +Writes `chunk` to the stream. Returns `true` if the data has been
|
| +flushed to the underlying resource. Returns `false` to indicate that
|
| +the buffer is full, and the data will be sent out in the future. The
|
| +`'drain'` event will indicate when the buffer is empty again.
|
| +
|
| +The specifics of when `write()` will return false, is determined by
|
| +the `highWaterMark` option provided to the constructor.
|
| +
|
| +### writable.end([chunk], [encoding], [callback])
|
| +
|
| +* `chunk` {Buffer | String} Optional final data to be written
|
| +* `encoding` {String} Optional. If `chunk` is a string, then encoding
|
| + defaults to `'utf8'`
|
| +* `callback` {Function} Optional. Called when the final chunk is
|
| + successfully written.
|
| +
|
| +Call this method to signal the end of the data being written to the
|
| +stream.
|
| +
|
| +### Event: 'drain'
|
| +
|
| +Emitted when the stream's write queue empties and it's safe to write
|
| +without buffering again. Listen for it when `stream.write()` returns
|
| +`false`.
|
| +
|
| +### Event: 'close'
|
| +
|
| +Emitted when the underlying resource (for example, the backing file
|
| +descriptor) has been closed. Not all streams will emit this.
|
| +
|
| +### Event: 'finish'
|
| +
|
| +When `end()` is called and there are no more chunks to write, this
|
| +event is emitted.
|
| +
|
| +### Event: 'pipe'
|
| +
|
| +* `source` {Readable Stream}
|
| +
|
| +Emitted when the stream is passed to a readable stream's pipe method.
|
| +
|
| +### Event 'unpipe'
|
| +
|
| +* `source` {Readable Stream}
|
| +
|
| +Emitted when a previously established `pipe()` is removed using the
|
| +source Readable stream's `unpipe()` method.
|
| +
|
| +## Class: stream.Duplex
|
| +
|
| +<!--type=class-->
|
| +
|
| +A "duplex" stream is one that is both Readable and Writable, such as a
|
| +TCP socket connection.
|
| +
|
| +Note that `stream.Duplex` is an abstract class designed to be
|
| +extended with an underlying implementation of the `_read(size)`
|
| +and `_write(chunk, encoding, callback)` methods as you would with a Readable or
|
| +Writable stream class.
|
| +
|
| +Since JavaScript doesn't have multiple prototypal inheritance, this
|
| +class prototypally inherits from Readable, and then parasitically from
|
| +Writable. It is thus up to the user to implement both the lowlevel
|
| +`_read(n)` method as well as the lowlevel `_write(chunk, encoding, cb)` method
|
| +on extension duplex classes.
|
| +
|
| +### new stream.Duplex(options)
|
| +
|
| +* `options` {Object} Passed to both Writable and Readable
|
| + constructors. Also has the following fields:
|
| + * `allowHalfOpen` {Boolean} Default=true. If set to `false`, then
|
| + the stream will automatically end the readable side when the
|
| + writable side ends and vice versa.
|
| +
|
| +In classes that extend the Duplex class, make sure to call the
|
| +constructor so that the buffering settings can be properly
|
| +initialized.
|
| +
|
| +## Class: stream.Transform
|
| +
|
| +A "transform" stream is a duplex stream where the output is causally
|
| +connected in some way to the input, such as a zlib stream or a crypto
|
| +stream.
|
| +
|
| +There is no requirement that the output be the same size as the input,
|
| +the same number of chunks, or arrive at the same time. For example, a
|
| +Hash stream will only ever have a single chunk of output which is
|
| +provided when the input is ended. A zlib stream will either produce
|
| +much smaller or much larger than its input.
|
| +
|
| +Rather than implement the `_read()` and `_write()` methods, Transform
|
| +classes must implement the `_transform()` method, and may optionally
|
| +also implement the `_flush()` method. (See below.)
|
| +
|
| +### new stream.Transform([options])
|
| +
|
| +* `options` {Object} Passed to both Writable and Readable
|
| + constructors.
|
| +
|
| +In classes that extend the Transform class, make sure to call the
|
| +constructor so that the buffering settings can be properly
|
| +initialized.
|
| +
|
| +### transform.\_transform(chunk, encoding, callback)
|
| +
|
| +* `chunk` {Buffer | String} The chunk to be transformed. Will always
|
| + be a buffer unless the `decodeStrings` option was set to `false`.
|
| +* `encoding` {String} If the chunk is a string, then this is the
|
| + encoding type. (Ignore if `decodeStrings` chunk is a buffer.)
|
| +* `callback` {Function} Call this function (optionally with an error
|
| + argument) when you are done processing the supplied chunk.
|
| +
|
| +Note: **This function MUST NOT be called directly.** It should be
|
| +implemented by child classes, and called by the internal Transform
|
| +class methods only.
|
| +
|
| +All Transform stream implementations must provide a `_transform`
|
| +method to accept input and produce output.
|
| +
|
| +`_transform` should do whatever has to be done in this specific
|
| +Transform class, to handle the bytes being written, and pass them off
|
| +to the readable portion of the interface. Do asynchronous I/O,
|
| +process things, and so on.
|
| +
|
| +Call `transform.push(outputChunk)` 0 or more times to generate output
|
| +from this input chunk, depending on how much data you want to output
|
| +as a result of this chunk.
|
| +
|
| +Call the callback function only when the current chunk is completely
|
| +consumed. Note that there may or may not be output as a result of any
|
| +particular input chunk.
|
| +
|
| +This method is prefixed with an underscore because it is internal to
|
| +the class that defines it, and should not be called directly by user
|
| +programs. However, you **are** expected to override this method in
|
| +your own extension classes.
|
| +
|
| +### transform.\_flush(callback)
|
| +
|
| +* `callback` {Function} Call this function (optionally with an error
|
| + argument) when you are done flushing any remaining data.
|
| +
|
| +Note: **This function MUST NOT be called directly.** It MAY be implemented
|
| +by child classes, and if so, will be called by the internal Transform
|
| +class methods only.
|
| +
|
| +In some cases, your transform operation may need to emit a bit more
|
| +data at the end of the stream. For example, a `Zlib` compression
|
| +stream will store up some internal state so that it can optimally
|
| +compress the output. At the end, however, it needs to do the best it
|
| +can with what is left, so that the data will be complete.
|
| +
|
| +In those cases, you can implement a `_flush` method, which will be
|
| +called at the very end, after all the written data is consumed, but
|
| +before emitting `end` to signal the end of the readable side. Just
|
| +like with `_transform`, call `transform.push(chunk)` zero or more
|
| +times, as appropriate, and call `callback` when the flush operation is
|
| +complete.
|
| +
|
| +This method is prefixed with an underscore because it is internal to
|
| +the class that defines it, and should not be called directly by user
|
| +programs. However, you **are** expected to override this method in
|
| +your own extension classes.
|
| +
|
| +### Example: `SimpleProtocol` parser
|
| +
|
| +The example above of a simple protocol parser can be implemented much
|
| +more simply by using the higher level `Transform` stream class.
|
| +
|
| +In this example, rather than providing the input as an argument, it
|
| +would be piped into the parser, which is a more idiomatic Node stream
|
| +approach.
|
| +
|
| +```javascript
|
| +function SimpleProtocol(options) {
|
| + if (!(this instanceof SimpleProtocol))
|
| + return new SimpleProtocol(options);
|
| +
|
| + Transform.call(this, options);
|
| + this._inBody = false;
|
| + this._sawFirstCr = false;
|
| + this._rawHeader = [];
|
| + this.header = null;
|
| +}
|
| +
|
| +SimpleProtocol.prototype = Object.create(
|
| + Transform.prototype, { constructor: { value: SimpleProtocol }});
|
| +
|
| +SimpleProtocol.prototype._transform = function(chunk, encoding, done) {
|
| + if (!this._inBody) {
|
| + // check if the chunk has a \n\n
|
| + var split = -1;
|
| + for (var i = 0; i < chunk.length; i++) {
|
| + if (chunk[i] === 10) { // '\n'
|
| + if (this._sawFirstCr) {
|
| + split = i;
|
| + break;
|
| + } else {
|
| + this._sawFirstCr = true;
|
| + }
|
| + } else {
|
| + this._sawFirstCr = false;
|
| + }
|
| + }
|
| +
|
| + if (split === -1) {
|
| + // still waiting for the \n\n
|
| + // stash the chunk, and try again.
|
| + this._rawHeader.push(chunk);
|
| + } else {
|
| + this._inBody = true;
|
| + var h = chunk.slice(0, split);
|
| + this._rawHeader.push(h);
|
| + var header = Buffer.concat(this._rawHeader).toString();
|
| + try {
|
| + this.header = JSON.parse(header);
|
| + } catch (er) {
|
| + this.emit('error', new Error('invalid simple protocol data'));
|
| + return;
|
| + }
|
| + // and let them know that we are done parsing the header.
|
| + this.emit('header', this.header);
|
| +
|
| + // now, because we got some extra data, emit this first.
|
| + this.push(b);
|
| + }
|
| + } else {
|
| + // from there on, just provide the data to our consumer as-is.
|
| + this.push(b);
|
| + }
|
| + done();
|
| +};
|
| +
|
| +var parser = new SimpleProtocol();
|
| +source.pipe(parser)
|
| +
|
| +// Now parser is a readable stream that will emit 'header'
|
| +// with the parsed header data.
|
| +```
|
| +
|
| +
|
| +## Class: stream.PassThrough
|
| +
|
| +This is a trivial implementation of a `Transform` stream that simply
|
| +passes the input bytes across to the output. Its purpose is mainly
|
| +for examples and testing, but there are occasionally use cases where
|
| +it can come in handy.
|
| +
|
| +
|
| +[EventEmitter]: events.html#events_class_events_eventemitter
|
|
|