{"record":{"id":"0934ab575183fc70","repo":"yewstack/yew","slug":"only-named-fields-are-supported","errorCode":null,"errorMessage":"only named fields are supported","messagePattern":"only named fields are supported","errorType":"validation","errorClass":"syn::Error","httpStatus":null,"severity":"error","filePath":"packages/yew-router-macro/src/routable_derive.rs","lineNumber":78,"sourceCode":"            ident,\n            variants: data.variants,\n            ats,\n            not_found_route,\n        })\n    }\n}\n\nfn parse_variants_attributes(\n    variants: &Punctuated<Variant, syn::token::Comma>,\n) -> syn::Result<(Option<Ident>, Vec<LitStr>)> {\n    let mut not_founds = vec![];\n    let mut ats: Vec<LitStr> = vec![];\n\n    let mut not_found_attrs = vec![];\n\n    for variant in variants.iter() {\n        if let Fields::Unnamed(ref field) = variant.fields {\n            return Err(syn::Error::new(\n                field.span(),\n                \"only named fields are supported\",\n            ));\n        }\n\n        let attrs = &variant.attrs;\n        let at_attrs = attrs\n            .iter()\n            .filter(|attr| attr.path().is_ident(AT_ATTR_IDENT))\n            .collect::<Vec<_>>();\n\n        let attr = match at_attrs.len() {\n            1 => *at_attrs.first().unwrap(),\n            0 => {\n                return Err(syn::Error::new(\n                    variant.span(),\n                    format!(\"{AT_ATTR_IDENT} attribute must be present on every variant\"),\n                ));","sourceCodeStart":60,"sourceCodeEnd":96,"githubUrl":"https://github.com/yewstack/yew/blob/0e4a05472fac4e5fce1befe60fa4a1e43a36b6a3/packages/yew-router-macro/src/routable_derive.rs#L60-L96","documentation":"Inside #[derive(Routable)] the variant scanner (packages/yew-router-macro/src/routable_derive.rs:78) rejects tuple variants (Fields::Unnamed) with 'only named fields are supported'. Route parameters captured by a pattern like #[at(\"/posts/{id}\")] are bound by name, so variant payloads must use named fields; unit variants are allowed for parameterless routes.","triggerScenarios":"Declaring a tuple variant in the route enum, e.g. Post(u32) with #[at(\"/posts/{id}\")] — the fields check fires before the #[at] attribute is even read.","commonSituations":"Writing concise enum payloads with tuple syntax by habit; converting a data model enum that used tuple variants into the route enum; following non-router enum examples.","solutions":["Rewrite the variant with named fields matching the route parameter names: Post { id: u32 }","For routes with no parameters use a unit variant (e.g. Home)","Keep field names in sync with the {param} segments in the #[at] pattern, otherwise a separate 'route parameter ... does not have a corresponding field' error follows"],"exampleFix":"// before\n#[derive(Routable, Clone)]\nenum Routes {\n    #[at(\"/posts/{id}\")]\n    Post(u32),\n}\n\n// after\n#[derive(Routable, Clone)]\nenum Routes {\n    #[at(\"/posts/{id}\")]\n    Post { id: u32 },\n}","handlingStrategy":"validation","validationCode":"// parameter-capturing variants must use named fields matching {param} names\n// #[at(\"/posts/{id}\")] Post { id: u32 },\n// static routes: unit variants  #[at(\"/\")] Home,","typeGuard":"// route parameters are bound by field name; ensure names line up at compile time\n// #[at(\"/posts/{id}\")] Post { id: u32 }  // `{id}` must equal a field ident","tryCatchPattern":null,"preventionTips":["Use named fields for variants with parameters; unit variants otherwise","Match field idents exactly to {param} segments in the #[at] string","Run cargo check after adding each variant — the derive reports shape problems early"],"tags":["rust","derive-macro","yew-router","compile-time","routing"],"backgroundTag":"derive-macro-wrong-item-type","analyzedSha":"0e4a05472fac4e5fce1befe60fa4a1e43a36b6a3","analyzedAt":"2026-08-22T21:16:31.212Z","schemaVersion":2},"datasetVersion":"2026-08-23T01:17:44.959Z"}