Created
November 19, 2020 17:25
-
-
Save nnmm/977ba79767cab6c936e38ffdcdf4cd78 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Straight-line version | |
// ===================== | |
// I imagine could be as easy as | |
auto future_a = client_a->async_send_request(); | |
auto future_b = client_b->async_send_request(); | |
auto status_a = future_a.wait_for(timeout); | |
auto status_b = future_b.wait_for(0ms); | |
if (status_a == ready && status_b == ready) { | |
auto response = std::make_tuple(future_a.get(), future_b.get()); | |
} | |
// Callback version | |
// ================ | |
// Here you'd need to synchronize with some shared state. Even assuming that a timeout argument is available and the callbacks don't run concurrently, it's not easy. I'm only 50% sure my solution works: | |
enum class result_status { waiting_both, waiting_for_a, waiting_for_b, errored }; | |
// Needs to persist after requesting function returns, so shared_ptr. | |
auto status = std::make_shared<result_status>(result_status::waiting_for_both); | |
auto response_a = std::make_shared<A::Response>(); | |
auto response_b = std::make_shared<B::Response>(); | |
client_a->async_send_request(timeout, [status, response_a, response_b](auto future_a){ | |
try { | |
*response_a = future_a.get(); | |
} catch (...) { | |
*status = result_status::errored; | |
return; | |
} | |
if (*status == result_status::waiting_for_a) { | |
auto response = std::make_tuple(*response_a, *response_b); // done! | |
} else if (*status == result_status::waiting_for_both) { | |
*status = result_status::waiting_for_b; | |
} | |
}); | |
client_b->async_send_request(timeout, [status, response_a, response_b](auto future_b){ | |
try { | |
*response_b = future_b.get(); | |
} catch (...) { | |
*status = result_status::errored; | |
return; | |
} | |
if (*status == result_status::waiting_for_b) { | |
auto response = std::make_tuple(*response_a, *response_b); // done! | |
} else if (*status == result_status::waiting_for_both) { | |
*status = result_status::waiting_for_a; | |
} | |
}); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment