APO 日誌介紹
採集流程圖
APO 使用 ilogtail 作為日誌採集組件並改造支持額外功能,在 vector 中進行日誌結構化處理。
APO 日誌功能
- 日誌指標
統計日誌數並生成日誌數指標。出現錯誤日誌時,計算日誌錯誤指標 - 故障現場日誌
應用程序出現慢或者錯誤trace時,將這段時間內的日誌收集並寫入clickhouse中。使用 k8s 信息或 pid 信息關聯故障鏈路和故障現場日誌 - 全量日誌
1.APO日誌界面中提供了為不同應用配置不同的日誌解析規則,vector 根據解析規則將日誌結構化,解析規則中提取的日誌字段會單獨成列加快查詢
2.日誌庫支持全文檢索和查看日誌上下文
APO 日誌中使用logstash或fluent
用户如果已經使用 logstash 或者 fluent 生態的日誌採集組件,可直接與APO日誌進行對接。但需要注意的是,使用對接日誌採集組件可能會導致某些信息的缺失或功能無法使用。
APO 日誌僅全量日誌功能可用
APO 日誌不可用功能
- 故障現場日誌:APO 使用改造後的 ilogtail 添加 K8S 信息或 PID 信息,使用 logstash 或 fluent 替換 ilogtail 會導致在 K8S 和虛機環境中均無法關聯鏈路和日誌信息,導致功能缺失
- 日誌指標:APO 使用 ilogtail 統計日誌指標,使用 logstash 或 fluent 替換 ilogtail 導致該功能缺失
logstash 或 fluent 需填充 K8S 相關信息
確保在 Kubernetes 環境中部署日誌採集組件,同時日誌需要填充以下標籤信息,同時這些標籤信息需要適當的重命名。重命名具體實現可以參考後續提供的 vector 配置示例。
- container.name -> 容器名
- container_id -> 容器ID
- k8s.namespace.name -> Kubernetes 命名空間
- k8s.pod.name -> Pod 名稱
- host.ip -> 節點 IP
- host.name -> 節點名稱
- source -> 文件路徑
- content -> 日誌內容
- timestamp -> 日誌採集時間
APO 接入日誌採集組件示例
當用户在 K8S環境中使用 Logstash 生態(如 filebeat, logstash)或 Fluent 生態(如 fluentd, fluent-bit),可參考如下示例接入 APO 日誌。
Logstash 生態示例 - 使用 Filebeat
1.設置 NODE_IP 和 NODE_NAME 環境變量
env:
- name: NODE_NAME
valueFrom:
fieldRef:
apiVersion: v1
fieldPath: spec.nodeName
- name: NODE_IP
valueFrom:
fieldRef:
apiVersion: v1
fieldPath: status.hostIP
2.配置 Filebeat
日誌採集組件如果和 APO Server 不在同一集羣,output.logstash 中的 hosts URL 設置為 Server 所在節點IP,Port 改為 30310
filebeat.inputs:
- type: filestream
id: kubernetes-container-logs
fields:
host.ip: ${NODE_IP}
fields_under_root: true
paths:
- /var/log/containers/*.log
parsers:
- container: ~
prospector:
scanner:
fingerprint.enabled: true
symlinks: true
file_identity.fingerprint: ~
processors:
- add_kubernetes_metadata:
host: ${NODE_NAME}
matchers:
- logs_path:
logs_path: "/var/log/containers/"
output.logstash:
hosts: ["apo-vector-svc.apo:4310"]
3.更新 apo-vector 的 ConfigMap
# 替換sources內容
sources:
logstash_log:
type: logstash
address: 0.0.0.0:4310
# 替換 transforms 的 flatten_logs 內容
transforms:
flatten_logs:
type: remap
inputs:
- logstash_log
source: |
."host.name" = .host.name
."host.ip" = .host.ip
.content = .message
."_source_" = .stream
."_container_id_" = .container.id
."k8s.namespace.name" = .kubernetes.namespace
."k8s.pod.name" = .kubernetes.pod.name
."container.name" = .kubernetes.container.name
del(.agent)
del(.log)
del(.message)
del(.kubernetes)
del(.container)
del(.input)
del(.orchestrator)
del(.ecs)
del(.host)
del(.@metadata)
del(.stream)
# 調試日誌信息,日誌採集對接成功後可移除
sinks:
to_print:
type: console
inputs:
- flatten_logs
encoding:
codec: json
json:
pretty: true
Fluent 生態示例 - 使用 Fluent Bit
1.設置 NODE_IP 和 NODE_NAME 環境變量
env:
- name: NODE_NAME
valueFrom:
fieldRef:
apiVersion: v1
fieldPath: spec.nodeName
- name: NODE_IP
valueFrom:
fieldRef:
apiVersion: v1
fieldPath: status.hostIP
2.配置 Fluent Bit 的解析、 輸入、過濾器和輸出配置。日誌採集組件如果和 APO Server 不在同一集羣,OUTPUT 中的 Host 設置為 Server 所在節點IP,Port 改為 30310
[Input]
Name tail
Path /var/log/containers/*.log
Refresh_Interval 10
Skip_Long_Lines true
Parser cri
Tag kube.*
[Filter]
Name kubernetes
Match kube.*
Kube_URL https://kubernetes.default.svc:443
Kube_CA_File /var/run/secrets/kubernetes.io/serviceaccount/ca.crt
Kube_Token_File /var/run/secrets/kubernetes.io/serviceaccount/token
Labels false
Annotations false
[FILTER]
Name modify
Match *
Add host_ip ${NODE_IP}
[OUTPUT]
Name forward
Match *
Host apo-vector-svc.apo
Port 4310
3.修改 apo-vector 的 ConfigMap 以匹配 Fluent Bit 輸出格式
# 替換sources內容
sources:
fluent_log:
type: fluent
address: 0.0.0.0:4310
# 替換 transforms 的 flatten_logs 內容
transforms:
flatten_logs:
type: remap
inputs:
- fluent_log
source: |
."host.name" = .kubernetes.host
."host.ip" = .host_ip
."_source_" = .stream
.content = .message
."_container_id_" = .kubernetes.docker_id
."k8s.namespace.name" = .kubernetes.namespace_name
."k8s.pod.name" = .kubernetes.pod_name
."container.name" = .kubernetes.container_name
del(.kubernetes)
del(.stream)
del(.message)
del(.host)
del(.host_ip)
# 調試日誌信息,日誌採集對接成功後可移除
sinks:
to_print:
type: console
inputs:
- flatten_logs
encoding:
codec: json
json:
pretty: true
APO 日誌對接問題排查
配置修改後,如果 APO 日誌界面仍未出現日誌,需要進行排查
問題1 vector中有日誌事件,但APO 界面無日誌
需要通過vector日誌查看日誌事件格式是否正確
vector 配置中添加調試日誌信息配置。觀察vector日誌中事件,通常正確的日誌信息包含如下信息。
{
"_container_id_": "852a7484f030",
"_source_": "stdout",
"container.name": "java-demo-1",
"content": "{\"level\":\"ERROR\",\"method\":\"org.apache.juli.logging.DirectJDKLog.log\",\"msg\":\"Servlet.service() for servlet [dispatcherServlet] in context with path [] threw exception [Request processing failed; nested exception is org.springframework.web.client.ResourceAccessException: I/O error on GET request for \\\"http://localhost:8082/api/jpa-demo/sleep\\\": Read timed out; nested exception is java.net.SocketTimeoutException: Read timed out] with root cause\",\"thread\":\"http-nio-8081-exec-2\"}",
"host.ip": "192.168.1.69",
"host.name": "node-69",
"k8s.namespace.name": "default",
"k8s.pod.name": "apo-java-demo-b7994cc54-ss58f",
"timestamp": "2024-09-25T07:46:38.146950792Z"
}
如果發現信息缺失,請參考填充 K8S 相關信息確保所有信息填充
問題2 vector日誌中未收到任何日誌事件
需要排查一下對接採集組件是否可以正常寫入vector
請查看filebeat,fluent-bit等採集組件等日誌信息
APO介紹:
國內開源首個 OpenTelemetry 結合 eBPF 的嚮導式可觀測性產品
apo.kindlingx.com
https://github.com/CloudDetail/apo