@@ -63,7 +63,7 @@ impl Push<OutboundPush> {
6363 }
6464}
6565
66- /// Information of a peer sent in protocol messages.
66+ /// Identify information of a peer sent in protocol messages.
6767#[ derive( Debug , Clone ) ]
6868pub struct Info {
6969 /// The public key of the local peer.
@@ -82,6 +82,41 @@ pub struct Info {
8282 pub observed_addr : Multiaddr ,
8383}
8484
85+ impl Info {
86+ pub fn merge ( & mut self , info : PushInfo ) {
87+ if let Some ( public_key) = info. public_key {
88+ self . public_key = public_key;
89+ }
90+ if let Some ( protocol_version) = info. protocol_version {
91+ self . protocol_version = protocol_version;
92+ }
93+ if let Some ( agent_version) = info. agent_version {
94+ self . agent_version = agent_version;
95+ }
96+ if !info. listen_addrs . is_empty ( ) {
97+ self . listen_addrs = info. listen_addrs ;
98+ }
99+ if !info. protocols . is_empty ( ) {
100+ self . protocols = info. protocols ;
101+ }
102+ if let Some ( observed_addr) = info. observed_addr {
103+ self . observed_addr = observed_addr;
104+ }
105+ }
106+ }
107+
108+ /// Identify push information of a peer sent in protocol messages.
109+ /// Note that missing fields should be ignored, as peers may choose to send partial updates containing only the fields whose values have changed.
110+ #[ derive( Debug , Clone ) ]
111+ pub struct PushInfo {
112+ pub public_key : Option < PublicKey > ,
113+ pub protocol_version : Option < String > ,
114+ pub agent_version : Option < String > ,
115+ pub listen_addrs : Vec < Multiaddr > ,
116+ pub protocols : Vec < StreamProtocol > ,
117+ pub observed_addr : Option < Multiaddr > ,
118+ }
119+
85120impl UpgradeInfo for Identify {
86121 type Info = StreamProtocol ;
87122 type InfoIter = iter:: Once < Self :: Info > ;
@@ -110,7 +145,7 @@ where
110145 type Future = Pin < Box < dyn Future < Output = Result < Self :: Output , Self :: Error > > + Send > > ;
111146
112147 fn upgrade_outbound ( self , socket : C , _: Self :: Info ) -> Self :: Future {
113- recv ( socket) . boxed ( )
148+ recv_identify ( socket) . boxed ( )
114149 }
115150}
116151
@@ -127,13 +162,13 @@ impl<C> InboundUpgrade<C> for Push<InboundPush>
127162where
128163 C : AsyncRead + AsyncWrite + Unpin + Send + ' static ,
129164{
130- type Output = BoxFuture < ' static , Result < Info , UpgradeError > > ;
165+ type Output = BoxFuture < ' static , Result < PushInfo , UpgradeError > > ;
131166 type Error = Void ;
132167 type Future = future:: Ready < Result < Self :: Output , Self :: Error > > ;
133168
134169 fn upgrade_inbound ( self , socket : C , _: Self :: Info ) -> Self :: Future {
135170 // Lazily upgrade stream, thus allowing upgrade to happen within identify's handler.
136- future:: ok ( recv ( socket) . boxed ( ) )
171+ future:: ok ( recv_push ( socket) . boxed ( ) )
137172 }
138173}
139174
@@ -184,7 +219,29 @@ where
184219 Ok ( ( ) )
185220}
186221
187- async fn recv < T > ( socket : T ) -> Result < Info , UpgradeError >
222+ async fn recv_push < T > ( socket : T ) -> Result < PushInfo , UpgradeError >
223+ where
224+ T : AsyncRead + AsyncWrite + Unpin ,
225+ {
226+ let info = recv ( socket) . await ?. try_into ( ) ?;
227+
228+ trace ! ( "Received {:?}" , info) ;
229+
230+ Ok ( info)
231+ }
232+
233+ async fn recv_identify < T > ( socket : T ) -> Result < Info , UpgradeError >
234+ where
235+ T : AsyncRead + AsyncWrite + Unpin ,
236+ {
237+ let info = recv ( socket) . await ?. try_into ( ) ?;
238+
239+ trace ! ( "Received {:?}" , info) ;
240+
241+ Ok ( info)
242+ }
243+
244+ async fn recv < T > ( socket : T ) -> Result < proto:: Identify , UpgradeError >
188245where
189246 T : AsyncRead + AsyncWrite + Unpin ,
190247{
@@ -199,61 +256,93 @@ where
199256 )
200257 . next ( )
201258 . await
202- . ok_or ( UpgradeError :: StreamClosed ) ??
203- . try_into ( ) ?;
204-
205- trace ! ( "Received: {:?}" , info) ;
259+ . ok_or ( UpgradeError :: StreamClosed ) ??;
206260
207261 Ok ( info)
208262}
209263
210- impl TryFrom < proto:: Identify > for Info {
211- type Error = UpgradeError ;
264+ fn parse_listen_addrs ( listen_addrs : Vec < Vec < u8 > > ) -> Vec < Multiaddr > {
265+ listen_addrs
266+ . into_iter ( )
267+ . filter_map ( |bytes| match Multiaddr :: try_from ( bytes) {
268+ Ok ( a) => Some ( a) ,
269+ Err ( e) => {
270+ debug ! ( "Unable to parse multiaddr: {e:?}" ) ;
271+ None
272+ }
273+ } )
274+ . collect ( )
275+ }
212276
213- fn try_from ( msg : proto:: Identify ) -> Result < Self , Self :: Error > {
214- fn parse_multiaddr ( bytes : Vec < u8 > ) -> Result < Multiaddr , multiaddr:: Error > {
215- Multiaddr :: try_from ( bytes)
277+ fn parse_protocols ( protocols : Vec < String > ) -> Vec < StreamProtocol > {
278+ protocols
279+ . into_iter ( )
280+ . filter_map ( |p| match StreamProtocol :: try_from_owned ( p) {
281+ Ok ( p) => Some ( p) ,
282+ Err ( e) => {
283+ debug ! ( "Received invalid protocol from peer: {e}" ) ;
284+ None
285+ }
286+ } )
287+ . collect ( )
288+ }
289+
290+ fn parse_public_key ( public_key : Option < Vec < u8 > > ) -> Option < PublicKey > {
291+ public_key. and_then ( |key| match PublicKey :: try_decode_protobuf ( & key) {
292+ Ok ( k) => Some ( k) ,
293+ Err ( e) => {
294+ debug ! ( "Unable to decode public key: {e:?}" ) ;
295+ None
216296 }
297+ } )
298+ }
217299
218- let listen_addrs = {
219- let mut addrs = Vec :: new ( ) ;
220- for addr in msg. listenAddrs . into_iter ( ) {
221- match parse_multiaddr ( addr) {
222- Ok ( a) => addrs. push ( a) ,
223- Err ( e) => {
224- debug ! ( "Unable to parse multiaddr: {e:?}" ) ;
225- }
226- }
227- }
228- addrs
229- } ;
300+ fn parse_observed_addr ( observed_addr : Option < Vec < u8 > > ) -> Option < Multiaddr > {
301+ observed_addr. and_then ( |bytes| match Multiaddr :: try_from ( bytes) {
302+ Ok ( a) => Some ( a) ,
303+ Err ( e) => {
304+ debug ! ( "Unable to parse observed multiaddr: {e:?}" ) ;
305+ None
306+ }
307+ } )
308+ }
230309
231- let public_key = PublicKey :: try_decode_protobuf ( & msg. publicKey . unwrap_or_default ( ) ) ?;
310+ impl TryFrom < proto:: Identify > for Info {
311+ type Error = UpgradeError ;
232312
233- let observed_addr = match parse_multiaddr ( msg. observedAddr . unwrap_or_default ( ) ) {
234- Ok ( a) => a,
235- Err ( e) => {
236- debug ! ( "Unable to parse multiaddr: {e:?}" ) ;
237- Multiaddr :: empty ( )
313+ fn try_from ( msg : proto:: Identify ) -> Result < Self , Self :: Error > {
314+ let public_key = {
315+ match parse_public_key ( msg. publicKey ) {
316+ Some ( key) => key,
317+ // This will always produce a DecodingError if the public key is missing.
318+ None => PublicKey :: try_decode_protobuf ( Default :: default ( ) ) ?,
238319 }
239320 } ;
321+
240322 let info = Info {
241323 public_key,
242324 protocol_version : msg. protocolVersion . unwrap_or_default ( ) ,
243325 agent_version : msg. agentVersion . unwrap_or_default ( ) ,
244- listen_addrs,
245- protocols : msg
246- . protocols
247- . into_iter ( )
248- . filter_map ( |p| match StreamProtocol :: try_from_owned ( p) {
249- Ok ( p) => Some ( p) ,
250- Err ( e) => {
251- debug ! ( "Received invalid protocol from peer: {e}" ) ;
252- None
253- }
254- } )
255- . collect ( ) ,
256- observed_addr,
326+ listen_addrs : parse_listen_addrs ( msg. listenAddrs ) ,
327+ protocols : parse_protocols ( msg. protocols ) ,
328+ observed_addr : parse_observed_addr ( msg. observedAddr ) . unwrap_or ( Multiaddr :: empty ( ) ) ,
329+ } ;
330+
331+ Ok ( info)
332+ }
333+ }
334+
335+ impl TryFrom < proto:: Identify > for PushInfo {
336+ type Error = UpgradeError ;
337+
338+ fn try_from ( msg : proto:: Identify ) -> Result < Self , Self :: Error > {
339+ let info = PushInfo {
340+ public_key : parse_public_key ( msg. publicKey ) ,
341+ protocol_version : msg. protocolVersion ,
342+ agent_version : msg. agentVersion ,
343+ listen_addrs : parse_listen_addrs ( msg. listenAddrs ) ,
344+ protocols : parse_protocols ( msg. protocols ) ,
345+ observed_addr : parse_observed_addr ( msg. observedAddr ) ,
257346 } ;
258347
259348 Ok ( info)
@@ -303,7 +392,7 @@ mod tests {
303392 ) ,
304393 } ;
305394
306- let info = Info :: try_from ( payload) . expect ( "not to fail" ) ;
395+ let info = PushInfo :: try_from ( payload) . expect ( "not to fail" ) ;
307396
308397 assert_eq ! ( info. listen_addrs, vec![ valid_multiaddr] )
309398 }
0 commit comments