Docker筆記(十三):容器日誌採集實踐
阿新 • • 發佈:2020-04-03
日誌是服務執行過程中的一個關鍵環節,藉助日誌,我們可以排查定位問題,也可以藉助集中化的日誌管理平臺(如ELK)來做一些必要的資料統計分析。在Docker環境中,日誌的採集比傳統環境更為複雜,因此瞭解Docker日誌的管理機制,及基於此熟悉日誌採集的最佳實踐對於開發運維人員來說也是避不開的一個知識點。那就開始吧。
## Docker容器的日誌管理機制
### 1. Docker Daemon日誌
Docker Daemon在Linux中本身作為systemd service啟動,因此可以通過 `sudo journalctl -u docker` 命令來檢視Daemon本身的日誌。
### 2. Docker容器日誌
通過 `docker logs container_id|container_name` 可以檢視Docker容器的輸出日誌,但這裡的日誌只包含容器的標準輸出(STDOUT)與標準錯誤輸出(STDERR),適用於一些將日誌輸出到STDOUT的容器,比如Nginx,檢視nginx的dockerfile可發現其是將日誌檔案連結到了STDOUT與STDERR來實現的,
```shell
RUN ln -sf /dev/stdout /var/log/nginx/access.log
&& ln -sf /dev/stderr /var/log/nginx/error.log
```
但如果容器內部應用日誌是輸出到日誌檔案(比如Spring Boot專案或Tomcat容器,一般將日誌輸出到日誌檔案中),則無法通過 `docker logs` 命令檢視。
> `docker logs` 會顯示歷史日誌,日誌太多的話要等半天才能看到最新日誌,同時也對Docker Daemon造成一定的壓力,可使用 `docker logs --tail 200 container_id`來檢視最新的N條或使用`docker logs -f container_id`(類似於tail -f)
### 3. Docker日誌處理機制
當我們啟動一個容器時,其實是作為Docker Daemon的一個子程序執行,Docker Daemon可以拿到容器裡程序的標準輸出與標準錯誤輸出,然後通過Docker的Log Driver模組來處理。如下圖所示
![docker-log-driver.png](https://img2020.cnblogs.com/other/632381/202004/632381-20200403091632758-1162008992.png)
目前支援的Log Drvier包括:
* none:容器沒有日誌,`docker logs`不輸出任何內容
* local:日誌以自定義格式儲存
* json-file:日誌以json格式儲存,預設的Log Driver
* syslog:將日誌寫入syslog。syslog守護程式必須在主機上執行
* journald:將日誌寫入journald。journald守護程式必須在主機上執行
* gelf:將日誌寫入Graylog Extended Log Format端點,如Graylog或Logstash
* fluentd:將日誌寫入fluentd。fluentd守護程式必須在主機上執行
* awslogs:將日誌寫入Amazon CloudWatch Logs
* splunk:通過HTTP Event Collector將日誌寫入splunk
* etwlogs:將日誌作為ETW(Event Tracing for Windows)事件寫入。只在Windows平臺可用
* gcplogs:將日誌寫入Google Cloud Platform Logging
* logentries:將日誌寫入Rapid7 Logentries
使用Docker-CE版本時,**`docker logs`命令僅適用於 local, json-file, journald 三種Log Driver**。
可通過`docker info`來檢視Docker Daemon(針對所有容器)或`docker inspect`來檢視單個容器所使用的Log Driver
```shell
# Docker Daemon
[devuser@test-server-1 ~]$ docker info |grep "Logging Driver"
Logging Driver: json-file
# 單個Docker 容器
[devuser@test-server-1 ~]$ docker inspect -f '{{.HostConfig.LogConfig.Type}}' 76f82aa32468
json-file
```
修改Docker Daemon使用的Log Driver可通過修改配置檔案 /etc/docker/daemon.json 進行,重啟Docker後該配置對該Docker Daemon管理的所有容器生效, 如
```json
{
"log-driver": "local",
"log-opts": {
"max-size": "10m",
"max-file": 3
}
}
```
設定單個容器的Log Driver則可以在容器執行時通過引數指定,如
```shell
[root@tool-server ~]# docker run -d --name nginx -p 80:80 --log-driver local --log-opt max-size=10m --log-opt max-file=3 --restart=always nginx
63155291e724276d6154a26958b0e523a003958b1cdf7df9f1f0903bfc989b99
[root@tool-server ~]# tail -f /var/lib/docker/containers/63155291e724276d6154a26958b0e523a003958b1cdf7df9f1f0903bfc989b99/local-logs/container.log
stdoutҭʡ