Warp + tokio + deadpool_postgres --> keeps hitting roadblocks

Hi Rustaceans,

I'm an experienced coder but in early man-weeks with Rust.
I'm trying to build a simple REST server and keep hitting roadblocks.
I'm probably making some newb-ish mistake but can't seem to spot it.

MUCH THANKS to those that give me a boost.

I think what I want is:

  1. main() configres a deadpool-postgres pool and warp filter
  2. warp__server() sends a request to do_jump() including the pool
  3. do_jump() gets a client connection from the pool and does database things

The code provided is the simplest version of the many approaches I've tried.

use deadpool_postgres::{Manager, ManagerConfig, Pool, RecyclingMethod};
use tokio_postgres::{NoTls};
use warp::Filter;

#[tokio::main]
async fn main()
{
    let mut pg_config = tokio_postgres::Config::new();
    pg_config.host("localhost");
    pg_config.user("cards2");
    pg_config.password("cards2");
    pg_config.dbname("cards2");
    let mgr_config = ManagerConfig {
        recycling_method: RecyclingMethod::Fast
    };
    let mgr = Manager::from_config(pg_config, NoTls, mgr_config);
    let pool = Pool::builder(mgr).max_size(16).build().unwrap();

    for i in 1..10 {
        let client = pool.get().await.unwrap();
        let stmt = client.prepare_cached("SELECT 1 + $1").await.unwrap();
        let rows = client.query(&stmt, &[&i]).await.unwrap();
        let value: i32 = rows[0].get(0);
        println!("{} {}", i, value);
        assert_eq!(value, i + 1);
    }

    let jump_filter = warp::path("jump")
        .and(pool.clone())
        .and_then(do_jump);

    warp::serve(jump_filter)
        .run(([127, 0, 0, 1], 3030))
        .await;
}

pub async fn do_jump(pool: deadpool_postgres::Pool) -> Result<impl warp::Reply, warp::Rejection>
{
    println!("running do_jump()");
    let client = pool.get().await.unwrap();

    //do database things

    let foo = "foo".to_string();
    Ok(warp::reply::html(foo))
}

It fails to compile with:

> 29 |         .and(pool.clone())
>    |              ^^^^^^^^^^^^ the trait `warp::filter::FilterBase` is not implemented for `deadpool::managed::Pool<Manager>`
> 
> error[E0599]: the method `and_then` exists for struct `warp::filter::and::And<Exact<warp::path::internal::Opaque<&str>>, deadpool::managed::Pool<Manager>>`, but its trait bounds were not satisfied
>   --> cards_db_test/src/main.rs:30:10
>    |
> 30 |         .and_then(do_jump);
>    |          ^^^^^^^^ method cannot be called on `warp::filter::and::And<Exact<warp::path::internal::Opaque<&str>>, deadpool::managed::Pool<Manager>>` due to unsatisfied trait bounds

My Cargo.toml:

[package]
name = "cards_db_test"
version = "0.1.0"
edition = "2021"

[dependencies]
warp = "0.3.2"
tokio = { version = "1.17.0", features = ["full"]}

tokio-postgres = {version = "0.7.5", features = ["with-serde_json-1"] }
deadpool-postgres = "0.10.2"

This impl runs afoul of warp's generic processing and privacy choices.
Other approaches run afoul of policies on global variables, or static initializers
or lazy_statics or futures or manual drops or macro processing.
I even tried a union to init a global early, then give it real values later on.

I guess you could say I'm trying to find a general way to create subsystems in
my code that each require some global state.

I'd welcome a solution to the above code,
but more so a better understanding of how a smart Rustacean should do this.

While this is frustrating, I guess I should admire the thoroughness of the compiler.

Best wishes to all!

I think you are close. I have simliar code (but with many routes etc) in r4s/mod.rs at main · kaj/r4s · GitHub . I think the main thing you need to do is that the thing you add as a filter should not be the pool, but a think you call to get the pool. So change this:

         .and(pool.clone())`

To this:

         .and(move || pool.clone())`

Thanks for the suggestion but it doesn't change the compiler errors.

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.