-
Notifications
You must be signed in to change notification settings - Fork 1.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
PoolConnection::drop
: don't wait until inside the future to call .float()
#1396
Comments
I experimented a little, and found a working version |
This issue is very similar to #1389 in that it's caused by the runtime going away while we're trying to spawn a task that's important to SQLx functioning correctly. In this case, it's due to waiting to call Because you're using a single-threaded runtime, the task we spawn in If you were using a multi-threaded runtime, you'd probably see similar panics to #1389. I need to fix this so that However, in the meantime, you probably don't want to be spawning a new runtime every time you want to run something in the background. You could instead use use actix_web::web::Data;
use tokio::runtime::Handle;
pub type TokioRuntime = Data<Handle>;
#[tokio::main(flavor = "multi_threaded")]
async fn main() {
let multithreaded_tokio = Data::new(Handle::current());
// do async setup stuff, like opening a `PgPool` and running migrations...
// `actix_main()` will quit on Ctrl-C
tokio::task::block_in_place(|| actix_main(multithreaded_tokio));
}
#[actix_web::main]
async fn actix_main(multithreaded_tokio: TokioRuntime) {
// now in the Actix runtime
HttpServer::new(move || {
App::new()
.app_data(multithreaded_tokio)
.service(handle_request)
})
.bind("0.0.0.0:8080")
.unwrap()
.run()
.await
.unwrap();
}
#[get("/v1/some/route")]
async fn handle_request(
tokio: TokioRuntime,
) -> HttpResponse {
tokio.spawn(async move { /* some long-running async operation */ });
HttpResponse::Ok().finish()
} (*): I keep forgetting that Actix-web is technically multithreaded in that it spawns a set of threads on start up, each with an Actix runtime, and then dispatches new connections to the threads. Spawned tasks in a given Actix runtime, however, will always execute on the same thread, and no work-stealing occurs between threads, so you could end up in a situation where one runtime is loaded down with more tasks than the others. |
PoolConnection::drop
: don't wait until inside the future to call .float()
Hi @abonander , there is something I can't figure out in the pattern you've proposed, I wish you could kindly help me understand. I've read in other posts that tokio runtimes can't be nested. It will panic when starting and dropping. In your pattern, |
It's because |
I'm using sqlx with actix_web and postgresql, I found a problem when trying to spawn a custom thread, I made a sample project to describe the issue.
There are 3 apis in the server.
/test
and/nostuck
works well,/stuck
is problematic. I can only query this apiDB_MAXCONN
(defined in .env) times, after that sqlx will get stuck atpool.begin
, even/nostuck
will get stuck too./test
shows that actix_web is working well.I don't know what's wrong with
/stuck
, it seems that in this api the connection isn't returned to the pool. What I'm trying to do in this api is I want to do something background without blocking the response,jh.join
on line 130 is only there to demonstrate the problem, I won't join the thread in actual code.The text was updated successfully, but these errors were encountered: