actix/actix-web · error · syn::Error

The #[route(..)] macro requires at least one `method` attrib

Error message

The #[route(..)] macro requires at least one `method` attribute

What it means

The `#[route("/path")]` macro, unlike `#[get(...)]`, carries no implicit HTTP method, so it requires at least one `method = "..."` option. At actix-web-codegen/src/route.rs:358-363 the macro errors if `args.methods` is empty after parsing options.

Source

Thrown at actix-web-codegen/src/route.rs:359

}

impl Route {
    pub fn new(args: RouteArgs, ast: syn::ItemFn, method: Option<MethodType>) -> syn::Result<Self> {
        let name = ast.sig.ident.clone();

        // Try and pull out the doc comments so that we can reapply them to the generated struct.
        // Note that multi line doc comments are converted to multiple doc attributes.
        let doc_attributes = ast
            .attrs
            .iter()
            .filter(|attr| attr.path().is_ident("doc"))
            .cloned()
            .collect();

        let args = Args::new(args, method)?;

        if args.methods.is_empty() {
            return Err(syn::Error::new(
                Span::call_site(),
                "The #[route(..)] macro requires at least one `method` attribute",
            ));
        }

        if matches!(ast.sig.output, syn::ReturnType::Default) {
            return Err(syn::Error::new_spanned(
                ast,
                "Function has no return type. Cannot be used as handler",
            ));
        }

        Ok(Self {
            name,
            args: vec![args],
            ast,
            doc_attributes,
        })

View on GitHub (pinned to 937960ca67)

Solutions

  1. Add at least one `method = "GET"` (or POST/PUT/etc.) option: `#[route("/items", method="GET")]`.
  2. If you only need one standard method, prefer the dedicated macro: `#[get("/items")]`.
  3. To handle multiple methods on one path, list several `method = "..."` options.

Example fix

// before
#[route("/items")]
async fn handler() -> HttpResponse { ... }

// after
#[route("/items", method = "GET")]
async fn handler() -> HttpResponse { ... }
Defensive patterns

Strategy: validation

Validate before calling

// Compile-time only. For every #[route("...")] ensure at least one
// `method = "..."` option is present. Prefer #[get]/#[post]/... for single methods.

Prevention

When it happens

Trigger: `#[route("/items")]` with no options, forgetting that `route` needs explicit methods.

Common situations: Confusing `#[route]` (generic, needs `method`) with `#[get]`/`#[post]` (method baked in).

Related errors


AI-assisted analysis of actix/actix-web@937960ca67 (2026-08-06). Data as JSON: /data/errors/6399bc9de79182c4.json. Report an issue: GitHub.