Implemented the localtime client/server example - yay

This commit is contained in:
Trustin Lee 2009-01-07 04:38:05 +00:00
parent d1838f4af7
commit b0f39dc687
8 changed files with 632 additions and 63 deletions

View File

@ -0,0 +1,124 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2008, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import java.net.InetSocketAddress;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Iterator;
import java.util.List;
import java.util.concurrent.Executors;
import org.jboss.netty.bootstrap.ClientBootstrap;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelFactory;
import org.jboss.netty.channel.ChannelFuture;
import org.jboss.netty.channel.socket.nio.NioClientSocketChannelFactory;
/**
* Sends a list of continent/city pairs to a {@link LocalTimeServer} to
* get the local times of the specified cities.
*
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
*
* @version $Rev$, $Date$
*/
public class LocalTimeClient {
public static void main(String[] args) throws Exception {
// Print usage if necessary.
if (args.length < 3) {
printUsage();
return;
}
// Parse options.
String host = args[0];
int port = Integer.parseInt(args[1]);
Collection<String> cities = parseCities(args, 2);
if (cities == null) {
return;
}
// Set up.
ChannelFactory factory =
new NioClientSocketChannelFactory(
Executors.newCachedThreadPool(),
Executors.newCachedThreadPool());
ClientBootstrap bootstrap = new ClientBootstrap(factory);
bootstrap.setPipelineFactory(new LocalTimeClientPipelineFactory());
bootstrap.setOption("tcpNoDelay", true);
bootstrap.setOption("keepAlive", true);
// Make a new connection.
ChannelFuture connectFuture =
bootstrap.connect(new InetSocketAddress(host, port));
// Wait until the connection is made successfully.
Channel channel = connectFuture.awaitUninterruptibly().getChannel();
// Get the handler instance to initiate the request.
LocalTimeClientHandler handler =
channel.getPipeline().get(LocalTimeClientHandler.class);
// Request and get the response.
List<String> response = handler.getLocalTimes(cities);
// Close the connection.
channel.close().awaitUninterruptibly();
// Shut down all thread pools to exit.
factory.releaseExternalResources();
// Print the response at last but not least.
Iterator<String> i1 = cities.iterator();
Iterator<String> i2 = response.iterator();
while (i1.hasNext()) {
System.out.format("%28s: %s%n", i1.next(), i2.next());
}
}
private static void printUsage() {
System.err.println(
"Usage: " + LocalTimeClient.class.getSimpleName() +
" <host> <port> <continent/city_name> ...");
System.err.println(
"Example: " + LocalTimeClient.class.getSimpleName() +
" localhost 8080 America/New_York Asia/Seoul");
}
private static List<String> parseCities(String[] args, int offset) {
List<String> cities = new ArrayList<String>();
for (int i = offset; i < args.length; i ++) {
if (!args[i].matches("^[_A-Za-z]+/[_A-Za-z]+$")) {
System.err.println("Syntax error: '" + args[i] + "'");
printUsage();
return null;
}
cities.add(args[i].trim());
}
return cities;
}
}

View File

@ -0,0 +1,134 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2008, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Formatter;
import java.util.List;
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelEvent;
import org.jboss.netty.channel.ChannelHandlerContext;
import org.jboss.netty.channel.ChannelPipelineCoverage;
import org.jboss.netty.channel.ChannelStateEvent;
import org.jboss.netty.channel.ExceptionEvent;
import org.jboss.netty.channel.MessageEvent;
import org.jboss.netty.channel.SimpleChannelHandler;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Continent;
import org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTime;
import org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTimes;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Location;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Locations;
/**
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
*
* @version $Rev$, $Date$
*/
@ChannelPipelineCoverage("one")
public class LocalTimeClientHandler extends SimpleChannelHandler {
private static final Logger logger = Logger.getLogger(
LocalTimeClientHandler.class.getName());
// Stateful properties
private volatile Channel channel;
private final BlockingQueue<LocalTimes> answer = new LinkedBlockingQueue<LocalTimes>();
public List<String> getLocalTimes(Collection<String> cities) {
Locations.Builder builder = Locations.newBuilder();
for (String c: cities) {
String[] components = c.split("/");
builder.addLocation(Location.newBuilder().
setContinent(Continent.valueOf(components[0].toUpperCase())).
setCity(components[1]).build());
}
channel.write(builder.build());
LocalTimes localTimes;
for (;;) {
try {
localTimes = answer.take();
break;
} catch (InterruptedException e) {
// Ignore.
}
}
List<String> result = new ArrayList<String>();
for (LocalTime lt: localTimes.getLocalTimeList()) {
result.add(
new Formatter().format(
"%4d-%02d-%02d %02d:%02d:%02d %s",
lt.getYear(),
lt.getMonth(),
lt.getDayOfMonth(),
lt.getHour(),
lt.getMinute(),
lt.getSecond(),
lt.getDayOfWeek().name()).toString());
}
return result;
}
@Override
public void handleUpstream(
ChannelHandlerContext ctx, ChannelEvent e) throws Exception {
if (e instanceof ChannelStateEvent) {
logger.info(e.toString());
}
super.handleUpstream(ctx, e);
}
@Override
public void channelOpen(ChannelHandlerContext ctx, ChannelStateEvent e)
throws Exception {
channel = e.getChannel();
super.channelOpen(ctx, e);
}
@Override
public void messageReceived(
ChannelHandlerContext ctx, final MessageEvent e) {
answer.offer((LocalTimes) e.getMessage());
}
@Override
public void exceptionCaught(
ChannelHandlerContext ctx, ExceptionEvent e) {
logger.log(
Level.WARNING,
"Unexpected exception from downstream.",
e.getCause());
e.getChannel().close();
}
}

View File

@ -0,0 +1,52 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2009, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import static org.jboss.netty.channel.Channels.*;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.channel.ChannelPipelineFactory;
import org.jboss.netty.handler.codec.frame.LengthFieldBasedFrameDecoder;
import org.jboss.netty.handler.codec.frame.LengthFieldPrepender;
import org.jboss.netty.handler.codec.protobuf.ProtobufDecoder;
import org.jboss.netty.handler.codec.protobuf.ProtobufEncoder;
/**
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
* @version $Rev$, $Date$
*/
public class LocalTimeClientPipelineFactory implements ChannelPipelineFactory {
public ChannelPipeline getPipeline() throws Exception {
ChannelPipeline p = pipeline();
p.addLast("frameDecoder", new LengthFieldBasedFrameDecoder(1048576, 0, 4, 0, 4));
p.addLast("protobufDecoder", new ProtobufDecoder(LocalTimeProtocol.LocalTimes.getDefaultInstance()));
p.addLast("frameEncoder", new LengthFieldPrepender(4));
p.addLast("protobufEncoder", new ProtobufEncoder());
p.addLast("handler", new LocalTimeClientHandler());
return p;
}
}

View File

@ -77,6 +77,68 @@ public final class LocalTimeProtocol {
}
}
public static enum DayOfWeek {
SUNDAY(0, 1),
MONDAY(1, 2),
TUESDAY(2, 3),
WEDNESDAY(3, 4),
THURSDAY(4, 5),
FRIDAY(5, 6),
SATURDAY(6, 7),
;
public final int getNumber() { return value; }
public static DayOfWeek valueOf(int value) {
switch (value) {
case 1: return SUNDAY;
case 2: return MONDAY;
case 3: return TUESDAY;
case 4: return WEDNESDAY;
case 5: return THURSDAY;
case 6: return FRIDAY;
case 7: return SATURDAY;
default: return null;
}
}
public final com.google.protobuf.Descriptors.EnumValueDescriptor
getValueDescriptor() {
return getDescriptor().getValues().get(index);
}
public final com.google.protobuf.Descriptors.EnumDescriptor
getDescriptorForType() {
return getDescriptor();
}
public static final com.google.protobuf.Descriptors.EnumDescriptor
getDescriptor() {
return org.jboss.netty.example.localtime.LocalTimeProtocol.getDescriptor().getEnumTypes().get(1);
}
private static final DayOfWeek[] VALUES = {
SUNDAY, MONDAY, TUESDAY, WEDNESDAY, THURSDAY, FRIDAY, SATURDAY,
};
public static DayOfWeek valueOf(
com.google.protobuf.Descriptors.EnumValueDescriptor desc) {
if (desc.getType() != getDescriptor()) {
throw new java.lang.IllegalArgumentException(
"EnumValueDescriptor is not for this type.");
}
return VALUES[desc.getIndex()];
}
private final int index;
private final int value;
private DayOfWeek(int index, int value) {
this.index = index;
this.value = value;
}
static {
org.jboss.netty.example.localtime.LocalTimeProtocol.getDescriptor();
}
}
public static final class Location extends
com.google.protobuf.GeneratedMessage {
// Use Location.newBuilder() to construct.
@ -708,23 +770,17 @@ public final class LocalTimeProtocol {
public boolean hasMonth() { return hasMonth; }
public int getMonth() { return month_; }
// required uint32 week = 3;
private boolean hasWeek;
private int week_ = 0;
public boolean hasWeek() { return hasWeek; }
public int getWeek() { return week_; }
// required uint32 dayOfMonth = 4;
private boolean hasDayOfMonth;
private int dayOfMonth_ = 0;
public boolean hasDayOfMonth() { return hasDayOfMonth; }
public int getDayOfMonth() { return dayOfMonth_; }
// required uint32 dayOfWeek = 5;
// required .org.jboss.netty.example.localtime.DayOfWeek dayOfWeek = 5;
private boolean hasDayOfWeek;
private int dayOfWeek_ = 0;
private org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek dayOfWeek_ = org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek.SUNDAY;
public boolean hasDayOfWeek() { return hasDayOfWeek; }
public int getDayOfWeek() { return dayOfWeek_; }
public org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek getDayOfWeek() { return dayOfWeek_; }
// required uint32 hour = 6;
private boolean hasHour;
@ -748,7 +804,6 @@ public final class LocalTimeProtocol {
public final boolean isInitialized() {
if (!hasYear) return false;
if (!hasMonth) return false;
if (!hasWeek) return false;
if (!hasDayOfMonth) return false;
if (!hasDayOfWeek) return false;
if (!hasHour) return false;
@ -766,14 +821,11 @@ public final class LocalTimeProtocol {
if (hasMonth()) {
output.writeUInt32(2, getMonth());
}
if (hasWeek()) {
output.writeUInt32(3, getWeek());
}
if (hasDayOfMonth()) {
output.writeUInt32(4, getDayOfMonth());
}
if (hasDayOfWeek()) {
output.writeUInt32(5, getDayOfWeek());
output.writeEnum(5, getDayOfWeek().getNumber());
}
if (hasHour()) {
output.writeUInt32(6, getHour());
@ -802,17 +854,13 @@ public final class LocalTimeProtocol {
size += com.google.protobuf.CodedOutputStream
.computeUInt32Size(2, getMonth());
}
if (hasWeek()) {
size += com.google.protobuf.CodedOutputStream
.computeUInt32Size(3, getWeek());
}
if (hasDayOfMonth()) {
size += com.google.protobuf.CodedOutputStream
.computeUInt32Size(4, getDayOfMonth());
}
if (hasDayOfWeek()) {
size += com.google.protobuf.CodedOutputStream
.computeUInt32Size(5, getDayOfWeek());
.computeEnumSize(5, getDayOfWeek().getNumber());
}
if (hasHour()) {
size += com.google.protobuf.CodedOutputStream
@ -958,9 +1006,6 @@ public final class LocalTimeProtocol {
if (other.hasMonth()) {
setMonth(other.getMonth());
}
if (other.hasWeek()) {
setWeek(other.getWeek());
}
if (other.hasDayOfMonth()) {
setDayOfMonth(other.getDayOfMonth());
}
@ -1018,16 +1063,18 @@ public final class LocalTimeProtocol {
setMonth(input.readUInt32());
break;
}
case 24: {
setWeek(input.readUInt32());
break;
}
case 32: {
setDayOfMonth(input.readUInt32());
break;
}
case 40: {
setDayOfWeek(input.readUInt32());
int rawValue = input.readEnum();
org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek value = org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek.valueOf(rawValue);
if (value == null) {
unknownFields.mergeVarintField(5, rawValue);
} else {
setDayOfWeek(value);
}
break;
}
case 48: {
@ -1083,24 +1130,6 @@ public final class LocalTimeProtocol {
return this;
}
// required uint32 week = 3;
public boolean hasWeek() {
return result.hasWeek();
}
public int getWeek() {
return result.getWeek();
}
public Builder setWeek(int value) {
result.hasWeek = true;
result.week_ = value;
return this;
}
public Builder clearWeek() {
result.hasWeek = false;
result.week_ = 0;
return this;
}
// required uint32 dayOfMonth = 4;
public boolean hasDayOfMonth() {
return result.hasDayOfMonth();
@ -1119,21 +1148,21 @@ public final class LocalTimeProtocol {
return this;
}
// required uint32 dayOfWeek = 5;
// required .org.jboss.netty.example.localtime.DayOfWeek dayOfWeek = 5;
public boolean hasDayOfWeek() {
return result.hasDayOfWeek();
}
public int getDayOfWeek() {
public org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek getDayOfWeek() {
return result.getDayOfWeek();
}
public Builder setDayOfWeek(int value) {
public Builder setDayOfWeek(org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek value) {
result.hasDayOfWeek = true;
result.dayOfWeek_ = value;
return this;
}
public Builder clearDayOfWeek() {
result.hasDayOfWeek = false;
result.dayOfWeek_ = 0;
result.dayOfWeek_ = org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek.SUNDAY;
return this;
}
@ -1527,17 +1556,20 @@ public final class LocalTimeProtocol {
"inent\030\001 \002(\0162,.org.jboss.netty.example.lo" +
"caltime.Continent\022\014\n\004city\030\002 \002(\t\"J\n\tLocat" +
"ions\022=\n\010location\030\001 \003(\0132+.org.jboss.netty" +
".example.localtime.Location\"\213\001\n\tLocalTim" +
"e\022\014\n\004year\030\001 \002(\r\022\r\n\005month\030\002 \002(\r\022\014\n\004week\030\003" +
" \002(\r\022\022\n\ndayOfMonth\030\004 \002(\r\022\021\n\tdayOfWeek\030\005 " +
"\002(\r\022\014\n\004hour\030\006 \002(\r\022\016\n\006minute\030\007 \002(\r\022\016\n\006sec" +
"ond\030\010 \002(\r\"M\n\nLocalTimes\022?\n\tlocalTime\030\001 \003" +
"(\0132,.org.jboss.netty.example.localtime.L" +
"ocalTime*\231\001\n\tContinent\022\n\n\006AFRICA\020\000\022\013\n\007AM" +
"ERICA\020\001\022\016\n\nANTARCTICA\020\002\022\n\n\006ARCTIC\020\003\022\010\n\004A" +
"SIA\020\004\022\014\n\010ATLANTIC\020\005\022\r\n\tAUSTRALIA\020\006\022\n\n\006EU" +
"ROPE\020\007\022\n\n\006INDIAN\020\010\022\013\n\007MIDEAST\020\t\022\013\n\007PACIF" +
"IC\020\nB\002H\001";
".example.localtime.Location\"\253\001\n\tLocalTim" +
"e\022\014\n\004year\030\001 \002(\r\022\r\n\005month\030\002 \002(\r\022\022\n\ndayOfM" +
"onth\030\004 \002(\r\022?\n\tdayOfWeek\030\005 \002(\0162,.org.jbos" +
"s.netty.example.localtime.DayOfWeek\022\014\n\004h" +
"our\030\006 \002(\r\022\016\n\006minute\030\007 \002(\r\022\016\n\006second\030\010 \002(" +
"\r\"M\n\nLocalTimes\022?\n\tlocalTime\030\001 \003(\0132,.org" +
".jboss.netty.example.localtime.LocalTime" +
"*\231\001\n\tContinent\022\n\n\006AFRICA\020\000\022\013\n\007AMERICA\020\001\022" +
"\016\n\nANTARCTICA\020\002\022\n\n\006ARCTIC\020\003\022\010\n\004ASIA\020\004\022\014\n" +
"\010ATLANTIC\020\005\022\r\n\tAUSTRALIA\020\006\022\n\n\006EUROPE\020\007\022\n" +
"\n\006INDIAN\020\010\022\013\n\007MIDEAST\020\t\022\013\n\007PACIFIC\020\n*g\n\t" +
"DayOfWeek\022\n\n\006SUNDAY\020\001\022\n\n\006MONDAY\020\002\022\013\n\007TUE" +
"SDAY\020\003\022\r\n\tWEDNESDAY\020\004\022\014\n\010THURSDAY\020\005\022\n\n\006F" +
"RIDAY\020\006\022\014\n\010SATURDAY\020\007B\002H\001";
com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner assigner =
new com.google.protobuf.Descriptors.FileDescriptor.InternalDescriptorAssigner() {
public com.google.protobuf.ExtensionRegistry assignDescriptors(
@ -1564,7 +1596,7 @@ public final class LocalTimeProtocol {
internal_static_org_jboss_netty_example_localtime_LocalTime_fieldAccessorTable = new
com.google.protobuf.GeneratedMessage.FieldAccessorTable(
internal_static_org_jboss_netty_example_localtime_LocalTime_descriptor,
new java.lang.String[] { "Year", "Month", "Week", "DayOfMonth", "DayOfWeek", "Hour", "Minute", "Second", },
new java.lang.String[] { "Year", "Month", "DayOfMonth", "DayOfWeek", "Hour", "Minute", "Second", },
org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTime.class,
org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTime.Builder.class);
internal_static_org_jboss_netty_example_localtime_LocalTimes_descriptor =

View File

@ -47,12 +47,21 @@ message Locations {
repeated Location location = 1;
}
enum DayOfWeek {
SUNDAY = 1;
MONDAY = 2;
TUESDAY = 3;
WEDNESDAY = 4;
THURSDAY = 5;
FRIDAY = 6;
SATURDAY = 7;
}
message LocalTime {
required uint32 year = 1;
required uint32 month = 2;
required uint32 week = 3;
required uint32 dayOfMonth = 4;
required uint32 dayOfWeek = 5;
required DayOfWeek dayOfWeek = 5;
required uint32 hour = 6;
required uint32 minute = 7;
required uint32 second = 8;

View File

@ -0,0 +1,59 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2008, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import java.net.InetSocketAddress;
import java.util.concurrent.Executors;
import org.jboss.netty.bootstrap.ServerBootstrap;
import org.jboss.netty.channel.ChannelFactory;
import org.jboss.netty.channel.socket.nio.NioServerSocketChannelFactory;
/**
* Receives a list of continent/city pairs from a {@link LocalTimeClient} to
* get the local times of the specified cities.
*
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
*
* @version $Rev$, $Date$
*/
public class LocalTimeServer {
public static void main(String[] args) throws Exception {
// Configure the server.
ChannelFactory factory =
new NioServerSocketChannelFactory(
Executors.newCachedThreadPool(),
Executors.newCachedThreadPool());
ServerBootstrap bootstrap = new ServerBootstrap(factory);
bootstrap.setPipelineFactory(new LocalTimeServerPipelineFactory());
bootstrap.setOption("child.tcpNoDelay", true);
bootstrap.setOption("child.keepAlive", true);
// Bind and start to accept incoming connections.
bootstrap.bind(new InetSocketAddress(8080));
}
}

View File

@ -0,0 +1,107 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2008, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import static java.util.Calendar.*;
import java.util.Calendar;
import java.util.TimeZone;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.jboss.netty.channel.ChannelEvent;
import org.jboss.netty.channel.ChannelHandlerContext;
import org.jboss.netty.channel.ChannelPipelineCoverage;
import org.jboss.netty.channel.ChannelStateEvent;
import org.jboss.netty.channel.ExceptionEvent;
import org.jboss.netty.channel.MessageEvent;
import org.jboss.netty.channel.SimpleChannelHandler;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Continent;
import org.jboss.netty.example.localtime.LocalTimeProtocol.DayOfWeek;
import org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTime;
import org.jboss.netty.example.localtime.LocalTimeProtocol.LocalTimes;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Location;
import org.jboss.netty.example.localtime.LocalTimeProtocol.Locations;
/**
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
*
* @version $Rev$, $Date$
*/
@ChannelPipelineCoverage("all")
public class LocalTimeServerHandler extends SimpleChannelHandler {
private static final Logger logger = Logger.getLogger(
LocalTimeServerHandler.class.getName());
@Override
public void handleUpstream(
ChannelHandlerContext ctx, ChannelEvent e) throws Exception {
if (e instanceof ChannelStateEvent) {
logger.info(e.toString());
}
super.handleUpstream(ctx, e);
}
@Override
public void messageReceived(
ChannelHandlerContext ctx, MessageEvent e) {
Locations locations = (Locations) e.getMessage();
long currentTime = System.currentTimeMillis();
LocalTimes.Builder builder = LocalTimes.newBuilder();
for (Location l: locations.getLocationList()) {
TimeZone tz = TimeZone.getTimeZone(
toString(l.getContinent()) + '/' + l.getCity());
Calendar calendar = Calendar.getInstance(tz);
calendar.setTimeInMillis(currentTime);
builder.addLocalTime(LocalTime.newBuilder().
setYear(calendar.get(YEAR)).
setMonth(calendar.get(MONTH) + 1).
setDayOfMonth(calendar.get(DAY_OF_MONTH)).
setDayOfWeek(DayOfWeek.valueOf(calendar.get(DAY_OF_WEEK))).
setHour(calendar.get(HOUR)).
setMinute(calendar.get(MINUTE)).
setSecond(calendar.get(SECOND)).build());
}
e.getChannel().write(builder.build());
}
@Override
public void exceptionCaught(
ChannelHandlerContext ctx, ExceptionEvent e) {
logger.log(
Level.WARNING,
"Unexpected exception from downstream.",
e.getCause());
e.getChannel().close();
}
private static String toString(Continent c) {
return "" + c.name().charAt(0) + c.name().toLowerCase().substring(1);
}
}

View File

@ -0,0 +1,52 @@
/*
* JBoss, Home of Professional Open Source
*
* Copyright 2009, Red Hat Middleware LLC, and individual contributors
* by the @author tags. See the COPYRIGHT.txt in the distribution for a
* full listing of individual contributors.
*
* This is free software; you can redistribute it and/or modify it
* under the terms of the GNU Lesser General Public License as
* published by the Free Software Foundation; either version 2.1 of
* the License, or (at your option) any later version.
*
* This software is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this software; if not, write to the Free
* Software Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
* 02110-1301 USA, or see the FSF site: http://www.fsf.org.
*/
package org.jboss.netty.example.localtime;
import static org.jboss.netty.channel.Channels.*;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.channel.ChannelPipelineFactory;
import org.jboss.netty.handler.codec.frame.LengthFieldBasedFrameDecoder;
import org.jboss.netty.handler.codec.frame.LengthFieldPrepender;
import org.jboss.netty.handler.codec.protobuf.ProtobufDecoder;
import org.jboss.netty.handler.codec.protobuf.ProtobufEncoder;
/**
* @author The Netty Project (netty-dev@lists.jboss.org)
* @author Trustin Lee (tlee@redhat.com)
* @version $Rev$, $Date$
*/
public class LocalTimeServerPipelineFactory implements ChannelPipelineFactory {
public ChannelPipeline getPipeline() throws Exception {
ChannelPipeline p = pipeline();
p.addLast("frameDecoder", new LengthFieldBasedFrameDecoder(1048576, 0, 4, 0, 4));
p.addLast("protobufDecoder", new ProtobufDecoder(LocalTimeProtocol.Locations.getDefaultInstance()));
p.addLast("frameEncoder", new LengthFieldPrepender(4));
p.addLast("protobufEncoder", new ProtobufEncoder());
p.addLast("handler", new LocalTimeServerHandler());
return p;
}
}