Skip to content

poem-openapi: implementation of Send is not general enough #995

@psi-psi-psi

Description

@psi-psi-psi

Expected Behavior

When deriving #[OpenAPI] on a struct using a boxed lifetime, it should work.

Actual Behavior

The compiler complains that &poem::Request has the wrong lifetime implementation of Send:

| #[OpenApi]
| ^^^^^^^^^^ implementation of `Send` is not general enough`
|
= note: `Send` would have to be implemented for the type `&poem::Request`
= note: ...but `Send` is actually implemented for the type `&'0 poem::Request`, for some specific lifetime `'0`

Minimized reproducible example

I tried to trigger this without diesel_async, but I was unable to find the magic mix of lifetimes and auto trait constraints. So bear with me that this mimimal example is 56 lines long and requires diesel:

use diesel::{prelude::Queryable, query_builder::AsQuery, table, QueryDsl};
use diesel_async::{methods::LoadQuery, AsyncPgConnection, RunQueryDsl};
use poem::web::Data;
use poem_openapi::{payload::Json, ApiResponse, Object, OpenApi};

#[derive(ApiResponse)]
enum Response {
   #[oai(status = 200)]
   Ok(Json<Vec<Obj>>)
}

struct Endpoints;

#[OpenApi]
impl Endpoints {
  #[oai(method = "get", path = "/")]
  async fn index(&self, db: Data<&Db>) -> Response {
    let mut conn = db.connection().await;
    let query = test_table::table.as_query();
    let query = query.into_boxed(); // if this line is commented out, it works!
    let res = load(query, &mut conn).await.unwrap();
    Response::Ok(Json(res))
  }
}

async fn load<'query, 'conn, Q, O>(
  query: Q,
  conn: &'conn mut AsyncPgConnection
) -> QueryResult<Vec<O>>
where
  O: Send,
  Q: LoadQuery<'query, AsyncPgConnection, U> + 'query,
{
  query.load::<U>(conn).await
}

struct Db {}
impl Db {
  async fn connection(&self) -> AsyncPgConnection { todo!("not relevant"); }
}

table! { test_table { id -> BigInt } }

#[derive(Object, Queryable)]
struct Obj {
  id: i64
}

Comments

There are many adjacent errors of a similar category. If I do not pass the Db as data, for instance, but instead create a connection from thin air in the handler, the error message is similar, but instead of complaining about &poem::Request it complains about Send not being implemented for diesel::BoxedSelectStatement. It can also sometimes be triggered on other traits than Send (Query, for instance) in some configurations, but that might be real implemenation mistakes on my part.

The error sounds related to rust issue 64452, but I am not sure.

Specifications

  • Version: poem 3.1.7, poem-openapi 5.1.8
  • Platform: Linux

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions