func main() { var addr string flag.StringVar(&addr, "addr", "127.0.0.1:10010", "echo server address") flag.Parse() session, err := link.Connect("tcp://"+addr, link.Packet(link.Uint16BE), link.String()) if err != nil { panic(err) } go func() { var msg string for { if err := session.Receive(&msg); err != nil { break } fmt.Printf("%s\n", msg) } }() for { var msg string if _, err := fmt.Scanf("%s\n", &msg); err != nil { break } if err = session.Send(msg); err != nil { break } } session.Close() println("bye") }
func main() { var addr string flag.StringVar(&addr, "addr", ":10010", "echo server address") flag.Parse() server, err := link.Serve("tcp", addr, link.Packet(2, 1024*1024, 1024, binary.LittleEndian, TestCodec{})) if err != nil { panic(err) } println("server start:", server.Listener().Addr().String()) for { session, err := server.Accept() if err != nil { break } go func() { //addr := session.Conn().RemoteAddr().String() //println("client", addr, "connected") for { var msg []byte if err = session.Receive(&msg); err != nil { break } if err = session.Send(msg); err != nil { break } } //println("client", addr, "closed") }() } }
func main() { var addr string flag.StringVar(&addr, "addr", "127.0.0.1:10010", "echo server address") flag.Parse() session, err := link.Connect("tcp", addr, link.Packet(2, 1024*1024, 1024, binary.LittleEndian, TestCodec{})) if err != nil { panic(err) } go func() { var msg string for { if err := session.Receive(&msg); err != nil { break } fmt.Printf("%s\n", msg) } }() for { var msg string if _, err := fmt.Scanf("%s\n", &msg); err != nil { break } if err = session.Send(msg); err != nil { break } } session.Close() println("bye") }
func Test_Simple(t *testing.T) { backend, err := StartEchoBackend() unitest.NotError(t, err) gateway := StartTestGateway(t, backend.Listener().Addr().String()) gatewayAddr := gateway.server.Listener().Addr().String() client, err := link.Connect("tcp://"+gatewayAddr, link.Packet(link.Uint16BE), link.Bytes()) unitest.NotError(t, err) for i := 0; i < 10000; i++ { msg1 := RandBytes(1024) err1 := client.Send(msg1) unitest.NotError(t, err1) var msg2 []byte err2 := client.Receive(&msg2) unitest.NotError(t, err2) if bytes.Equal(msg1, msg2) == false { t.Log(i, msg1, msg2) t.Fail() } unitest.Pass(t, bytes.Equal(msg1, msg2)) } client.Close() gateway.Stop() backend.Stop() time.Sleep(time.Second * 2) MakeSureSessionGoroutineExit(t) }
// This is an benchmark tool work with the echo_server. // // Start echo_server with 'bench' flag // go run echo_server.go -bench // // Start benchmark with echo_server address // go run echo_benchmark.go // go run echo_benchmark.go -num=100 // go run echo_benchmark.go -size=1024 // go run echo_benchmark.go -time=20 // go run echo_benchmark.go -addr="127.0.0.1:10010" func main() { flag.Parse() if MultiProcess() { return } var ( msg = make([]byte, *messageSize) timeout = time.Now().Add(time.Second * time.Duration(*runTime)) initWait = new(sync.WaitGroup) startChan = make(chan int) conns = make([]*CountConn, 0, *clientNum) ) var codecType link.CodecType if *pro { pool := binary.NewBufferPool(2, 1, 32) codecType = link.PacketPro(2, *messageSize, *messageSize*2, link.LittleEndian, pool, TestCodec{}) } else { codecType = link.Packet(2, *messageSize, *messageSize*2, link.LittleEndian, TestCodec{}) } for i := 0; i < *clientNum; i++ { conn, err := net.DialTimeout("tcp", *serverAddr, time.Second*3) if err != nil { panic(err) } countConn := &CountConn{Conn: conn} conns = append(conns, countConn) initWait.Add(2) go client(initWait, countConn, startChan, timeout, msg, codecType) } initWait.Wait() close(startChan) time.Sleep(time.Second * time.Duration(*runTime)) var sum CountConn for i := 0; i < *clientNum; i++ { conn := conns[i] conn.Conn.Close() sum.SendCount += conn.SendCount sum.RecvCount += conn.RecvCount sum.ReadCount += conn.ReadCount sum.WriteCount += conn.WriteCount } fmt.Printf(OutputFormat, sum.SendCount, sum.RecvCount, sum.ReadCount, sum.WriteCount) }
// This is broadcast server demo work with the echo_client. // usage: // cd src/github.com/funny/link // go generate channel.go // go run example/echo/broadcast.go func main() { var addr string flag.StringVar(&addr, "addr", ":10010", "echo server address") flag.Parse() server, err := link.Serve("tcp", addr, link.Async(1024, link.Packet(2, 1024*1024, 1024, binary.LittleEndian, TestCodec{}))) if err != nil { panic(err) } println("server start:", server.Listener().Addr().String()) channel := link.NewUint64Channel() go func() { for range time.Tick(time.Second * 2) { now := "from channel: " + time.Now().Format("2006-01-02 15:04:05") channel.Fetch(func(session *link.Session) { session.Send(now) }) } }() for { session, err := server.Accept() if err != nil { break } go func() { addr := session.Conn().RemoteAddr().String() println("client", addr, "connected") channel.Put(session.Id(), session) for { var msg string if err := session.Receive(&msg); err != nil { break } println(addr, "say:", msg) channel.Fetch(func(session *link.Session) { session.Send("from " + addr + ": " + string(msg)) }) } println("client", addr, "closed") channel.Remove(session.Id()) }() } }
func client(initWait *sync.WaitGroup, conn *CountConn, startChan chan int, timeout time.Time, msg []byte) { pConn, _ := link.Packet(link.Uint16BE).NewClientConn(conn) client := link.NewSession(pConn, link.Bytes()) var wg sync.WaitGroup wg.Add(1) go func() { defer wg.Done() initWait.Done() <-startChan for { outMsg := msg if *randsize { outMsg = make([]byte, rand.Intn(*messageSize)) } if err := client.Send(outMsg); err != nil { if timeout.After(time.Now()) { println("send error:", err.Error()) } break } atomic.AddUint32(&conn.SendCount, 1) } }() wg.Add(1) go func() { defer wg.Done() initWait.Done() <-startChan var inMsg []byte for { if err := client.Receive(&inMsg); err != nil { if timeout.After(time.Now()) { println("recv error:", err.Error()) } break } atomic.AddUint32(&conn.RecvCount, 1) } }() wg.Wait() }
func client(initWait *sync.WaitGroup, conn *CountConn, startChan chan int, timeout time.Time, msg []byte) { client := link.NewSession(conn, link.Packet(2, *messageSize, 4096, binary.LittleEndian, TestCodec{})) var wg sync.WaitGroup wg.Add(1) go func() { defer wg.Done() initWait.Done() <-startChan for { outMsg := msg if *randsize { outMsg = msg[:rand.Intn(*messageSize)] } if err := client.Send(outMsg); err != nil { if timeout.After(time.Now()) { println("send error:", err.Error()) } break } atomic.AddUint32(&conn.SendCount, 1) } }() wg.Add(1) go func() { defer wg.Done() initWait.Done() <-startChan var inMsg []byte for { if err := client.Receive(&inMsg); err != nil { if timeout.After(time.Now()) { println("recv error:", err.Error()) } break } atomic.AddUint32(&conn.RecvCount, 1) } }() wg.Wait() }
func StartTestGateway(t *testing.T, backendAddr string) *Frontend { listener, err := link.ListenPacket("tcp://0.0.0.0:0", link.Packet(link.Uint16BE)) unitest.NotError(t, err) var linkIds []uint64 gateway := NewFrontend(listener, func(_ *link.Session) (uint64, error) { return linkIds[rand.Intn(len(linkIds))], nil }) for i := 0; i < 1; i++ { id, err := gateway.AddBackend("tcp://"+backendAddr, link.Stream()) unitest.NotError(t, err) linkIds = append(linkIds, id) } return gateway }
func main() { var addr string var pro bool flag.StringVar(&addr, "addr", ":10010", "echo server address") flag.BoolVar(&pro, "pro", true, "use PacketPro()") flag.Parse() var codecType link.CodecType if pro { pool := binary.NewBufferPool(2, 1, 32) codecType = link.PacketPro(2, 1024*1024, 1024, link.LittleEndian, pool, TestCodec{}) } else { codecType = link.Packet(2, 1024*1024, 1024, link.LittleEndian, TestCodec{}) } server, err := link.Serve("tcp", addr, codecType) if err != nil { panic(err) } println("server start:", server.Listener().Addr().String()) for { session, err := server.Accept() if err != nil { break } go func() { //addr := session.Conn().RemoteAddr().String() //println("client", addr, "connected") for { var msg []byte if err = session.Receive(&msg); err != nil { break } if err = session.Send(msg); err != nil { break } } //println("client", addr, "closed") }() } }
// This is broadcast server demo work with the echo_client. // usage: // go run echo_broadcast.go func main() { var addr string flag.StringVar(&addr, "addr", ":10010", "echo server address") flag.Parse() server, err := link.Serve("tcp://"+addr, link.Packet(link.Uint16BE), link.String()) if err != nil { panic(err) } println("server start:", server.Listener().Addr().String()) channel := link.NewChannel() go func() { for range time.Tick(time.Second * 2) { now := time.Now().Format("2006-01-02 15:04:05") channel.Broadcast("from channel: " + now) } }() server.Loop(func(session *link.Session) { addr := session.Conn().RemoteAddr().String() println("client", addr, "connected") session.EnableAsyncSend(1024) channel.Join(session) for { var msg string if err := session.Receive(&msg); err != nil { break } println(addr, "say:", msg) channel.Broadcast("from " + addr + ": " + string(msg)) } println("client", addr, "closed") channel.Exit(session) }) }
func Test_Broadcast(t *testing.T) { var ( clientNum = 20 packetNum = 2000 channel = NewChannel(link.Bytes()) broadcastMsg []byte broadcastWait sync.WaitGroup clientWait sync.WaitGroup ) backend, err := link.Serve("tcp://0.0.0.0:0", NewBackend(), link.Bytes()) unitest.NotError(t, err) go backend.Loop(func(session *link.Session) { channel.Join(session) clientWait.Done() for { var msg []byte if err := session.Receive(&msg); err != nil { break } unitest.Pass(t, bytes.Equal(msg, broadcastMsg)) broadcastWait.Done() } }) clientWait.Add(clientNum) go func() { clientWait.Wait() for i := 0; i < packetNum; i++ { broadcastMsg = RandBytes(1024) channel.Broadcast(broadcastMsg) broadcastWait.Add(clientNum) broadcastWait.Wait() } }() gateway := StartTestGateway(t, backend.Listener().Addr().String()) gatewayAddr := gateway.server.Listener().Addr().String() var wg sync.WaitGroup for i := 0; i < clientNum; i++ { wg.Add(1) go func() { defer wg.Done() client, err := link.Connect("tcp://"+gatewayAddr, link.Packet(link.Uint16BE), link.Bytes()) unitest.NotError(t, err) for j := 0; j < packetNum; j++ { var msg []byte err := client.Receive(&msg) unitest.NotError(t, err) err = client.Send(msg) unitest.NotError(t, err) } client.Close() }() } wg.Wait() gateway.Stop() backend.Stop() time.Sleep(time.Second * 2) MakeSureSessionGoroutineExit(t) }
package global import ( // "runtime" "github.com/funny/link" . "tools" "tools/codecType" "tools/dispatch" "tools/gc" ) var ( PackCodecType_UnSafe link.CodecType = link.Packet(4, 1024*1024, 4096, link.LittleEndian, codecType.NetCodecType{}) PackCodecType_Safe link.CodecType = link.ThreadSafe(PackCodecType_UnSafe) PackCodecType_Async link.CodecType = link.Async(4096, PackCodecType_UnSafe) ) //服务器启动 func Startup(serverName string, logFile string, stopServerFunc func()) { // runtime.GOMAXPROCS(runtime.NumCPU()) // 开启Log记录 SetLogFile(logFile) SetLogPrefix(serverName) // 信号量监听 go SignalProc(stopServerFunc) // 开启GC及系统环境信息监测 gc.SysRoutine()
"strconv" "sync" "testing" "time" "tools/codecType" ) import ( proto "code.google.com/p/goprotobuf/proto" "protos/gameProto" . "tools" "tools/cfg" "tools/unitest" ) var protocol = link.Packet(4, 1024*1024, 4096, link.LittleEndian, codecType.NetCodecType{}) func Test_gateway(t *testing.T) { DEBUG("消息通信测试") var wg sync.WaitGroup var successNum uint32 for i := 0; i < 3000; i++ { wg.Add(1) go func(flag int) { // if flag != 0 && random.RandomInt31n(100) < 50 { // flag -= 1 // } defer wg.Done() var count uint32 = 0 var userName string = "User" + strconv.Itoa(flag)