diff --git a/nosql_lib/redis/inc/drogon/nosql/RedisClient.h b/nosql_lib/redis/inc/drogon/nosql/RedisClient.h index 97615c0cf4..498666c519 100644 --- a/nosql_lib/redis/inc/drogon/nosql/RedisClient.h +++ b/nosql_lib/redis/inc/drogon/nosql/RedisClient.h @@ -164,26 +164,40 @@ class DROGON_EXPORT RedisClient std::string_view command, Args &&...args) { - std::shared_ptr> pro(new std::promise); - std::future f = pro->get_future(); + return execCommandSync>( + std::move(processFunc), command, std::forward(args)...); + } + + /** + * @brief Execute a redis command synchronously + * Return type can be deduced automatically in this version. + */ + template + std::invoke_result_t execCommandSync( + F &&processFunc, + std::string_view command, + Args &&...args) + { + using Ret = std::invoke_result_t; + std::promise prom; execCommandAsync( - [process = std::move(processFunc), pro](const RedisResult &result) { + [&processFunc, &prom](const RedisResult &result) { try { - pro->set_value(process(result)); + prom.set_value(processFunc(result)); } catch (...) { - pro->set_exception(std::current_exception()); + prom.set_exception(std::current_exception()); } }, - [pro](const RedisException &err) { - pro->set_exception(std::make_exception_ptr(err)); + [&prom](const RedisException &err) { + prom.set_exception(std::make_exception_ptr(err)); }, command, std::forward(args)...); - return f.get(); + return prom.get_future().get(); } /** diff --git a/nosql_lib/redis/tests/redis_test.cc b/nosql_lib/redis/tests/redis_test.cc index 552b2065c7..6a1c982545 100644 --- a/nosql_lib/redis/tests/redis_test.cc +++ b/nosql_lib/redis/tests/redis_test.cc @@ -168,11 +168,14 @@ DROGON_TEST(RedisTest) SUCCESS(); } + // 12. Test omit template parameter try { - redisClient->execCommandSync([](const RedisResult &) { return 1; }, - "del %s", - "sync_key"); + auto i = redisClient->execCommandSync( + [](const RedisResult &r) { return r.asInteger(); }, + "del %s", + "sync_key"); + MANDATE(i == 1); } catch (const RedisException &err) {