Chat App 项目介绍与解析(一)-CSDN博客文章浏览阅读468次,点赞12次,收藏3次。Chat App 是一个实时聊天应用程序,旨在为用户提供一个简单、直观的聊天平台。该应用程序不仅支持普通用户的注册和登录,还提供了管理员登录功能,以便管理员可以查看和管理聊天记录。本文将详细介绍index.html文件的实现细节,包括代码解释、实现效果、实现方法以及后续需要实现的功能。https://blog.csdn.net/qq_45519030/article/details/141330140Chat App 项目之解析(二)-CSDN博客文章浏览阅读496次,点赞10次,收藏16次。在前一篇博客中,我们介绍了 Chat App 的主页index.html。本篇将深入探讨用户注册页面,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。https://blog.csdn.net/qq_45519030/article/details/141330781Chat App 项目之解析(三)-CSDN博客文章浏览阅读426次,点赞18次,收藏17次。在前一篇博客中,我们介绍了用户注册页面。本篇将深入探讨用户登录页面login.html,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。login.html。https://blog.csdn.net/qq_45519030/article/details/141331037
Chat App 项目之解析(四)-CSDN博客文章浏览阅读705次,点赞28次,收藏19次。在前一篇博客中,我们详细介绍了用户登录页面login.html。本篇将深入探讨聊天室页面chat.html,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。chat.html。https://blog.csdn.net/qq_45519030/article/details/141331411Chat App 项目之解析(五)-CSDN博客文章浏览阅读890次,点赞25次,收藏7次。在前一篇博客中,我们详细介绍了聊天室页面chat.html。本篇将深入探讨样式表styles.css,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。styles.css。https://blog.csdn.net/qq_45519030/article/details/141331696Chat App 项目之解析(六)-CSDN博客文章浏览阅读274次,点赞18次,收藏14次。在前一篇博客中,我们详细介绍了样式表styles.css。本篇将深入探讨管理员登录页面,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。https://blog.csdn.net/qq_45519030/article/details/141331943Chat App 项目之解析(七)-CSDN博客文章浏览阅读842次,点赞16次,收藏9次。在前一篇博客中,我们详细介绍了管理员登录页面。本篇将深入探讨管理员聊天记录页面,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。https://blog.csdn.net/qq_45519030/article/details/141332107Chat App 项目之解析(八)-CSDN博客文章浏览阅读681次,点赞14次,收藏22次。在前一篇博客中,我们详细介绍了管理员聊天记录页面。本篇将深入探讨后端服务server.go,包括其代码解释、实现效果、实现方法以及后续需要实现的功能。用户认证模块:负责用户的注册和登录。WebSocket 通信模块:实现客户端与服务器之间的实时消息传递。数据库模块:存储用户信息和聊天记录。管理员接口:提供管理员查看、删除和过滤聊天记录的功能。用户在线状态管理:实时显示用户的在线状态。消息加密与解密:确保消息在传输过程中的安全性。用户权限控制:实现更复杂的用户权限管理。用户注册。https://blog.csdn.net/qq_45519030/article/details/141332531
用户在线状态管理模块负责实时显示用户的在线状态。服务器维护一个在线用户列表,当用户连接或断开 WebSocket 连接时,更新该列表并通知所有客户端。
package main
import (
"encoding/json"
"log"
"net/http"
"sync"
"github.com/gorilla/websocket"
)
func onlineStatusHandler(w http.ResponseWriter, r *http.Request) {
if err != nil {
log.Println("Error upgrading connection:", err)
return
}
defer conn.Close()
if email == "" {
http.Error(w, "Invalid email", http.StatusBadRequest)
return
}
onlineUsersMutex.Lock()
defer func() {
onlineUsersMutex.Lock()
}()
for {
if err != nil {
log.Println("Error reading message:", err)
break
}
}
}
func broadcastOnlineUsers() {
for {
onlineUsersMutex.Lock()
onlineUsersMutex.Unlock()
msg, err := json.Marshal(users)
if err != nil {
log.Println("Error marshalling online users:", err)
continue
}
for conn := range connections {
if err := conn.WriteMessage(websocket.TextMessage, msg); err != nil {
log.Println("Error writing message:", err)
continue
}
}
}
}
代码解释:
onlineStatusHandler
函数处理用户在线状态的 WebSocket 连接。onlineUsersMutex
互斥锁管理在线用户列表,确保并发安全。broadcastOnlineUsers
函数定期广播在线用户列表给所有连接的客户端。消息加密与解密模块确保消息在传输过程中的安全性。服务器在发送消息前对其进行加密,客户端在接收消息后对其进行解密。
package main
import (
"crypto/aes"
"crypto/cipher"
"crypto/rand"
"encoding/base64"
"io"
"log"
)
func encrypt(text []byte) (string, error) {
block, err := aes.NewCipher(key)
if err != nil {
return "", err
}
if _, err := io.ReadFull(rand.Reader, iv); err != nil {
return "", err
}
stream := cipher.NewCFBEncrypter(block, iv)
return base64.URLEncoding.EncodeToString(ciphertext), nil
}
func decrypt(cryptoText string) ([]byte, error) {
ciphertext, err := base64.URLEncoding.DecodeString(cryptoText)
if err != nil {
return nil, err
}
block, err := aes.NewCipher(key)
if err != nil {
return nil, err
}
iv := ciphertext[:aes.BlockSize]
ciphertext = ciphertext[aes.BlockSize:]
stream := cipher.NewCFBDecrypter(block, iv)
stream.XORKeyStream(ciphertext, ciphertext)
return ciphertext, nil
}
func messageHandlerWithEncryption(w http.ResponseWriter, r *http.Request) {
conn, err := upgrader.Upgrade(w, r, nil)
if err != nil {
log.Println("Error upgrading connection:", err)
return
}
defer conn.Close()
for {
_, message, err := conn.ReadMessage()
if err != nil {
log.Println("Error reading message:", err)
connMutex.Lock()
connMutex.Unlock()
break
}
if err := json.Unmarshal(message, &msg); err != nil {
log.Println("Error unmarshalling message:", err)
continue
}
encryptedMessage, err := encrypt([]byte(msg.Message))
if err != nil {
log.Println("Error encrypting message:", err)
continue
}
msg.Message = encryptedMessage
log.Printf("Received message from %s: %s\n", msg.Email, msg.Message)
if err != nil {
log.Println("Error inserting message:", err)
}
for conn := range connections {
if err := conn.WriteJSON(msg); err != nil {
log.Println("Error writing message:", err)
continue
}
}
}
}
代码解释:
encrypt
函数对消息进行加密。decrypt
函数对消息进行解密。messageHandlerWithEncryption
函数处理 WebSocket 消息,并在发送消息前对其进行加密。用户权限控制模块实现更复杂的用户权限管理。服务器根据用户的角色和权限,限制其访问某些功能和数据。
package main
import (
"log"
"net/http"
)
func adminOnly(h http.HandlerFunc) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
email := r.Header.Get("Email")
var role string
if err != nil {
log.Println("Error querying user role:", err)
return
}
if role != "admin" {
http.Error(w, "Forbidden", http.StatusForbidden)
return
}
h(w, r)
}
}
func userOnly(h http.HandlerFunc) http.HandlerFunc {
return func(w http.ResponseWriter, r *http.Request) {
email := r.Header.Get("Email")
if email == "" {
http.Error(w, "Unauthorized", http.StatusUnauthorized)
return
}
if err != nil {
log.Println("Error querying user role:", err)
http.Error(w, "Internal server error", http.StatusInternalServerError)
return
}
if role != "user" && role != "admin" {
http.Error(w, "Forbidden", http.StatusForbidden)
return
}
h(w, r)
}
}
func main() {
log.Println("Starting server on :8080")
log.Fatal(http.ListenAndServe(":8080", nil))
}
代码解释:
adminOnly
函数是一个中间件,用于限制只有管理员角色的用户才能访问特定的处理函数。userOnly
函数是一个中间件,用于限制只有用户或管理员角色的用户才能访问特定的处理函数。main
函数中,使用这些中间件来保护特定的API端点。在实现上述功能的同时,我们也考虑了一些安全性问题:
本文深入探讨了如何使用 Go 语言构建一个功能完备的实时聊天系统,该系统不仅支持用户注册、登录,还提供了管理员接口用于管理聊天记录。
此外,我们还扩展了系统的功能,包括用户在线状态管理、消息加密和解密、以及更复杂的用户权限控制。
希望本项目能为对实时通信系统感兴趣的读者提供一些参考和帮助。
完整详细代码请访问以下链接(godev/ChatAPP):
GitHub - alexjjzc/godev: go language developmentgo language development. Contribute to alexjjzc/godev development by creating an account on GitHub.https://github.com/alexjjzc/godev