/** * * @file RedisClientImpl.h * @author An Tao * * Copyright 2018, An Tao. All rights reserved. * https://github.com/an-tao/drogon * Use of this source code is governed by a MIT license * that can be found in the License file. * * Drogon * */ #pragma once #include "RedisConnection.h" #include "RedisSubscriberImpl.h" #include "SubscribeContext.h" #include #include #include #include #include #include #include namespace drogon { namespace nosql { class RedisConnection; using RedisConnectionPtr = std::shared_ptr; class RedisClientImpl final : public RedisClient, public trantor::NonCopyable, public std::enable_shared_from_this { public: RedisClientImpl(const trantor::InetAddress &serverAddress, size_t numberOfConnections, std::string username = "", std::string password = "", unsigned int db = 0); void execCommandAsync(RedisResultCallback &&resultCallback, RedisExceptionCallback &&exceptionCallback, std::string_view command, ...) noexcept override; ~RedisClientImpl() override; std::shared_ptr newSubscriber() noexcept override; RedisTransactionPtr newTransaction() noexcept(false) override { std::promise prom; auto f = prom.get_future(); newTransactionAsync([&prom](const RedisTransactionPtr &transPtr) { prom.set_value(transPtr); }); auto trans = f.get(); if (!trans) { throw RedisException( RedisErrorCode::kTimeout, "Timeout, no connection available for transaction"); } return trans; } void newTransactionAsync( const std::function &callback) override; void setTimeout(double timeout) override { timeout_ = timeout; } void init(); void closeAll() override; private: trantor::EventLoopThreadPool loops_; std::mutex connectionsMutex_; std::unordered_set connections_; std::vector readyConnections_; size_t connectionPos_{0}; const trantor::InetAddress serverAddr_; const std::string username_; const std::string password_; const unsigned int db_; const size_t numberOfConnections_; double timeout_{-1.0}; std::list>> tasks_; RedisConnectionPtr newConnection(trantor::EventLoop *loop); RedisConnectionPtr newSubscribeConnection( trantor::EventLoop *loop, const std::shared_ptr &subscriber); std::shared_ptr makeTransaction( const RedisConnectionPtr &connPtr); void handleNextTask(const RedisConnectionPtr &connPtr); void execCommandAsyncWithTimeout(std::string_view command, RedisResultCallback &&resultCallback, RedisExceptionCallback &&exceptionCallback, va_list ap); }; } // namespace nosql } // namespace drogon