Filebeatを使ってサーバーのコンテナログを収集する

kubernetesのコンテナログをElastisearchサーバーに送る際のFilebeatの構築方法を説明します．values.yamlを作りhelmでインストールします．

## 環境

<img width="400" alt="image.png" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/3519238/81d7b81d-b1ee-4b98-44ab-ba026a444f54.png">

kubernetesにあるすべてのNodeのログをFilebeatで収集します．

Elastisearchサーバーには，ElastisearchとLogstashが立っていればOKです．
Elastisearchだけでも可能ですが，ログを検索する際にログが構造化されて便利なので入れておくといいと思います．
上の図にはありませんがKibanaでログが収集できているか簡単に確認することができます．

やることは下記の2つです．
①Elastisearchのユーザー名とパスワードをsetしたsecretをkubernetesに作る
②failbeatのvalues.yamlを書いてhelmでインストール


## ①Elastisearchのユーザー名とパスワードをsetしたsecretをkubernetesに作る

まずElastisearchサーバーにsshしてElastisearchのsecret名を確認します．
```
user@user-vm:~$ kubectl get secret -n elastic
NAME                               TYPE                 DATA   AGE
sh.helm.release.v1.kb.v1           helm.sh/release.v1   1      28d
sh.helm.release.v1.ls.v1           helm.sh/release.v1   1      28d
sh.helm.release.v1.fb.v1           helm.sh/release.v1   1      28d
sh.helm.release.v1.fb.v2           helm.sh/release.v1   1      19d
sh.helm.release.v1.ls.v2           helm.sh/release.v1   1      20d
elasticsearch-master-credentials   Opaque               2      7d1h
```
一番下のelasticsearch-master-credentialsにelasticsearchのユーザー名とパスワードが書かれています．

次にこのsecretからユーザー名とパスワードを確認します．

ユーザー名
```
user@user-vm:~$ kubectl get secret elasticsearch-master-credentials -n elastic -o jsonpath='{.data.username}' | base64 --decode

elastic
```
パスワード
```
user@user-vm::~$ kubectl get secret elasticsearch-master-credentials -n elastic -o jsonpath='{.data.password}' | base64 --decode

zS7ZFirfC21h48Qn
```
上記の場合，ユーザー名がelastic，パスワードがzS7ZFirfC21h48Qnになります．

次にコンテナログを収集したいkubernetesクラスタにsshします．
さっきのユーザー名とパスワードをsetしてelasticsearch-master-credentialsという名前のsecretを作ります．
```
kubectl create secret generic elasticsearch-master-credentials --from-literal=username=user --from-literal=password=zS7ZFirfC21h48Qn -n filebeat
```

念のため確認します．
```
user@kube:~$ kubectl get secret -A
NAMESPACE     NAME                                    TYPE                 DATA   AGE
kube-system   test-wordpress.node-password.k3s        Opaque               1      52d
kube-system   chart-values-traefik-crd                Opaque               0      52d
kube-system   chart-values-traefik                    Opaque               1      52d
kube-system   sh.helm.release.v1.traefik-crd.v1       helm.sh/release.v1   1      52d
kube-system   sh.helm.release.v1.traefik.v1           helm.sh/release.v1   1      52d
kube-system   k3s-serving                             kubernetes.io/tls    2      52d
filebeat      elasticsearch-master-credentials        Opaque               2      7d1h
filebeat      sh.helm.release.v1.fb.v1                helm.sh/release.v1   1      7d1h
```
これでネームスペースfilebeatにelasticsearch-master-credentialsというsecretができました．

## ②failbeatのvalues.yamlを書いてhelmでインストール
yamlを書きます．このyamlで全てのノードを指定でき，ノードの数分Filebeatが立ちます．
ホスト名，ポート番号とindex名を自分のものに変えてください．
indexが分からない場合はyamlの下にあるコマンドを使ってください．

```fb-values.yaml
extraEnvs: []
daemonset:
  filebeatConfig:
    filebeat.yml: |
      logging.level: error
      filebeat.autodiscover:
        providers:
          - type: kubernetes
            node: ${NODE_NAME}
            hints.enabled: true
            hints.default_config:
              type: container
              paths:
                - /var/log/containers/*${data.kubernetes.container.id}.log
              fields:
                index: logstash
          - type: kubernetes
            node: worker-node-label
            hints.enabled: true
            hints.default_config:
              type: container
              paths:
                - /var/log/containers/*${data.kubernetes.container.id}.log
              fields:
                index: logstash　#ログを入れたいインデックス名にする
          - type: kubernetes
            hints.enabled: true
            hints.default_config:
              type: container
              paths:
                - /var/log/containers/*.log
              fields:
                index: logstash
      output.logstash: 
        hosts: ["ls-logstash:5044"] #ここを持ってくるサーバーのホスト名とポート番号にする
      setup.template:
        name: "k8s"
        pattern: "k8s-*"
        enabled: false
      setup.ilm.enabled: false
  secretMounts: []
  deployment:
    extraEnvs: []
    annotations: {}

```

index確認コマンド
↓ここではlogstashとeclog2というindexがElastisearchにあります．
そのため，上記のyamlではこのどちらかを設定します．
```
user@kube:~$ curl -X GET "http://user@user-vm:30594/_cat/indices?v"
health status index    uuid                   pri rep docs.count docs.deleted store.size pri.store.size
green  open   logstash ffnbMqQRSVCSoe7DUg-WqA   1   1    1253300       152543      3.1gb          1.5gb
green  open   eclog2   4TMqod3gTuq_XP4K38spYA   1   1      75615       204555     75.1mb         37.5mb
```

helmでインストールします．
まずrepoを追加します．
```
helm repo add elastic https://helm.elastic.co
```
インストール
unifbのところはhelmのリリース名なので好きに決めてください．
```
helm install unifb elastic/filebeat -n filebeat -f fb.yaml
```

これでFilebeatが立ちます．
出力結果　
```
uset@user:~$ kubectl get all
NAME                             READY   STATUS    RESTARTS         AGE
pod/unifb-filebeat-zpl9p         1/1     Running   43 (3d11h ago)   16d
pod/unifb-filebeat-gzdsl         1/1     Running   3 (4d12h ago)    16d
pod/unifb-filebeat-zqpxr         1/1     Running   3 (4d12h ago)    16d

NAME                            DESIRED   CURRENT   READY   UP-TO-DATE   AVAILABLE   NODE SELECTOR   AGE
daemonset.apps/unifb-filebeat   4         4         4       4            4           <none>          33d
```