use of org.jboss.netty.channel.ChannelFuture in project load-balancer by RestComm.
the class HttpRequestHandler method writeStatisticResponse.
private void writeStatisticResponse(MessageEvent e) {
GsonBuilder builder = new GsonBuilder();
Gson gson = builder.setPrettyPrinting().create();
JsonElement je = gson.toJsonTree(new StatisticObject(balancerRunner));
JsonObject jo = new JsonObject();
jo.add("Metrics", je);
String output = jo.toString();
HttpResponse response = new DefaultHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.OK);
response.setHeader(HttpHeaders.Names.CONTENT_TYPE, APPLICATION_JSON);
ChannelBuffer buf = ChannelBuffers.copiedBuffer(output, Charset.forName("UTF-8"));
response.setContent(buf);
ChannelFuture future = e.getChannel().write(response);
future.addListener(ChannelFutureListener.CLOSE);
}
use of org.jboss.netty.channel.ChannelFuture in project load-balancer by RestComm.
the class HttpRequestHandler method writeResponse.
private void writeResponse(MessageEvent e, HttpResponseStatus status, String responseString) {
// Convert the response content to a ChannelBuffer.
ChannelBuffer buf = ChannelBuffers.copiedBuffer(responseString, Charset.forName("UTF-8"));
// Decide whether to close the connection or not.
boolean close = HttpHeaders.Values.CLOSE.equalsIgnoreCase(request.getHeader(HttpHeaders.Names.CONNECTION)) || request.getProtocolVersion().equals(HttpVersion.HTTP_1_0) && !HttpHeaders.Values.KEEP_ALIVE.equalsIgnoreCase(request.getHeader(HttpHeaders.Names.CONNECTION));
// Build the response object.
HttpResponse response = new DefaultHttpResponse(HttpVersion.HTTP_1_1, status);
response.setContent(buf);
response.setHeader(HttpHeaders.Names.CONTENT_TYPE, "text/plain; charset=UTF-8");
if (!close) {
// There's no need to add 'Content-Length' header
// if this is the last response.
response.setHeader(HttpHeaders.Names.CONTENT_LENGTH, String.valueOf(buf.readableBytes()));
}
String cookieString = request.getHeader(HttpHeaders.Names.COOKIE);
if (cookieString != null) {
CookieDecoder cookieDecoder = new CookieDecoder();
Set<Cookie> cookies = cookieDecoder.decode(cookieString);
if (!cookies.isEmpty()) {
// Reset the cookies if necessary.
CookieEncoder cookieEncoder = new CookieEncoder(true);
for (Cookie cookie : cookies) {
cookieEncoder.addCookie(cookie);
}
response.addHeader(HttpHeaders.Names.SET_COOKIE, cookieEncoder.encode());
}
}
// Write the response.
ChannelFuture future = null;
if (status.equals(HttpResponseStatus.SERVICE_UNAVAILABLE) || status.equals(HttpResponseStatus.LOCKED))
future = e.getChannel().write(buf);
else
future = e.getChannel().write(response);
// Close the connection after the write operation is done if necessary.
if (close) {
future.addListener(ChannelFutureListener.CLOSE);
}
}
use of org.jboss.netty.channel.ChannelFuture in project load-balancer by RestComm.
the class HttpRequestHandler method sendRedirectResponse.
private void sendRedirectResponse(MessageEvent e, HttpRequest request) {
HttpResponse response = new DefaultHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.FOUND);
String host = request.getHeader("Host");
host = host.replace(balancerRunner.balancerContext.lbConfig.getHttpConfiguration().getHttpPort().toString(), balancerRunner.balancerContext.lbConfig.getHttpConfiguration().getHttpsPort().toString());
response.setHeader("Location", "https://" + host + request.getUri());
ChannelFuture future = e.getChannel().write(response);
future.addListener(ChannelFutureListener.CLOSE);
}
use of org.jboss.netty.channel.ChannelFuture in project load-balancer by RestComm.
the class HttpRequestHandler method writeInfoResponse.
private void writeInfoResponse(MessageEvent e) {
GsonBuilder builder = new GsonBuilder();
Gson gson = builder.setPrettyPrinting().create();
JsonElement je = gson.toJsonTree(new NodesInfoObject(balancerRunner));
JsonObject jo = new JsonObject();
jo.add("Nodes info", je);
String output = jo.toString();
HttpResponse response = new DefaultHttpResponse(HttpVersion.HTTP_1_1, HttpResponseStatus.OK);
ChannelBuffer buf = ChannelBuffers.copiedBuffer(output, Charset.forName("UTF-8"));
response.setContent(buf);
ChannelFuture future = e.getChannel().write(response);
future.addListener(ChannelFutureListener.CLOSE);
}
use of org.jboss.netty.channel.ChannelFuture in project load-balancer by RestComm.
the class HttpRequestHandler method handleHttpRequest.
private void handleHttpRequest(ChannelHandlerContext ctx, final MessageEvent e) throws Exception {
String currAddress = e.getRemoteAddress().toString();
semaphore = semaphoreMap.get(currAddress);
if (semaphore == null) {
semaphore = new Semaphore(1);
Semaphore tempSemaphore = semaphoreMap.putIfAbsent(currAddress, semaphore);
if (tempSemaphore != null)
semaphore = tempSemaphore;
}
try {
semaphore.acquire();
} catch (InterruptedException ex) {
}
if (!readingChunks && e.getMessage() instanceof HttpRequest) {
request = (HttpRequest) e.getMessage();
if (logger.isDebugEnabled()) {
logger.debug("Request URI accessed: " + request.getUri() + " channel " + e.getChannel());
}
if (HttpChannelAssociations.urlRewriteFilter != null)
HttpChannelAssociations.urlRewriteFilter.doFilter(request, e);
AdvancedChannel currentAC = HttpChannelAssociations.channels.get(new AdvancedChannel(e.getChannel()));
Channel associatedChannel = null;
if (currentAC != null)
associatedChannel = currentAC.getChannel();
InvocationContext invocationContext = balancerRunner.getLatestInvocationContext();
// SIPNode node = null;
try {
// TODO: If WebSocket request, choose a NODE that is able to
// handle WebSocket requests (has a websocket connector)
node = invocationContext.balancerAlgorithm.processHttpRequest(request);
} catch (Exception ex) {
StringWriter sw = new StringWriter();
ex.printStackTrace(new PrintWriter(sw));
logger.warn("Problem in balancer algorithm", ex);
writeResponse(e, HttpResponseStatus.INTERNAL_SERVER_ERROR, "Load Balancer Error: Exception in the balancer algorithm:\n" + sw.toString());
return;
}
if (node == null) {
if (logger.isInfoEnabled()) {
logger.info("Service unavailable. No server is available.");
}
writeResponse(e, HttpResponseStatus.SERVICE_UNAVAILABLE, IOUtils.toString(this.getClass().getClassLoader().getResourceAsStream("500.html")));
return;
}
if (associatedChannel != null && associatedChannel.isConnected()) {
semaphore.release();
associatedChannel.write(request);
} else {
e.getChannel().getCloseFuture().addListener(new ChannelFutureListener() {
public void operationComplete(ChannelFuture arg0) throws Exception {
closeChannelPair(arg0.getChannel());
}
});
// Start the connection attempt.
ChannelFuture future = null;
Set<String> headers = request.getHeaderNames();
if (headers.contains("Sec-WebSocket-Protocol")) {
if (request.getHeader("Sec-WebSocket-Protocol").equalsIgnoreCase("sip")) {
if (logger.isDebugEnabled()) {
logger.debug("New SIP over WebSocket request. WebSocket uri: " + request.getUri());
logger.debug("Dispatching WebSocket request to node: " + node.getIp() + " port: " + node.getProperties().get("wsPort"));
}
wsrequest = true;
wsVersion = request.getHeader(Names.SEC_WEBSOCKET_VERSION);
websocketServerPipelineFactory = new WebsocketModifyClientPipelineFactory();
future = HttpChannelAssociations.inboundBootstrap.connect(new InetSocketAddress(node.getIp(), Integer.parseInt(node.getProperties().get("wsPort"))));
}
} else {
if (!isSecured) {
if (logger.isDebugEnabled()) {
logger.debug("Dispatching HTTP request to node: " + node.getIp() + " port: " + node.getProperties().get("httpPort"));
}
future = HttpChannelAssociations.inboundBootstrap.connect(new InetSocketAddress(node.getIp(), Integer.parseInt(node.getProperties().get("httpPort"))));
} else {
if (logger.isDebugEnabled()) {
logger.debug("Dispatching HTTPS request to node: " + node.getIp() + " port: " + node.getProperties().get("sslPort"));
}
future = HttpChannelAssociations.inboundSecureBootstrap.connect(new InetSocketAddress(node.getIp(), Integer.parseInt(node.getProperties().get("sslPort"))));
}
}
future.addListener(new ChannelFutureListener() {
public void operationComplete(ChannelFuture arg0) throws Exception {
Channel channel = arg0.getChannel();
if (pattern != null && pattern.matcher(request.getUri()).find()) {
logger.info("request : " + request.getUri() + " matches to pattern : " + pattern);
HttpChannelAssociations.channels.put(new AdvancedChannel(e.getChannel(), true), new AdvancedChannel(channel, true));
HttpChannelAssociations.channels.put(new AdvancedChannel(channel, true), new AdvancedChannel(e.getChannel(), true));
} else {
HttpChannelAssociations.channels.put(new AdvancedChannel(e.getChannel(), false), new AdvancedChannel(channel, false));
HttpChannelAssociations.channels.put(new AdvancedChannel(channel, false), new AdvancedChannel(e.getChannel(), false));
}
if (request.isChunked()) {
readingChunks = true;
}
semaphore.release();
channel.write(request);
if (wsrequest) {
if (logger.isDebugEnabled()) {
logger.debug("This is a websocket request, changing the pipeline");
}
// Modify the Client Pipeline - Phase 1
ChannelPipeline p = channel.getPipeline();
websocketServerPipelineFactory.upgradeClientPipelineFactoryPhase1(p, wsVersion);
}
channel.getCloseFuture().addListener(new ChannelFutureListener() {
public void operationComplete(ChannelFuture arg0) throws Exception {
closeChannelPair(arg0.getChannel());
}
});
}
});
}
} else {
HttpChunk chunk = (HttpChunk) e.getMessage();
if (chunk.isLast()) {
readingChunks = false;
}
semaphore.release();
HttpChannelAssociations.channels.get(new AdvancedChannel(e.getChannel())).getChannel().write(chunk);
if (logger.isDebugEnabled())
logger.debug("Send chunked request from : " + e.getChannel().getLocalAddress() + " to : " + e.getChannel().getRemoteAddress() + " capacity : " + chunk.getContent().capacity());
}
}
Aggregations