vectordotdev/vector · error · syn::Error

`required_one_of` is not supported on newtype struct fields

Error message

`required_one_of` is not supported on newtype struct fields

What it means

Compile-time error from `build_newtype_struct_generate_schema_fn`. A newtype struct (`struct Wrapper(T)`) is transparent in serde — it serializes as the inner value directly, with no object key for the single field — so `required_one_of`, which keys on field names, cannot apply. The macro rejects it before generating the schema function.

Source

Thrown at lib/vector-config-macros/src/configurable.rs:554

        // Don't map this field if it's marked to be skipped for both serialization and deserialization.
        .filter(|field| field.visible())
        .map(generate_tuple_struct_field);

    quote! {
        fn generate_schema(schema_gen: &::std::cell::RefCell<::vector_config::schema::SchemaGenerator>) -> std::result::Result<::vector_config::schema::SchemaObject, ::vector_config::GenerateError> {
            let mut subschemas = ::std::collections::Vec::new();

            #(#mapped_fields)*

            Ok(::vector_config::schema::generate_tuple_schema(&subschemas))
        }
    }
}

fn build_newtype_struct_generate_schema_fn(fields: &[Field<'_>]) -> proc_macro2::TokenStream {
    for field in fields.iter() {
        if field.required_one_of().is_some() {
            return syn::Error::new(
                field.span(),
                "`required_one_of` is not supported on newtype struct fields",
            )
            .to_compile_error();
        }
    }

    // Map the fields normally, but we should end up with a single field at the end.
    let mut mapped_fields = fields
        .iter()
        // Don't map this field if it's marked to be skipped for both serialization and deserialization.
        .filter(|field| field.visible())
        .map(generate_struct_field)
        .collect::<Vec<_>>();

    if mapped_fields.len() != 1 {
        panic!("newtype structs should never have more than one field");
    }

View on GitHub (pinned to 3708c39b12)

Solutions

  1. Remove the `required_one_of` attribute from the newtype field
  2. Or change the wrapper to a named struct with one named, optional field and put the group there

Example fix

// before
struct Wrapper(#[configurable(required_one_of = ["x"])] Inner);

// after
struct Wrapper {
    #[configurable(required_one_of = ["x", "y"])]
    inner: Option<Inner>,
}
Defensive patterns

Strategy: validation

Validate before calling

# CI gate: unsupported newtype usage fails at compile time
cargo check --workspace --all-targets

Prevention

When it happens

Trigger: `#[derive(Configurable)]` on a newtype struct whose single field has `#[configurable(required_one_of(...))]`.

Common situations: Wrapping an existing config type in a newtype (e.g. for the newtype pattern or type safety) while keeping attributes that only make sense on named-struct fields.

Related errors


AI-assisted analysis of vectordotdev/vector@3708c39b12 (2026-08-20). Data as JSON: /api/errors/81324a790aede998. Report an issue: GitHub.