cpp-redis / cpp_redis

C++11 Lightweight Redis client: async, thread-safe, no dependency, pipelining, multi-platform
MIT License
720 stars 199 forks source link

Why established too many connections with server? #6

Closed pengweichu closed 5 years ago

pengweichu commented 5 years ago

Hi, I have encountered a critical issue, when I run the client and connect to redis server, it's seems the cpp_redis created around 30K connections , I have turned on the logs of cpp_redis and tacopie, the log seems no problem - please see attached the log files.

In the app_logs.txt we can see the cpp_reis and tacopie logs. In the app_lsof.log we can see the TCP connections which established from my app to redis server. I've added some logs in tacopie for log thecreate_socket_if_necessary() functions.

In the redis-server.log we can see the redis server log shows it accepted the connections.

The application run on CentOS 7.5, X64, and redis server is 4.0.11.

Please help, don't know why cause this problem, thanks in advance.

app_logs.txt app_lsof.log redis-server.log

appkins commented 5 years ago

How are you using the client? Is the the client's scope shared by every caller? I'll need to see how you're using it to provide any feedback, but I would suggest running the examples to see if you encounter the same issue.

Notice in the sentinel example:

//! Call connect with optional timeout
  //! Can put a loop around this until is_connected() returns true.
  client.connect("mymaster", [](const std::string& host, std::size_t port, cpp_redis::connect_state status) {
    if (status == cpp_redis::connect_state::dropped) {
      std::cout << "client disconnected from " << host << ":" << port << std::endl;
    }
  },
    0, -1, 5000);

The connection is invoked prior to the while loop, and the client's context is shared for each iteration. The expected behavior in this example is that the connection should be established only once. If connect is invoked more than once, it would be expected that the client would connect on each iteration.

It is also important to note that requests are pipelined and will not execute until committed. Invoking a member function of the client will add the redis command to the pipeline and execute upon commit.