废话不说了,直接上代码.里面注释应该很清楚了
/**
* Created with IntelliJ IDEA.
* User: Admin
* Date: 12-8-30
* Time: 下午1:27
* To change this template use File | Settings | File Templates.
*/
package main
import (
"fmt"
"net"
"os"
"io"
)
type tcpPacket struct {
data string;
con net.Conn;
}
func main() {
fmt.Println("启动服务器... (Ctrl-C 停止)");
var (
host = "0.0.0.0";
port = "12345";
laddr = host + ":" + port;
)
//创建data_cn程道,所有的客户端连接都会通过data_cn程道将消息发送到handle去程处理
data_ch := make(chan tcpPacket);
//实施listen去程,将所有客户端发来的消息,发送给data_cn程道
go listen(data_ch, laddr);
//死循环
for {
//当程道data_ch收到消息时,实施handle去程
go handle( <- data_ch );
}
}
/*
监听端口
*/
func listen(data_ch chan tcpPacket, laddr string) {
fmt.Println("开始监听");
lis, error := net.Listen("tcp", laddr);
//函数结束后,监听关闭
defer lis.Close();
if error != nil {
fmt.Printf("监听出错: %s\n", error );
os.Exit(1);
}
//死循环
for {
//获取连接和错误信息
con, error := lis.Accept();
if error != nil { fmt.Printf("接收到意外数据: %s\n", error); os.Exit(2); }
//实施listen_socket去程
go listen_socket(data_ch, con);
}
}
/*
处理单独连接
*/
func listen_socket(data_ch chan tcpPacket, con net.Conn) {
fmt.Printf("[新连接]参数: %s \n", con.RemoteAddr());
data := make([]byte, 1024);
defer con.Close();
for {
n, error := con.Read(data);
switch error {
case nil:
packet := tcpPacket{ string(data[0:n]), con };
data_ch <- packet;
case io.EOF:
fmt.Printf("警告!连接已断开: %s \n", error);
return;
default:
fmt.Printf("错误!收到意外的数据 : %s \n", error);
return;
}
}
}
/*
处理客户端连接发送来的消息
*/
func handle(packet tcpPacket) {
// 读取客户端连接信息
addr := packet.con.RemoteAddr();
fmt.Printf("从 %s 收到数据: '%s'\n", addr.String(), packet.data);
// 将接受到的数据发送回客户端(echo)
packet.con.Write([]byte(packet.data));
}