您的位置:首页 > 编程语言 > Go语言

奇妙的go语言(聊天室的开发)

2014-08-09 17:50 399 查看
【 声明:版权全部,欢迎转载,请勿用于商业用途。 联系信箱:feixiaoxing @163.com】

这是一篇关于聊天室开发的博客,原来文章的地址来自于。这篇文章非常具有代表性,对于代码中的函数部分内容,不想多说什么,仅仅是对它的实现进行一些必要的解说。关于代码,大家既能够在这里阅读,也能够跳转到那篇博客,继续阅读。

package main

import(
"fmt"
"os"
"net"
)

////////////////////////////////////////////////////////
//
//错误检查
//
////////////////////////////////////////////////////////
func checkError(err error,info string) (res bool) {

if(err != nil){
fmt.Println(info+"  " + err.Error())
return false
}
return true
}

////////////////////////////////////////////////////////
//
//server端接收数据线程
//參数:
//		数据连接 conn
//		通讯通道 messages
//
////////////////////////////////////////////////////////
func Handler(conn net.Conn,messages chan string){

fmt.Println("connection is connected from ...",conn.RemoteAddr().String())

buf := make([]byte,1024)
for{
lenght, err := conn.Read(buf)
if(checkError(err,"Connection")==false){
conn.Close()
break
}
if lenght > 0{
buf[lenght]=0
}
//fmt.Println("Rec[",conn.RemoteAddr().String(),"] Say :" ,string(buf[0:lenght]))
reciveStr :=string(buf[0:lenght])
messages <- reciveStr

}

}

////////////////////////////////////////////////////////
//
//server发送数据的线程
//
//參数
//		连接字典 conns
//		数据通道 messages
//
////////////////////////////////////////////////////////
func echoHandler(conns *map[string]net.Conn,messages chan string){

for{
msg:= <- messages
fmt.Println(msg)

for key,value := range *conns {

fmt.Println("connection is connected from ...",key)
_,err :=value.Write([]byte(msg))
if(err != nil){
fmt.Println(err.Error())
delete(*conns,key)
}

}
}

}

////////////////////////////////////////////////////////
//
//启动server
//參数
//	端口 port
//
////////////////////////////////////////////////////////
func StartServer(port string){
service:=":"+port //strconv.Itoa(port);
tcpAddr, err := net.ResolveTCPAddr("tcp4", service)
checkError(err,"ResolveTCPAddr")
l,err := net.ListenTCP("tcp",tcpAddr)
checkError(err,"ListenTCP")
conns:=make(map[string]net.Conn)
messages := make(chan string,10)

//启动server广播线程
go echoHandler(&conns,messages)

for  {
fmt.Println("Listening ...")
conn,err := l.Accept()
checkError(err,"Accept")
fmt.Println("Accepting ...")
conns[conn.RemoteAddr().String()]=conn
//启动一个新线程
go Handler(conn,messages)

}

}

////////////////////////////////////////////////////////
//
//client发送线程
//參数
//		发送连接 conn
//
////////////////////////////////////////////////////////
func chatSend(conn net.Conn){

var input string
username := conn.LocalAddr().String()
for {

fmt.Scanln(&input)
if input == "/quit"{
fmt.Println("ByeBye..")
conn.Close()
os.Exit(0);
}

lens,err :=conn.Write([]byte(username + " Say :::" + input))
fmt.Println(lens)
if(err != nil){
fmt.Println(err.Error())
conn.Close()
break
}

}

}

////////////////////////////////////////////////////////
//
//client启动函数
//參数
//		远程ip地址和端口 tcpaddr
//
////////////////////////////////////////////////////////
func StartClient(tcpaddr string){

tcpAddr, err := net.ResolveTCPAddr("tcp4", tcpaddr)
checkError(err,"ResolveTCPAddr")
conn, err := net.DialTCP("tcp", nil, tcpAddr)
checkError(err,"DialTCP")
//启动client发送线程
go chatSend(conn)

//開始client轮训
buf := make([]byte,1024)
for{

lenght, err := conn.Read(buf)
if(checkError(err,"Connection")==false){
conn.Close()
fmt.Println("Server is dead ...ByeBye")
os.Exit(0)
}
fmt.Println(string(buf[0:lenght]))

}
}

////////////////////////////////////////////////////////
//
//主程序
//
//參数说明:
//	启动server端:  Chat server [port]				eg: Chat server 9090
//	启动client:    Chat client [Server Ip Addr]:[Server Port]  	eg: Chat client 192.168.0.74:9090
//
////////////////////////////////////////////////////////
func main(){

if len(os.Args)!=3  {
fmt.Println("Wrong pare")
os.Exit(0)
}

if os.Args[1]=="server" && len(os.Args)==3 {

StartServer(os.Args[2])
}

if os.Args[1]=="client" && len(os.Args)==3 {

StartClient(os.Args[2])
}

}


主要知识点例如以下:

(1)代码中包含了server和client的内容,假设是server,直接输入./chat server 9090就可以,client也非常easy,输入./chat client :9090就好;

(2)假设是client,事实上就包含了两部分内容,一部分是chatSend函数,接受用户的输入;还有一部分是connect到server,接受相关信息;

(3)假设是server,略微复杂一点,有三个部分组成。第一部分就是不停地accept各个client;第二个就是为每个client创立Handler函数,接受client发来的信息;第三个就是echoHandler函数,它的作用就是将从某一用户接受过来的信息广播给其它全部的client,就是这么简单。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: