public void close() {
    isClosed = true;
    synchronized (IoTDBDataNodeAsyncClientManager.class) {
      RECEIVER_ATTRIBUTES_REF_COUNT.computeIfPresent(
          receiverAttributes,
          (attributes, refCount) -> {
            if (refCount <= 1) {
              final IClientManager<TEndPoint, AsyncPipeDataTransferServiceClient> clientManager =
                  ASYNC_PIPE_DATA_TRANSFER_CLIENT_MANAGER_HOLDER.remove(receiverAttributes);
              if (clientManager != null) {
                try {
                  clientManager.close();
                } catch (final Exception e) {
                  LOGGER.warn("Failed to close client manager.", e);
                }
              }
              return null;
            }
            return refCount - 1;
          });
    }
  }
Handshake with the target if necessary.

@param client client to handshake
@return {@code true} if the handshake is already finished, {@code false} if the handshake is
    not finished yet and finished in this method
@throws Exception if an error occurs.
iotdb-core/datanode/src/main/java/org/apache/iotdb/db/pipe/connector/client/IoTDBDataNodeAsyncClientManager.java