Package com.aphyr.riemann.client

Source Code of com.aphyr.riemann.client.TcpHandler

package com.aphyr.riemann.client;

import java.net.InetSocketAddress;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.Executors;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.atomic.*;
import java.net.*;
import java.io.*;
import org.jboss.netty.util.HashedWheelTimer;
import org.jboss.netty.util.Timer;
import org.jboss.netty.channel.*;
import org.jboss.netty.channel.group.*;
import org.jboss.netty.handler.codec.oneone.*;
import org.jboss.netty.handler.codec.protobuf.*;
import org.jboss.netty.handler.codec.frame.*;
import org.jboss.netty.bootstrap.ClientBootstrap;
import org.jboss.netty.handler.execution.ExecutionHandler;
import org.jboss.netty.handler.execution.OrderedMemoryAwareThreadPoolExecutor;
import com.aphyr.riemann.Proto.Msg;
import java.util.concurrent.atomic.AtomicBoolean;
import java.util.concurrent.LinkedBlockingQueue;

public class TcpHandler extends SimpleChannelHandler {
  public final WriteQueue queue = new WriteQueue();

  public final AtomicInteger maxInflightRequests;

  // The last error used to fulfill outstanding promises.
  public volatile IOException lastError =
    new IOException("Channel closed.");

  public final ExceptionReporter exceptionReporter;

  public TcpHandler(final ExceptionReporter exceptionReporter,
                    final AtomicInteger maxInflightRequests) {
    this.exceptionReporter = exceptionReporter;
    this.maxInflightRequests = maxInflightRequests;
  }

  // When we open, add our channel to the channel group.
  @Override
  public void channelOpen(ChannelHandlerContext c, ChannelStateEvent e) throws Exception {
    super.channelOpen(c, e);
  }

  // When we connect, save the channel so we can write to it.
  @Override
  public void channelConnected(ChannelHandlerContext c,
                               ChannelStateEvent e) throws Exception {
    queue.open();
    super.channelConnected(c, e);
  }

  @Override
  public void channelClosed(ChannelHandlerContext c,
                            ChannelStateEvent e) throws Exception {
    // Mark the queue as closed.
    queue.close();

    super.channelClosed(c, e);
  }

  // We receive a Write, and pass the Write's message downstream, enqueuing the
  // corresponding promise when the write completes.
  public void handleDownstream(ChannelHandlerContext ctx, ChannelEvent e)
    throws Exception {

    // Pass through anything that isn't a message event
    if (!(e instanceof MessageEvent)) {
      ctx.sendDownstream(e);
      return;
    }

    // Bounce back anything that isn't a Write.
    final MessageEvent me = (MessageEvent) e;
    if (!(me.getMessage() instanceof Write)) {
     ctx.sendUpstream(me);
      return;
    }

    // Destructure the write
    final Write write = (Write) me.getMessage();
    final Msg message = write.message;
    final Promise promise = write.promise;

    // If we're over capacity, abort the promise and drop the message here.
    if (maxInflightRequests.get() <= queue.size) {
      promise.deliver(
          new OverloadedException("Too many requests in flight")
      );
      return;
    }

    // When the message event is written...
    me.getFuture().addListener(new ChannelFutureListener() {
      // Enqueue the corresponding promise.
      public void operationComplete(ChannelFuture future) throws Exception {
        if (future.isSuccess()) {
          queue.put(promise);
        } else if (future.getCause() != null) {
          promise.deliver(
            new IOException("Write failed.", future.getCause()));
        } else {
          promise.deliver(new IOException("Write failed."));
        }
      }
    });

    // Send the message event downstream
    Channels.write(ctx, me.getFuture(), message);
  }

  // When messages are received, deliver them to the next queued promise.
  @Override
  public void messageReceived(ChannelHandlerContext c, MessageEvent e) {
    Msg message = (Msg) e.getMessage();
    queue.take().deliver(message);
  }

  // Log exceptions and close.
  @Override
  public void exceptionCaught(ChannelHandlerContext c, ExceptionEvent e) {
    try {
      exceptionReporter.reportException(e.getCause());
    } catch (final Exception ee) {
      // Oh well
    }

    e.getChannel().close();
  }
}
TOP

Related Classes of com.aphyr.riemann.client.TcpHandler

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.