支持多连接。
Server运行之后,进入Accept阻塞状态。Accept得到一个Conn之后,开启一个协程,分别有两个协程阻塞在Read和Write。当Read一个数据之后,将Read得到的数据写入readChannel中,之后再对其进行处理。在writeChannel得到一个数据之后,向Conn写入数据。
Client运行后,接入Server,之后开启两个协程阻塞在Read和Write的Channel中。在Scan得到一个数据之后,向writeChannel写入数据,唤醒阻塞的协程向Conn中写入数据。当Server中有数据返回时,read协程被唤醒,将数据写入readChannel中。
当然,还有诸多细节要处理。比如Conn的关闭在什么时候等等。
客户端源码
package client import ( "net" "git.oschina.net/sdlszjb/unix_socket/errs" "fmt" ) func StartClient1() { tcpAddress,err := net.ResolveTCPAddr("tcp4","127.0.0.1:1300") if err != nil { errs.Error_exit(err) } conn,err := net.DialTCP("tcp",nil,tcpAddress) if err != nil { errs.Error_exit(err) } writeChan := make(chan []byte,1024) readChan := make(chan []byte,1024) go writeConnection(conn,writeChan) go readConnection(conn,readChan) //go handleReadChannel(readChan) for { var s string fmt.Scan(&s) writeChan <- []byte(s) } } func readConnection(conn *net.TCPConn,channel chan []byte) { defer conn.Close() buffer := make([]byte,2048) for { n,err := conn.Read(buffer) if err != nil { errs.Error_print(err) return } println("Received from:",conn.RemoteAddr(),string(buffer[:n])) //channel <- buffer[:n] } } func writeConnection(conn *net.TCPConn,channel chan []byte) { defer conn.Close() for { select { case data := <- channel: _,err := conn.Write(data) if err != nil { errs.Error_exit(err) } println("Write to:",string(data)) } } }
服务端代码:
package server import ( "net" "git.oschina.net/sdlszjb/unix_socket/errs" "fmt" ) var client_num int = 0 func StartServer1() { l,err := net.Listen("tcp",":1300") if err != nil { errs.Error_exit(err) } defer l.Close() for { conn,err := l.Accept() if err != nil { errs.Error_print(err) continue } client_num++ fmt.Printf("A new Connection %d.\n",client_num) go handlerConnection(conn) } } func handlerConnection(conn net.Conn) { defer closeConnection(conn) readChannel := make(chan []byte,1024) writeChannel := make(chan []byte,1024) go readConnection(conn,readChannel) go writeConnection(conn,writeChannel) for { select { case data := <- readChannel: if string(data) == "bye" { return } writeChannel <- append([]byte("Back"),data...) } } } func writeConnection(conn net.Conn,channel chan []byte) { for { select { case data := <- channel: println("Write:",conn.RemoteAddr().String(),string(data)) _,err := conn.Write(data) if err != nil { errs.Error_print(err) return } } } } func readConnection(conn net.Conn,channel chan []byte) { buffer := make([]byte,2048) for { n,err := conn.Read(buffer) if err != nil { errs.Error_print(err) channel <- []byte("bye") //这里须要进一步改进! break } println("Recei:",string(buffer[:n])) channel <- buffer[:n] } } func closeConnection(conn net.Conn) { conn.Close() client_num-- fmt.Printf("Now,%d connections is alve.\n",client_num) }