持續分析 Kubernetes 中服務的性能
開發人員通常需要查看生產應用程序中的性能瓶頸以確定問題的原因。為此,您通常需要可以通過日志和代碼工具收集的信息。不幸的是,這種方法通常很耗時,并且不能提供有關潛在問題的足夠詳細信息。
一種現代且更先進的方法是應用和使用分析技術和工具來突出顯示最慢的應用程序代碼,即消耗大部分資源的區域。
在這篇文章中,我們將討論持續分析,然后使用名為 Pyroscope 的開源工具檢測在 Kubernetes 上運行的微服務。
什么是Pyroscope?
必須對代碼進行分析、調試和審查,以確定使其運行得更快的最有效方法。使用分析工具檢查應用程序的代碼有助于我們定位和修復性能瓶頸。這可以快速診斷應用程序的執行情況,并使程序員能夠深入了解性能不佳的核心細節。結果是一個簡化的代碼庫,減少了 CPU/內存消耗,使用戶體驗更好!
Profiling 是一種程序分析,用于測量程序的內存、時間復雜度或函數調用的頻率和持續時間。分析信息用于幫助程序優化和性能。Profiler 程序可以跟蹤每一行代碼。
連續分析
Continuous Profiler 用于更快、更輕松地進行故障排除。Continuous Profiler 是生產代碼分析器,可讓您隨時間分析整個環境中的代碼級性能。隨著配置文件的不斷收集,它們可以在引入新代碼后快速揭示資源最密集的特性(或代碼行)。優化可以減少最終云提供商帳戶和用戶的延遲。
有哪些連續分析器?
因此,這里列出了您可能遇到的一些分析器:
- Pyroscope:Pyroscope是一個開源平臺,由服務器和代理組成。它允許用戶以 CPU 和磁盤高效的方式收集、存儲和查詢分析數據。
- Parca:Parca收集、存儲和提供配置文件,以便隨著時間的推移進行查詢。它是開源的,可以部署在生產環境中,因為 Parca 專注于對兩種主要類型的配置文件進行采樣分析:跟蹤和采樣。
- Datadog:Datadog Continuous Profiler始終在任何環境(包括生產環境)中分析和比較代碼性能。它指出了由低效代碼導致的難以復制的生產問題。還具有自動代碼分析洞察力。
- Google - Cloud Profiler:Cloud Profiler是一種低開銷的統計分析器,可從您的生產應用程序中持續收集 CPU 使用率和內存分配信息。它具有可操作的應用程序分析、低影響的生產 Profilin 和廣泛的平臺支持。
為什么使用 Pyroscope
在我們開始探索 Pyroscope 之前,讓我們看看它與市場上其他少數可用的連續分析工具有何不同。DataDog 和 Google Cloud Profiler 在業界被廣泛使用。正如一位 Reddit 用戶所指出的,以下是 Pyroscope 比其他兩個更好的一些原因。
資料來源:Datadog、Google Cloud 和 Pyroscope 連續分析功能的比較
Pyroscope 專注于構建專門用于分析數據的存儲引擎,以盡可能高效地存儲和查詢數據。它使用代理服務器模型將配置文件從應用程序發送到 Pyroscope 服務器:
資料來源:Pyroscope 是如何工作的?
Pyroscope 允許任何語言的分析器向其發送數據,并讓存儲引擎有效地存儲該數據。例如,Pyroscope 具有針對 Go、Python、Ruby、eBPF、Java、.NET、PHP 和 Rust 的語言特定代理。
另一方面,Parca 采用了稍微不同的方法,它依賴 eBPF 來編譯 C、C++、Go 等語言。在撰寫本文時,對其他語言的支持正在進行中。與 Pyroscope 類似,它也可以從 HTTP 端點讀取任何pprof 格式的配置文件。
從理論上講,由于所有這些語言最終都會編譯下來并在內核上運行,因此 eBPF 應該適用于這些語言中的任何一種。然而,在實踐中,如果你真的為 Python 等解釋性語言運行 eBPF,在許多情況下,函數名稱對人類來說是不可讀的。這是因為符號不是以這些語言存儲的。
出于這個原因,Pyroscope 同時支持特定于語言的分析器和 eBPF 分析器。與僅在內核級別運行的 eBPF 相比,這以集成語言特定代理的工作量稍多為代價。但它也帶來了更多可操作和人類可讀的配置文件的好處。
如何安裝 Pyroscope?
無論您使用什么,Docker、Linux,或者正在尋找 Ruby 或 Go 文檔,Pyroscope 都可以啟動服務器,然后再啟動代理。即使您的目標是 10 秒或 10 個月的軟件分析數據,他們定制設計的存儲引擎也可以進行快速查詢。
— Pyroscope 網站
我們將使用 minikube 來運行 Kubernetes 集群。使用 minikube 創建集群:
minikube start
添加 Helm 圖表存儲庫:
helm repo add pyroscope-io https://pyroscope-io.github.io/helm-chart
安裝 Helm 圖表:
helm install pyroscope pyroscope-io/pyroscope --set service.type=NodePort
檢查 Pyroscope Helm 圖表安裝成功:
helm list
檢查 Pyroscope 是否正在運行:
kubectl get all
現在我們的 Kubernetes 集群中運行了 Pyroscope,我們將繼續使用該應用程序的步驟。我們將使用Google 微服務來進行此演示。
將 Google 微服務演示與 Pyroscope 集成
我們將修改我們的容器鏡像以使用 pyroscope 二進制文件。這個二進制文件將啟動我們的應用程序并注入自己進行監控。您可以在此 Pyroscope 文檔中參考更多內容。
我們將使用來自 Google 微服務的 Python、Go 和 .NET 微服務進行演示。所有修改都推送到GitHub 上的 Google 微服務分支,讓我們來看看每個服務的這些更改。
注意:要在 Google 微服務演示中試用 Pyroscope,您無需自己構建 Docker 鏡像。您可以只應用 Kubernetes 清單,如從微服務獲取分析數據部分所示。
(1) Python
我們將使用用 Python 編寫的電子郵件服務應用程序。在DockerfilePyroscope 中使用 Python 應用程序需要進行以下更改。
COPY --from=pyroscope/pyroscope:latest /usr/bin/pyroscope /usr/bin/pyroscope
CMD [ "pyroscope", "exec", "python", "email_server.py" ]
編輯 Dockerfile 后,在同一文件夾下,我們繼續構建和推送鏡像。
docker build . -t beellzrocks/emailservice:latest
docker push beellzrocks/emailservice:latest
(2) .NET
我們將使用適用于 .NET 的應用程序 Cart Service。要將 .NET 應用程序與 Pyroscope 一起使用,需要對 Dockerfile 進行以下更改。
COPY --from=pyroscope/pyroscope:latest /usr/bin/pyroscope /usr/bin/pyroscope
ENTRYPOINT ["pyroscope", "exec", "-spy-name", "dotnetspy", "/app/cartservice"]
編輯 Dockerfile 后,我們繼續構建和推送鏡像。
(3) GO
我們將采用 Go 編寫的 Product Catalog Service 應用程序。要使用帶有 Pyroscope 的 Go 應用程序,需要對server.go進行以下更改。
import (
pyroscope "github.com/pyroscope-io/pyroscope/pkg/agent/profiler"
)
func main() {
pyroscope.Start(pyroscope.Config{
ApplicationName: os.Getenv("APPLICATION_NAME"),
ServerAddress: os.Getenv("SERVER_ADDRESS"),
})
// code here
)
編輯 server.go 后,我們繼續構建和推送鏡像。
從微服務獲取分析數據
我們修改了 Kubernetes 清單以將我們的圖像與 Pyroscope 一起使用。
該kubernetes-manifests.yaml文件包含所有應用程序的資源。我們對其進行了編輯以使用我們在上述步驟中構建的鏡像,即電子郵件服務、購物車服務、產品目錄服務。
containers:
- name: server
image: beellzrocks/emailservice
在 Kubernetes 中運行 Pyroscope 時,我們需要做以下更改:
- 添加SYS_PTRACE能力。
- 告訴代理 Pyroscope 服務器的位置,以及使用環境變量的應用程序名稱。
containers:
- name: server
env:
- name: PYROSCOPE_SERVER_ADDRESS # To change Pyroscope Server Port change the value
value: "http://pyroscope:4040"
- name: PYROSCOPE_APPLICATION_NAME # Application name shown in the UI
value: "email.service"
securityContext:
capabilities:
add:
- SYS_PTRACE
現在,要部署所有服務,您可以將 Kubernetes 清單應用到您的集群。
kubectl apply -f https://raw.githubusercontent.com/infracloudio/microservices-demo-dev/master/release/kubernetes-manifests.yaml
獲取 Pyroscope 的服務 url:
minikube service pyroscope
|-----------|-----------|-------------|---------------------------|
| NAMESPACE | NAME | TARGET PORT | URL |
|-----------|-----------|-------------|---------------------------|
| default | pyroscope | http/4040 | http://192.168.49.2:30639 |
|-----------|-----------|-------------|---------------------------|
?? Opening service default/pyroscope in default browser
要訪問 Pyroscope UI,您可以訪問 URL:http://192.168.49.2:30639(依據上述反饋打開實際地址)。
帶有 Pyroscope 服務器 CPU 的 Pyroscope UI
正如您在上面的屏幕截圖中看到的,Pyroscope 本身在本地存儲數據時占用的 CPU 使用率很低。它使用 Badger 數據庫在本地存儲數據。
Pyroscope 資源利用
監控 Kubernetes pod 在資源使用、利用率和成本控制方面也很重要。Pyroscope 使用低資源和低開銷。
Pyroscope CPU 利用率
使用 Pyroscope 進行監控
Pyroscope 根據編程語言使用不同的代理來分析代碼。下面是一些使用 Pyroscope 的分析應用程序的火焰圖示例。
帶有 Go 產品目錄服務應用程序的 Pyroscope
Pyroscope 與 .Net Cart 應用程序
帶有 Python 電子郵件應用程序的 Pyroscope
結論
持續分析性能是滿足最終用戶期望的關鍵因素。如果出現性能問題,您必須準備好在影響最終用戶體驗之前診斷問題。
因此,請繼續優化您的應用程序并立即解決問題,以繼續使用 Pyroscope 等工具為用戶提供超快速的應用程序性能。Pyroscope 展示了一層可見性,可幫助您了解如何在生產環境中提高代碼性能并降低云基礎架構成本。