bare-http1 4.1.0 → 4.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/index.d.ts +0 -2
- package/lib/client-connection.js +50 -171
- package/lib/client-request.js +12 -7
- package/lib/constants.d.ts +0 -7
- package/lib/constants.js +0 -7
- package/lib/errors.d.ts +1 -1
- package/lib/errors.js +3 -3
- package/lib/server-connection.js +61 -179
- package/lib/server-response.js +14 -8
- package/package.json +2 -1
package/index.d.ts
CHANGED
package/lib/client-connection.js
CHANGED
|
@@ -1,8 +1,12 @@
|
|
|
1
|
+
const HTTPParser = require('bare-http-parser')
|
|
1
2
|
const HTTPIncomingMessage = require('./incoming-message')
|
|
2
|
-
const constants = require('./constants')
|
|
3
3
|
const errors = require('./errors')
|
|
4
4
|
|
|
5
|
-
const
|
|
5
|
+
const {
|
|
6
|
+
constants: { RESPONSE, DATA, END }
|
|
7
|
+
} = HTTPParser
|
|
8
|
+
|
|
9
|
+
const EMPTY = Buffer.alloc(0)
|
|
6
10
|
|
|
7
11
|
module.exports = class HTTPClientConnection {
|
|
8
12
|
static _connections = new WeakMap()
|
|
@@ -25,10 +29,7 @@ module.exports = class HTTPClientConnection {
|
|
|
25
29
|
|
|
26
30
|
this._IncomingMessage = IncomingMessage
|
|
27
31
|
|
|
28
|
-
this.
|
|
29
|
-
this._length = -1
|
|
30
|
-
this._read = 0
|
|
31
|
-
this._buffer = null
|
|
32
|
+
this._parser = new HTTPParser()
|
|
32
33
|
this._idle = true
|
|
33
34
|
|
|
34
35
|
this._onerror = this._onerror.bind(this)
|
|
@@ -68,154 +69,53 @@ module.exports = class HTTPClientConnection {
|
|
|
68
69
|
_ondata(data) {
|
|
69
70
|
this._idle = false
|
|
70
71
|
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
? null
|
|
111
|
-
: this._buffer.subarray(i + 1)
|
|
112
|
-
i = 0
|
|
113
|
-
hits = 0
|
|
114
|
-
this._onchunk(chunk)
|
|
115
|
-
|
|
116
|
-
if (this._buffer === null) break
|
|
117
|
-
}
|
|
118
|
-
} else if (hits === 2 && b === 13) {
|
|
119
|
-
hits++
|
|
120
|
-
} else if (hits === 3 && b === 10) {
|
|
121
|
-
if (this._state === constants.state.BEFORE_HEAD) {
|
|
122
|
-
const head = this._buffer.subarray(0, i - 3)
|
|
123
|
-
this._buffer =
|
|
124
|
-
i + 1 === this._buffer.byteLength
|
|
125
|
-
? null
|
|
126
|
-
: this._buffer.subarray(i + 1)
|
|
127
|
-
i = 0
|
|
128
|
-
hits = 0
|
|
129
|
-
this._onhead(head)
|
|
130
|
-
|
|
131
|
-
if (this._buffer === null) break
|
|
72
|
+
try {
|
|
73
|
+
for (const op of this._parser.push(data)) {
|
|
74
|
+
switch (op.type) {
|
|
75
|
+
case RESPONSE:
|
|
76
|
+
this.req.on('close', () => {
|
|
77
|
+
this.req = null
|
|
78
|
+
})
|
|
79
|
+
|
|
80
|
+
this.res = new this._IncomingMessage(this.socket, op.headers, {
|
|
81
|
+
statusCode: op.code,
|
|
82
|
+
statusMessage: op.reason
|
|
83
|
+
})
|
|
84
|
+
|
|
85
|
+
this.res.on('close', () => {
|
|
86
|
+
this.res = null
|
|
87
|
+
|
|
88
|
+
this._idle = true
|
|
89
|
+
|
|
90
|
+
this.socket.emit('free')
|
|
91
|
+
})
|
|
92
|
+
|
|
93
|
+
if (
|
|
94
|
+
op.headers.connection &&
|
|
95
|
+
op.headers.connection.toLowerCase() === 'upgrade'
|
|
96
|
+
) {
|
|
97
|
+
return this._onupgrade(this._parser.end())
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
this.req.emit('response', this.res)
|
|
101
|
+
break
|
|
102
|
+
|
|
103
|
+
case DATA:
|
|
104
|
+
this.res.push(op.data)
|
|
105
|
+
break
|
|
106
|
+
|
|
107
|
+
case END:
|
|
108
|
+
if (this.res) this.res.push(null)
|
|
109
|
+
if (this.req) this.req._continueFinal()
|
|
110
|
+
break
|
|
132
111
|
}
|
|
133
|
-
} else {
|
|
134
|
-
hits = 0
|
|
135
|
-
}
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
_onhead(data) {
|
|
140
|
-
this._state = constants.state.IN_HEAD
|
|
141
|
-
|
|
142
|
-
const r = data.toString().split('\r\n')
|
|
143
|
-
if (r.length === 0) return this.socket.destroy()
|
|
144
|
-
|
|
145
|
-
const [, statusCode, ...statusMessage] = r[0].split(' ')
|
|
146
|
-
if (!statusCode || !statusMessage.length) return this.socket.destroy()
|
|
147
|
-
|
|
148
|
-
const headers = {}
|
|
149
|
-
|
|
150
|
-
for (let i = 1; i < r.length; i++) {
|
|
151
|
-
const [name, value] = splitHeader(r[i])
|
|
152
|
-
if (name === null) return this.socket.destroy()
|
|
153
|
-
headers[name.toLowerCase()] = value
|
|
154
|
-
}
|
|
155
|
-
|
|
156
|
-
this.req.on('close', () => {
|
|
157
|
-
this.req = null
|
|
158
|
-
})
|
|
159
|
-
|
|
160
|
-
this.res = new this._IncomingMessage(this.socket, headers, {
|
|
161
|
-
statusCode: parseInt(statusCode, 10),
|
|
162
|
-
statusMessage: statusMessage.join(' ')
|
|
163
|
-
})
|
|
164
|
-
|
|
165
|
-
this.res.on('close', () => {
|
|
166
|
-
this.res = null
|
|
167
|
-
this._onreset()
|
|
168
|
-
})
|
|
169
|
-
|
|
170
|
-
if (headers.connection && headers.connection.toLowerCase() === 'upgrade') {
|
|
171
|
-
const head = this._buffer
|
|
172
|
-
this._buffer = null
|
|
173
|
-
return this._onupgrade(head)
|
|
174
|
-
}
|
|
175
|
-
|
|
176
|
-
this.req.emit('response', this.res)
|
|
177
|
-
|
|
178
|
-
if (headers['transfer-encoding'] === 'chunked') {
|
|
179
|
-
this._state = constants.state.BEFORE_CHUNK
|
|
180
|
-
} else {
|
|
181
|
-
this._length = parseInt(headers['content-length'], 10) || 0
|
|
182
|
-
|
|
183
|
-
if (this._length === 0) return this._onfinished()
|
|
184
|
-
|
|
185
|
-
this._state = constants.state.IN_BODY
|
|
186
|
-
|
|
187
|
-
if (this._buffer) {
|
|
188
|
-
const body = this._buffer
|
|
189
|
-
this._buffer = null
|
|
190
|
-
this._onbody(body)
|
|
191
112
|
}
|
|
113
|
+
} catch (err) {
|
|
114
|
+
this.socket.destroy(err)
|
|
192
115
|
}
|
|
193
116
|
}
|
|
194
117
|
|
|
195
|
-
|
|
196
|
-
this._length = parseInt(data.toString(), 16)
|
|
197
|
-
|
|
198
|
-
if (this._length === 0) this._onfinished()
|
|
199
|
-
else this._state = constants.state.IN_CHUNK
|
|
200
|
-
}
|
|
201
|
-
|
|
202
|
-
_onchunk(data) {
|
|
203
|
-
this._read += data.byteLength
|
|
204
|
-
|
|
205
|
-
this.res.push(data)
|
|
206
|
-
|
|
207
|
-
this._state = constants.state.BEFORE_CHUNK
|
|
208
|
-
}
|
|
209
|
-
|
|
210
|
-
_onbody(data) {
|
|
211
|
-
this._read += data.byteLength
|
|
212
|
-
|
|
213
|
-
this.res.push(data)
|
|
214
|
-
|
|
215
|
-
if (this._read === this._length) this._onfinished()
|
|
216
|
-
}
|
|
217
|
-
|
|
218
|
-
_onupgrade(head) {
|
|
118
|
+
_onupgrade(data) {
|
|
219
119
|
this._ondetach()
|
|
220
120
|
|
|
221
121
|
const req = this.req
|
|
@@ -223,7 +123,7 @@ module.exports = class HTTPClientConnection {
|
|
|
223
123
|
req.upgrade = true
|
|
224
124
|
req.destroy()
|
|
225
125
|
|
|
226
|
-
if (req.emit('upgrade', this.res, this.socket,
|
|
126
|
+
if (req.emit('upgrade', this.res, this.socket, data || EMPTY)) return
|
|
227
127
|
|
|
228
128
|
this.socket.destroy()
|
|
229
129
|
}
|
|
@@ -232,21 +132,6 @@ module.exports = class HTTPClientConnection {
|
|
|
232
132
|
if (this.req) this.req.emit('timeout')
|
|
233
133
|
}
|
|
234
134
|
|
|
235
|
-
_onfinished() {
|
|
236
|
-
if (this.res) this.res.push(null)
|
|
237
|
-
if (this.req) this.req._continueFinal()
|
|
238
|
-
}
|
|
239
|
-
|
|
240
|
-
_onreset() {
|
|
241
|
-
this._state = constants.state.BEFORE_HEAD
|
|
242
|
-
this._length = -1
|
|
243
|
-
this._read = 0
|
|
244
|
-
this._buffer = null
|
|
245
|
-
this._idle = true
|
|
246
|
-
|
|
247
|
-
this.socket.emit('free')
|
|
248
|
-
}
|
|
249
|
-
|
|
250
135
|
_ondrain() {
|
|
251
136
|
if (this.req) this.req._continueWrite()
|
|
252
137
|
}
|
|
@@ -263,9 +148,3 @@ module.exports = class HTTPClientConnection {
|
|
|
263
148
|
HTTPClientConnection._connections.delete(this.socket)
|
|
264
149
|
}
|
|
265
150
|
}
|
|
266
|
-
|
|
267
|
-
function splitHeader(s) {
|
|
268
|
-
const i = s.indexOf(': ')
|
|
269
|
-
if (i === -1) return [null, null]
|
|
270
|
-
return [s.slice(0, i), s.slice(i + 2)]
|
|
271
|
-
}
|
package/lib/client-request.js
CHANGED
|
@@ -35,6 +35,11 @@ module.exports = class HTTPClientRequest extends HTTPOutgoingMessage {
|
|
|
35
35
|
if (onresponse) this.once('response', onresponse)
|
|
36
36
|
}
|
|
37
37
|
|
|
38
|
+
// For Node.js compatibility
|
|
39
|
+
abort() {
|
|
40
|
+
return this.destroy()
|
|
41
|
+
}
|
|
42
|
+
|
|
38
43
|
_header() {
|
|
39
44
|
let h = `${this.method} ${this.path} HTTP/1.1\r\n`
|
|
40
45
|
|
|
@@ -64,15 +69,15 @@ module.exports = class HTTPClientRequest extends HTTPOutgoingMessage {
|
|
|
64
69
|
if (this.headersSent === false) this.flushHeaders()
|
|
65
70
|
|
|
66
71
|
if (this._chunked) {
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
CHUNK_DELIMITER,
|
|
70
|
-
data,
|
|
71
|
-
CHUNK_DELIMITER
|
|
72
|
-
])
|
|
72
|
+
this.socket.write(Buffer.from(data.byteLength.toString(16)))
|
|
73
|
+
this.socket.write(CHUNK_DELIMITER)
|
|
73
74
|
}
|
|
74
75
|
|
|
75
|
-
|
|
76
|
+
let flushed = this.socket.write(data)
|
|
77
|
+
|
|
78
|
+
if (this._chunked) flushed = this.socket.write(CHUNK_DELIMITER)
|
|
79
|
+
|
|
80
|
+
if (flushed) cb(null)
|
|
76
81
|
else this._pendingWrite = cb
|
|
77
82
|
}
|
|
78
83
|
|
package/lib/constants.d.ts
CHANGED
package/lib/constants.js
CHANGED
package/lib/errors.d.ts
CHANGED
package/lib/errors.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
module.exports = class HTTPError extends Error {
|
|
2
|
-
constructor(msg,
|
|
2
|
+
constructor(msg, fn = HTTPError, code = fn.name) {
|
|
3
3
|
super(`${code}: ${msg}`)
|
|
4
4
|
this.code = code
|
|
5
5
|
|
|
@@ -13,10 +13,10 @@ module.exports = class HTTPError extends Error {
|
|
|
13
13
|
}
|
|
14
14
|
|
|
15
15
|
static NOT_IMPLEMENTED(msg = 'Method not implemented') {
|
|
16
|
-
return new HTTPError(msg,
|
|
16
|
+
return new HTTPError(msg, HTTPError.NOT_IMPLEMENTED)
|
|
17
17
|
}
|
|
18
18
|
|
|
19
19
|
static CONNECTION_LOST(msg = 'Socket hung up') {
|
|
20
|
-
return new HTTPError(msg,
|
|
20
|
+
return new HTTPError(msg, HTTPError.CONNECTION_LOST)
|
|
21
21
|
}
|
|
22
22
|
}
|
package/lib/server-connection.js
CHANGED
|
@@ -1,10 +1,14 @@
|
|
|
1
1
|
const tcp = require('bare-tcp')
|
|
2
2
|
const { isEnded, isFinished, getStreamError } = require('bare-stream')
|
|
3
|
+
const HTTPParser = require('bare-http-parser')
|
|
3
4
|
const HTTPIncomingMessage = require('./incoming-message')
|
|
4
5
|
const HTTPServerResponse = require('./server-response')
|
|
5
|
-
const constants = require('./constants')
|
|
6
6
|
|
|
7
|
-
const
|
|
7
|
+
const {
|
|
8
|
+
constants: { REQUEST, DATA, END }
|
|
9
|
+
} = HTTPParser
|
|
10
|
+
|
|
11
|
+
const EMPTY = Buffer.alloc(0)
|
|
8
12
|
|
|
9
13
|
module.exports = class HTTPServerConnection {
|
|
10
14
|
static _connections = new WeakMap()
|
|
@@ -28,10 +32,7 @@ module.exports = class HTTPServerConnection {
|
|
|
28
32
|
this._IncomingMessage = IncomingMessage
|
|
29
33
|
this._ServerResponse = ServerResponse
|
|
30
34
|
|
|
31
|
-
this.
|
|
32
|
-
this._length = -1
|
|
33
|
-
this._read = 0
|
|
34
|
-
this._buffer = null
|
|
35
|
+
this._parser = new HTTPParser()
|
|
35
36
|
this._idle = true
|
|
36
37
|
|
|
37
38
|
this._onclose = this._onclose.bind(this)
|
|
@@ -65,161 +66,64 @@ module.exports = class HTTPServerConnection {
|
|
|
65
66
|
_ondata(data) {
|
|
66
67
|
this._idle = false
|
|
67
68
|
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
if (this._state === constants.state.BEFORE_HEAD) {
|
|
119
|
-
const head = this._buffer.subarray(0, i - 3)
|
|
120
|
-
this._buffer =
|
|
121
|
-
i + 1 === this._buffer.byteLength
|
|
122
|
-
? null
|
|
123
|
-
: this._buffer.subarray(i + 1)
|
|
124
|
-
i = 0
|
|
125
|
-
hits = 0
|
|
126
|
-
this._onhead(head)
|
|
127
|
-
|
|
128
|
-
if (this._buffer === null) break
|
|
69
|
+
try {
|
|
70
|
+
for (const op of this._parser.push(data)) {
|
|
71
|
+
switch (op.type) {
|
|
72
|
+
case REQUEST:
|
|
73
|
+
this.req = new this._IncomingMessage(this.socket, op.headers, {
|
|
74
|
+
method: op.method,
|
|
75
|
+
url: op.url
|
|
76
|
+
})
|
|
77
|
+
|
|
78
|
+
this.req.on('close', () => {
|
|
79
|
+
this.req = null
|
|
80
|
+
|
|
81
|
+
this._idle = true
|
|
82
|
+
|
|
83
|
+
if (this.server._state & tcp.constants.state.CLOSING) {
|
|
84
|
+
this.socket.destroy()
|
|
85
|
+
}
|
|
86
|
+
})
|
|
87
|
+
|
|
88
|
+
// Eagerly open the request stream
|
|
89
|
+
this.req.resume()
|
|
90
|
+
this.req.pause()
|
|
91
|
+
|
|
92
|
+
if (
|
|
93
|
+
op.headers.connection &&
|
|
94
|
+
op.headers.connection.toLowerCase() === 'upgrade'
|
|
95
|
+
) {
|
|
96
|
+
return this._onupgrade(this._parser.end())
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
this.res = new this._ServerResponse(
|
|
100
|
+
this.socket,
|
|
101
|
+
this.req,
|
|
102
|
+
op.headers.connection === 'close'
|
|
103
|
+
)
|
|
104
|
+
|
|
105
|
+
this.res.on('close', () => {
|
|
106
|
+
this.res = null
|
|
107
|
+
})
|
|
108
|
+
|
|
109
|
+
this.server.emit('request', this.req, this.res)
|
|
110
|
+
break
|
|
111
|
+
|
|
112
|
+
case DATA:
|
|
113
|
+
this.req.push(op.data)
|
|
114
|
+
break
|
|
115
|
+
|
|
116
|
+
case END:
|
|
117
|
+
if (this.req) this.req.push(null)
|
|
118
|
+
break
|
|
129
119
|
}
|
|
130
|
-
} else {
|
|
131
|
-
hits = 0
|
|
132
|
-
}
|
|
133
|
-
}
|
|
134
|
-
}
|
|
135
|
-
|
|
136
|
-
_onhead(data) {
|
|
137
|
-
this._state = constants.state.IN_HEAD
|
|
138
|
-
|
|
139
|
-
const r = data.toString().split('\r\n')
|
|
140
|
-
if (r.length === 0) return this.socket.destroy()
|
|
141
|
-
|
|
142
|
-
const [method, url] = r[0].split(' ')
|
|
143
|
-
if (!method || !url) return this.socket.destroy()
|
|
144
|
-
|
|
145
|
-
const headers = {}
|
|
146
|
-
|
|
147
|
-
for (let i = 1; i < r.length; i++) {
|
|
148
|
-
const [name, value] = splitHeader(r[i])
|
|
149
|
-
if (name === null) return this.socket.destroy()
|
|
150
|
-
headers[name.toLowerCase()] = value
|
|
151
|
-
}
|
|
152
|
-
|
|
153
|
-
this.req = new this._IncomingMessage(this.socket, headers, { method, url })
|
|
154
|
-
|
|
155
|
-
this.req.on('close', () => {
|
|
156
|
-
this.req = null
|
|
157
|
-
this._onreset()
|
|
158
|
-
})
|
|
159
|
-
|
|
160
|
-
// Eagerly open the request stream
|
|
161
|
-
this.req.resume()
|
|
162
|
-
this.req.pause()
|
|
163
|
-
|
|
164
|
-
if (headers.connection && headers.connection.toLowerCase() === 'upgrade') {
|
|
165
|
-
const head = this._buffer
|
|
166
|
-
this._buffer = null
|
|
167
|
-
return this._onupgrade(head)
|
|
168
|
-
}
|
|
169
|
-
|
|
170
|
-
this.res = new this._ServerResponse(
|
|
171
|
-
this.socket,
|
|
172
|
-
this.req,
|
|
173
|
-
headers.connection === 'close'
|
|
174
|
-
)
|
|
175
|
-
|
|
176
|
-
this.res.on('close', () => {
|
|
177
|
-
this.res = null
|
|
178
|
-
})
|
|
179
|
-
|
|
180
|
-
this.server.emit('request', this.req, this.res)
|
|
181
|
-
|
|
182
|
-
if (headers['transfer-encoding'] === 'chunked') {
|
|
183
|
-
this._state = constants.state.BEFORE_CHUNK
|
|
184
|
-
} else {
|
|
185
|
-
this._length = parseInt(headers['content-length'], 10) || 0
|
|
186
|
-
|
|
187
|
-
if (this._length === 0) return this._onfinished()
|
|
188
|
-
|
|
189
|
-
this._state = constants.state.IN_BODY
|
|
190
|
-
|
|
191
|
-
if (this._buffer) {
|
|
192
|
-
const body = this._buffer
|
|
193
|
-
this._buffer = null
|
|
194
|
-
this._onbody(body)
|
|
195
120
|
}
|
|
121
|
+
} catch (err) {
|
|
122
|
+
this.socket.destroy(err)
|
|
196
123
|
}
|
|
197
124
|
}
|
|
198
125
|
|
|
199
|
-
|
|
200
|
-
this._length = parseInt(data.toString(), 16)
|
|
201
|
-
|
|
202
|
-
if (this._length === 0) this._onfinished()
|
|
203
|
-
else this._state = constants.state.IN_CHUNK
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
_onchunk(data) {
|
|
207
|
-
this._read += data.byteLength
|
|
208
|
-
|
|
209
|
-
this.req.push(data)
|
|
210
|
-
|
|
211
|
-
this._state = constants.state.BEFORE_CHUNK
|
|
212
|
-
}
|
|
213
|
-
|
|
214
|
-
_onbody(data) {
|
|
215
|
-
this._read += data.byteLength
|
|
216
|
-
|
|
217
|
-
this.req.push(data)
|
|
218
|
-
|
|
219
|
-
if (this._read === this._length) this._onfinished()
|
|
220
|
-
}
|
|
221
|
-
|
|
222
|
-
_onupgrade(head) {
|
|
126
|
+
_onupgrade(data) {
|
|
223
127
|
this._ondetach()
|
|
224
128
|
|
|
225
129
|
const req = this.req
|
|
@@ -227,7 +131,7 @@ module.exports = class HTTPServerConnection {
|
|
|
227
131
|
req.upgrade = true
|
|
228
132
|
req.destroy()
|
|
229
133
|
|
|
230
|
-
this.server.emit('upgrade', req, this.socket,
|
|
134
|
+
this.server.emit('upgrade', req, this.socket, data || EMPTY)
|
|
231
135
|
}
|
|
232
136
|
|
|
233
137
|
_ontimeout() {
|
|
@@ -238,22 +142,6 @@ module.exports = class HTTPServerConnection {
|
|
|
238
142
|
if (!reqTimeout && !resTimeout && !serverTimeout) this.socket.destroy()
|
|
239
143
|
}
|
|
240
144
|
|
|
241
|
-
_onfinished() {
|
|
242
|
-
if (this.req) this.req.push(null)
|
|
243
|
-
}
|
|
244
|
-
|
|
245
|
-
_onreset() {
|
|
246
|
-
this._state = constants.state.BEFORE_HEAD
|
|
247
|
-
this._length = -1
|
|
248
|
-
this._read = 0
|
|
249
|
-
this._buffer = null
|
|
250
|
-
this._idle = true
|
|
251
|
-
|
|
252
|
-
if (this.server._state & tcp.constants.state.CLOSING) {
|
|
253
|
-
this.socket.destroy()
|
|
254
|
-
}
|
|
255
|
-
}
|
|
256
|
-
|
|
257
145
|
_ondrain() {
|
|
258
146
|
if (this.res) this.res._continueWrite()
|
|
259
147
|
}
|
|
@@ -271,9 +159,3 @@ module.exports = class HTTPServerConnection {
|
|
|
271
159
|
}
|
|
272
160
|
|
|
273
161
|
function noop() {}
|
|
274
|
-
|
|
275
|
-
function splitHeader(s) {
|
|
276
|
-
const i = s.indexOf(': ')
|
|
277
|
-
if (i === -1) return [null, null]
|
|
278
|
-
return [s.slice(0, i), s.slice(i + 2)]
|
|
279
|
-
}
|
package/lib/server-response.js
CHANGED
|
@@ -1,6 +1,9 @@
|
|
|
1
1
|
const HTTPOutgoingMessage = require('./outgoing-message')
|
|
2
2
|
const constants = require('./constants')
|
|
3
3
|
|
|
4
|
+
const CHUNK_DELIMITER = Buffer.from('\r\n')
|
|
5
|
+
const CHUNK_TERMINATOR = Buffer.from('0\r\n\r\n')
|
|
6
|
+
|
|
4
7
|
module.exports = class HTTPServerResponse extends HTTPOutgoingMessage {
|
|
5
8
|
constructor(socket, req, close) {
|
|
6
9
|
super(socket)
|
|
@@ -77,14 +80,15 @@ module.exports = class HTTPServerResponse extends HTTPOutgoingMessage {
|
|
|
77
80
|
if (this._onlyHeaders === true) return cb(null)
|
|
78
81
|
|
|
79
82
|
if (this._chunked) {
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
data,
|
|
83
|
-
Buffer.from('\r\n')
|
|
84
|
-
])
|
|
83
|
+
this.socket.write(Buffer.from(data.byteLength.toString(16)))
|
|
84
|
+
this.socket.write(CHUNK_DELIMITER)
|
|
85
85
|
}
|
|
86
86
|
|
|
87
|
-
|
|
87
|
+
let flushed = this.socket.write(data)
|
|
88
|
+
|
|
89
|
+
if (this._chunked) flushed = this.socket.write(CHUNK_DELIMITER)
|
|
90
|
+
|
|
91
|
+
if (flushed) cb(null)
|
|
88
92
|
else this._pendingWrite = cb
|
|
89
93
|
}
|
|
90
94
|
|
|
@@ -94,8 +98,10 @@ module.exports = class HTTPServerResponse extends HTTPOutgoingMessage {
|
|
|
94
98
|
this.flushHeaders()
|
|
95
99
|
}
|
|
96
100
|
|
|
97
|
-
if (this._chunked && this._onlyHeaders === false)
|
|
98
|
-
this.socket.write(
|
|
101
|
+
if (this._chunked && this._onlyHeaders === false) {
|
|
102
|
+
this.socket.write(CHUNK_TERMINATOR)
|
|
103
|
+
}
|
|
104
|
+
|
|
99
105
|
if (this._close) this.socket.end()
|
|
100
106
|
|
|
101
107
|
cb(null)
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "bare-http1",
|
|
3
|
-
"version": "4.1.
|
|
3
|
+
"version": "4.1.2",
|
|
4
4
|
"description": "Native HTTP/1 library for JavaScript",
|
|
5
5
|
"exports": {
|
|
6
6
|
"./package": "./package.json",
|
|
@@ -37,6 +37,7 @@
|
|
|
37
37
|
"homepage": "https://github.com/holepunchto/bare-http1#readme",
|
|
38
38
|
"dependencies": {
|
|
39
39
|
"bare-events": "^2.6.0",
|
|
40
|
+
"bare-http-parser": "^1.0.0",
|
|
40
41
|
"bare-stream": "^2.3.0",
|
|
41
42
|
"bare-tcp": "^2.0.3"
|
|
42
43
|
},
|