kakkotetsu

Nexus9000v で Telemetry

最初に

やること/サマリ

  • NX-OS の Telemetry 機能を軽く様子見
    • 細かいカスタマイズをシコシコやっていると、まるで盆栽のように終わりがなかったので、ほんの触り
    • 送信側は以下のように動かす
      • 送信プロトコル gRPC
        • 選択肢としては HTTP や TCPUDP も可能らしい
      • エンコード方式 GPB(Google protocol buffer)
        • 選択肢としては JSON も可能らしい
      • データコレクタタイプ DME(Data Management Engine)
        • メーカがプレ定義したスキーマに従う (netconf schema やら SNMP MIB やら...を思い浮かべて頂ければと)
        • show コマンドの結果を NX-OS API を使って出すこともできるらしい
    • 受信側は以下のように動かす
      • gRPC サーバ、GPB デコード、Elasticsearch への転送をしてくれる Cisco の Receiver を使う
      • Elasticsearch にデータを溜め込み、Kibana で可視化(クエリの定義などシコシコシコシコ...) これも Cisco が用意しているものをベースにする

今回の完成図はこんなところまで

f:id:kakkotetsu:20171009140610p:plain

構成

前回の構成 と一緒
BGP + VxLAN + EVPN あたりが動いている torSW101a を送信側として使います。

なお、receiver 側は各スイッチの management ポートと通信可能なところに、適当なサーバを置いておきます。

参考資料

機器側からの送信に関してはマニュアルとデータ構造(詳細仕様までは分からないが...)が揃っています。
受信に関しては、インストールしてノンカスタマイズで綺麗に見えるようなメーカ謹製系のやつは見当たらなかったので、メーカが提供している Docker Hub 上のそれっぽいのを。

環境情報

受信側サーバ (前述の Cisco Docker image を動かす)

Docker インストールは Get Docker CE for Ubuntu あたりを参考に済ませているものとして。

$ uname -a
Linux receiver 4.4.0-96-generic #119-Ubuntu SMP Tue Sep 12 14:59:54 UTC 2017 x86_64 x86_64 x86_64 GNU/Linux

$ cat /etc/lsb-release
DISTRIB_ID=Ubuntu
DISTRIB_RELEASE=16.04
DISTRIB_CODENAME=xenial
DISTRIB_DESCRIPTION="Ubuntu 16.04.3 LTS"

$ docker --version
Docker version 17.09.0-ce, build afdb6d4

$ docker-compose --version
docker-compose version 1.16.1, build 6d1ac21

NX-OS

例によって 4GB メモリで限界を狙う。

torsw101a# show version

...

NX-OSv9K is a demo version of the Nexus Operating System

Software
  BIOS: version
  NXOS: version 7.0(3)I6(1)
  BIOS compile time:
  NXOS image file is: bootflash:///nxos.7.0.3.I6.1.bin
  NXOS compile time:  5/16/2017 22:00:00 [05/17/2017 15:21:28]


Hardware
  cisco NX-OSv Chassis
   with 4037916 kB of memory.
  Processor Board ID 90SNLUQJ25I

  Device name: torsw101a
  bootflash:    3509454 kB
Kernel uptime is 28 day(s), 7 hour(s), 12 minute(s), 9 second(s)

構築~動作確認

Telemetry Receiver 初期設定

以下、どちらも同じサーバ上で動かします。
何度も立ち上げなおしたり恒久的に動かすものでもないので docker-compose は使ってないです。

dockercisco/elklat インストール~サービス起動

まずは Docker Hub の公式手順 ままで pull ~ run ~ 初期設定

$ docker pull dockercisco/elklat
$ docker images
REPOSITORY                      TAG                 IMAGE ID            CREATED             SIZE
dockercisco/elklat              latest              826e2f062fc4        10 months ago       6.54GB


$ docker run -d -p 5601:5601 -p 9200:9200 -p 5044:5044 -it 826e2f062fc bash

$ docker exec -it  cranky_sinoussi service elasticsearch start
$ docker exec -it  cranky_sinoussi service elasticsearch status
 * elasticsearch is running

$ docker exec -it  cranky_sinoussi service kibana start
$ docker exec -it  cranky_sinoussi service kibana status
 * kibana is running

これで http://<Docker母艦IPアドレス>:5601/ で Kibana の画面を見られる筈です。

Elasticsearch の mapping 設定(最低限)

Kibana で各 _source@timestamp を拾うにあたって、Elasticsearch に格納されているどのフィールドを使うか...という設定をするのですが。
この後入れる telemetryreceiver が送り付けてくるデータ構造は、postDate というフィールドが何故か Unix Time 形式になってしまっています。
このまま Elasticsearch で自動的に mapping が生成されると postDate が Kibana 上で String やら Integer やらとして解釈されてしまいます。
仕方ないので、ここだけは手動で mapping を作ってやります。

まず、既に過去のデータが telemetry という index に格納されているので、これを掃除して

$ curl -XDELETE <Docker母艦IPアドレス>:9200/telemetry

そのうえで以下のように mapping を定義

$ curl -X PUT -H "Content-Type: application/json" -d @- <<EOT http://<Docker母艦IPアドレス>:9200/_template/tmpl_telemetry
{
  "template": "telemetry*",
  "mappings": {
    "modify": {
      "properties": {
          "postDate": {
            "type": "date",
            "format": "strict_date_optional_time||epoch_millis"
          }
      }
    }
  }
}
EOT

dockercisco/telemetryreceiver インストール

2017/10/08 時点で見たところ latest の更新日時が 2017/10/06 になっていて、絶賛開発中の模様です。
で、なんとなく嫌な予感がして一世代前の v4 を入れました。(深い理由はないです)

$ docker pull dockercisco/telemetryreceiver:v4

$ docker images
REPOSITORY                      TAG                 IMAGE ID            CREATED             SIZE
dockercisco/telemetryreceiver   latest              fbbc29139f5b        2 days ago          1.1GB
dockercisco/telemetryreceiver   v4                  454c1e98fcbb        7 weeks ago         1.1GB
dockercisco/elklat              latest              826e2f062fc4        10 months ago       6.54GB

$ docker run -d -p 50001:50001 -it fbbc29139f5b bash
$ docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS                                                                    NAMES
a70cce08a261        fbbc29139f5b        "bash"              46 seconds ago      Up 45 seconds       0.0.0.0:50001->50001/tcp                                                 dreamy_lamarr
68a5f661093b        826e2f062fc         "bash"              6 minutes ago       Up 6 minutes        0.0.0.0:5044->5044/tcp, 0.0.0.0:5601->5601/tcp, 0.0.0.0:9200->9200/tcp   cranky_sinoussi

$ docker exec -it  vigilant_benz /grpc/telemetry/src/telemetry_receiver 50001 <Docker母艦IPアドレス> 9200 1
Server listening on 0.0.0.0:50001

最後の receiver プログラムを動かすやつは、公式手順では 末尾 "&" でバックグラウンド動作させています。
フォアグラウンドで動かしておくと、標準出力で以下のように NX-OS からの受信状況をリアルタイムで見るのに便利なので、そうしただけ。

Received GPB RPC with Data size is: 237550 Total RPC count:4926
Received GPB RPC with Data size is: 9043 Total RPC count:4927
Received GPB RPC with Data size is: 4627 Total RPC count:4928
Received GPB RPC with Data size is: 237550 Total RPC count:4929
Received GPB RPC with Data size is: 9043 Total RPC count:4930
Received GPB RPC with Data size is: 4627 Total RPC count:4931
Received GPB RPC with Data size is: 237550 Total RPC count:4932

Telemetry Sender 設定

NX-OS 側の設定を。
7.0(3)I6(1) では、エージェントインストールなど特にする必要なく、単純に CLI で feature 有効化~送信設定をするだけです。

torsw101a# show run section telemetry
show running-config | section telemetry

feature telemetry
telemetry
  destination-group 100
    ip address <Docker母艦IPアドレス> port 50001 protocol gRPC encoding GPB
  sensor-group 100
    path sys/bgp depth unbounded
    path sys/bd depth unbounded
    path sys/epId-1/nws depth unbounded
  subscription 600
    dst-grp 100
    snsr-grp 100 sample-interval 10000

sensor-group にて Cisco 公式 / Cisco Nexus 3000 and 9000 Series Telemetry Sources や実際に送信されるデータ内容を見比べながら、シコシコシコシコとカスタマイズをしていくことになります。

Kibana 初期設定(index)

ここまでで「NX-OS がデータを送信して、telemetry_receiverがデコード~Elasticsearchに格納」ってところまではできている筈です。
まあ必要に応じて、Elasticsearch に $ curl -XGET <Docker母艦IPアドレス>:9200/telemetry/_search -d '{"query" : { "match_all" : {} }}' | python3 -m json.tool とかすれば、格納されている情報がザッと(デフォルトは10件まで)見える。

なので、今度は Kibana の設定をば。
telemetry_receiver はデフォルトで telemetry という名前で index 作っているので、それを拾う設定をします。
以下のように、既に届いているデータ構造の中から Time-field name として postDate が選択肢に現れるので、それを選択します。(先の mapping 設定 at Elasticsearch がちゃんとしていれば)

f:id:kakkotetsu:20171009010547p:plain

これで画面上側の Discover タブを選んで、左上の index 選択で telemetry を選んでやれば、ザーッと右側にデータが並びます。

f:id:kakkotetsu:20171009010617p:plain

Kibana / NX-OS でカスタマイズ

ここからは、以下のようなカスタマイズをひたすらに繰り返していくことになります。

  • どんな情報を NX-OS から送信して
  • どんな情報をどんな条件で Kibana で Visualize して
  • どんな風に Kibana で Dashboard を見るか

既に Kibana の画面上で Settings > Objects を見ると各種 VisualizationDashboard が並んでいます。
が、これは別にそのまま使えるわけではなく(何かのデモで使ったものをベースにしているのか、開発中のものなのか)、少なくとも以下のようなカスタマイズが必要です。

  • KibanaVisualizations
    • indextelemetry 以外が指定されていたりするので、適宜変更
      • なお telemetry_receiverlatest では index も自分で指定できるようになっていたので、もう少しカスタマイズがきく筈
    • node_id_str という Field (要はNX-OS側のホスト名)がハードコードされていたりするので、適宜変更
    • 送信側である程度条件を絞っている、という前提がある(ものもある)ようで、送信側を雑に設定した時には期待通りの値を得られないので適宜変更
    • 仮想版では正常に得られないような情報もありそうなので適宜修正
    • etc etc
  • NX-OSsensor-group path
    • 送信したい情報を選択
      • どの階層にどの情報があるのか、マニュアルだけだとちゃんと分からないので試行錯誤

それでも、受信側をゼロから全てやっていくよりは大分マシだと思いますが。

例えば、以下のように事前定義されている Visualizations Object が並んでいますが

f:id:kakkotetsu:20171009010644p:plain

その一つを編集画面はこんな感じで、「あー、この情報を NX-OS 側から送信するのね」とかやっていきます。

f:id:kakkotetsu:20171009010718p:plain

んで、自分向けのカスタマイズをして Visualizations の一つが最低限の正しい情報が見られるようになって...

f:id:kakkotetsu:20171009010756p:plain

それを繰り返していけば、デフォルトの Dashboard も少しずつ情報が埋まっていくし、自分好みのものも作れるでしょう。(折角なので時系列なやつも見られるようにしたいですよね)

f:id:kakkotetsu:20171009010819p:plain

おしまい ~ここからが本当の地獄だ...!!~

最後に述べたような盆栽カスタマイズをしていて、メーカ謹製の受信側アプリケーションがあると楽が出来るのかなーと。(SNMPの時代から変わらないですが)
Kibana も Elasticsearch も大規模環境でお守りをしていく...ことを考えると、なかなかしんどい。この辺はまあ、自分で頑張るか金で何とかするかの話ですね...。
あと、特に受信側はコンピュータリソースをかなり食うので、得たい・得るべき情報とそのコストを天秤にかけて運用に乗せるには結構手をかけねばな、という感触です。

はい、グダグダ言ってないで盆栽弄りに戻ります...。