@Override
  public void process(CommandProcessorContext ctx) {
    PullSpecificMessageCommand reqCmd = (PullSpecificMessageCommand) ctx.getCommand();
    long correlationId = reqCmd.getHeader().getCorrelationId();
    String topic = reqCmd.getTopic();
    int partition = reqCmd.getPartition();
    List<Offset> offsets = reqCmd.getOffsets();

    try {
      Lease lease = m_leaseContainer.acquireLease(topic, partition, m_config.getSessionId());
      if (lease != null) {
        List<TppConsumerMessageBatch> batches =
            m_messageQueueManager.findMessagesByOffsets( //
                topic, partition, offsets);
        if (!batches.isEmpty()) {
          PullMessageResultCommandV2 cmd = new PullMessageResultCommandV2();
          cmd.setBrokerAccepted(true);
          cmd.addBatches(batches);
          cmd.getHeader().setCorrelationId(correlationId);
          ctx.getChannel().writeAndFlush(cmd);
          return;
        }
      } else {
        log.debug(
            "No broker lease to handle pull message cmd. [op-id: {}] {} {}",
            correlationId,
            topic,
            partition);
      }
    } catch (Exception e) {
      log.debug(
          "Handle pull message reqeust failed. [op-id: {}] {} {}",
          correlationId,
          topic,
          partition,
          e);
    }
    PullMessageResultCommandV2 cmd = new PullMessageResultCommandV2();
    cmd.setBrokerAccepted(false);
    cmd.getHeader().setCorrelationId(correlationId);
    ctx.getChannel().writeAndFlush(cmd);
  }
  @Override
  public void process(final CommandProcessorContext ctx) {
    SendMessageCommandV3 reqCmd = (SendMessageCommandV3) ctx.getCommand();

    Lease lease =
        m_leaseContainer.acquireLease(
            reqCmd.getTopic(), reqCmd.getPartition(), m_config.getSessionId());

    if (m_metaService.findTopicByName(reqCmd.getTopic()) != null) {
      if (lease != null) {
        if (log.isDebugEnabled()) {
          log.debug(
              "Send message reqeust arrived(topic={}, partition={}, msgCount={})",
              reqCmd.getTopic(),
              reqCmd.getPartition(),
              reqCmd.getMessageCount());
        }

        logElapseToCat(reqCmd);

        // FIXME if dumper's queue is full, reject it.
        writeAck(ctx, true);

        Map<Integer, MessageBatchWithRawData> rawBatches = reqCmd.getMessageRawDataBatches();

        bizLog(ctx, rawBatches, reqCmd.getPartition());

        final SendMessageResultCommand result =
            new SendMessageResultCommand(reqCmd.getMessageCount());
        result.correlate(reqCmd);

        FutureCallback<Map<Integer, Boolean>> completionCallback =
            new AppendMessageCompletionCallback(result, ctx, reqCmd.getTopic());

        for (Map.Entry<Integer, MessageBatchWithRawData> entry : rawBatches.entrySet()) {
          MessageBatchWithRawData batch = entry.getValue();
          Tpp tpp =
              new Tpp(reqCmd.getTopic(), reqCmd.getPartition(), entry.getKey() == 0 ? true : false);
          try {
            ListenableFuture<Map<Integer, Boolean>> future =
                m_queueManager.appendMessageAsync(
                    tpp, batch, m_systemClockService.now() + reqCmd.getTimeout());

            if (future != null) {
              Futures.addCallback(future, completionCallback);
            }
          } catch (Exception e) {
            log.error("Failed to append messages async.", e);
          }
        }

        return;

      } else {
        if (log.isDebugEnabled()) {
          log.debug(
              "No broker lease to handle client send message reqeust(topic={}, partition={})",
              reqCmd.getTopic(),
              reqCmd.getPartition());
        }
      }
    } else {
      if (log.isDebugEnabled()) {
        log.debug("Topic {} not found", reqCmd.getTopic());
      }
    }

    writeAck(ctx, false);
    reqCmd.release();
  }