gNOIシステムサービス
gNOI System サービスを使用して、デバイスの再起動、ソフトウェアのアップグレード、ネットワークのトラブルシューティングなど、ターゲットネットワークデバイス上でシステム操作を実行します。
概要
gNOI System サービスは、RPCがネットワークデバイス上で以下の操作を含むさまざまなシステム操作を実行することを可能にします。
- デバイスの再起動
- ping コマンドとtracerouteコマンドを実行して、ネットワークのトラブルシューティングを行う
- ソフトウェアのアップグレード
- ルーティングエンジンスイッチオーバーを実行する
プロト定義ファイルは https://github.com/openconfig/gnoi/blob/master/system/system.proto にあります。
システム障害が発生した場合、 gnoi-system プロセスが再起動します。手動で再起動するには、 restart gnoi-system コマンドを使用します。
ネットワークデバイスの設定
始める前に:
- gRPCサービスを設定するの説明に従って、ネットワークデバイス上でgRPCサービスを設定します。
- gNOIサービスを設定するで説明されているように、gNOI操作をサポートするようにネットワーク管理システムを構成します。
SystemサービスRPCを使用するために追加の設定は必要ありません。
Pingとtraceroute
ネットワークデバイス上でpingおよびtracerouteコマンドを実行して、ネットワークの問題をトラブルシューティングできます。
| RPC | 説明 | リリースで導入 |
|---|---|---|
Ping() |
デバイスに Ping を実行します。 デフォルトのパケット数:5 |
Junos OS Evolved 22.2R1 |
Traceroute() |
ターゲットデバイスでtracerouteコマンドを実行し、結果をストリーミングバックします。 デフォルトのホップ数:30 |
Junos OS Evolved 22.2R1 |
例:Ping
この例では、クライアントは gnoi_ping_request.py Pythonアプリケーションを実行します。アプリケーションは Ping() RPCをネットワークデバイスに送信し、ネットワーク上の指定されたデバイスにpingを実行します。
gnoi_ping_request.pyアプリケーションは、チャネルを確立するためのgrpc_channelモジュールをインポートします。grpc_channelモジュールについては、gNOIサービスの設定で説明しています。アプリケーションの引数はgnoi_ping_request_args.txtファイルに格納されます。アプリケーションファイルと引数ファイルがここに示されています。
gnoi_ping_request.py
"""gRPC gNOI ping request utility.""" from __future__ import print_function import argparse import logging from getpass import getpass import system_pb2 import system_pb2_grpc from grpc_channel import grpc_authenticate_channel_mutual def get_args(parser): parser.add_argument('--server', dest='server', type=str, default='localhost', help='Server IP or name. Default is localhost') parser.add_argument('--port', dest='port', nargs='?', type=int, default=32767, help='The server port. Default is 32767') parser.add_argument('--client_key', dest='client_key', type=str, default='', help='Full path of the client private key. Default ""') parser.add_argument('--client_cert', dest='client_cert', type=str, default='', help='Full path of the client certificate. Default ""') parser.add_argument('--root_ca_cert', dest='root_ca_cert', required=True, type=str, help='Full path of the Root CA certificate.') parser.add_argument('--user_id', dest='user_id', required=True, type=str, help='User ID for RPC call credentials.') # Ping request arguments parser.add_argument('--destination', dest='destination', type=str, default=None, help='Destination IP. Default None') parser.add_argument('--source', dest='source', type=str, default=None, help='Source IP. Default None') parser.add_argument('--count', dest='count', type=int, default=None, help='Count of packets. Default None') parser.add_argument('--interval', dest='interval', type=int, default=None, help='Interval of packets in nanoseconds. Default None') parser.add_argument('--wait', dest='wait', type=int, default=None, help='Wait of packets in nanoseconds. Default None') parser.add_argument('--size', dest='size', type=int, default=None, help='Size of packets. Default None') parser.add_argument('--dnfragment', dest='dnfragment', type=int, default=0, help='Do not fragment. Default 0 (False)') parser.add_argument('--dnresolve', dest='dnresolve', type=int, default=0, help='Do not resolve. Default 0 (False)') parser.add_argument('--l3protocol', dest='l3protocol', type=int, default=None, help='L3 protocol (1=ipv4,2=ipv6). Default None') parser.add_argument('--timeout', dest='timeout', type=int, default=30, help='Timeout for ping. Default: 30 seconds') args = parser.parse_args() return args def send_rpc(channel, metadata, args): stub = system_pb2_grpc.SystemStub(channel) print("Executing GNOI::System::Ping Request RPC") req = system_pb2.PingRequest() if args.count != None: req.count = args.count if args.source != None: req.source = args.source if args.destination != None: req.destination = args.destination if args.interval != None: req.interval = args.interval if args.wait != None: req.wait = args.wait if args.size != None: req.size = args.size if args.dnfragment != 0: req.do_not_fragment = args.dnfragment if args.dnresolve != 0: req.do_not_resolve = args.dnresolve if args.l3protocol != None: req.l3protocol = args.l3protocol try: print("Ping Request Response starts\n") count = 1 for ping in stub.Ping(request=req, metadata=metadata, timeout=args.timeout): print("Response Source%s: %s " % (count, ping.source)) print("Time%s: %s" % (count, ping.time)) print("Sent%s: %s" % (count, ping.sent)) print("Receive%s: %s" % (count, ping.received)) print("Mintime%s: %s" % (count, ping.min_time)) print("Avgtime%s: %s" % (count, ping.avg_time)) print("Stddev%s: %s" % (count, ping.std_dev)) print("Bytes%s: %s" % (count, ping.bytes)) print("Sequence%s: %s" % (count, ping.sequence)) print("TTL%s: %s" % (count, ping.ttl)) count += 1 print("Ping Request Response ends\n") except Exception as e: logging.error('Error: %s', e) print(e) def main(): parser = argparse.ArgumentParser(fromfile_prefix_chars='@') args = get_args(parser) grpc_server_password = getpass("gRPC server password for executing RPCs: ") metadata = [('username', args.user_id), ('password', grpc_server_password)] try: # Establish grpc channel to network device channel = grpc_authenticate_channel_mutual( args.server, args.port, args.root_ca_cert, args.client_key, args.client_cert) response = send_rpc(channel, metadata, args) except Exception as e: logging.error('Received error: %s', e) print(e) if __name__ == '__main__': logging.basicConfig(filename='gnoi-testing.log', format='%(asctime)s %(levelname)-8s %(message)s', level=logging.INFO, datefmt='%Y-%m-%d %H:%M:%S') main()
gnoi_ping_request_args.txt
--server=10.0.2.1 --port=32767 --root_ca_cert=/etc/pki/certs/serverRootCA.crt --client_key=/home/lab/certs/client.key --client_cert=/home/lab/certs/client.crt --user_id=gnoi-user --destination=10.0.3.1 --source=10.0.2.1 --count=5
アプリケーションの実行
クライアントでアプリケーションを実行すると、RPC 呼び出し資格情報に対するサーバーのパスワードの入力を求められます。この PingResponse は、デバイスが5つのpingを送信したことを示しています。最終的な応答には、デバイスが 5 回の ping を送信し、5 回の応答を受信したことを示す ping リクエストの概要統計が含まれています。
lab@gnoi-client:~/src/gnoi/proto$ python3 gnoi_ping_request.py @gnoi_ping_request_args.txt gRPC server password for executing RPCs: Creating channel Executing GNOI::System::Ping Request RPC Ping Request Response starts Response Source1: 10.0.3.1 Time1: 741000 Sent1: 0 Receive1: 0 Mintime1: 0 Avgtime1: 0 Stddev1: 0 Bytes1: 64 Sequence1: 1 TTL1: 59 Response Source2: 10.0.3.1 Time2: 734000 Sent2: 0 Receive2: 0 Mintime2: 0 Avgtime2: 0 Stddev2: 0 Bytes2: 64 Sequence2: 2 TTL2: 59 Response Source3: 10.0.3.1 Time3: 704000 Sent3: 0 Receive3: 0 Mintime3: 0 Avgtime3: 0 Stddev3: 0 Bytes3: 64 Sequence3: 3 TTL3: 59 Response Source4: 10.0.3.1 Time4: 767000 Sent4: 0 Receive4: 0 Mintime4: 0 Avgtime4: 0 Stddev4: 0 Bytes4: 64 Sequence4: 4 TTL4: 59 Response Source5: 10.0.3.1 Time5: 800000 Sent5: 0 Receive5: 0 Mintime5: 0 Avgtime5: 0 Stddev5: 0 Bytes5: 64 Sequence5: 5 TTL5: 59 Response Source6: 10.0.3.1 Time6: 4111000000 Sent6: 5 Receive6: 5 Mintime6: 704000 Avgtime6: 749000 Stddev6: 32000 Bytes6: 0 Sequence6: 0 TTL6: 0 Ping Request Response ends
デバイスの再起動
SystemサービスRPCを使用して、デバイスをリモートで再起動し、再起動のステータスを確認し、必要に応じて再起動をキャンセルします。これらのRPCは、デバイス上または特定のサブコンポーネント上で実行できます。Junosデバイスは、以下の再起動方法をサポートしています。
-
COLD(1):すべてのタイプの再起動に使用できます。
-
パワーダウン(2):FPCおよびルーティングエンジン(コントローラカード)の再起動に使用します。
-
HALT (3): アクティブな制御プロセッサの再起動に使用します。
-
POWERUP(7):FPCおよびルーティングエンジン(コントローラカード)の再起動に使用します。
Junos OS Evolvedリリース25.2R1以降、ルーティングエンジンコンポーネントでPOWERDOWNおよびPOWERUPオプションを使用できるようになりました。デュアル ルーティングエンジン システムでは ルーティングエンジン の電源のみをダウンでき、両方のルーティング エンジンの電源を同時にオフにすることはできません。ルーティングエンジンは、次の再起動まで電源がオフのままになります。
ルーティングエンジンの電源を切り、再起動後も状態を維持するには、OpenConfig パス /components/component/controller-card/config/power-admin-state/ を POWER_DISABLED に設定します。この状態変更は、バックアップのルーティングエンジン上で直ちに有効になります。プライマリルーティングエンジンの状態は、再起動またはスイッチオーバー後にのみ変化します。
| RPC | 説明 | リリースで導入 |
|---|---|---|
Reboot() |
ターゲットを再起動します。ターゲットに対して一度に実行できる再起動要求は1つだけです。 オプションで、将来再起動する遅延を設定したり、サブコンポーネントを個別に再起動したり、再起動開始時にメッセージを追加したりできます。遅延はナノ秒単位で設定されます。 Junosデバイスは、以下の再起動方法をサポートしています。
|
Junos OS Evolved 22.2R1 |
RebootStatus() |
再起動のステータスを返します。 |
Junos OS Evolved 22.2R1 |
CancelReboot() |
保留中の再起動要求をキャンセルします。 |
Junos OS Evolved 22.2R1 |
例:再起動
この例では、クライアントは gnoi_reboot_request.py Pythonアプリケーションを実行します。アプリケーションは再起動要求を送信し、再起動のステータスを確認します。
このアプリケーションでは、ユーザーは再起動の遅延を秒単位で設定できます。 RebootRequest() は遅延をナノ秒単位で解釈するため、アプリケーションはユーザー入力をリクエストのナノ秒に変換します。この例では、クライアントは再起動操作に 60 秒の遅延を指定します。
gnoi_reboot_request.pyアプリケーションは、チャネルを確立するためのgrpc_channelモジュールをインポートします。grpc_channelモジュールについては、gNOIサービスを設定するで説明しています。アプリケーションの引数はreboot_status_request_args.txtファイルに格納されます。アプリケーションファイルと引数ファイルがここに示されています。
gnoi_reboot_status_request.py
"""gRPC gNOI reboot request and reboot status utility.""" from __future__ import print_function import argparse import logging from getpass import getpass import types_pb2 import system_pb2 import system_pb2_grpc from grpc_channel import grpc_authenticate_channel_mutual def get_args(parser): parser.add_argument('--server', dest='server', type=str, default='localhost', help='Server IP or name. Default is localhost') parser.add_argument('--port', dest='port', nargs='?', type=int, default=32767, help='The server port. Default is 32767') parser.add_argument('--client_key', dest='client_key', type=str, default='', help='Full path of the client private key. Default ""') parser.add_argument('--client_cert', dest='client_cert', type=str, default='', help='Full path of the client certificate. Default ""') parser.add_argument('--root_ca_cert', dest='root_ca_cert', required=True, type=str, help='Full path of the Root CA certificate.') parser.add_argument('--user_id', dest='user_id', required=True, type=str, help='User ID for RPC call credentials.') # Arguments for RebootRequest parser.add_argument('--method', dest='method', type=int, default=1, help='Reboot method. Valid value: 0 (UNKNOWN), 1 (COLD), 2 (POWERDOWN), 3 (HALT), 6 (reserved), 7 (POWERUP). Default 1') parser.add_argument('--delay', dest='delay', type=int, default=None, help='Delay in seconds before rebooting. Default 0') parser.add_argument('--message', dest='message', type=str, default=None, help='Message for rebooting.') parser.add_argument('--force', dest='force', type=int, default=None, help='Force reboot. Valid value 0|1. Default 0') parser.add_argument('--subcomponents', dest='subcomponents', type=str, default='', help='Subcomponents to reboot. Valid value re0,re1,fpc0,fpc8,etc. Default ""') args = parser.parse_args() return args def send_rpc(channel, metadata, args): # RebootRequest stub = system_pb2_grpc.SystemStub(channel) print("Executing GNOI::System::Reboot RPC") req = system_pb2.RebootRequest() # Add RebootRequest arguments req.method = args.method if args.delay != None: # gNOI delay is in nanoseconds. Convert from seconds to nanoseconds. req.delay = args.delay*(10**9) if args.message != None: req.message = args.message if args.force != None: req.force = args.force for subcomponent in args.subcomponents.split(","): if subcomponent == "": continue elem_key = {} elem_key["%s" % subcomponent] = subcomponent path_elem = [types_pb2.PathElem( name="%s" % subcomponent, key=elem_key)] path = types_pb2.Path(origin="origin", elem=path_elem) req.subcomponents.extend([path]) # RebootStatus print("Executing GNOI::System::Reboot Status RPC") req_status = system_pb2.RebootStatusRequest() try: reboot_response = stub.Reboot( request=req, metadata=metadata, timeout=60) status_response = stub.RebootStatus( request=req_status, metadata=metadata, timeout=60) print("Reboot status response received. %s" % status_response) except Exception as e: logging.error('Error: %s', e) print(e) else: logging.info('Received reboot status: %s', status_response) def main(): parser = argparse.ArgumentParser(fromfile_prefix_chars='@') args = get_args(parser) grpc_server_password = getpass("gRPC server password for executing RPCs: ") metadata = [('username', args.user_id), ('password', grpc_server_password)] try: # Establish grpc channel to network device channel = grpc_authenticate_channel_mutual( args.server, args.port, args.root_ca_cert, args.client_key, args.client_cert) send_rpc(channel, metadata, args) except Exception as e: print(e) logging.error('Received error: %s', e) if __name__ == '__main__': logging.basicConfig(filename='gnoi-testing.log', format='%(asctime)s %(levelname)-8s %(message)s', level=logging.INFO, datefmt='%Y-%m-%d %H:%M:%S') main()
reboot_status_request_args.txt
--server=10.0.2.1 --port=32767 --root_ca_cert=/etc/pki/certs/serverRootCA.crt --client_key=/home/lab/certs/client.key --client_cert=/home/lab/certs/client.crt --user_id=gnoi-user --message="Testing gNOI reboot" --delay=60
アプリケーションの実行
クライアントがアプリケーションを実行すると、RPC 呼び出し資格情報のサーバーのパスワードの入力を求められます。その後、アプリケーションは 60 秒の遅延後にサーバーを再起動し、該当する再起動ステータスメッセージを返します。 reason の下に設定されたメッセージは、サーバーが再起動する直前にサーバーにも表示されます。この例では、サーバーにログインしているすべてのユーザーに、再起動直前に「GNOI再起動のテスト中」と表示されます。
lab@gnoi-client:~/src/gnoi/proto$ python3 gnoi_reboot_status_request.py @reboot_status_request_args.txt gRPC server password for executing RPCs: Creating channel Executing GNOI::System::Reboot RPC Executing GNOI::System::Reboot Status RPC Reboot status response received! active: true wait: 59266969677 when: 1651788480000000000 reason: "Testing gNOI reboot" count: 5
ソフトウェアのアップグレード
表3は 、ソフトウェアアップグレードをサポートする システム サービスRPCの一覧です。
| RPC | 説明 | リリースで導入 |
|---|---|---|
SetPackage() |
ターゲットデバイスにソフトウェアイメージをインストールします。 |
Junos OS Evolved 22.2R1 |
SetPackage() RPCを使用して、ソフトウェアイメージをターゲットデバイスにコピーし、インストールできます。ソースソフトウェアイメージは、ローカルネットワーク管理システム上に存在する必要があります。ファイルのコピー操作が成功し、同じ名前のファイルがターゲットの場所に既に存在する場合、ファイルは上書きされます。RPC は、ターゲットの場所が存在しない場合、またはデータの書き込み中にエラーが発生した場合にエラーを返します。
デフォルトでは、デバイスの再起動やソフトウェアのアクティブ化は行われSetPackage()ません。新しいソフトウェアをアクティブ化するには、SetPackageRequestメッセージでactivateオプションを1に明示的に設定する必要があります。ソフトウェアをアクティブ化すると、デバイスが再起動し、新しいソフトウェア イメージが使用されます。ソフトウェアをアクティブ化しない場合は、関連するノードを再起動してインストールを完了し、新しいソフトウェア イメージをアクティブ化する必要があります。
例: ソフトウェア パッケージのインストール
この例では、クライアントは gnoi_system_set_package.py Pythonアプリケーションを実行し、以下の操作を実行します。
- ローカルネットワーク管理システムからネットワークデバイスにソフトウェアパッケージをコピーします。
- ネットワークデバイスにパッケージをインストールします。
- ネットワークデバイスを再起動して、新しいソフトウェアイメージをアクティブにします。
アプリケーションは、コピーおよびインストール操作の要求を定義する適切なパラメーターを使用して SetPackageRequest メッセージを構築します。次に、アプリケーションは SetPackage() RPC を呼び出して、ネットワーク デバイスに要求を送信します。 SetPackageRequest メッセージには、以下のコンポーネントが含まれています。
- ソフトウェアイメージのパスとファイル情報を含む最初の
Packageメッセージ。activate引数を1(True)に設定すると、デバイスが再起動し、ソフトウェアがアクティブになります。 - 64KBを超えない連続メッセージ内のソフトウェアイメージファイルのコンテンツのストリーム。
- ファイルの内容の整合性を検証するためのファイルのチェックサムを含む最後のメッセージ。
gnoi_system_set_package.pyアプリケーションは、チャネルを確立するためにgrpc_channelモジュールをインポートします。grpc_channelモジュールについては、gNOIサービスを設定するで説明しています。アプリケーションの引数はargs_system_set_package.txtファイルに格納されます。アプリケーションファイルと引数ファイルは次のとおりです。
gnoi_system_set_package.py
"""gRPC gNOI OS Upgrade Utility.""" from __future__ import print_function import argparse import hashlib import logging from functools import partial from getpass import getpass import system_pb2 import system_pb2_grpc from grpc_channel import grpc_authenticate_channel_mutual MAX_BYTES = 65536 def get_args(parser): parser.add_argument('--server', dest='server', type=str, default='localhost', help='Server IP or name. Default is localhost') parser.add_argument('--port', dest='port', nargs='?', type=int, default=32767, help='The server port. Default is 32767') parser.add_argument('--client_key', dest='client_key', type=str, default='', help='Full path of the client private key. Default ""') parser.add_argument('--client_cert', dest='client_cert', type=str, default='', help='Full path of the client certificate. Default ""') parser.add_argument('--root_ca_cert', dest='root_ca_cert', required=True, type=str, help='Full path of the Root CA certificate.') parser.add_argument('--user_id', dest='user_id', required=True, type=str, help='User ID for RPC call credentials.') parser.add_argument('--activate', dest='activate', type=int, default=0, help='Reboot and activate the package. Default: 0 (Do not reboot/activate). Valid value: 1 (Reboot/activate).') parser.add_argument('--filename', dest='filename', type=str, default='', help='Destination path and filename of the package. Default ""') parser.add_argument('--source_package', dest='source_package', type=str, default='', help='Full path of the source file to send. Default ""') parser.add_argument('--timeout', dest='timeout', type=int, default=None, help='Timeout in seconds.') parser.add_argument('--version', dest='version', type=str, default='', help='Version of the package. Default ""') args = parser.parse_args() return args def send_rpc(channel, metadata, args): stub = system_pb2_grpc.SystemStub(channel) print("Executing GNOI::System::SetPackage") # Create request # Add file information to request req = system_pb2.SetPackageRequest() req.package.activate = args.activate req.package.filename = args.filename it = [] it.append(req) # Prepare hash generator gen_hash = hashlib.sha256() # Read source package and add to request with open(args.source_package, "rb") as fd: # Read data in 64 KB chunks and calculate checksum and data messages for data in iter(partial(fd.read, MAX_BYTES), b''): req = system_pb2.SetPackageRequest() req.contents = data it.append(req) gen_hash.update(data) # Add checksum to request req = system_pb2.SetPackageRequest() req.hash.hash = gen_hash.hexdigest().encode() req.hash.method = 1 it.append(req) # Install the package try: logging.info('Installing package %s', args.source_package) print('SetPackage start.') response = stub.SetPackage( iter(it), metadata=metadata, timeout=args.timeout) print('SetPackage complete.') except Exception as e: logging.error('Software install error: %s', e) print(e) else: logging.info('SetPackage complete.') return response def main(): parser = argparse.ArgumentParser(fromfile_prefix_chars='@') args = get_args(parser) grpc_server_password = getpass("gRPC server password for executing RPCs: ") metadata = [('username', args.user_id), ('password', grpc_server_password)] try: # Establish grpc channel to network device channel = grpc_authenticate_channel_mutual( args.server, args.port, args.root_ca_cert, args.client_key, args.client_cert) response = send_rpc(channel, metadata, args) except Exception as e: logging.error('Error: %s', e) print(e) if __name__ == '__main__': logging.basicConfig(filename='gnoi-install.log', format='%(asctime)s %(levelname)-8s %(message)s', level=logging.INFO, datefmt='%Y-%m-%d %H:%M:%S') main()
args_system_set_package.txt
--server=10.0.2.1 --port=32767 --root_ca_cert=/etc/pki/certs/serverRootCA.crt --client_key=/home/lab/certs/client.key --client_cert=/home/lab/certs/client.crt --user_id=gnoi-user --activate=1 --filename=/var/tmp/junos-evo-install-ptx-x86-64-22.2R1.13-EVO.iso --source_package=/home/lab/images/junos-evo-install-ptx-x86-64-22.2R1.13-EVO.iso --timeout=1800
アプリケーションの実行
クライアントがアプリケーションを実行すると、アプリケーションはローカルデバイスからネットワークデバイスにパッケージをコピーしてインストールし、デバイスを再起動してインストールを完了します。
lab@gnoi-client:~/src/gnoi/proto$ python3 gnoi_system_set_package.py @args_system_set_package.txt gRPC server password for executing RPCs: Creating channel Executing GNOI::System::SetPackage SetPackage start. SetPackage complete.
ルーティングエンジンスイッチオーバー
SwitchControlProcessor() RPCを使用して、ルーティングエンジンスイッチオーバーを実行できます。
連続したルーティングエンジンスイッチオーバーイベントは、両方のルーティングエンジンが立ち上がってから少なくとも400秒間隔でなければなりません。
| RPC | 説明 | リリースで導入 |
|---|---|---|
SwitchControlProcessor() |
現在のルーティングエンジンから指定されたルーティングエンジンに切り替えます。現在のルーティングエンジンと指定されたルーティングエンジンが同じであれば、NOOPです。ターゲットが存在しない場合、RPC はエラーを返します。
注:
Junosデバイスは、 |
Junos OS Evolved 22.2R1 |
例:ルーティングエンジンのスイッチオーバー
この例では、gNOIクライアントが gnoi_system_switch_control_processor.py アプリケーションを実行してルーティングエンジンスイッチオーバーを実行します。クライアントは、 control_processor 引数を含めることで、どのスイッチ制御プロセッサ (ルーティングエンジン) をプライマリ ルーティングエンジンにするかを指定します。ターゲットルーティングエンジンが存在しない場合、RPC は INVALID_ARGUMENT エラーを返します。
アプリケーションは、チャネルを確立するための grpc_channel モジュールをインポートします。 grpc_channel モジュールについては、 gNOIサービスを設定するで説明しています。
gnoi_system_switch_control_processor.py
"""gNOI Routing Engine switchover request utility.""" from __future__ import print_function import argparse import logging from getpass import getpass import system_pb2 import system_pb2_grpc import types_pb2 from grpc_channel import grpc_authenticate_channel_mutual def get_args(parser): parser.add_argument('--server', dest='server', type=str, default='localhost', help='Server IP or name. Default is localhost') parser.add_argument('--port', dest='port', nargs='?', type=int, default=32767, help='The server port. Default is 32767') parser.add_argument('--client_key', dest='client_key', type=str, default='', help='Full path of the client private key. Default ""') parser.add_argument('--client_cert', dest='client_cert', type=str, default='', help='Full path of the client certificate. Default ""') parser.add_argument('--root_ca_cert', dest='root_ca_cert', required=True, type=str, help='Full path of the Root CA certificate.') parser.add_argument('--user_id', dest='user_id', required=True, type=str, help='User ID for RPC call credentials.') parser.add_argument('--control_processor', dest='control_processor', type=str, default='re1', help='Control processor that will assume the role of primary. Default is re1. Valid values are re0,re1.') args = parser.parse_args() return args def send_rpc(channel, metadata, processor): stub = system_pb2_grpc.SystemStub(channel) print("Executing GNOI::System::SwitchControlProcessor") elem_key = {} elem_key["%s" % processor] = processor path_elem = [types_pb2.PathElem(name="%s" % processor, key=elem_key)] path = types_pb2.Path(origin="origin", elem=path_elem) req = system_pb2.SwitchControlProcessorRequest(control_processor=path) # Send the request try: response = stub.SwitchControlProcessor( req, metadata=metadata, timeout=60) print("SwitchControlProcessor response:\n", response) except Exception as e: logging.error('Switchover error: %s', e) print(e) else: logging.info('SwitchControlProcessor response:\n %s', response) return response def main(): parser = argparse.ArgumentParser() args = get_args(parser) grpc_server_password = getpass("gRPC server password for executing RPCs: ") metadata = [('username', args.user_id), ('password', grpc_server_password)] try: # Establish grpc channel to network device channel = grpc_authenticate_channel_mutual( args.server, args.port, args.root_ca_cert, args.client_key, args.client_cert) response = send_rpc(channel, metadata, args.control_processor) except Exception as e: logging.error('Received error: %s', e) print(e) if __name__ == '__main__': logging.basicConfig(filename='gnoi-testing.log', format='%(asctime)s %(levelname)-8s %(message)s', level=logging.INFO, datefmt='%Y-%m-%d %H:%M:%S') main()
アプリケーションの実行
クライアントはアプリケーションを実行し、re1 がプライマリ ルーティングエンジンになるように control_processor 引数を re1 に設定します。
lab@gnoi-client:~/src/gnoi/proto$ python3 gnoi_system_switch_control_processor.py --server 10.0.2.1 --port 32767 --root_ca_cert /etc/pki/certs/serverRootCA.crt --client_key /home/lab/certs/client.key --client_cert /home/lab/certs/client.crt --user_id gnoi-user --control_processor re1 gRPC server password for executing RPCs: Creating channel Executing GNOI::System::SwitchControlProcessor SwitchControlProcessor response: version: "22.2R1.13-EVO" uptime: 1652478709000000000
操作の実行後、re1はターゲットデバイス上のプライマリルーティングエンジンとなります。
{master}
lab@gnoi-server-re1>
変更履歴テーブル
サポートされる機能は、使用しているプラットフォームとリリースによって決まります。 機能エクスプローラー を使用して、機能がお使いのプラットフォームでサポートされているかどうかを確認します。
System サービス Reboot() RPC を使用して、デュアル ルーティングエンジン デバイスの ルーティングエンジン(コントローラー カード)の電源をオンおよびオフにすることができます。