「Go 工具箱」解析 http 中的 user-agent,就用這個包:user_agent
大家好,我是漁夫子。「Go 學堂」新推出 “Go 工具箱” 系列,意在給大家分享使用 go 語言編寫的、實用的、好玩的工具。
今天給大家推薦一個解析 HTTP 請求頭中 user-agent 字段的庫:user_agent 。目前騰訊藍鯨智雲配置平臺都在用這個包。
一、User-Agent 是什麼
User-Agent 叫做用戶代理,是 HTTP 協議中請求頭中的一個字段值。通過該字段值可以告訴網站服務器用戶使用的什麼產品發送的 http 請求。該信息一般發送請求的產品名稱、操作系統、版本號等信息。大家熟知的瀏覽器其實就是所謂的一種用戶代理。
通過谷歌的 chrome 瀏覽器,我們可以看到 user-agent 字段值如下:user-agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/107.0.0.0 Safari/537.36
user-agent 是一個文本字符串,其符合以下語法:
User-Agent: <product> / <product-version> <comment>
該語法我們可以稱之爲一個組成單元,在一個 user-agent 中可以有多個這樣的組成單元,組成單元之間用空格分隔。
一般瀏覽器的 user-agent 的格式如下:
User-Agent: Mozilla/5.0 (<system-information>) <platform> (<platform-details>) <extensions>
看起來有點跟最上面 user-agent 的通用語法不一樣。下面是 chrome 瀏覽器中一個 http 請求的真實的 user-agent 值。我們以該值爲例來分解器結構:
Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/107.0.0.0 Safari/537.36
該值中我們通過 4 種顏色劃分了 4 個部分,每個部分實際上是通過空格劃分的。每個部分實際上都是符合 / 的語法的。如下:
在這個瀏覽器的實例中,每個部分又代表了不同的信息。如下:
關於瀏覽器中 UA 還有一些有趣的發展歷史,大家可以參考文末的參考鏈接。
二、User-Agent 能做什麼
2.1 根據用戶使用瀏覽器的不同,顯示不同的排版從而爲用戶提供更好的體驗。這就是我們平時看到的,用手機訪問谷歌和電腦訪問是不一樣的,這些是谷歌根據訪問者的 UA 來判斷的。
2.2 用於數據統計分析。例如可以根據 user-agent 中的信息統計來源於各平臺(PC、mobile、平板等)、用戶使用的操作系統(Android、iOS、Unix、Windows)等的數據。通過數據分析後進一步改善用戶的體驗。
當然,用戶代理不僅僅是瀏覽器,還可以是機器人、網絡爬蟲。網站服務器可以根據 user-agent 進行識別,以輸出不同的內容。
三、安裝 user-agent 包
使用 go get 進行安裝:
go get github.com/mssola/user_agent
四、user-agent 包的基本使用
我們看下 user-agent 包的使用。使用很簡單,直接上代碼:
package main
import (
"fmt"
"github.com/mssola/user_agent"
)
func main() {
// The "New" function will create a new UserAgent object and it will parse
// the given string. If you need to parse more strings, you can re-use
// this object and call: ua.Parse("another string")
ua := user_agent.New("Mozilla/5.0 (Linux; U; Android 2.3.7; en-us; Nexus One Build/FRF91) AppleWebKit/533.1 (KHTML, like Gecko) Version/4.0 Mobile Safari/533.1")
fmt.Printf("%v\n", ua.Mobile()) // => true
fmt.Printf("%v\n", ua.Bot()) // => false
fmt.Printf("%v\n", ua.Mozilla()) // => "5.0"
fmt.Printf("%v\n", ua.Model()) // => "Nexus One"
fmt.Printf("%v\n", ua.Platform()) // => "Linux"
fmt.Printf("%v\n", ua.OS()) // => "Android 2.3.7"
name, version := ua.Engine()
fmt.Printf("%v\n", name) // => "AppleWebKit"
fmt.Printf("%v\n", version) // => "533.1"
name, version = ua.Browser()
fmt.Printf("%v\n", name) // => "Android"
fmt.Printf("%v\n", version) // => "4.0"
// Let's see an example with a bot.
ua.Parse("Mozilla/5.0 (compatible; Googlebot/2.1; +http://www.google.com/bot.html)")
fmt.Printf("%v\n", ua.Bot()) // => true
name, version = ua.Browser()
fmt.Printf("%v\n", name) // => Googlebot
fmt.Printf("%v\n", version) // => 2.1
}
該包的實現原理本質上就是對字符串按上面的規格進行解析。但同時需要考慮各種 user-agent 中的細微差別。所以該包不僅僅是一個簡單的封裝,而是需要具有對 user-agent 在各平臺、各種場景下的深入瞭解才能做到的。
參考鏈接:
瀏覽器 UA 的發展歷史:https://www.zhihu.com/question/306775584
瀏覽器 UA 的發展歷史(英文版):https://webaim.org/blog/user-agent-string-history/
本文由 Readfog 進行 AMP 轉碼,版權歸原作者所有。
來源:https://mp.weixin.qq.com/s/8YRqypiW1dQQVlZkmCd1mQ