基于Nginx和Cookie的灰度系统
2023-11-27 22:11:45 381
import (
"flag"
"fmt"
"net/http"
)
func main() {
port := flag.Int("port", 4444, "HTTP server port")
content := flag.String("content", "", "content")
flag.Parse()
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
htmlContent := "<!DOCTYPE html><html><head><title>Test Page</title></head><body><h1>Hello, this is a " + *content + "!</h1></body></html>"
w.Header().Set("Content-Type", "text/html")
w.Write([]byte(htmlContent))
})
addr := fmt.Sprintf(":%d", *port)
fmt.Printf("Server is running on http://localhost%s\n", addr)
err := http.ListenAndServe(addr, nil)
if err != nil {
fmt.Printf("Error starting server: %s\n", err)
}
}
go build server.go
改改参数, 启动两个进程
nohup ./server -port 4445 -content test1 > /dev/null 2>&1 &
修改nginx配置
upstream go-server1 {
server 127.0.0.1:4445;
}
upstream go-server2 {
server 127.0.0.1:4446;
}
upstream default {
server 127.0.0.1:4445;
}
server {
listen 80;
server_name localhost;
set $group "default";
if ($http_cookie ~* "version=1.0") {
set $group go-server1;
}
if ($http_cookie ~* "version=2.0") {
set $group go-server2;
}
location / {
proxy_pass http://$group;
}
}
实现效果
root@localhost:/usr/local/nginx# curl -H "Cookie: version=1.0" localhost
<!DOCTYPE html><html><head><title>Test Page</title></head><body><h1>Hello, this is a test1!</h1></body></html>
root@localhost:/usr/local/nginx# curl -H "Cookie: version=2.0" localhost
<!DOCTYPE html><html><head><title>Test Page</title></head><body><h1>Hello, this is a test2!</h1></body></html>
这样,我们就实现了灰度的功能
配合灰度配置系统, 进行流量染色, 即可实现完整的灰度发布.
流量染色可以是后端代码处理, 也可以是独立的中间件处理
这里以代码处理示例
修改server.go代码如下
package main
import (
"flag"
"fmt"
"math/rand"
"net/http"
"time"
)
func main() {
rand.Seed(time.Now().UnixNano())
port := flag.Int("port", 4444, "HTTP server port")
content := flag.String("content", "", "content")
flag.Parse()
http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {
htmlContent := "<!DOCTYPE html><html><head><title>Test Page</title></head><body><h1>Hello, this is a " + *content + "!</h1></body></html>"
random := rand.Intn(10)
if random < 2 {
cookie := http.Cookie{
Name: "version",
Value: "2.0",
}
http.SetCookie(w, &cookie)
}
w.Header().Set("Content-Type", "text/html")
w.Write([]byte(htmlContent))
})
addr := fmt.Sprintf(":%d", *port)
fmt.Printf("Server is running on http://localhost%s\n", addr)
err := http.ListenAndServe(addr, nil)
if err != nil {
fmt.Printf("Error starting server: %s\n", err)
}
}
在postman中发起调用, 请求几次后即可看到转发到了2.0
灰度系统=标记+染色