我正在尝试添加一个将常量字段添加到结构的过程宏。
例子:
#[add_const]
struct MyStruct {
id: u32,
name: String
}
// Expands to:
struct MyStruct {
id: u32,
name: String
}
impl MyStruct {
const FIELDS: [&'static str; 2] = ["id", "name"];
const TYPES: [syn::Type; 2] = [/*Types of the fields*/];
}
我的程序宏代码如下:
#[proc_macro_attribute]
pub fn add_const(_attrs: TokenStream, input: TokenStream) -> TokenStream {
let item_struct = parse_macro_input!(input as ItemStruct);
let struct_name = &item_struct.ident;
let fields: Vec<(String, syn::Type)>;
if let syn::Fields::Named(ref _fields) = item_struct.fields {
let _fields = &_fields.named;
fields = _fields.iter().map(|field| {
if let Some(ident) = &field.ident {
let field_name: String = ident.to_string();
let field_type = &field.ty;
let entry = (field_name, field_type.to_owned());
entry
} else {
panic!("Only named fields are supported.")
}
}).collect();
} else {
panic!("The row struct has no fields.");
}
let mut field_names: Vec<String> = Vec::new();
let mut field_types: Vec<syn::Type> = Vec::new();
fields.iter().for_each(|field| {
let (_name, _type) = field;
field_names.push(_name.to_owned());
field_types.push(_type.to_owned());
});
TokenStream::from(
quote!(
#item_struct
impl #struct_name {
const FIELDS: [&'static str; #field_len] = [#(#field_names),*];
const TYPES: [syn::Type; #field_len] = [#(#field_types),*];
}
)
)
}
这会引发以下错误:
error[E0423]: expected value, found builtin type `i32`
--> tests/table_row.rs:7:13
|
7 | id: i32,
| ^^^ not a value
error[E0423]: expected value, found struct `String`
--> tests/table_row.rs:8:15
|
8 | name: String,
| ^^^^^^ help: use struct literal syntax instead: `String { vec: val }`
|
::: /Users/jonaseveraert/.rustup/toolchains/stable-x86_64-apple-darwin/lib/rustlib/src/rust/library/alloc/src/string.rs:292:1
|
292 | pub struct String {
| ----------------- `String` defined here
我已经能够确定问题所在;
/*CODE*/
impl #struct_name {
const FIELDS: [&'static str; #field_len] = [#(#field_names),*];
// const TYPES: [syn::Type; #field_len] = [#(#field_types),*]; // Commenting out this line makes the errors disappear
}
/*MORE CODE*/
我怎样才能解决这个问题?即如何添加第二个常量而不出现错误,为什么会出现这些错误?
提前谢谢你,乔纳斯