|
|
- var hpack = require('../hpack');
- var utils = hpack.utils;
- var encoder = hpack.encoder;
- var table = hpack.table;
- var assert = utils.assert;
-
- var inherits = require('inherits');
- var Duplex = require('readable-stream').Duplex;
-
- function Compressor(options) {
- Duplex.call(this, {
- writableObjectMode: true
- });
-
- this._encoder = null;
- this._table = table.create(options.table);
- }
- inherits(Compressor, Duplex);
- module.exports = Compressor;
-
- Compressor.create = function create(options) {
- return new Compressor(options);
- };
-
- Compressor.prototype._read = function _read() {
- // We only push!
- };
-
- Compressor.prototype._write = function _write(data, enc, cb) {
- assert(Array.isArray(data), 'Compressor.write() expects list of headers');
-
- this._encoder = encoder.create();
- for (var i = 0; i < data.length; i++)
- this._encodeHeader(data[i]);
-
- var data = this._encoder.render();
- this._encoder = null;
-
- cb(null);
- for (var i = 0; i < data.length; i++)
- this.push(data[i]);
- };
-
- Compressor.prototype.updateTableSize = function updateTableSize(size) {
- if (size >= this._table.protocolMaxSize) {
- size = this._table.protocolMaxSize;
-
- var enc = encoder.create();
-
- // indexed = 0
- // incremental = 0
- // update = 1
- enc.encodeBits(1, 3);
- enc.encodeInt(size);
-
- var data = enc.render();
- for (var i = 0; i < data.length; i++)
- this.push(data[i]);
- }
-
- this._table.updateSize(size);
- };
-
- Compressor.prototype.reset = function reset() {
- var enc = encoder.create();
- var size = this._table.maxSize;
-
- // indexed = 0
- // incremental = 0
- // update = 1
- enc.encodeBits(1, 3);
- enc.encodeInt(0);
-
- // Evict everything
- this._table.updateSize(0);
-
- // indexed = 0
- // incremental = 0
- // update = 1
- enc.encodeBits(1, 3);
- enc.encodeInt(size);
-
- // Revert size
- this._table.updateSize(size);
-
- var data = enc.render();
- for (var i = 0; i < data.length; i++)
- this.push(data[i]);
- };
-
- Compressor.prototype._encodeHeader = function _encodeHeader(header) {
- if (header.neverIndex) {
- var index = 0;
- var neverIndex = 1;
- var isIndexed = 0;
- var isIncremental = 0;
- } else {
- var index = this._table.reverseLookup(header.name, header.value);
- var isIndexed = index > 0;
- var isIncremental = header.incremental !== false;
- var neverIndex = 0;
- }
-
- this._encoder.encodeBit(isIndexed);
- if (isIndexed) {
- this._encoder.encodeInt(index);
- return;
- }
-
- var name = utils.toArray(header.name);
- var value = utils.toArray(header.value);
-
- this._encoder.encodeBit(isIncremental);
- if (isIncremental) {
- this._table.add(header.name, header.value, name.length, value.length);
- } else {
- // Update = false
- this._encoder.encodeBit(0);
- this._encoder.encodeBit(neverIndex);
- }
-
- // index is negative for `name`-only headers
- this._encoder.encodeInt(-index);
- if (index === 0)
- this._encoder.encodeStr(name, header.huffman !== false);
- this._encoder.encodeStr(value, header.huffman !== false);
- };
|