@@ -24,18 +24,50 @@ import { HandshakeTimeoutError } from './errors.js'
24
24
import { generateCertificate , verifyPeerCertificate , itToStream , streamToIt } from './utils.js'
25
25
import { PROTOCOL } from './index.js'
26
26
import type { TLSComponents } from './index.js'
27
- import type { MultiaddrConnection , ConnectionEncrypter , SecuredConnection , Logger , SecureConnectionOptions , PrivateKey } from '@libp2p/interface'
27
+ import type { MultiaddrConnection , ConnectionEncrypter , SecuredConnection , Logger , SecureConnectionOptions , CounterGroup } from '@libp2p/interface'
28
28
import type { Duplex } from 'it-stream-types'
29
29
import type { Uint8ArrayList } from 'uint8arraylist'
30
30
31
31
export class TLS implements ConnectionEncrypter {
32
32
public protocol : string = PROTOCOL
33
33
private readonly log : Logger
34
- private readonly privateKey : PrivateKey
34
+ private readonly components : TLSComponents
35
+ private readonly metrics : {
36
+ server : {
37
+ events ?: CounterGroup
38
+ errors ?: CounterGroup
39
+ }
40
+ client : {
41
+ events ?: CounterGroup
42
+ errors ?: CounterGroup
43
+ }
44
+ }
35
45
36
46
constructor ( components : TLSComponents ) {
37
47
this . log = components . logger . forComponent ( 'libp2p:tls' )
38
- this . privateKey = components . privateKey
48
+ this . components = components
49
+ this . metrics = {
50
+ server : {
51
+ events : components . metrics ?. registerCounterGroup ( 'libp2p_tls_server_events_total' , {
52
+ label : 'event' ,
53
+ help : 'Total count of TLS connection encryption events by type'
54
+ } ) ,
55
+ errors : components . metrics ?. registerCounterGroup ( 'libp2p_tls_server_errors_total' , {
56
+ label : 'event' ,
57
+ help : 'Total count of TLS connection encryption errors by type'
58
+ } )
59
+ } ,
60
+ client : {
61
+ events : components . metrics ?. registerCounterGroup ( 'libp2p_tls_server_events_total' , {
62
+ label : 'event' ,
63
+ help : 'Total count of TLS connection encryption events by type'
64
+ } ) ,
65
+ errors : components . metrics ?. registerCounterGroup ( 'libp2p_tls_server_errors_total' , {
66
+ label : 'event' ,
67
+ help : 'Total count of TLS connection encryption errors by type'
68
+ } )
69
+ }
70
+ }
39
71
}
40
72
41
73
readonly [ Symbol . toStringTag ] = '@libp2p/tls'
@@ -57,7 +89,7 @@ export class TLS implements ConnectionEncrypter {
57
89
*/
58
90
async _encrypt < Stream extends Duplex < AsyncGenerator < Uint8Array | Uint8ArrayList > > = MultiaddrConnection > ( conn : Stream , isServer : boolean , options ?: SecureConnectionOptions ) : Promise < SecuredConnection < Stream > > {
59
91
const opts : TLSSocketOptions = {
60
- ...await generateCertificate ( this . privateKey ) ,
92
+ ...await generateCertificate ( this . components . privateKey ) ,
61
93
isServer,
62
94
// require TLS 1.3 or later
63
95
minVersion : 'TLSv1.3' ,
@@ -83,9 +115,13 @@ export class TLS implements ConnectionEncrypter {
83
115
84
116
return new Promise < SecuredConnection < Stream > > ( ( resolve , reject ) => {
85
117
options ?. signal ?. addEventListener ( 'abort' , ( ) => {
86
- const err = new HandshakeTimeoutError ( )
87
- socket . destroy ( err )
88
- reject ( err )
118
+ this . metrics [ isServer ? 'server' : 'client' ] . events ?. increment ( {
119
+ abort : true
120
+ } )
121
+ this . metrics [ isServer ? 'server' : 'client' ] . errors ?. increment ( {
122
+ encrypt_abort : true
123
+ } )
124
+ socket . emit ( 'error' , new HandshakeTimeoutError ( ) )
89
125
} )
90
126
91
127
const verifyRemote = ( ) : void => {
@@ -104,21 +140,42 @@ export class TLS implements ConnectionEncrypter {
104
140
} )
105
141
} )
106
142
. catch ( ( err : Error ) => {
107
- reject ( err )
143
+ this . metrics [ isServer ? 'server' : 'client' ] . errors ?. increment ( {
144
+ verify_peer_certificate : true
145
+ } )
146
+ socket . emit ( 'error' , err )
108
147
} )
109
148
}
110
149
111
150
socket . on ( 'error' , ( err : Error ) => {
151
+ this . log . error ( 'error encrypting %s connection - %e' , isServer ? 'server' : 'client' , err )
152
+
153
+ if ( err . name !== 'HandshakeTimeoutError' ) {
154
+ this . metrics [ isServer ? 'server' : 'client' ] . events ?. increment ( {
155
+ error : true
156
+ } )
157
+ }
158
+
159
+ socket . destroy ( err )
112
160
reject ( err )
113
161
} )
114
162
socket . once ( 'secure' , ( ) => {
115
163
this . log ( 'verifying remote certificate' )
164
+ this . metrics [ isServer ? 'server' : 'client' ] . events ?. increment ( {
165
+ secure : true
166
+ } )
116
167
verifyRemote ( )
117
168
} )
118
- } )
119
- . catch ( err => {
120
- socket . destroy ( err )
121
- throw err
169
+ socket . on ( 'connect' , ( ) => {
170
+ this . metrics [ isServer ? 'server' : 'client' ] . events ?. increment ( {
171
+ connect : true
172
+ } )
122
173
} )
174
+ socket . on ( 'close' , ( ) => {
175
+ this . metrics [ isServer ? 'server' : 'client' ] . events ?. increment ( {
176
+ close : true
177
+ } )
178
+ } )
179
+ } )
123
180
}
124
181
}
0 commit comments