4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

Juniper JUNOS PyEz (python library)を試すメモ 3 ~PyEzによる設定変更~

Last updated at Posted at 2016-09-21

時間が空いてしまいましたが、前回までに環境構築とJUNOSの情報取得をしたため、今回は、JUNOSの設定変更を試してみる。

#1.概要
PyEzのjnpr.junos.utils.config.Configモジュールを使用することで、ASCII text, Junos XML, or Junos OS setコマンドのファイルを読み込み、設定変更をしたり、Jinja2 Template objectsを使ったテンプレートベースの設定変更が可能。

設定変更を行う場合は、JUNOSのCLIと同じように設定読込とCommitによる反映という、以下のようなプロセスで行われる。

Configuration Process

  • lock() - コンフィグレーションのロック
  • load() - 設定の読込 (rollback()やrescue()による設定戻しも可)
  • commit() - 設定の反映
  • unlock() - コンフィグレーションのアンロック

commit時のオプションを指定して、コメントを残したり、RE冗長時にsynchさせたりすることもできる。

尚、設定の読込は、 こちらもJUNOSのCLIの load replace, load merge, or load overwriteと同じく、上書きや追加の指定して設定変更する。
これは、loadオペレーションのときに、mergeおよびoverwriteパラメータを指定することで、選択可能。

今回はASCII textのファイルを読み込んで設定追加をする方法と、Jinja2を使ったテンプレートベースの設定追加を試してみる。

#2.ファイルからのコンフィグレーション読み込み
ファイルの読み込みの場合、拡張子でASCII text(.conf,.text,.txt), Junosのsetコマンド(.set), XML(.xml)を指定する。

読み読み時に、pathパラメータでファイルのパスを指定することで、そのファイルを読み込む。
例えば、

conf_file = "configs/junos-config-add-syslog-ntp.conf"
cu.load(path=conf_file, format="text", merge=True)

サンプルとして、syslogのntp notice設定を追加するのをPyEzで行う場合を示す。
pythonファイルの他に読込用のコンフィグレーションファイルを用意。

junos-config-add-syslog-ntp.conf
system {
    syslog {
        file messages {
            ntp notice;
        }
    }
}

こちらがPythonのサンプル。

ch-config-ntp.py
from jnpr.junos import Device
from jnpr.junos.utils.config import Config

conf_file = 'configs/junos-config-add-syslog-ntp.conf'

# open a connection with the device and start a NETCONF session
dev = Device(host='10.0.0.243', user='xxx', password='xxx', port='22', gather_facts=False)
dev.open()
dev.bind(cu=Config)

# Lock the configuration, load configuration changes, and commit as load merge
print "Locking the configuration"
dev.cu.lock()

print "Loading configuration changes"
dev.cu.load(path=conf_file, merge=True)

print "Committing the configuration"
dev.cu.commit(comment='Loaded by example.')

print "Unlocking the configuration"
dev.cu.unlock()

# End the NETCONF session and close the connection
dev.close()

尚、 jnpr.junos.exceptionモジュールでexceptionも用意されているため、実行できなかったときのエラー確認のために、それぞれのプロセスでexceptしておくと以下のようになる。

ch-config-ntp-exception.py
from jnpr.junos import Device
from jnpr.junos.utils.config import Config
from jnpr.junos.exception import ConnectError
from jnpr.junos.exception import LockError
from jnpr.junos.exception import UnlockError
from jnpr.junos.exception import ConfigLoadError
from jnpr.junos.exception import CommitError

conf_file = 'configs/junos-config-add-syslog-ntp.conf'


def main():
    # open a connection with the device and start a NETCONF session
    try:
        dev = Device(host='10.0.0.243', user='xxxx', password='xxxx', port='22
', gather_facts=False)
        dev.open()
    except ConnectError as err:
        print "Cannot connect to device: {0}".format(err)
        return

    dev.bind(cu=Config)

    # Lock the configuration, load configuration changes, and commit
    print "Locking the configuration"
    try:
        dev.cu.lock()
    except LockError as err:
        print "Unable to lock configuration: {0}".format(err)
        dev.close()
        return

    print "Loading configuration changes"
    try:
        dev.cu.load(path=conf_file, merge=True)
    except (ConfigLoadError, Exception) as err:
        print "Unable to load configuration changes: {0}".format(err)
        print "Unlocking the configuration"
        try:
                dev.cu.unlock()
        except UnlockError:
            print "Unable to unlock configuration: {0}".format(err)
        dev.close()
        return

    print "Committing the configuration"
    try:
        dev.cu.commit(comment='Loaded by example.')
    except CommitError as err:
        print "Unable to commit configuration: {0}".format(err)
        print "Unlocking the configuration"
        try:
            dev.cu.unlock()
        except UnlockError as err:
            print "Unable to unlock configuration: {0}".format(err)
        dev.close()
        return

    print "Unlocking the configuration"
    try:
        dev.cu.unlock()
    except UnlockError as err:
        print "Unable to unlock configuration: {0}".format(err)

    # End the NETCONF session and close the connection
    dev.close()

if __name__ == "__main__":
        main()

#3.Jinja2テンプレートの活用
Jinja2を使うことで、テンプレートを利用して、類似コンフィグが容易に作成することもできる。
Jinja2とは、Pythonのテンプレートエンジンで、名前の由来は、テンプレート ⇒ テンプル ⇒ 神社、のようだ。
Jinja2のテンプレートは、ファイル読込と同じく、サポートされたフォーマットのASCII text, Junos XML elements, Junos OS setコマンドを使用する。
Jinjaのテンプレートのフォーマットは、{% ... %} や {{ ... }} が可変部分で、それ以外の部分はすべて定型文となる。
 {% ... %} は変数宣言・代入やループ処理などを実行
 {{ ... }} は結果の表示
{%に使用するの制御構造はこちらを参照。

テンプレートを使用する方法は、load()メソッドのオプションでテンプレートを指定。
template_pathでテンプレートのファイルを指定し、template_varsでパラメータを指定。

cu.load(template_path=conf_file, template_vars=config, merge=True)

今回は、各interfaceにmpls,rsvpの設定追加をするテンプレートを使用し、パラメータであるinterface名などはyamlファイルで読込んでみる。テンプレートもASCII textにしている。

テンプレートファイルはこちら

junos-config-interfaces-mpls.conf
interfaces {
    {% for item in interfaces %}
    {{ item }} {
        description "{{ description }}";
        unit 0 {
            family {{ family }};
        }
    } {% endfor %}
}
protocols {
    mpls {
        {% for item in interfaces %}
        interface {{ item }};
        {% endfor %}
    }
    rsvp {
        {% for item in interfaces %}
        interface {{ item }};
        {% endfor %}
    }

}

パラメータファイルはこちら

mpls_interface.yml
---
interfaces:
    - ge-0/0/0
    - ge-0/0/1
description: 'MPLS interface'
family: mpls

基本的には、ファイル読み込みの時と同じスクリプト(ch-config-ntp-exception.py)をベースにして、load()でテンプレートやパラメータを指定しているだけのため、異なる部分だけ抜粋する。

add-config-mpls-template.py抜粋

import yaml

conf_file = 'configs/junos-config-interfaces-mpls.conf'
yml_config = yaml.load(open('configs/mpls_interface.yml'))

dev.cu.load(template_path=conf_file, template_vars=yml_config, merge=Tru
e)

これで指定したinterfaceに対するmpls, rsvpの設定が追加できる。

#4.まとめ
今回もつらつら書いたが、PyEzを使って、JUNOSの設定変更ができることが確認できた。
PyEzでは、情報取得や設定変更以外にも、configの比較、OSのアップグレード、scpによるファイル転送なども可能。

JUNOSとPyEzの両方を把握しないと触りにくいかもしれないが、Pythonを詳しく知らないエンジニアでも、簡単に必要なパラメータの確認や、設定変更ができそう。これらを使って、webで叩けるように仕組みを作っておくと、エキスパートのネットワークエンジニア以外でも確認や変更ができたり、他システムと連携させることで、ダイナミックに状況にあわせて設定変更が可能なネットワークインフラを作るなど、アイデア次第で活用方法は広がりそうだ。

今後は不定期に、ほかのAutomation Stackなども試してみる予定。

4
3
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
4
3

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?