Skip to content
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

Next request timeouts after error in File upload #3194

Open
Dummerle opened this issue Nov 19, 2023 · 3 comments
Open

Next request timeouts after error in File upload #3194

Dummerle opened this issue Nov 19, 2023 · 3 comments

Comments

@Dummerle
Copy link

Current Behavior

When uploading an image or some other kind of file, but a custom extractor returns an error, the next request runs into a timeout.

Expected Behavior

Get no timeout

Possible Solution

No idea

Steps to Reproduce (for bugs)

I have this small example

use std::future::{Ready, ready};
use actix_web::{App, FromRequest, get, HttpRequest, HttpResponse, HttpServer, post, Responder};
use actix_web::error::{ErrorBadRequest};
use actix_web::web::Payload;

struct SomeFailingExtractor;
impl FromRequest for SomeFailingExtractor {
    type Error = actix_web::Error;
    type Future = Ready<Result<Self, Self::Error>>;

    fn from_request(_: &HttpRequest, _: &mut actix_web::dev::Payload) -> Self::Future {
        return ready(Err(ErrorBadRequest("Bad request")));
    }
}

#[post("/image")]
async fn upload_image(
    _: SomeFailingExtractor,
    _payload: Payload
) -> impl Responder {
    return HttpResponse::Ok().body("Uploaded");
}

#[get("/other")]
async fn other_endpoint() -> impl Responder {
    println!("Other endpoint called");
    return HttpResponse::Ok().body("Hello there");
}

#[actix_web::main]
async fn main() {
    HttpServer::new(move || {
        App::new()
            .service(upload_image)
            .service(other_endpoint)
    })
        .bind(("0.0.0.0", 8080)).expect("Error")
        .run()
        .await.expect("Error")
}

The following python script runs into the timeout. It works, if you don't use a session. The second request on /other works. The bug also occurs on a simple website

import requests

session = requests.session()
file = open("/path/to/image.png", "rb").read()

resp1 = session.post(
    "http://localhorst:8080/image",
    data=file,
    headers={
        # also happens with multipart/form-data,  image/png
        "content-type": "application/octet-stream",
    }
)

print(resp1.text)

try:
    resp2 = session.get("http://localhorst:8080/other", timeout=30)
    print(resp2.text)
except requests.exceptions.ReadTimeout:
    print("Timeout")
    resp2 = session.get("http://localhorst:8080/other", timeout=3)
    print(resp2.text) 

Context

I wanted to add an endpoint, where you can upload an image.

Your Environment

  • Rust Version (I.e, output of rustc -V): 1.74, but also doesn't work with 1.69
  • Actix Web Version: 4.4.0
  • OS: Arch Linux
@Dummerle
Copy link
Author

A temporary workaround is to disable keep_alive.

@Dummerle Dummerle changed the title Request timeout after uploading a file Next request timeouts after error in File upload Nov 21, 2023
@bublikOff
Copy link

Just bumped the same issue. One more note. If I try to upload 2.4MB image file everything FromRequest works well. If i try to upload small size image (in my case less than 100kb) it will stack on next request

@jonatansalemes
Copy link

jonatansalemes commented Apr 17, 2024

related to #3220
pr: #3221

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants