Skip to main content

volans_swarm_derive/
lib.rs

1use heck::ToUpperCamelCase;
2use proc_macro::TokenStream;
3use quote::quote;
4use syn::{
5    Data, DataStruct, DeriveInput, Expr, ExprLit, Lit, Meta, Token, parse_macro_input,
6    punctuated::Punctuated,
7};
8
9trait RequireStrLit {
10    fn require_str_lit(&self) -> syn::Result<String>;
11}
12
13impl RequireStrLit for Expr {
14    fn require_str_lit(&self) -> syn::Result<String> {
15        match self {
16            Expr::Lit(ExprLit {
17                lit: Lit::Str(str), ..
18            }) => Ok(str.value()),
19            _ => Err(syn::Error::new_spanned(self, "expected a string literal")),
20        }
21    }
22}
23
24#[proc_macro_derive(NetworkIncomingBehavior, attributes(behavior))]
25pub fn network_incoming_macro_derive(input: TokenStream) -> TokenStream {
26    // 解析输入的 AST
27    let ast = parse_macro_input!(input as DeriveInput);
28    build_incoming(&ast).unwrap_or_else(|e| e.to_compile_error().into())
29}
30
31#[proc_macro_derive(NetworkOutgoingBehavior, attributes(behavior))]
32pub fn network_outgoing_macro_derive(input: TokenStream) -> TokenStream {
33    // 解析输入的 AST
34    let ast = parse_macro_input!(input as DeriveInput);
35    build_outgoing(&ast).unwrap_or_else(|e| e.to_compile_error().into())
36}
37
38fn build_incoming(ast: &DeriveInput) -> syn::Result<TokenStream> {
39    match ast.data {
40        // 只能解析结构体
41        Data::Struct(ref s) => build_incoming_struct(ast, s),
42        Data::Enum(_) => Err(syn::Error::new_spanned(
43            ast,
44            "Cannot derive `NetworkIncomingBehavior` on enums",
45        )),
46        Data::Union(_) => Err(syn::Error::new_spanned(
47            ast,
48            "Cannot derive `NetworkIncomingBehavior` on union",
49        )),
50    }
51}
52
53fn build_outgoing(ast: &DeriveInput) -> syn::Result<TokenStream> {
54    match ast.data {
55        // 只能解析结构体
56        Data::Struct(ref s) => build_outgoing_struct(ast, s),
57        Data::Enum(_) => Err(syn::Error::new_spanned(
58            ast,
59            "Cannot derive `NetworkOutgoingBehavior` on enums",
60        )),
61        Data::Union(_) => Err(syn::Error::new_spanned(
62            ast,
63            "Cannot derive `NetworkOutgoingBehavior` on union",
64        )),
65    }
66}
67
68struct PreludeTokenStream {
69    addr: proc_macro2::TokenStream,
70    peer_id: proc_macro2::TokenStream,
71    behavior_event: proc_macro2::TokenStream,
72    listener_event: proc_macro2::TokenStream,
73    connection_id: proc_macro2::TokenStream,
74    connection_denied: proc_macro2::TokenStream,
75    network_behavior_to_impl: proc_macro2::TokenStream,
76    network_incoming_behavior_to_impl: proc_macro2::TokenStream,
77    network_outgoing_behavior_to_impl: proc_macro2::TokenStream,
78    handler_select: proc_macro2::TokenStream,
79    t_handler: proc_macro2::TokenStream,
80    t_handler_event: proc_macro2::TokenStream,
81    t_handler_action: proc_macro2::TokenStream,
82    connection_handler: proc_macro2::TokenStream,
83    // inbound_stream_handler: proc_macro2::TokenStream,
84    // outbound_stream_handler: proc_macro2::TokenStream,
85    either: proc_macro2::TokenStream,
86
87    dial_opts: proc_macro2::TokenStream,
88
89    // error
90    connection_error: proc_macro2::TokenStream,
91    listen_error: proc_macro2::TokenStream,
92    dial_error: proc_macro2::TokenStream,
93
94    impl_generics: proc_macro2::TokenStream,
95}
96
97struct CommonParsed {
98    prelude: PreludeTokenStream,
99    attributes: BehaviorAttributes,
100}
101
102fn parse_common_token_stream(ast: &DeriveInput) -> syn::Result<CommonParsed> {
103    let attributes = parse_attributes(ast)?;
104    let BehaviorAttributes { prelude_path, .. } = &attributes;
105
106    let impl_generics = {
107        let tp = ast.generics.type_params();
108        let lf = ast.generics.lifetimes();
109        let cst = ast.generics.const_params();
110        quote! {<#(#lf,)* #(#tp,)* #(#cst,)*>}
111    };
112
113    let prelude = PreludeTokenStream {
114        addr: quote! { #prelude_path::Multiaddr },
115        peer_id: quote! { #prelude_path::PeerId },
116        behavior_event: quote! { #prelude_path::BehaviorEvent },
117        listener_event: quote! { #prelude_path::ListenerEvent },
118        connection_id: quote! { #prelude_path::ConnectionId },
119        connection_denied: quote! { #prelude_path::ConnectionDenied },
120        network_behavior_to_impl: quote! { #prelude_path::NetworkBehavior },
121        network_incoming_behavior_to_impl: quote! { #prelude_path::NetworkIncomingBehavior },
122        network_outgoing_behavior_to_impl: quote! { #prelude_path::NetworkOutgoingBehavior },
123        handler_select: quote! { #prelude_path::ConnectionHandlerSelect },
124        t_handler: quote! { #prelude_path::THandler },
125        t_handler_event: quote! { #prelude_path::THandlerEvent },
126        t_handler_action: quote! { #prelude_path::THandlerAction },
127        connection_handler: quote! { #prelude_path::ConnectionHandler },
128        // inbound_stream_handler: quote! { #prelude_path::InboundStreamHandler },
129        // outbound_stream_handler: quote! { #prelude_path::OutboundStreamHandler },
130        either: quote! { #prelude_path::Either },
131        connection_error: quote! { #prelude_path::ConnectionError },
132        listen_error: quote! { #prelude_path::ListenError },
133        dial_error: quote! { #prelude_path::DialError },
134        dial_opts: quote! { #prelude_path::DialOpts },
135        impl_generics,
136    };
137
138    Ok(CommonParsed {
139        prelude,
140        attributes,
141    })
142}
143
144fn build_event_impl(
145    ast: &DeriveInput,
146    data_struct: &DataStruct,
147    common: &CommonParsed,
148) -> (
149    syn::Type,
150    Option<proc_macro2::TokenStream>,
151    Vec<proc_macro2::TokenStream>,
152) {
153    let CommonParsed {
154        prelude:
155            PreludeTokenStream {
156                network_behavior_to_impl,
157                impl_generics,
158                ..
159            },
160        attributes:
161            BehaviorAttributes {
162                user_specified_out_event,
163                ..
164            },
165    } = common;
166
167    // 结构体名称
168    let name = &ast.ident;
169    // ty_generics: 泛型参数, where_clause: where 子句
170    let (_, ty_generics, where_clause) = ast.generics.split_for_impl();
171
172    match user_specified_out_event {
173        Some(name) => {
174            let definition = None;
175            let from_clauses = data_struct
176                .fields
177                .iter()
178                .map(|field| {
179                    let ty = &field.ty;
180                    quote! {#name: From< <#ty as #network_behavior_to_impl>::Event >}
181                })
182                .collect::<Vec<_>>();
183            (name.clone(), definition, from_clauses)
184        }
185        None => {
186            let enum_name_str = ast.ident.to_string() + "Event";
187            let enum_name: syn::Type =
188                syn::parse_str(&enum_name_str).expect("ident + `Event` is a valid type");
189            let definition = {
190                let fields = data_struct.fields.iter().map(|field| {
191                    let variant: syn::Variant = syn::parse_str(
192                        &field
193                            .ident
194                            .clone()
195                            .expect("Fields of NetworkBehaviour implementation to be named.")
196                            .to_string()
197                            .to_upper_camel_case(),
198                    )
199                    .expect("uppercased field name to be a valid enum variant");
200                    let ty = &field.ty;
201                    (variant, ty)
202                });
203
204                let enum_variants = fields.clone().map(
205                    |(variant, ty)| quote! {#variant(<#ty as #network_behavior_to_impl>::Event)},
206                );
207
208                let visibility = &ast.vis;
209
210                let additional = fields
211                    .clone()
212                    .map(|(_variant, tp)| quote! { #tp : #network_behavior_to_impl })
213                    .collect::<Vec<_>>();
214
215                let additional_debug = fields
216                        .clone()
217                        .map(|(_variant, ty)| quote! { <#ty as #network_behavior_to_impl>::Event : ::core::fmt::Debug })
218                        .collect::<Vec<_>>();
219
220                let where_clause = {
221                    if let Some(where_clause) = where_clause {
222                        if where_clause.predicates.trailing_punct() {
223                            Some(quote! {#where_clause #(#additional),* })
224                        } else {
225                            Some(quote! {#where_clause, #(#additional),*})
226                        }
227                    } else if additional.is_empty() {
228                        None
229                    } else {
230                        Some(quote! {where #(#additional),*})
231                    }
232                };
233
234                let where_clause_debug = where_clause
235                    .as_ref()
236                    .map(|where_clause| quote! {#where_clause, #(#additional_debug),*});
237
238                let match_variants = fields.map(|(variant, _ty)| variant);
239                let msg = format!("`NetworkBehavior::Event` produced by {name}.");
240
241                Some(quote! {
242                    #[doc = #msg]
243                    #visibility enum #enum_name #impl_generics
244                        #where_clause
245                    {
246                        #(#enum_variants),*
247                    }
248
249                    impl #impl_generics ::core::fmt::Debug for #enum_name #ty_generics #where_clause_debug {
250                        fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::result::Result<(), std::fmt::Error> {
251                            match &self {
252                                #(#enum_name::#match_variants(event) => {
253                                    write!(f, "{}: {:?}", #enum_name_str, event)
254                                }),*
255                            }
256                        }
257                    }
258                })
259            };
260            let from_clauses = vec![];
261            (enum_name, definition, from_clauses)
262        }
263    }
264}
265
266fn where_clause_token(
267    ast: &DeriveInput,
268    data_struct: &DataStruct,
269    out_event_from_clauses: Vec<proc_macro2::TokenStream>,
270    trait_to_impl: &proc_macro2::TokenStream,
271) -> Option<proc_macro2::TokenStream> {
272    let (_, _, where_clause) = ast.generics.split_for_impl();
273
274    let where_clause = {
275        let additional = data_struct
276            .fields
277            .iter()
278            .map(|field| {
279                let ty = &field.ty;
280                quote! {#ty: #trait_to_impl}
281            })
282            .chain(out_event_from_clauses)
283            .collect::<Vec<_>>();
284
285        if let Some(where_clause) = where_clause {
286            if where_clause.predicates.trailing_punct() {
287                Some(quote! {#where_clause #(#additional),* })
288            } else {
289                Some(quote! {#where_clause, #(#additional),*})
290            }
291        } else {
292            Some(quote! {where #(#additional),*})
293        }
294    };
295    where_clause
296}
297
298fn build_network_behavior_impl(
299    ast: &DeriveInput,
300    data_struct: &DataStruct,
301    common_parsed: &CommonParsed,
302) -> (proc_macro2::TokenStream, Vec<proc_macro2::TokenStream>) {
303    // 结构体名称
304    let name = &ast.ident;
305    // ty_generics: 泛型参数, where_clause: where 子句
306    let (_, ty_generics, _) = ast.generics.split_for_impl();
307
308    let (out_event_name, out_event_definition, out_event_from_clauses) =
309        build_event_impl(ast, data_struct, common_parsed);
310
311    let where_clause = where_clause_token(
312        ast,
313        data_struct,
314        out_event_from_clauses.clone(),
315        &common_parsed.prelude.network_behavior_to_impl,
316    );
317
318    let out_event_reference = if out_event_definition.is_some() {
319        quote! { #out_event_name #ty_generics }
320    } else {
321        quote! { #out_event_name }
322    };
323
324    let CommonParsed {
325        prelude:
326            PreludeTokenStream {
327                peer_id,
328                behavior_event,
329                connection_id,
330                network_behavior_to_impl,
331                handler_select,
332                t_handler,
333                t_handler_event,
334                t_handler_action,
335                either,
336                impl_generics,
337                ..
338            },
339        ..
340    } = &common_parsed;
341
342    let connection_handler_ty = {
343        let mut ph_ty = None;
344        for field in data_struct.fields.iter() {
345            let ty = &field.ty;
346            let field_info = quote! { #t_handler<#ty> };
347            match ph_ty {
348                Some(ev) => ph_ty = Some(quote! { #handler_select<#ev, #field_info> }),
349                ref mut ev @ None => *ev = Some(field_info),
350            }
351        }
352        ph_ty.unwrap_or(quote! {()})
353    };
354
355    let on_connection_handler_event_stmts = data_struct.fields.iter().enumerate().enumerate().map(
356        |(enum_n, (field_n, field))| {
357            let mut elem = if enum_n != 0 {
358                quote! { #either::Right(ev) }
359            } else {
360                quote! { ev }
361            };
362
363            for _ in 0..data_struct.fields.len() - 1 - enum_n {
364                elem = quote! { #either::Left(#elem) };
365            }
366
367            Some(match field.ident {
368                Some(ref i) => quote! { #elem => {
369                #network_behavior_to_impl::on_connection_handler_event(&mut self.#i, id, peer_id, ev) }},
370                None => quote! { #elem => {
371                #network_behavior_to_impl::on_connection_handler_event(&mut self.#field_n, id, peer_id, ev) }},
372            })
373        },
374    );
375
376    let poll_stmts = data_struct
377        .fields
378        .iter()
379        .enumerate()
380        .map(|(field_n, field)| {
381            let field = field
382                .ident
383                .clone()
384                .expect("Fields of NetworkBehavior implementation to be named.");
385
386            let mut wrapped_event = if field_n != 0 {
387                quote! { #either::Right(event) }
388            } else {
389                quote! { event }
390            };
391            for _ in 0..data_struct.fields.len() - 1 - field_n {
392                wrapped_event = quote! { #either::Left(#wrapped_event) };
393            }
394
395            let map_event = if out_event_definition.is_some() {
396                let event_variant: syn::Variant =
397                    syn::parse_str(&field.to_string().to_upper_camel_case())
398                        .expect("field name to be a valid enum variant name");
399                quote! { #out_event_name::#event_variant }
400            } else {
401                quote! { |e| e.into() }
402            };
403
404            let map_handler_action = quote! { |event| #wrapped_event };
405
406            quote! {
407                match #network_behavior_to_impl::poll(&mut self.#field, cx) {
408                    std::task::Poll::Ready(e) => return std::task::Poll::Ready(e.map_event(#map_event).map_handler_action(#map_handler_action)),
409                    std::task::Poll::Pending => {},
410                }
411            }
412        });
413
414    let final_quote = quote! {
415        #out_event_definition
416        impl #impl_generics #network_behavior_to_impl for #name #ty_generics
417        #where_clause
418        {
419            type ConnectionHandler = #connection_handler_ty;
420            type Event = #out_event_reference;
421
422            fn on_connection_handler_event(
423                &mut self,
424                id: #connection_id,
425                peer_id: #peer_id,
426                event: #t_handler_event<Self>
427            ) {
428                match event {
429                    #(#on_connection_handler_event_stmts),*
430                }
431            }
432
433            fn poll(
434                &mut self,
435                cx: &mut std::task::Context<'_>,
436            ) -> std::task::Poll<#behavior_event<Self::Event, #t_handler_action<Self>>> {
437                #(#poll_stmts)*
438                std::task::Poll::Pending
439            }
440
441        }
442    };
443
444    return (final_quote, out_event_from_clauses);
445}
446
447fn build_incoming_struct(ast: &DeriveInput, data_struct: &DataStruct) -> syn::Result<TokenStream> {
448    let common_parsed = parse_common_token_stream(ast)?;
449    // 结构体名称
450    let name = &ast.ident;
451    // ty_generics: 泛型参数, where_clause: where 子句
452    let (_, ty_generics, _) = ast.generics.split_for_impl();
453
454    let (network_behavior_token, out_event_from_clauses) =
455        build_network_behavior_impl(ast, data_struct, &common_parsed);
456
457    let CommonParsed {
458        prelude:
459            PreludeTokenStream {
460                addr,
461                peer_id,
462                listener_event,
463                connection_id,
464                connection_denied,
465                network_incoming_behavior_to_impl,
466                connection_handler,
467                listen_error,
468                connection_error,
469                impl_generics,
470                ..
471            },
472        ..
473    } = &common_parsed;
474
475    let where_clause = where_clause_token(
476        ast,
477        data_struct,
478        out_event_from_clauses,
479        network_incoming_behavior_to_impl,
480    );
481
482    // 生成 fn handle_pending_inbound_connection
483    let handle_pending_inbound_connection_stmts =
484        data_struct
485            .fields
486            .iter()
487            .enumerate()
488            .map(|(field_n, field)| {
489                match field.ident {
490                    Some(ref i) => quote! {
491                        #network_incoming_behavior_to_impl::handle_pending_connection(&mut self.#i, id, local_addr, remote_addr)?;
492                    },
493                    None => quote! {
494                        #network_incoming_behavior_to_impl::handle_pending_connection(&mut self.#field_n, id, local_addr, remote_addr)?;
495                    }
496                }
497            });
498
499    let handle_established_inbound_connection = {
500        let mut out_handler = None;
501
502        for (field_n, field) in data_struct.fields.iter().enumerate() {
503            let field_name = match field.ident {
504                Some(ref i) => quote! { self.#i },
505                None => quote! { self.#field_n },
506            };
507
508            let builder = quote! {
509                #field_name.handle_established_connection(id, peer_id, local_addr, remote_addr)?
510            };
511
512            match out_handler {
513                Some(h) => out_handler = Some(quote! { #connection_handler::select(#h, #builder) }),
514                ref mut h @ None => *h = Some(builder),
515            }
516        }
517
518        out_handler.unwrap_or(quote! {()})
519    };
520
521    // 生成 on_listen_failure
522    let on_listen_failure_stmts = data_struct.fields.iter().enumerate().map(
523        |(field_n, field)| {
524            match field.ident {
525                Some(ref i) => quote! {
526                    #network_incoming_behavior_to_impl::on_listen_failure(&mut self.#i, id, peer_id, local_addr, remote_addr, error);
527                },
528                None => quote! {
529                    #network_incoming_behavior_to_impl::on_listen_failure(&mut self.#field_n, id, peer_id, local_addr, remote_addr, error);
530                },
531            }
532        },
533    );
534
535    // 生成 on_connection_established
536    let on_connection_established_stmts = data_struct.fields.iter().enumerate().map(
537        |(field_n, field)| {
538            match field.ident {
539                Some(ref i) => quote! {
540                    #network_incoming_behavior_to_impl::on_connection_established(&mut self.#i, id, peer_id, local_addr, remote_addr);
541                },
542                None => quote! {
543                    #network_incoming_behavior_to_impl::on_connection_established(&mut self.#field_n, id, peer_id, local_addr, remote_addr);
544                },
545            }
546        },
547    );
548
549    // 生成 on_connection_closed
550    let on_connection_closed_stmts = data_struct.fields.iter().enumerate().map(
551        |(field_n, field)| {
552            match field.ident {
553                Some(ref i) => quote! {
554                    #network_incoming_behavior_to_impl::on_connection_closed(&mut self.#i, id, peer_id, local_addr, remote_addr, reason);
555                },
556                None => quote! {
557                    #network_incoming_behavior_to_impl::on_connection_closed(&mut self.#field_n, id, peer_id, local_addr, remote_addr, reason);
558                },
559            }
560        },
561    );
562
563    // 生成 on_listener_event
564    let on_listener_event_stmts = {
565        data_struct
566            .fields
567            .iter()
568            .enumerate()
569            .map(|(field_n, field)| match field.ident {
570                Some(ref i) => quote! {
571                    self.#i.on_listener_event(event);
572                },
573                None => quote! {
574                    self.#field_n.on_listener_event(event);
575                },
576            })
577    };
578
579    let final_quote = quote! {
580        #network_behavior_token
581        impl #impl_generics #network_incoming_behavior_to_impl for #name #ty_generics
582        #where_clause
583        {
584            fn handle_pending_connection(
585                &mut self,
586                id: #connection_id,
587                local_addr: &#addr,
588                remote_addr: &#addr
589            ) -> Result<(), #connection_denied> {
590                #(#handle_pending_inbound_connection_stmts)*
591                Ok(())
592            }
593
594            fn handle_established_connection(
595                &mut self,
596                id: #connection_id,
597                peer_id: #peer_id,
598                local_addr: &#addr,
599                remote_addr: &#addr
600            ) -> Result<Self::ConnectionHandler, #connection_denied> {
601                Ok(#handle_established_inbound_connection)
602            }
603
604            fn on_connection_established(
605                &mut self,
606                id: #connection_id,
607                peer_id: #peer_id,
608                local_addr: &#addr,
609                remote_addr: &#addr,
610            ) {
611                #(#on_connection_established_stmts)*
612            }
613
614            fn on_connection_closed(
615                &mut self,
616                id: #connection_id,
617                peer_id: #peer_id,
618                local_addr: &#addr,
619                remote_addr: &#addr,
620                reason: Option<&#connection_error>,
621            ) {
622                #(#on_connection_closed_stmts)*
623            }
624
625            fn on_listen_failure(
626                &mut self,
627                id: #connection_id,
628                peer_id: Option<#peer_id>,
629                local_addr: &#addr,
630                remote_addr: &#addr,
631                error: &#listen_error,
632            ) {
633                #(#on_listen_failure_stmts)*
634            }
635
636            fn on_listener_event(&mut self, event: #listener_event<'_>) {
637                #(#on_listener_event_stmts)*
638            }
639        }
640
641    };
642
643    return Ok(final_quote.into());
644}
645
646fn build_outgoing_struct(ast: &DeriveInput, data_struct: &DataStruct) -> syn::Result<TokenStream> {
647    let common_parsed = parse_common_token_stream(ast)?;
648    // 结构体名称
649    let name = &ast.ident;
650    // ty_generics: 泛型参数, where_clause: where 子句
651    let (_, ty_generics, _) = ast.generics.split_for_impl();
652
653    let (network_behavior_token, out_event_from_clauses) =
654        build_network_behavior_impl(ast, data_struct, &common_parsed);
655
656    let CommonParsed {
657        prelude:
658            PreludeTokenStream {
659                addr,
660                peer_id,
661                connection_id,
662                connection_denied,
663                network_outgoing_behavior_to_impl,
664                connection_handler,
665                dial_error,
666                connection_error,
667                dial_opts,
668                impl_generics,
669                ..
670            },
671        ..
672    } = &common_parsed;
673
674    let where_clause = where_clause_token(
675        ast,
676        data_struct,
677        out_event_from_clauses,
678        network_outgoing_behavior_to_impl,
679    );
680
681    let handle_pending_outbound_connection = {
682        let extend_stmts =
683            data_struct
684                .fields
685                .iter()
686                .enumerate()
687                .map(|(field_n, field)| {
688                    match field.ident {
689                        Some(ref i) => quote! {
690                            if let Some(addr) = #network_outgoing_behavior_to_impl::handle_pending_connection(&mut self.#i, id, maybe_peer, &maybe_addr)? {
691                                maybe_addr = Some(addr);
692                            }
693                        },
694                        None => quote! {
695                            if let Some(addr) = #network_outgoing_behavior_to_impl::handle_pending_connection(&mut self.#field_n, id, maybe_peer, &maybe_addr)? {
696                                maybe_addr = Some(addr);
697                            }
698                        }
699                    }
700                });
701
702        quote! {
703            let mut maybe_addr = maybe_addr.clone();
704            #(#extend_stmts)*
705            Ok(maybe_addr)
706        }
707    };
708
709    let handle_established_outbound_connection = {
710        let mut out_handler = None;
711
712        for (field_n, field) in data_struct.fields.iter().enumerate() {
713            let field_name = match field.ident {
714                Some(ref i) => quote! { self.#i },
715                None => quote! { self.#field_n },
716            };
717
718            let builder = quote! {
719                #field_name.handle_established_connection(id, peer_id, addr)?
720            };
721
722            match out_handler {
723                Some(h) => out_handler = Some(quote! { #connection_handler::select(#h, #builder) }),
724                ref mut h @ None => *h = Some(builder),
725            }
726        }
727        out_handler.unwrap_or(quote! {()})
728    };
729
730    // 生成 on_connection_established
731    let on_connection_established_stmts = data_struct.fields.iter().enumerate().map(
732        |(field_n, field)| {
733            match field.ident {
734                Some(ref i) => quote! {
735                    #network_outgoing_behavior_to_impl::on_connection_established(&mut self.#i, id, peer_id, addr);
736                },
737                None => quote! {
738                    #network_outgoing_behavior_to_impl::on_connection_established(&mut self.#field_n, id, peer_id, addr);
739                },
740            }
741        },
742    );
743
744    // 生成 on_connection_closed
745    let on_connection_closed_stmts = data_struct.fields.iter().enumerate().map(
746        |(field_n, field)| {
747            match field.ident {
748                Some(ref i) => quote! {
749                    #network_outgoing_behavior_to_impl::on_connection_closed(&mut self.#i, id, peer_id, addr, reason);
750                },
751                None => quote! {
752                    #network_outgoing_behavior_to_impl::on_connection_closed(&mut self.#field_n, id, peer_id, addr, reason);
753                },
754            }
755        },
756    );
757
758    // 生成 on_dial_failure
759    let on_dial_failure_stmts = data_struct.fields.iter().enumerate().map(
760        |(field_n, field)| {
761            match field.ident {
762                Some(ref i) => quote! {
763                    #network_outgoing_behavior_to_impl::on_dial_failure(&mut self.#i, id, maybe_peer, maybe_addr, error);
764                },
765                None => quote! {
766                    #network_outgoing_behavior_to_impl::on_dial_failure(&mut self.#field_n, id, maybe_peer, maybe_addr, error);
767                },
768            }
769        },
770    );
771
772    let poll_stmts = data_struct.fields.iter().enumerate().map(|(_, field)| {
773        let field = field
774            .ident
775            .clone()
776            .expect("Fields of NetworkBehavior implementation to be named.");
777        quote! {
778            match #network_outgoing_behavior_to_impl::poll_dial(&mut self.#field, cx) {
779                std::task::Poll::Ready(opts) => return std::task::Poll::Ready(opts),
780                std::task::Poll::Pending => {},
781            }
782        }
783    });
784
785    let final_quote = quote! {
786        #network_behavior_token
787        impl #impl_generics #network_outgoing_behavior_to_impl for #name #ty_generics
788        #where_clause
789        {
790            fn handle_pending_connection(
791                &mut self,
792                id: #connection_id,
793                maybe_peer: Option<#peer_id>,
794                maybe_addr: &Option<#addr>,
795            ) -> Result<Option<#addr>, #connection_denied> {
796                #handle_pending_outbound_connection
797            }
798
799            fn handle_established_connection(
800                &mut self,
801                id: #connection_id,
802                peer_id: #peer_id,
803                addr: &#addr,
804            ) -> Result<Self::ConnectionHandler, #connection_denied> {
805                Ok(#handle_established_outbound_connection)
806            }
807
808            /// 连接处理器事件处理
809            fn on_connection_established(
810                &mut self,
811                id: #connection_id,
812                peer_id: #peer_id,
813                addr: &#addr
814            ) {
815                #(#on_connection_established_stmts)*
816            }
817
818            fn on_connection_closed(
819                &mut self,
820                id: #connection_id,
821                peer_id: #peer_id,
822                addr: &#addr,
823                reason: Option<&#connection_error>,
824            ) {
825                #(#on_connection_closed_stmts)*
826            }
827
828            fn on_dial_failure(
829                &mut self,
830                id: #connection_id,
831                maybe_peer: Option<#peer_id>,
832                maybe_addr: Option<&#addr>,
833                error: &#dial_error,
834            ) {
835                #(#on_dial_failure_stmts)*
836            }
837
838            fn poll_dial(&mut self, cx: &mut std::task::Context<'_>) -> std::task::Poll<#dial_opts> {
839                #(#poll_stmts)*
840                std::task::Poll::Pending
841            }
842        }
843    };
844    return Ok(final_quote.into());
845}
846
847struct BehaviorAttributes {
848    // 引入的预定义模块路径
849    prelude_path: syn::Path,
850    // 用户指定的事件类型
851    user_specified_out_event: Option<syn::Type>,
852}
853
854// 解析结构体中的#[behavior]属性
855fn parse_attributes(ast: &DeriveInput) -> syn::Result<BehaviorAttributes> {
856    // 默认参数
857    let mut attributes = BehaviorAttributes {
858        prelude_path: syn::parse_quote! { ::volans::swarm::derive_prelude },
859        user_specified_out_event: None,
860    };
861
862    // 查找并解析 #[behavior] 属性
863    for attr in ast
864        .attrs
865        .iter()
866        .filter(|attr| attr.path().is_ident("behavior"))
867    {
868        // #[behavior(prelude=path, to_swarm=Type, out_event=Type)]
869        let nested = attr.parse_args_with(Punctuated::<Meta, Token![,]>::parse_terminated)?;
870        for meta in nested {
871            if meta.path().is_ident("prelude") {
872                let value = meta.require_name_value()?.value.require_str_lit()?;
873                attributes.prelude_path = syn::parse_str(&value)?;
874            } else if meta.path().is_ident("to_swarm") || meta.path().is_ident("out_event") {
875                let value = meta.require_name_value()?.value.require_str_lit()?;
876                attributes.user_specified_out_event = Some(syn::parse_str(&value)?);
877            }
878        }
879    }
880
881    Ok(attributes)
882}