{"record":{"id":"14e6eafb9eabd206","repo":"risingwavelabs/risingwave","slug":"you-can-t-use-the-macro-on-this-type","errorCode":null,"errorMessage":"You can't use the macro on this type","messagePattern":"You can't use the macro on this type","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"src/common/proc_macro/src/serde_prefix_all.rs","lineNumber":134,"sourceCode":"        mode: mode.unwrap_or(Mode::Rename),\n    })\n}\n\npub(crate) fn try_prefix_all(\n    args: AttributeArgs,\n    mut input: DeriveInput,\n) -> syn::Result<TokenStream> {\n    let ParsedArgs {\n        prefix,\n        prefix_span,\n        mode,\n    } = parse_args(args)?;\n\n    match &mut input.data {\n        Data::Enum(item_enum) => handle_enum(item_enum, &prefix[..], mode)?,\n        Data::Struct(item_struct) => handle_struct(item_struct, &prefix[..], mode)?,\n        _ => {\n            return Err(Error::new(\n                prefix_span,\n                \"You can't use the macro on this type\",\n            ));\n        }\n    };\n\n    Ok(input.to_token_stream().into())\n}\n\nfn create_attribute(prefix: &str, field_name: &str, mode: Mode) -> Attribute {\n    let attr_prefix = format!(\"{prefix}{field_name}\");\n    match mode {\n        Mode::Rename => parse_quote! { #[serde(rename = #attr_prefix)] },\n        Mode::Alias => parse_quote! { #[serde(alias = #attr_prefix)] },\n    }\n}\n\nfn take_skip_attr(attrs: &mut Vec<Attribute>) -> syn::Result<bool> {","sourceCodeStart":116,"sourceCodeEnd":152,"githubUrl":"https://github.com/risingwavelabs/risingwave/blob/6469eb736d691e8e9b8a419a57edd6429ca77417/src/common/proc_macro/src/serde_prefix_all.rs#L116-L152","documentation":"The #[serde_prefix_all] attribute macro only supports enums and structs. It fails at compile time when applied to a union or any other non-enum/non-struct item, because there is no defined way to prefix fields or variants of such a type. The error is emitted by try_prefix_all in the proc-macro crate when the derive input's Data falls into neither the Enum nor Struct arm.","triggerScenarios":"Annotating a Rust `union` (or any item whose parsed DeriveInput data is not Data::Enum or Data::Struct) with #[serde_prefix_all(\"prefix\")]. E.g. `#[serde_prefix_all(\"cfg_\")] union Foo { a: u32, b: f32 }`.","commonSituations":"Developers converting a serde type to use the prefix macro accidentally apply it to a union used for FFI or low-level byte reinterpretation; copy-pasting the attribute above the wrong item; changing a struct into a union later and leaving the attribute in place.","solutions":["Remove the #[serde_prefix_all] attribute from the union; the macro cannot run on unions.","Convert the type to a struct (or enum) if prefixing semantics are actually needed.","Handle prefixing manually with #[serde(rename = \"...\")] on each field instead.","Move the attribute to a sibling struct/enum that wraps or serializes the union's payload."],"exampleFix":"// before\n#[serde_prefix_all(\"cfg_\")]\nunion Packed {\n    raw: u64,\n    f: f64,\n}\n\n// after\n#[derive(Serialize)]\n#[serde_prefix_all(\"cfg_\")]\nstruct PackedView {\n    raw: u64,\n}","handlingStrategy":"validation","validationCode":"// Compile-time check before relying on the macro:\nmacro_rules! assert_is_struct_or_enum {\n    ($t:ty) => {\n        const _: () = {\n            // Applying serde_prefix_all to a union fails to compile;\n            // only attach it to structs/enums.\n        };\n    };\n}\n// Practical pre-check: confirm the item below the attribute is\n// `struct` or `enum` — never `union`.","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Only place #[serde_prefix_all] directly above `struct` or `enum` declarations.","Never attach the macro to `union` types used for FFI/byte reinterpretation.","If converting a struct to a union, remove the attribute first.","Let the compiler catch it early: run `cargo check` immediately after adding the attribute."],"tags":["proc-macro","compile-time","serde","rust"],"backgroundTag":"unsupported-operation","analyzedSha":"6469eb736d691e8e9b8a419a57edd6429ca77417","analyzedAt":"2026-09-11T21:06:21.487Z","contentChangedAt":"2026-09-11T21:06:21.487Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}