You can not select more than 25 topics
			Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
		
		
		
		
		
			
		
			
				
					
					
						
							135 lines
						
					
					
						
							3.2 KiB
						
					
					
				
			
		
		
	
	
							135 lines
						
					
					
						
							3.2 KiB
						
					
					
				'use strict'; | 
						|
 | 
						|
var NodeHTTPParser = require('http-parser-js').HTTPParser, | 
						|
    Buffer         = require('safe-buffer').Buffer; | 
						|
 | 
						|
var TYPES = { | 
						|
  request:  NodeHTTPParser.REQUEST  || 'request', | 
						|
  response: NodeHTTPParser.RESPONSE || 'response' | 
						|
}; | 
						|
 | 
						|
var HttpParser = function(type) { | 
						|
  this._type     = type; | 
						|
  this._parser   = new NodeHTTPParser(TYPES[type]); | 
						|
  this._complete = false; | 
						|
  this.headers   = {}; | 
						|
 | 
						|
  var current = null, | 
						|
      self    = this; | 
						|
 | 
						|
  this._parser.onHeaderField = function(b, start, length) { | 
						|
    current = b.toString('utf8', start, start + length).toLowerCase(); | 
						|
  }; | 
						|
 | 
						|
  this._parser.onHeaderValue = function(b, start, length) { | 
						|
    var value = b.toString('utf8', start, start + length); | 
						|
 | 
						|
    if (self.headers.hasOwnProperty(current)) | 
						|
      self.headers[current] += ', ' + value; | 
						|
    else | 
						|
      self.headers[current] = value; | 
						|
  }; | 
						|
 | 
						|
  this._parser.onHeadersComplete = this._parser[NodeHTTPParser.kOnHeadersComplete] = | 
						|
  function(majorVersion, minorVersion, headers, method, pathname, statusCode) { | 
						|
    var info = arguments[0]; | 
						|
 | 
						|
    if (typeof info === 'object') { | 
						|
      method     = info.method; | 
						|
      pathname   = info.url; | 
						|
      statusCode = info.statusCode; | 
						|
      headers    = info.headers; | 
						|
    } | 
						|
 | 
						|
    self.method     = (typeof method === 'number') ? HttpParser.METHODS[method] : method; | 
						|
    self.statusCode = statusCode; | 
						|
    self.url        = pathname; | 
						|
 | 
						|
    if (!headers) return; | 
						|
 | 
						|
    for (var i = 0, n = headers.length, key, value; i < n; i += 2) { | 
						|
      key   = headers[i].toLowerCase(); | 
						|
      value = headers[i+1]; | 
						|
      if (self.headers.hasOwnProperty(key)) | 
						|
        self.headers[key] += ', ' + value; | 
						|
      else | 
						|
        self.headers[key] = value; | 
						|
    } | 
						|
 | 
						|
    self._complete = true; | 
						|
  }; | 
						|
}; | 
						|
 | 
						|
HttpParser.METHODS = { | 
						|
  0:  'DELETE', | 
						|
  1:  'GET', | 
						|
  2:  'HEAD', | 
						|
  3:  'POST', | 
						|
  4:  'PUT', | 
						|
  5:  'CONNECT', | 
						|
  6:  'OPTIONS', | 
						|
  7:  'TRACE', | 
						|
  8:  'COPY', | 
						|
  9:  'LOCK', | 
						|
  10: 'MKCOL', | 
						|
  11: 'MOVE', | 
						|
  12: 'PROPFIND', | 
						|
  13: 'PROPPATCH', | 
						|
  14: 'SEARCH', | 
						|
  15: 'UNLOCK', | 
						|
  16: 'BIND', | 
						|
  17: 'REBIND', | 
						|
  18: 'UNBIND', | 
						|
  19: 'ACL', | 
						|
  20: 'REPORT', | 
						|
  21: 'MKACTIVITY', | 
						|
  22: 'CHECKOUT', | 
						|
  23: 'MERGE', | 
						|
  24: 'M-SEARCH', | 
						|
  25: 'NOTIFY', | 
						|
  26: 'SUBSCRIBE', | 
						|
  27: 'UNSUBSCRIBE', | 
						|
  28: 'PATCH', | 
						|
  29: 'PURGE', | 
						|
  30: 'MKCALENDAR', | 
						|
  31: 'LINK', | 
						|
  32: 'UNLINK' | 
						|
}; | 
						|
 | 
						|
var VERSION = process.version | 
						|
  ? process.version.match(/[0-9]+/g).map(function(n) { return parseInt(n, 10) }) | 
						|
  : []; | 
						|
 | 
						|
if (VERSION[0] === 0 && VERSION[1] === 12) { | 
						|
  HttpParser.METHODS[16] = 'REPORT'; | 
						|
  HttpParser.METHODS[17] = 'MKACTIVITY'; | 
						|
  HttpParser.METHODS[18] = 'CHECKOUT'; | 
						|
  HttpParser.METHODS[19] = 'MERGE'; | 
						|
  HttpParser.METHODS[20] = 'M-SEARCH'; | 
						|
  HttpParser.METHODS[21] = 'NOTIFY'; | 
						|
  HttpParser.METHODS[22] = 'SUBSCRIBE'; | 
						|
  HttpParser.METHODS[23] = 'UNSUBSCRIBE'; | 
						|
  HttpParser.METHODS[24] = 'PATCH'; | 
						|
  HttpParser.METHODS[25] = 'PURGE'; | 
						|
} | 
						|
 | 
						|
HttpParser.prototype.isComplete = function() { | 
						|
  return this._complete; | 
						|
}; | 
						|
 | 
						|
HttpParser.prototype.parse = function(chunk) { | 
						|
  var consumed = this._parser.execute(chunk, 0, chunk.length); | 
						|
 | 
						|
  if (typeof consumed !== 'number') { | 
						|
    this.error     = consumed; | 
						|
    this._complete = true; | 
						|
    return; | 
						|
  } | 
						|
 | 
						|
  if (this._complete) | 
						|
    this.body = (consumed < chunk.length) | 
						|
              ? chunk.slice(consumed) | 
						|
              : Buffer.alloc(0); | 
						|
}; | 
						|
 | 
						|
module.exports = HttpParser;
 | 
						|
 |