Comment utiliser le Websocket de Golang pour développer des fonctions de cartographie en temps réel
Dans le développement d'applications Web d'aujourd'hui, les exigences en temps réel sont de plus en plus élevées, en particulier celles impliquant des applications liées à la localisation géographique, telles que les fonctions de cartographie en temps réel . La technologie Websocket de Golang peut fournir une communication bidirectionnelle rapide et en temps réel, adaptée au développement de fonctions cartographiques en temps réel. Dans cet article, je vais vous présenter comment utiliser le Websocket de Golang pour développer des fonctions cartographiques en temps réel, tout en fournissant des exemples de code spécifiques.
1. Concepts de base
1.1 Websocket
Websocket est un nouveau protocole introduit par HTML5. C'est une technologie qui établit une communication bidirectionnelle sur le protocole HTTP traditionnel. Websocket utilise le port standard HTTP/HTTPS pour établir une longue connexion entre le client et le serveur, afin que le serveur puisse transmettre des données au client en temps réel. Dans le même temps, Websocket prend également en charge la communication bidirectionnelle similaire au protocole TCP, permettant au client et au serveur de transmettre des données en même temps.
1.2 Golang
Golang est un langage de programmation rapide, efficace et sûr, particulièrement adapté au développement Web. Le développement Websocket de Golang peut utiliser le module websocket fourni par la bibliothèque standard net/http, ce qui est très pratique et simple.
2. Étapes de mise en œuvre
2.1 Configuration de l'environnement
Tout d'abord, vous devez installer Golang, qui peut être téléchargé et installé à partir du site officiel. Ensuite, entrez la commande suivante sur la ligne de commande pour installer le module websocket :
allez chercher github.com/gorilla/websocket
2.2 Implémentation du backend
Dans Golang, écrire le serveur Websocket est relativement simple. Vous pouvez utiliser la fonction HandleFunc de la bibliothèque http pour créer un routeur et spécifier la fonction de traitement des requêtes. Dans la fonction de traitement, utilisez la fonction Upgrader de la bibliothèque websocket pour basculer le protocole HTTP vers le protocole Websocket et utilisez les fonctions ReadMessage et WriteMessage pour implémenter une communication bidirectionnelle. Voici un exemple simple :
package main import ( "log" "net/http" "github.com/gorilla/websocket" ) func main() { http.HandleFunc("/", serveHome) http.HandleFunc("/ws", handleWebSocket) if err := http.ListenAndServe(":8080", nil); err != nil { log.Fatal("ListenAndServe: ", err) } } func serveHome(w http.ResponseWriter, r *http.Request) { http.ServeFile(w, r, "index.html") } var upgrader = websocket.Upgrader{ ReadBufferSize: 1024, WriteBufferSize: 1024, } func handleWebSocket(w http.ResponseWriter, r *http.Request) { conn, err := upgrader.Upgrade(w, r, nil) if err != nil { log.Println(err) return } defer conn.Close() for { messageType, p, err := conn.ReadMessage() if err != nil { log.Println(err) return } log.Printf("Received message: %s", p) err = conn.WriteMessage(messageType, p) if err != nil { log.Println(err) return } } }
2.3 Implémentation du front-end
Dans le front-end, utilisez JavaScript pour établir une connexion Websocket, puis utilisez la fonction send pour envoyer des informations au serveur et utilisez la fonction onmessage pour recevoir messages poussés par le serveur. Voici un exemple simple :
var socket = new WebSocket("ws://localhost:8080/ws"); socket.onopen = function(event) { socket.send("Hello, server!"); }; socket.onmessage = function(event) { console.log("Received message: " + event.data); };
3. Exemple de carte en temps réel
Ci-dessous, nous allons combiner les deux parties ci-dessus et utiliser la technologie Websocket de Golang pour implémenter une fonction de carte en temps réel.
3.1 Implémentation du backend
Côté serveur, nous pouvons utiliser la bibliothèque standard de Golang « net/http » et la bibliothèque tierce « gorilla/websocket » pour implémenter la communication Websocket. Le code spécifique est le suivant :
package main import ( "encoding/json" "flag" "fmt" "html/template" "log" "net/http" "sync" "github.com/gorilla/websocket" ) const ( MapWidth = 800 MapHeight = 600 ) var ( port = flag.Int("port", 8888, "http listen port") addr = flag.String("addr", "localhost", "http server address") mu sync.Mutex connections map[*websocket.Conn]bool ) func init() { connections = make(map[*websocket.Conn]bool) } type Position struct { X float64 `json:"x"` Y float64 `json:"y"` } type Location struct { Name string `json:"name"` Position Position `json:"position"` } type Map struct { Name string `json:"name"` ImageURL string `json:"image_url"` Locations []Location `json:"locations"` } var ( maps = []Map{ Map{ Name: "Campus Map", ImageURL: "/static/campus_map.png", Locations: []Location{ Location{ Name: "Library", Position: Position{ X: 400, Y: 300, }, }, Location{ Name: "Dormitory Building", Position: Position{ X: 300, Y: 200, }, }, Location{ Name: "Teaching Building", Position: Position{ X: 500, Y: 400, }, }, }, }, } ) func main() { flag.Parse() http.HandleFunc("/", indexPageHandler) http.HandleFunc("/ws", wsHandler) staticHandler := http.FileServer(http.Dir("static")) http.Handle("/static/", http.StripPrefix("/static/", staticHandler)) addr := fmt.Sprintf("%s:%d", *addr, *port) log.Printf("Starting server on %s", addr) err := http.ListenAndServe(addr, nil) if err != nil { log.Fatal("ListenAndServe: ", err) } } func indexPageHandler(w http.ResponseWriter, r *http.Request) { indexTemplate := template.Must(template.ParseFiles("templates/index.html")) indexTemplate.ExecuteTemplate(w, "index.html", maps) } type Message struct { Action string `json:"action"` Location string `json:"location"` } func wsHandler(w http.ResponseWriter, r *http.Request) { ws, err := websocket.Upgrade(w, r, nil, 1024, 1024) if err != nil { http.Error(w, "Could not open websocket connection", http.StatusBadRequest) return } defer ws.Close() mu.Lock() connections[ws] = true mu.Unlock() for { msgType, msg, err := ws.ReadMessage() if err != nil { delete(connections, ws) return } else { log.Printf("Received: %s ", msg) m := &Message{} if err := json.Unmarshal(msg, m); err != nil { log.Printf("Failed to unmarshal message %s: %v", msg, err) } else { switch m.Action { case "move": sendUpdate(ws, m.Location) updateMap(m.Location) case "logout": delete(connections, ws) } } } for c := range connections { err = c.WriteMessage(msgType, msg) if err != nil { delete(connections, c) log.Printf("Error writing to user [%s]: %v ", c.RemoteAddr(), err) } } } } func updateMap(loc string) { for i := range maps { for j := range maps[i].Locations { if maps[i].Locations[j].Name == loc { maps[i].Locations[j].Position.X += 20 maps[i].Locations[j].Position.Y += 20 } } } } func sendUpdate(ws *websocket.Conn, loc string) { for i := range maps { if maps[i].Name == "Campus Map" { msg := &Message{ Action: "update", Location: loc, } for j := range maps[i].Locations { location := maps[i].Locations[j] msgBody, _ := json.Marshal(location) if err := ws.WriteMessage(websocket.TextMessage, msgBody); err != nil { log.Printf("Could not send message: %v", err) } } break } } }
3.2 Implémentation du front-end
Dans le front-end, utilisez JavaScript pour établir une connexion Websocket, puis utilisez la fonction send pour envoyer des informations au serveur et utilisez la fonction onmessage pour recevoir messages poussés par le serveur. Des cartes en direct HTML5 peuvent être dessinées à l'aide de balises SVG. Voici un exemple simple :
<!doctype html> <html> <head> <title>Realtime Map</title> <style> #map { width: 800px; height: 600px; } </style> </head> <body> <svg id="map"> <image xlink:href="{{ .ImageURL }}" width="{{ .Width }}" height="{{ .Height }}" /> {{ range $location := .Locations }} <circle id="{{ $location.Name }}" cx="{{ $location.Position.X }}" cy="{{ $location.Position.Y }}" r="5" fill="red" /> {{ end }} </svg> <script> var ws = new WebSocket("ws://localhost:8888/ws"); ws.onopen = function(event) { console.log("WebSocket connected"); }; ws.onmessage = function(event) { var data = JSON.parse(event.data); if (data.action === "update") { var location = data.location; var $circle = document.getElementById(location.name); var x = parseFloat($circle.getAttribute("cx")); var y = parseFloat($circle.getAttribute("cy")); $circle.setAttribute("cx", x + location.position.x); $circle.setAttribute("cy", y + location.position.y); } }; window.addEventListener("load", function() { var $circles = document.querySelectorAll("#map circle"); for (var i = 0; i < $circles.length; i++) { $circles[i].addEventListener("click", function() { var location = this.id; var msg = { action: "move", location: location }; ws.send(JSON.stringify(msg)); }); } }); </script> </body> </html>
IV. Résumé
Après avoir présenté les concepts de base de la technologie Websocket de Golang, cet article fournit un exemple de développement de la fonction de carte en temps réel. L'exemple ci-dessus peut dessiner une carte via des balises HTML5 et SVG, utiliser la technologie Websocket pour réaliser une communication bidirectionnelle en temps réel et réaliser la fonction de carte en temps réel. Bien entendu, ce qui précède ne sont que des exemples. Dans des scénarios réels, des améliorations et des optimisations appropriées doivent être apportées en fonction des exigences spécifiques de l'application.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!