c语言sscanf函数的用法是什么
265
2022-11-23
【Golang】实战-聊天室 【建议收藏】
【Golang】✔️实战✔️ 聊天室 ☢️建议手收藏☢️
概述服务端实现客户端实现日志
概述
今天我们会结合之前几节课的知识来综合实战一下, 实现一个聊天室.
服务端实现
运行的时候我们可以开启一个服务端和 N 个客户端, 来实现聊天室.
代码:
package mainimport ( "fmt" "log" "net" "os" "strings" "time")// ================常量================const ( // 日志路径 log_path = "chat_room/")// ===============全局变量==============// 文件日志var logFile *os.File// 日志类var logger *log.Logger// 客户端连接, key: ip端口, value: 连接对象var onlineConns = make(map[string]net.Conn)// 消息队列, 缓冲区var message_quene = make(chan string, 1024)// 消息, 处理程序退出var quitchan = make(chan bool)// 消息协程func comsume_msg() { for { select { // 取出消息 case msg := <- message_quene: process_msg(msg) // 处理退出 case <- quitchan: break } }}// 消息解析协程func process_msg(message string) { // 字符串切割 contents := strings.Split(message, "#") if len(contents) > 1 { // 取出地址 address := contents[0] // 取出消息 message := contents[1] // 删除首尾 address = strings.Trim(address, " ") // 在线连接 conn, ok := onlineConns[address] if ok { _, err := conn.Write([]byte(message)) fmt.Println("发送消息:", message, "目的地:", address) if err != nil { fmt.Println("在线连接发送失败") } } } else { // 查看list contents = strings.Split(message, "&") if contents[1] == "list" { var str = "" // 向每个客户端发送信息 for i := range onlineConns { // str += "||||" + i } // 在线连接 conn, ok := onlineConns[contents[0]] if ok { _, err := conn.Write([]byte(str)) if err != nil { fmt.Println("在线发送失败:", err) } } fmt.Println("发送消息:", str, "目的地:", conn.RemoteAddr()) logger.Println("发送消息:", str, "目的地:", conn.RemoteAddr()) } }}// 接收消息func receive_info(conn net.Conn) { // 缓冲 buffer := make([]byte, 1024) // 循环读取 for { // 读取数据 nums, err := conn.Read(buffer) if err != nil { break } if nums != 0 { // 获取地址 address := conn.RemoteAddr() // 获取消息 message := string(buffer[:nums]) // 调试输出 fmt.Println("收到消息:", message, "来自:", address) logger.Println("收到消息:", message, "来自:", address) // 处理客户端退出 if message == "exit" { // 调试输出 fmt.Println("客户端:", conn.RemoteAddr(), "正在退出...") logger.Println("客户端:", conn.RemoteAddr(), "正在退出...") // 退出 client_exit(conn) } else{ // 消息队列存储消息 message_quene <- message } } }}// 处理退出func client_exit(conn net.Conn) { // 获取地址 address := fmt.Sprint(conn.RemoteAddr()) // 客户端退出时, 从map中移除地址 delete(onlineConns, address) // 关闭连接 conn.Close() // 输出当前列表 fmt.Println("客户端列表:\n--------------------") logger.Println("客户端列表:\n--------------------") for i := range onlineConns { fmt.Println(i) }}// 错误处理func error_check(err error) { if err != nil { fmt.Println("Error:", err) os.Exit(1) }}func main() { fmt.Println("服务端正在启动...") // 打开日志文件 name := fmt.Sprintf("%d_%02d_%02d_%02d_%02d_%02d_server.log", time.Now().Year(), time.Now().Month(), time.Now().Day(), time.Now().Hour(), time.Now().Minute(), time.Now().Second(), ) log_file, err := os.OpenFile((log_path + name), os.O_RDWR | os.O_CREATE, 0) if err != nil { fmt.Println("日志文件打开失败:", err.Error()) os.Exit(-1) } // 关闭 defer log_file.Close() // 创建一个日志对象 logger = log.New(log_file, "\r\n", log.Ldate | log.Ltime | log.Llongfile) logger.Println("写入日志, 服务器正在启动...") // 创建TCP服务端 listen_socket, err := net.Listen("tcp", "127.0.0.1:8888") error_check(err) // 关闭 defer listen_socket.Close() fmt.Println("服务端启动完毕, 等待连接...") // 协程 go comsume_msg() // 启动连接 for { // 连接新客户端 conn, err := listen_socket.Accept() error_check(err) fmt.Println("服务端连接到客服端, 客户端地址:", conn.RemoteAddr()) logger.Println("服务端连接到客服端, 客户端地址:", conn.RemoteAddr()) // 获取地址 address := fmt.Sprint(conn.RemoteAddr()) // 添加到全局变量 onlineConns[address] = conn // 遍历每一个连接 fmt.Println("客户端列表:\n--------------------") logger.Println("客户端列表:\n---------------------------------------------------") for i := range onlineConns { fmt.Println(i) logger.Println(i) } // 发送消息 go receive_info(conn) }}
客户端实现
package mainimport ( "bufio" "fmt" "net" "os")// 发送消息func send_msg(conn net.Conn) { // 循环发送 for { // 读取键盘输入 reader := bufio.NewReader(os.Stdin) // 读取一行 data, _, _ := reader.ReadLine() // 发送输入的字符串 _, err := conn.Write(data) fmt.Println("发送消息:", string(data)) if err != nil { conn.Close() fmt.Println("Error:", err, "客户端关闭") os.Exit(0) } // 收到exit, 关闭客户端 if string(data) == "exit" { fmt.Println("客户端关闭") os.Exit(0) } }}func main() { fmt.Println("客服端正在建立连接...") // 建立网络连接 conn, err := net.Dial("tcp", "127.0.0.1:8888") if err != nil { fmt.Println("网络连接错误") os.Exit(1) } fmt.Println("客户端成功连接到服务端, 服务端地址:", conn.RemoteAddr()) // 发送消息 go send_msg(conn) // 接收消息 buffer := make([]byte, 1024) // 循环接收 for { // 读取消息 nums, err := conn.Read(buffer) if err != nil { fmt.Println("读取消息出错, 退出客户端") os.Exit(0) } fmt.Println("收到消息:", string(buffer[:nums])) }}
输出结果:
server:
服务端正在启动...服务端启动完毕, 等待连接...服务端连接到客服端, 客户端地址: 127.0.0.1:63776客户端列表:--------------------127.0.0.1:63776服务端连接到客服端, 客户端地址: 127.0.0.1:63777客户端列表:--------------------127.0.0.1:63776127.0.0.1:63777收到消息: 127.0.0.1:63776&list 来自: 127.0.0.1:63776发送消息: ||||127.0.0.1:63776||||127.0.0.1:63777 目的地: 127.0.0.1:63776收到消息: 127.0.0.1:63777#hi, client2 来自: 127.0.0.1:63776发送消息: hi, client2 目的地: 127.0.0.1:63777收到消息: 127.0.0.1:63777&list 来自: 127.0.0.1:63777发送消息: ||||127.0.0.1:63776||||127.0.0.1:63777 目的地: 127.0.0.1:63777收到消息: 127.0.0.1:63776#hi, client1 来自: 127.0.0.1:63777发送消息: hi, client1 目的地: 127.0.0.1:63776收到消息: exit 来自: 127.0.0.1:63776客户端: 127.0.0.1:63776 正在退出...客户端列表:--------------------127.0.0.1:63777收到消息: exit 来自: 127.0.0.1:63777客户端: 127.0.0.1:63777 正在退出...客户端列表:--------------------
client1:
客服端正在建立连接...客户端成功连接到服务端, 服务端地址: 127.0.0.1:8888127.0.0.1:63776&list发送消息: 127.0.0.1:63776&list收到消息: ||||127.0.0.1:63776||||127.0.0.1:63777127.0.0.1:63777#hi, client2发送消息: 127.0.0.1:63777#hi, client2收到消息: hi, client1exit发送消息: exit客户端关闭
client2:
客服端正在建立连接...客户端成功连接到服务端, 服务端地址: 127.0.0.1:8888收到消息: hi, client2127.0.0.1:63777&list发送消息: 127.0.0.1:63777&list收到消息: ||||127.0.0.1:63776||||127.0.0.1:63777127.0.0.1:63776#hi, client1发送消息: 127.0.0.1:63776#hi, client1exit发送消息: exit客户端关闭
日志
2021/08/27 01:08:04 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:209: 写入日志, 服务器正在启动...2021/08/27 01:08:07 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:231: 服务端连接到客服端, 客户端地址: 127.0.0.1:637762021/08/27 01:08:07 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:242: 客户端列表:---------------------------------------------------2021/08/27 01:08:07 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:245: 127.0.0.1:637762021/08/27 01:08:09 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:231: 服务端连接到客服端, 客户端地址: 127.0.0.1:637772021/08/27 01:08:09 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:242: 客户端列表:---------------------------------------------------2021/08/27 01:08:09 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:245: 127.0.0.1:637762021/08/27 01:08:09 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:245: 127.0.0.1:637772021/08/27 01:08:20 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: 127.0.0.1:63776&list 来自: 127.0.0.1:637762021/08/27 01:08:20 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:104: 发送消息: ||||127.0.0.1:63776||||127.0.0.1:63777 目的地: 127.0.0.1:637762021/08/27 01:08:31 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: 127.0.0.1:63777#hi, client2 来自: 127.0.0.1:637762021/08/27 01:08:42 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: 127.0.0.1:63777&list 来自: 127.0.0.1:637772021/08/27 01:08:42 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:104: 发送消息: ||||127.0.0.1:63776||||127.0.0.1:63777 目的地: 127.0.0.1:637772021/08/27 01:08:53 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: 127.0.0.1:63776#hi, client1 来自: 127.0.0.1:637772021/08/27 01:09:04 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: exit 来自: 127.0.0.1:637762021/08/27 01:09:04 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:142: 客户端: 127.0.0.1:63776 正在退出...2021/08/27 01:09:04 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:168: 客户端列表:--------------------2021/08/27 01:09:11 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:135: 收到消息: exit 来自: 127.0.0.1:637772021/08/27 01:09:11 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:142: 客户端: 127.0.0.1:63777 正在退出...2021/08/27 01:09:11 C:/Users/Windows/Desktop/project2/chat_room/server2/server.go:168: 客户端列表:--------------------
版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。
发表评论
暂时没有评论,来抢沙发吧~