Reputation: 1599
I want to instantiate a struct instance and then call a method of that instance in an api route. Here's an example of what I want, but it results in an error:
use axum::{http::StatusCode, routing::get, Router, Server};
#[derive(Clone)]
struct Api {
name: String
}
impl Api {
async fn hello(&self) -> Result<String, StatusCode> {
Ok(format!("Hello {}!", self.name))
}
}
#[tokio::main]
async fn main() {
let api = Api { name: "Alice".to_owned() };
let app = Router::new()
.route("/hello-user", get(api.hello));
Server::bind(&([127, 0, 0, 1], 3000).into())
.serve(app.into_make_service())
.await
.unwrap();
}
error[E0615]: attempted to take value of method `hello` on type `Api`
--> src\main.rs:19:39
|
19 | .route("/hello-user", get(api.hello));
| ^^^^^ method, not a field
I have attempted to get around this by defining a function which calls the instance method:
let hello_method = move || async {
match api.hello().await {
Ok(response) => response,
Err(_) => "error".to_owned(),
}
};
let app = Router::new()
.route("/hello-user", get(hello_method));
However, with this I get a "lifetime may not live long enough" error. How should I go about calling an instance method from an axum server route?
Upvotes: 7
Views: 2028
Reputation: 155
You can move api
into the closure and then into the future:
let hello_method = move || async move {
match api.hello().await {
Ok(response) => response,
Err(_) => "error".to_owned(),
}
};
or with using of nightly
feature #![feature(async_closure)]
:
let hello_method = async move || {
match api.hello().await {
Ok(response) => response,
Err(_) => "error".to_owned(),
}
};
Upvotes: 6