@libp2p/http-utils 1.0.2 → 2.0.1
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/dist/index.min.js +24 -25
- package/dist/index.min.js.map +4 -4
- package/dist/src/index.d.ts +1 -1
- package/dist/src/index.d.ts.map +1 -1
- package/dist/src/index.js +65 -63
- package/dist/src/index.js.map +1 -1
- package/dist/src/stream-to-socket.d.ts +10 -2
- package/dist/src/stream-to-socket.d.ts.map +1 -1
- package/dist/src/stream-to-socket.js +98 -67
- package/dist/src/stream-to-socket.js.map +1 -1
- package/package.json +11 -11
- package/src/index.ts +74 -70
- package/src/stream-to-socket.ts +111 -75
package/src/index.ts
CHANGED
|
@@ -7,18 +7,19 @@
|
|
|
7
7
|
import { HTTPParser } from '@achingbrain/http-parser-js'
|
|
8
8
|
import { InvalidParametersError, isPeerId, ProtocolError } from '@libp2p/interface'
|
|
9
9
|
import { peerIdFromString } from '@libp2p/peer-id'
|
|
10
|
-
import {
|
|
10
|
+
import { getNetConfig } from '@libp2p/utils'
|
|
11
|
+
import { CODE_P2P, isMultiaddr, multiaddr } from '@multiformats/multiaddr'
|
|
11
12
|
import { multiaddrToUri } from '@multiformats/multiaddr-to-uri'
|
|
12
13
|
import { uriToMultiaddr } from '@multiformats/uri-to-multiaddr'
|
|
13
|
-
import { queuelessPushable } from 'it-queueless-pushable'
|
|
14
14
|
import itToBrowserReadableStream from 'it-to-browser-readablestream'
|
|
15
15
|
import { base36 } from 'multiformats/bases/base36'
|
|
16
16
|
import { base64pad } from 'multiformats/bases/base64'
|
|
17
17
|
import { sha1 } from 'multiformats/hashes/sha1'
|
|
18
|
+
import { raceEvent } from 'race-event'
|
|
18
19
|
import { Uint8ArrayList } from 'uint8arraylist'
|
|
19
20
|
import { fromString as uint8ArrayFromString } from 'uint8arrays/from-string'
|
|
20
21
|
import { Request } from './request.js'
|
|
21
|
-
import type { AbortOptions, PeerId, Stream } from '@libp2p/interface'
|
|
22
|
+
import type { AbortOptions, PeerId, Stream, StreamMessageEvent } from '@libp2p/interface'
|
|
22
23
|
import type { Multiaddr } from '@multiformats/multiaddr'
|
|
23
24
|
|
|
24
25
|
const DNS_CODECS = ['dns', 'dns4', 'dns6', 'dnsaddr']
|
|
@@ -89,10 +90,10 @@ export function streamToRequest (info: HeaderInfo, stream: Stream): globalThis.R
|
|
|
89
90
|
}
|
|
90
91
|
|
|
91
92
|
if ((init.method !== 'GET' || info.upgrade) && init.method !== 'HEAD') {
|
|
92
|
-
let source:
|
|
93
|
+
let source: AsyncIterable<any> = stream
|
|
93
94
|
|
|
94
95
|
if (!info.upgrade) {
|
|
95
|
-
source = takeBytes(stream
|
|
96
|
+
source = takeBytes(stream, info.headers.get('content-length'))
|
|
96
97
|
}
|
|
97
98
|
|
|
98
99
|
init.body = itToBrowserReadableStream<Uint8Array>(source)
|
|
@@ -104,13 +105,7 @@ export function streamToRequest (info: HeaderInfo, stream: Stream): globalThis.R
|
|
|
104
105
|
}
|
|
105
106
|
|
|
106
107
|
export async function responseToStream (res: Response, stream: Stream): Promise<void> {
|
|
107
|
-
|
|
108
|
-
stream.sink(pushable)
|
|
109
|
-
.catch(err => {
|
|
110
|
-
stream.abort(err)
|
|
111
|
-
})
|
|
112
|
-
|
|
113
|
-
await pushable.push(uint8ArrayFromString([
|
|
108
|
+
stream.send(uint8ArrayFromString([
|
|
114
109
|
`HTTP/1.1 ${res.status} ${res.statusText}`,
|
|
115
110
|
...writeHeaders(res.headers),
|
|
116
111
|
'',
|
|
@@ -118,28 +113,29 @@ export async function responseToStream (res: Response, stream: Stream): Promise<
|
|
|
118
113
|
].join('\r\n')))
|
|
119
114
|
|
|
120
115
|
if (res.body == null) {
|
|
121
|
-
await
|
|
116
|
+
await stream.close().catch(err => {
|
|
117
|
+
stream.abort(err)
|
|
118
|
+
})
|
|
122
119
|
return
|
|
123
120
|
}
|
|
124
121
|
|
|
125
122
|
const reader = res.body.getReader()
|
|
126
|
-
let result = await reader.read()
|
|
127
123
|
|
|
128
124
|
while (true) {
|
|
125
|
+
const result = await reader.read()
|
|
126
|
+
|
|
129
127
|
if (result.value != null) {
|
|
130
|
-
|
|
128
|
+
if (!stream.send(result.value)) {
|
|
129
|
+
await stream.onDrain()
|
|
130
|
+
}
|
|
131
131
|
}
|
|
132
132
|
|
|
133
133
|
if (result.done) {
|
|
134
134
|
break
|
|
135
135
|
}
|
|
136
|
-
|
|
137
|
-
result = await reader.read()
|
|
138
136
|
}
|
|
139
137
|
|
|
140
|
-
await
|
|
141
|
-
|
|
142
|
-
await stream.closeWrite()
|
|
138
|
+
await stream.close()
|
|
143
139
|
.catch(err => {
|
|
144
140
|
stream.abort(err)
|
|
145
141
|
})
|
|
@@ -187,7 +183,7 @@ export function writeHeaders (headers: Headers): string[] {
|
|
|
187
183
|
return output
|
|
188
184
|
}
|
|
189
185
|
|
|
190
|
-
async function * takeBytes (source:
|
|
186
|
+
async function * takeBytes (source: AsyncIterable<Uint8Array | Uint8ArrayList>, bytes?: number | string | null): AsyncGenerator<Uint8Array> {
|
|
191
187
|
bytes = parseInt(`${bytes ?? ''}`)
|
|
192
188
|
|
|
193
189
|
if (bytes == null || isNaN(bytes)) {
|
|
@@ -329,12 +325,16 @@ export function getHost (addresses: URL | Multiaddr[], headers: Headers): string
|
|
|
329
325
|
// try to use remote PeerId as domain
|
|
330
326
|
if (!isValidHost(host) && Array.isArray(addresses)) {
|
|
331
327
|
for (const address of addresses) {
|
|
332
|
-
const peerStr = address.
|
|
328
|
+
const peerStr = address.getComponents()
|
|
329
|
+
.findLast(c => c.code === CODE_P2P)?.value
|
|
333
330
|
|
|
334
331
|
// try to extract port from multiaddr if it is available
|
|
335
332
|
try {
|
|
336
|
-
const
|
|
337
|
-
|
|
333
|
+
const config = getNetConfig(address)
|
|
334
|
+
|
|
335
|
+
if (config.port != null) {
|
|
336
|
+
port = config.port
|
|
337
|
+
}
|
|
338
338
|
} catch {}
|
|
339
339
|
|
|
340
340
|
if (peerStr != null) {
|
|
@@ -350,9 +350,11 @@ export function getHost (addresses: URL | Multiaddr[], headers: Headers): string
|
|
|
350
350
|
if (!isValidHost(host) && Array.isArray(addresses)) {
|
|
351
351
|
for (const address of addresses) {
|
|
352
352
|
try {
|
|
353
|
-
const
|
|
353
|
+
const config = getNetConfig(address)
|
|
354
354
|
|
|
355
|
-
host
|
|
355
|
+
if (config.host != null) {
|
|
356
|
+
host = config.host
|
|
357
|
+
}
|
|
356
358
|
break
|
|
357
359
|
} catch {}
|
|
358
360
|
}
|
|
@@ -490,55 +492,57 @@ export async function getServerUpgradeHeaders (headers: Headers | Record<string,
|
|
|
490
492
|
/**
|
|
491
493
|
* Reads HTTP headers from an incoming stream
|
|
492
494
|
*/
|
|
493
|
-
export async function readHeaders (stream: Stream): Promise<HeaderInfo> {
|
|
494
|
-
|
|
495
|
-
|
|
496
|
-
|
|
497
|
-
const earlyData = new Uint8ArrayList()
|
|
498
|
-
let headersComplete = false
|
|
499
|
-
|
|
500
|
-
parser[HTTPParser.kOnHeadersComplete] = (info) => {
|
|
501
|
-
headersComplete = true
|
|
502
|
-
const headers = new Headers()
|
|
503
|
-
|
|
504
|
-
// set incoming headers
|
|
505
|
-
for (let i = 0; i < info.headers.length; i += 2) {
|
|
506
|
-
headers.set(info.headers[i].toLowerCase(), info.headers[i + 1])
|
|
507
|
-
}
|
|
495
|
+
export async function readHeaders (stream: Stream, options?: AbortOptions): Promise<HeaderInfo> {
|
|
496
|
+
const parser = new HTTPParser('REQUEST')
|
|
497
|
+
const earlyData = new Uint8ArrayList()
|
|
498
|
+
let headerInfo: HeaderInfo | undefined
|
|
508
499
|
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
500
|
+
parser[HTTPParser.kOnHeadersComplete] = (info) => {
|
|
501
|
+
const headers = new Headers()
|
|
502
|
+
|
|
503
|
+
// set incoming headers
|
|
504
|
+
for (let i = 0; i < info.headers.length; i += 2) {
|
|
505
|
+
headers.set(info.headers[i].toLowerCase(), info.headers[i + 1])
|
|
515
506
|
}
|
|
516
507
|
|
|
517
|
-
|
|
518
|
-
|
|
519
|
-
|
|
520
|
-
|
|
521
|
-
|
|
522
|
-
|
|
523
|
-
|
|
524
|
-
|
|
525
|
-
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
529
|
-
|
|
508
|
+
headerInfo = {
|
|
509
|
+
...info,
|
|
510
|
+
headers,
|
|
511
|
+
raw: earlyData,
|
|
512
|
+
method: HTTPParser.methods[info.method]
|
|
513
|
+
}
|
|
514
|
+
}
|
|
515
|
+
|
|
516
|
+
try {
|
|
517
|
+
while (true) {
|
|
518
|
+
const { data } = await raceEvent<StreamMessageEvent>(stream, 'message', options?.signal)
|
|
519
|
+
const buf = data.subarray()
|
|
520
|
+
|
|
521
|
+
const read = parser.execute(buf, 0, buf.byteLength)
|
|
522
|
+
|
|
523
|
+
if (read instanceof Error) {
|
|
524
|
+
throw read
|
|
530
525
|
}
|
|
531
526
|
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
|
|
539
|
-
|
|
540
|
-
|
|
541
|
-
|
|
527
|
+
// collect raw header bytes
|
|
528
|
+
earlyData.append(buf.subarray(0, read))
|
|
529
|
+
|
|
530
|
+
if (read < buf.byteLength) {
|
|
531
|
+
// reading headers finished and we have early data
|
|
532
|
+
stream.push(buf.subarray(read))
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
if (headerInfo != null) {
|
|
536
|
+
return headerInfo
|
|
537
|
+
}
|
|
538
|
+
}
|
|
539
|
+
} catch (err: any) {
|
|
540
|
+
stream.abort(err)
|
|
541
|
+
} finally {
|
|
542
|
+
parser.finish()
|
|
543
|
+
}
|
|
544
|
+
|
|
545
|
+
throw new Error('Failed to read header info from request')
|
|
542
546
|
}
|
|
543
547
|
|
|
544
548
|
/**
|
package/src/stream-to-socket.ts
CHANGED
|
@@ -1,7 +1,5 @@
|
|
|
1
1
|
import { Duplex } from 'node:stream'
|
|
2
|
-
import {
|
|
3
|
-
import type { Connection, Stream } from '@libp2p/interface'
|
|
4
|
-
import type { ByteStream } from 'it-byte-stream'
|
|
2
|
+
import type { Connection, Logger, Stream } from '@libp2p/interface'
|
|
5
3
|
import type { Socket, SocketConnectOpts, AddressInfo, SocketReadyState } from 'node:net'
|
|
6
4
|
|
|
7
5
|
const MAX_TIMEOUT = 2_147_483_647
|
|
@@ -15,97 +13,135 @@ export class Libp2pSocket extends Duplex {
|
|
|
15
13
|
public bytesWritten: number
|
|
16
14
|
public timeout = MAX_TIMEOUT
|
|
17
15
|
public allowHalfOpen: boolean
|
|
16
|
+
public remoteFamily: string | undefined
|
|
17
|
+
public remotePort: number | undefined
|
|
18
18
|
|
|
19
|
+
#initStream: Promise<Stream>
|
|
19
20
|
#stream?: Stream
|
|
20
|
-
#bytes?: ByteStream<Stream>
|
|
21
21
|
|
|
22
|
-
|
|
22
|
+
#log?: Logger
|
|
23
|
+
|
|
24
|
+
constructor (stream: Stream, connection: Connection)
|
|
25
|
+
constructor (initStream: Promise<{ stream: Stream, connection: Connection }>)
|
|
26
|
+
constructor (...args: any[]) {
|
|
23
27
|
super()
|
|
24
28
|
|
|
25
29
|
this.bytesRead = 0
|
|
26
30
|
this.bytesWritten = 0
|
|
27
31
|
this.allowHalfOpen = true
|
|
28
32
|
this.remoteAddress = ''
|
|
33
|
+
|
|
34
|
+
if (args.length === 2) {
|
|
35
|
+
this.gotStream({ stream: args[0], connection: args[1] })
|
|
36
|
+
this.#initStream = Promise.resolve(args[0])
|
|
37
|
+
} else {
|
|
38
|
+
this.#initStream = args[0].then(this.gotStream.bind(this), (err: any) => {
|
|
39
|
+
this.emit('error', err)
|
|
40
|
+
throw err
|
|
41
|
+
})
|
|
42
|
+
}
|
|
29
43
|
}
|
|
30
44
|
|
|
31
|
-
|
|
32
|
-
this.#
|
|
33
|
-
this.#stream = stream
|
|
45
|
+
private gotStream ({ stream, connection }: { stream: Stream, connection: Connection }): Stream {
|
|
46
|
+
this.#log = stream.log.newScope('libp2p-socket')
|
|
34
47
|
this.remoteAddress = connection.remoteAddr.toString()
|
|
48
|
+
|
|
49
|
+
stream.addEventListener('message', (evt) => {
|
|
50
|
+
this.push(evt.data.subarray())
|
|
51
|
+
})
|
|
52
|
+
|
|
53
|
+
stream.addEventListener('close', (evt) => {
|
|
54
|
+
if (evt.error != null) {
|
|
55
|
+
this.destroy(evt.error)
|
|
56
|
+
} else {
|
|
57
|
+
this.push(null)
|
|
58
|
+
}
|
|
59
|
+
})
|
|
60
|
+
|
|
61
|
+
stream.pause()
|
|
62
|
+
|
|
63
|
+
this.emit('connect')
|
|
64
|
+
|
|
65
|
+
return stream
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
getStream (cb: (stream: Stream) => void): void {
|
|
69
|
+
if (this.#stream != null) {
|
|
70
|
+
cb(this.#stream)
|
|
71
|
+
return
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
this.#initStream.then(stream => {
|
|
75
|
+
this.#stream = stream
|
|
76
|
+
cb(stream)
|
|
77
|
+
}, (err) => {
|
|
78
|
+
this.emit('error', err)
|
|
79
|
+
})
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
destroy (error?: Error): this {
|
|
83
|
+
return super.destroy(error)
|
|
35
84
|
}
|
|
36
85
|
|
|
37
86
|
_write (chunk: Uint8Array, encoding: string, cb: (err?: Error) => void): void {
|
|
38
|
-
this.#
|
|
87
|
+
this.#log?.('write %d bytes', chunk.byteLength)
|
|
39
88
|
|
|
40
89
|
this.bytesWritten += chunk.byteLength
|
|
41
|
-
|
|
42
|
-
|
|
90
|
+
|
|
91
|
+
this.getStream(stream => {
|
|
92
|
+
if (!stream.send(chunk)) {
|
|
93
|
+
stream.onDrain()
|
|
94
|
+
.then(() => {
|
|
95
|
+
cb()
|
|
96
|
+
}, (err) => {
|
|
97
|
+
cb(err)
|
|
98
|
+
})
|
|
99
|
+
} else {
|
|
43
100
|
cb()
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
})
|
|
101
|
+
}
|
|
102
|
+
})
|
|
47
103
|
}
|
|
48
104
|
|
|
49
105
|
_read (size: number): void {
|
|
50
|
-
this.#
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
const chunk = await this.#bytes?.read({
|
|
56
|
-
signal: AbortSignal.timeout(this.timeout)
|
|
57
|
-
})
|
|
58
|
-
|
|
59
|
-
if (chunk == null) {
|
|
60
|
-
this.#stream?.log('socket readable end closed')
|
|
61
|
-
this.push(null)
|
|
62
|
-
return
|
|
63
|
-
}
|
|
64
|
-
|
|
65
|
-
this.bytesRead += chunk.byteLength
|
|
106
|
+
this.#log?.('asked to read %d bytes', size)
|
|
107
|
+
this.getStream(stream => {
|
|
108
|
+
stream.resume()
|
|
109
|
+
})
|
|
110
|
+
}
|
|
66
111
|
|
|
67
|
-
|
|
68
|
-
|
|
112
|
+
_destroy (err: Error, cb: (err?: Error) => void): void {
|
|
113
|
+
this.#log?.('destroy with %d bytes buffered - %e', this.bufferSize, err)
|
|
69
114
|
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
}
|
|
75
|
-
|
|
115
|
+
this.getStream(stream => {
|
|
116
|
+
if (err != null) {
|
|
117
|
+
stream.abort(err)
|
|
118
|
+
cb()
|
|
119
|
+
} else {
|
|
120
|
+
stream.close()
|
|
121
|
+
.then(() => {
|
|
122
|
+
cb()
|
|
123
|
+
})
|
|
124
|
+
.catch(err => {
|
|
125
|
+
stream.abort(err)
|
|
126
|
+
cb(err)
|
|
127
|
+
})
|
|
76
128
|
}
|
|
77
129
|
})
|
|
78
130
|
}
|
|
79
131
|
|
|
80
|
-
|
|
81
|
-
this.#
|
|
132
|
+
_final (cb: (err?: Error) => void): void {
|
|
133
|
+
this.#log?.('final')
|
|
82
134
|
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
cb()
|
|
86
|
-
} else {
|
|
87
|
-
this.#bytes?.unwrap().close()
|
|
135
|
+
this.getStream(stream => {
|
|
136
|
+
stream.close()
|
|
88
137
|
.then(() => {
|
|
89
138
|
cb()
|
|
90
139
|
})
|
|
91
140
|
.catch(err => {
|
|
92
|
-
|
|
141
|
+
stream.abort(err)
|
|
93
142
|
cb(err)
|
|
94
143
|
})
|
|
95
|
-
}
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
_final (cb: (err?: Error) => void): void {
|
|
99
|
-
this.#stream?.log('final')
|
|
100
|
-
|
|
101
|
-
this.#bytes?.unwrap().closeWrite()
|
|
102
|
-
.then(() => {
|
|
103
|
-
cb()
|
|
104
|
-
})
|
|
105
|
-
.catch(err => {
|
|
106
|
-
this.#bytes?.unwrap().abort(err)
|
|
107
|
-
cb(err)
|
|
108
|
-
})
|
|
144
|
+
})
|
|
109
145
|
}
|
|
110
146
|
|
|
111
147
|
public get readyState (): SocketReadyState {
|
|
@@ -129,7 +165,7 @@ export class Libp2pSocket extends Duplex {
|
|
|
129
165
|
}
|
|
130
166
|
|
|
131
167
|
destroySoon (): void {
|
|
132
|
-
this.#
|
|
168
|
+
this.#log?.('destroySoon with %d bytes buffered', this.bufferSize)
|
|
133
169
|
this.destroy()
|
|
134
170
|
}
|
|
135
171
|
|
|
@@ -138,24 +174,27 @@ export class Libp2pSocket extends Duplex {
|
|
|
138
174
|
connect (port: number, connectionListener?: () => void): this
|
|
139
175
|
connect (path: string, connectionListener?: () => void): this
|
|
140
176
|
connect (...args: any[]): this {
|
|
141
|
-
this.#
|
|
177
|
+
this.#log?.('connect %o', args)
|
|
142
178
|
return this
|
|
143
179
|
}
|
|
144
180
|
|
|
145
181
|
setEncoding (encoding?: BufferEncoding): this {
|
|
146
|
-
this.#
|
|
182
|
+
this.#log?.('setEncoding %s', encoding)
|
|
147
183
|
return this
|
|
148
184
|
}
|
|
149
185
|
|
|
150
186
|
resetAndDestroy (): this {
|
|
151
|
-
this.#
|
|
152
|
-
|
|
187
|
+
this.#log?.('resetAndDestroy')
|
|
188
|
+
|
|
189
|
+
this.getStream(stream => {
|
|
190
|
+
stream.abort(new Error('Libp2pSocket.resetAndDestroy'))
|
|
191
|
+
})
|
|
153
192
|
|
|
154
193
|
return this
|
|
155
194
|
}
|
|
156
195
|
|
|
157
196
|
setTimeout (timeout: number, callback?: () => void): this {
|
|
158
|
-
this.#
|
|
197
|
+
this.#log?.('setTimeout %d', timeout)
|
|
159
198
|
|
|
160
199
|
if (callback != null) {
|
|
161
200
|
this.addListener('timeout', callback)
|
|
@@ -167,31 +206,31 @@ export class Libp2pSocket extends Duplex {
|
|
|
167
206
|
}
|
|
168
207
|
|
|
169
208
|
setNoDelay (noDelay?: boolean): this {
|
|
170
|
-
this.#
|
|
209
|
+
this.#log?.('setNoDelay %b', noDelay)
|
|
171
210
|
|
|
172
211
|
return this
|
|
173
212
|
}
|
|
174
213
|
|
|
175
214
|
setKeepAlive (enable?: boolean, initialDelay?: number): this {
|
|
176
|
-
this.#
|
|
215
|
+
this.#log?.('setKeepAlive %b %d', enable, initialDelay)
|
|
177
216
|
|
|
178
217
|
return this
|
|
179
218
|
}
|
|
180
219
|
|
|
181
220
|
address (): AddressInfo | Record<string, any> {
|
|
182
|
-
this.#
|
|
221
|
+
this.#log?.('address')
|
|
183
222
|
|
|
184
223
|
return {}
|
|
185
224
|
}
|
|
186
225
|
|
|
187
226
|
unref (): this {
|
|
188
|
-
this.#
|
|
227
|
+
this.#log?.('unref')
|
|
189
228
|
|
|
190
229
|
return this
|
|
191
230
|
}
|
|
192
231
|
|
|
193
232
|
ref (): this {
|
|
194
|
-
this.#
|
|
233
|
+
this.#log?.('ref')
|
|
195
234
|
|
|
196
235
|
return this
|
|
197
236
|
}
|
|
@@ -204,8 +243,5 @@ export class Libp2pSocket extends Duplex {
|
|
|
204
243
|
}
|
|
205
244
|
|
|
206
245
|
export function streamToSocket (stream: Stream, connection: Connection): Socket {
|
|
207
|
-
|
|
208
|
-
socket.setStream(stream, connection)
|
|
209
|
-
|
|
210
|
-
return socket
|
|
246
|
+
return new Libp2pSocket(stream, connection)
|
|
211
247
|
}
|