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

Ability to detect client disconnection #2190

Open
dkalinowski opened this issue Oct 22, 2024 · 8 comments
Open

Ability to detect client disconnection #2190

dkalinowski opened this issue Oct 22, 2024 · 8 comments

Comments

@dkalinowski
Copy link

Is your feature request related to a problem? Please describe.
In our project we are trying to use Drogon for very long requests (up to 10 minutes long). While it is possible to detect client disconnection when using async streaming responses (by checking stream->send() return value), it is impossible to detect client disconnection early using standard response. It makes it impossible to stop long running workloads and free server resources upon client disconnection.

Describe the solution you'd like
It would be nice to be able to install client disconnection callback. We could use the callback to execute workload stopping mechanism on our end.

Describe alternatives you've considered
There is no alternative I know of.

@fantasy-peak
Copy link
Contributor

#2191

@dkalinowski
Copy link
Author

#2191

This PR added ability to check the connection state in case we have access to http request object.
The issue is related to scenario when there is no access to request object, during streaming, example: https://github.com/drogonframework/drogon/blob/master/examples/async_stream/main.cc#L13-L24

@fantasy-peak

@nqf
Copy link

nqf commented Oct 30, 2024

    app().registerHandler(
        "/stream",
        [](const HttpRequestPtr & ptr,
           std::function<void(const HttpResponsePtr &)> &&callback) {
            std::thread([=] {
                        while (true)
                        {
                            std::lock_guard lk(mm);
                            std::cout <<"aaaaaaaaaa:" << std::boolalpha
                                      << ptr->connected() << std::endl;
                            std::this_thread::sleep_for(
                                std::chrono::seconds(2));
                        }
            }).detach();

➜  build git:(check-conn) ✗ ./examples/async_stream
20241030 01:19:13.772283 UTC 11147 INFO  Server running on 127.0.0.1:8848 - main.cc:100
20241030 01:19:16.940796 UTC 11148 DEBUG [makeHeaderString] send stream with transfer-encoding chunked - HttpResponseImpl.cc:547
aaaaaaaaaa:true
aaaaaaaaaa:true
aaaaaaaaaa:true

@nqf
Copy link

nqf commented Oct 30, 2024

You can still use HttpRequestPtr

@dkalinowski
Copy link
Author

dkalinowski commented Nov 4, 2024

@nqf even if you can check connection status the way you described, we still have no way to get disconnection information when workload is blocking. The example would be running your example with no while (true), but single blocking operation.
The solution would be to have an ability to install disconnection callback in which the caller could define logic to stop the blocking workload.

What do you think about it?

@fantasy-peak
Copy link
Contributor

Do you mean that drogon's worker thread is blocked?

@dkalinowski
Copy link
Author

Yes, consider the example be slightly modified:

    app().registerHandler(
        "/stream",
        [](const HttpRequestPtr & ptr,
           std::function<void(const HttpResponsePtr &)> &&callback) {
            std::thread([=] {
              my_workload->run(); // blocking for 10 minutes
            }).detach();

If we would be able to set up disconnection callback, we could run my_workload->stop() and cancel it to save resources

@fantasy-peak
Copy link
Contributor

add a new mr

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

4 participants
@nqf @dkalinowski @fantasy-peak and others