はじめに
<バージョン>
ansible 2.9.7
textfsm 1.1.0
ネットワーク機器のshowコマンド取得結果はそのままだと機械処理に向いていないので、
parserなどを使って機械処理に向いたデータに変換する必要があります。
以下はCisco ASAにおけるshow route結果をparserで変換した例になります。
※networktocode/ntc-templates - GitHub のcisco_asa_show_route.textfsmを使用しました。
Codes: L - local, C - connected, S - static, R - RIP, M - mobile, B - BGP
D - EIGRP, EX - EIGRP external, O - OSPF, IA - OSPF inter area
N1 - OSPF NSSA external type 1, N2 - OSPF NSSA external type 2
E1 - OSPF external type 1, E2 - OSPF external type 2, V - VPN
i - IS-IS, su - IS-IS summary, L1 - IS-IS level-1, L2 - IS-IS level-2
ia - IS-IS inter area, * - candidate default, U - per-user static route
o - ODR, P - periodic downloaded static route, + - replicated route
SI - Static InterVRF
Gateway of last resort is 172.31.16.1 to network 0.0.0.0
S* 0.0.0.0 0.0.0.0 [1/0] via 172.31.16.1, management
C 172.31.16.0 255.255.240.0 is directly connected, management
L 172.31.19.91 255.255.255.255 is directly connected, management
- DISTANCE: '1'
MASK: 0.0.0.0
METRIC: '0'
NETWORK: 0.0.0.0
NEXTHOPIF: management
NEXTHOPIP: 172.31.16.1
PROTOCOL: S
TYPE: ''
UPTIME: ''
- DISTANCE: ''
MASK: 255.255.240.0
METRIC: ''
NETWORK: 172.31.16.0
NEXTHOPIF: management
NEXTHOPIP: ''
PROTOCOL: C
TYPE: ''
UPTIME: ''
- DISTANCE: ''
MASK: 255.255.255.255
METRIC: ''
NETWORK: 172.31.19.91
NEXTHOPIF: management
NEXTHOPIP: ''
PROTOCOL: L
TYPE: ''
UPTIME: ''
showコマンド結果の抽出はパターンが多いので難しいのですが、以下のように
__parseする各データが1行に入っており、検索パターンが少ない場合__は
__正規表現の知識だけでparserが作れる__ので実際にやってみましょう。
id name age comment
1 Taro 20 hello
2 Hanako 22
3 Satoru 1
0. 下準備
今回はtextfsmを使用するのでインストールしておきましょう。
pip install textfsm
1. 必要な変数(出力する変数)の数を把握する
サンプルデータより、必要な変数は4つであるとわかります。
変数がわかったら以下のように正規表現でまとめましょう。
変数 | 正規表現 |
---|---|
id | \d+ |
name | [A-Z][a-z]+ |
age | \d+ |
comment | \w+ |
2. データ行の検索パターンを把握する
今回は以下の2通りであるとわかります。
(1)末尾にコメントがある場合
(2)末尾にコメントがない場合
確実にヒットさせるために、行頭を表す「^」と行末を表す「$$(2個)」を入れておきましょう。
^${id} ${name} ${age} ${comment}$$
^${id} ${name} ${age}$$
3. textfsmファイルを作成する
ここまでまとめてきた内容をtextfsmファイル(fsm_sample.textfsm)に書き起こしましょう。
__ValueやRecordなど決まっている変数の先頭は大文字にしないとエラー__になります。
- 出力する変数を記入する部分
- __Value 変数名 (正規表現)__と記入
- マッチさせるパターンを記入する部分
- Startと書いた行の下に、検索条件 -> Record と記入
- Recordの部分で変数が出力され、変数がリセットされる
# 出力する変数を記入
Value id (\d+)
Value name ([A-Z][a-z]+)
Value age (\d+)
Value comment (\w+)
# マッチさせるパターンを記入
Start
^${id} ${name} ${age} ${comment}$$ -> Record
^${id} ${name} ${age}$$ -> Record
4. parse用playbook作成
今回parseしたい内容は、sample_input内に記入しました。
parseする際は、「parse_cli_textfsm(fsmファイルのパス)」と記入してください。
---
- hosts: localhost
gather_facts: false
vars:
sample_input: |
id name age comment
1 Taro 20 hello
2 Hanako 22
3 Satoru 1
tasks:
- name: debug
debug:
var: sample_input | parse_cli_textfsm('./fsm_sample.textfsm')
5. 実行結果
想定通りparseすることが出来ました。
(venv) [centos@ip-<ip-addr> ansible]$ ansible-playbook fsm_test.yml
PLAY [localhost] *******************************************************************************************************
TASK [debug] ***********************************************************************************************************
ok: [localhost] =>
sample_input | parse_cli_textfsm('./fsm_sample.textfsm'):
- age: '20'
comment: hello
id: '1'
name: Taro
- age: '22'
comment: ''
id: '2'
name: Hanako
- age: '1'
comment: ''
id: '3'
name: Satoru
PLAY RECAP *************************************************************************************************************
localhost : ok=1 changed=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
まとめ
簡単なparserなら正規表現の知識さえあれば作れることが分かったと思います。
parserがあると機械処理の幅が広がるので、自分でも作ってみましょう。
関連記事
ネットワーク機器のコマンド結果をパースする parse_cli_textfsm フィルタープラグインを試す
networktocode/ntc-templates - GitHub
google/textfsm - GitHub
【Ansible】textfsmのparserは簡単に作れる~応用編~