proc-macro-workshop:builder-5

godme發表於2022-06-29
// This test case should be a freebie if the previous ones are already working.
// It shows that we can chain method calls on the builder.

use derive_builder::Builder;

#[derive(Builder)]
pub struct Command {
    executable: String,
    args: Vec<String>,
    env: Vec<String>,
    current_dir: String,
}

fn main() {
    let command = Command::builder()
        .executable("cargo".to_owned())
        .args(vec!["build".to_owned(), "--release".to_owned()])
        .env(vec![])
        .current_dir("..".to_owned())
        .build()
        .unwrap();

    assert_eq!(command.executable, "cargo");
}

這一題和前一題的差別在於setter方法的鏈式呼叫,在第三關的時候我們已經說明了。

可以回看一下第三關,這裡簡單的貼一下

// solution35.rs
pub(super) fn soultion(
    fields: &crate::common::FieldsType,
    builder_ident: &syn::Ident,
) -> proc_macro2::TokenStream {
    let idents: Vec<_> = fields.iter().map(|f| &f.ident).collect();
    let tys: Vec<_> = fields.iter().map(|f| &f.ty).collect();

    quote::quote! {
        impl #builder_ident {
            #(
                pub fn #idents(&mut self, #idents: #tys) -> &mut Self {
                    self.#idents = std::option::Option::Some(#idents);
                    // 返回自身引用,順便解決第五題鏈式呼叫
                    self
                }
            )*
        }
    }
}

整體結構不變

本作品採用《CC 協議》,轉載必須註明作者和本文連結