mirror of
https://git.proxmox.com/git/mirror_frr
synced 2025-08-05 06:23:04 +00:00
doc: initial documentation for gRPC
Give the FRR users some examples of gRPC usage in scripts to let them start experimenting with the new configuration interface provided by YANG/northbound. Signed-off-by: Rafael Zalamena <rzalamena@opensourcerouting.org>
This commit is contained in:
parent
0ddf7da445
commit
d92f5fd847
249
doc/developer/grpc.rst
Normal file
249
doc/developer/grpc.rst
Normal file
@ -0,0 +1,249 @@
|
||||
.. _grpc-dev:
|
||||
|
||||
***************
|
||||
Northbound gRPC
|
||||
***************
|
||||
|
||||
.. _grpc-languages-bindings:
|
||||
|
||||
Programming Language Bindings
|
||||
=============================
|
||||
|
||||
The gRPC supported programming language bindings can be found here:
|
||||
https://grpc.io/docs/languages/
|
||||
|
||||
After picking a programming language that supports gRPC bindings, the
|
||||
next step is to generate the FRR northbound bindings. To generate the
|
||||
northbound bindings you'll need the programming language binding
|
||||
generator tools and those are language specific.
|
||||
|
||||
Next sections will use Ruby as an example for writing scripts to use
|
||||
the northbound.
|
||||
|
||||
|
||||
.. _grpc-ruby-generate:
|
||||
|
||||
Generating Ruby FRR Bindings
|
||||
----------------------------
|
||||
|
||||
Generating FRR northbound bindings for Ruby example:
|
||||
|
||||
::
|
||||
|
||||
# Install the required gems:
|
||||
# - grpc: the gem that will talk with FRR's gRPC plugin.
|
||||
# - grpc-tools: the gem that provides the code generator.
|
||||
gem install grpc
|
||||
gem install grpc-tools
|
||||
|
||||
# Create your project/scripts directory:
|
||||
mkdir /tmp/frr-ruby
|
||||
|
||||
# Go to FRR's grpc directory:
|
||||
cd grpc
|
||||
|
||||
# Generate the ruby bindings:
|
||||
grpc_tools_ruby_protoc \
|
||||
--ruby_out=/tmp/frr-ruby \
|
||||
--grpc_out=/tmp/frr-ruby \
|
||||
frr-northbound.proto
|
||||
|
||||
|
||||
.. _grpc-ruby-if-sample:
|
||||
|
||||
Using Ruby To Get Interfaces State
|
||||
----------------------------------
|
||||
|
||||
Here is a sample script to print all interfaces FRR discovered:
|
||||
|
||||
::
|
||||
|
||||
require 'frr-northbound_services_pb'
|
||||
|
||||
# Create the connection with FRR's gRPC:
|
||||
stub = Frr::Northbound::Stub.new('localhost:50051', :this_channel_is_insecure)
|
||||
|
||||
# Create a new state request to get interface state:
|
||||
request = Frr::GetRequest.new
|
||||
request.type = :STATE
|
||||
request.path.push('/frr-interface:lib')
|
||||
|
||||
# Ask FRR.
|
||||
response = stub.get(request)
|
||||
|
||||
# Print the response.
|
||||
response.each do |result|
|
||||
result.data.data.each_line do |line|
|
||||
puts line
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
The generated files will assume that they are in the search path (e.g.
|
||||
inside gem) so you'll need to either edit it to use ``require_relative`` or
|
||||
tell Ruby where to look for them. For simplicity we'll use ``-I .`` to tell
|
||||
it is in the current directory.
|
||||
|
||||
|
||||
The previous script will output something like this:
|
||||
|
||||
::
|
||||
|
||||
$ cd /tmp/frr-ruby
|
||||
# Add `-I.` so ruby finds the FRR generated file locally.
|
||||
$ ruby -I. interface.rb
|
||||
{
|
||||
"frr-interface:lib": {
|
||||
"interface": [
|
||||
{
|
||||
"name": "eth0",
|
||||
"vrf": "default",
|
||||
"state": {
|
||||
"if-index": 2,
|
||||
"mtu": 1500,
|
||||
"mtu6": 1500,
|
||||
"speed": 1000,
|
||||
"metric": 0,
|
||||
"phy-address": "11:22:33:44:55:66"
|
||||
},
|
||||
"frr-zebra:zebra": {
|
||||
"state": {
|
||||
"up-count": 0,
|
||||
"down-count": 0
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "lo",
|
||||
"vrf": "default",
|
||||
"state": {
|
||||
"if-index": 1,
|
||||
"mtu": 0,
|
||||
"mtu6": 65536,
|
||||
"speed": 0,
|
||||
"metric": 0,
|
||||
"phy-address": "00:00:00:00:00:00"
|
||||
},
|
||||
"frr-zebra:zebra": {
|
||||
"state": {
|
||||
"up-count": 0,
|
||||
"down-count": 0
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.. _grpc-ruby-bfd-profile-sample:
|
||||
|
||||
Using Ruby To Create BFD Profiles
|
||||
---------------------------------
|
||||
|
||||
In this example you'll learn how to edit configuration using JSON
|
||||
and programmatic (XPath) format.
|
||||
|
||||
::
|
||||
|
||||
require 'frr-northbound_services_pb'
|
||||
|
||||
# Create the connection with FRR's gRPC:
|
||||
stub = Frr::Northbound::Stub.new('localhost:50051', :this_channel_is_insecure)
|
||||
|
||||
# Create a new candidate configuration change.
|
||||
new_candidate = stub.create_candidate(Frr::CreateCandidateRequest.new)
|
||||
|
||||
# Use JSON to configure.
|
||||
request = Frr::LoadToCandidateRequest.new
|
||||
request.candidate_id = new_candidate.candidate_id
|
||||
request.type = :MERGE
|
||||
request.config = Frr::DataTree.new
|
||||
request.config.encoding = :JSON
|
||||
request.config.data = <<-EOJ
|
||||
{
|
||||
"frr-bfdd:bfdd": {
|
||||
"bfd": {
|
||||
"profile": [
|
||||
{
|
||||
"name": "test-prof",
|
||||
"detection-multiplier": 4,
|
||||
"required-receive-interval": 800000
|
||||
}
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
EOJ
|
||||
|
||||
# Load configuration to candidate.
|
||||
stub.load_to_candidate(request)
|
||||
|
||||
# Commit candidate.
|
||||
stub.commit(
|
||||
Frr::CommitRequest.new(
|
||||
candidate_id: new_candidate.candidate_id,
|
||||
phase: :ALL,
|
||||
comment: 'create test-prof'
|
||||
)
|
||||
)
|
||||
|
||||
#
|
||||
# Now lets delete the previous profile and create a new one.
|
||||
#
|
||||
|
||||
# Create a new candidate configuration change.
|
||||
new_candidate = stub.create_candidate(Frr::CreateCandidateRequest.new)
|
||||
|
||||
# Edit the configuration candidate.
|
||||
request = Frr::EditCandidateRequest.new
|
||||
request.candidate_id = new_candidate.candidate_id
|
||||
|
||||
# Delete previously created profile.
|
||||
request.delete.push(
|
||||
Frr::PathValue.new(
|
||||
path: "/frr-bfdd:bfdd/bfd/profile[name='test-prof']",
|
||||
)
|
||||
)
|
||||
|
||||
# Add new profile with two configurations.
|
||||
request.update.push(
|
||||
Frr::PathValue.new(
|
||||
path: "/frr-bfdd:bfdd/bfd/profile[name='test-prof-2']/detection-multiplier",
|
||||
value: 5.to_s
|
||||
)
|
||||
)
|
||||
request.update.push(
|
||||
Frr::PathValue.new(
|
||||
path: "/frr-bfdd:bfdd/bfd/profile[name='test-prof-2']/desired-transmission-interval",
|
||||
value: 900_000.to_s
|
||||
)
|
||||
)
|
||||
|
||||
# Modify the candidate.
|
||||
stub.edit_candidate(request)
|
||||
|
||||
# Commit the candidate configuration.
|
||||
stub.commit(
|
||||
Frr::CommitRequest.new(
|
||||
candidate_id: new_candidate.candidate_id,
|
||||
phase: :ALL,
|
||||
comment: 'replace test-prof with test-prof-2'
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
And here is the new FRR configuration:
|
||||
|
||||
::
|
||||
|
||||
$ sudo vtysh -c 'show running-config'
|
||||
...
|
||||
bfd
|
||||
profile test-prof-2
|
||||
detect-multiplier 5
|
||||
transmit-interval 900
|
||||
!
|
||||
!
|
@ -12,6 +12,7 @@ FRRouting Developer's Guide
|
||||
testing
|
||||
bgpd
|
||||
fpm
|
||||
grpc
|
||||
ospf
|
||||
zebra
|
||||
vtysh
|
||||
|
@ -28,6 +28,7 @@ dev_RSTFILES = \
|
||||
doc/developer/cli.rst \
|
||||
doc/developer/conf.py \
|
||||
doc/developer/frr-release-procedure.rst \
|
||||
doc/developer/grpc.rst \
|
||||
doc/developer/hooks.rst \
|
||||
doc/developer/include-compile.rst \
|
||||
doc/developer/index.rst \
|
||||
|
66
doc/user/grpc.rst
Normal file
66
doc/user/grpc.rst
Normal file
@ -0,0 +1,66 @@
|
||||
.. _grpc:
|
||||
|
||||
***************
|
||||
Northbound gRPC
|
||||
***************
|
||||
|
||||
.. program:: configure
|
||||
|
||||
*gRPC* provides a combined front end to all FRR daemons using the YANG
|
||||
northbound. It is currently disabled by default due its experimental
|
||||
stage, but it can be enabled with :option:`--enable-grpc` option in the
|
||||
configure script.
|
||||
|
||||
|
||||
.. _grpc-features:
|
||||
|
||||
Northbound gRPC Features
|
||||
========================
|
||||
|
||||
* Get/set configuration using JSON/XML/XPath encondings.
|
||||
* Execute YANG RPC calls.
|
||||
* Lock/unlock configuration.
|
||||
* Create/edit/load/update/commit candidate configuration.
|
||||
* List/get transactions.
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
There is currently no support for YANG notifications.
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
You can find more information on how to code programs to interact
|
||||
with FRR by reading the gRPC Programming Language Bindings section
|
||||
in the `developer's documentation
|
||||
<http://docs.frrouting.org/projects/dev-guide/en/latest/grpc.html>`_.
|
||||
|
||||
|
||||
.. _grpc-config:
|
||||
|
||||
Daemon gRPC Configuration
|
||||
=========================
|
||||
|
||||
The *gRPC* module accepts the following run time option:
|
||||
|
||||
- ``port``: the port to listen to (defaults to ``50051``).
|
||||
|
||||
|
||||
.. note::
|
||||
|
||||
At the moment only localhost connections with no SSL/TLS are
|
||||
supported.
|
||||
|
||||
|
||||
To configure FRR daemons to listen to gRPC you need to append the
|
||||
following parameter to the daemon's command line: ``-M grpc``
|
||||
(optionally ``-M grpc:PORT`` to specify listening port).
|
||||
|
||||
To do that in production you need to edit the ``/etc/frr/daemons`` file
|
||||
so the daemons get started with the command line argument. Example:
|
||||
|
||||
::
|
||||
|
||||
# other daemons...
|
||||
bfdd_options=" --daemon -A 127.0.0.1 -M grpc"
|
@ -23,6 +23,7 @@ Basics
|
||||
|
||||
basic
|
||||
vtysh
|
||||
grpc
|
||||
filter
|
||||
routemap
|
||||
ipv6
|
||||
|
@ -15,6 +15,7 @@ user_RSTFILES = \
|
||||
doc/user/filter.rst \
|
||||
doc/user/frr-reload.rst \
|
||||
doc/user/glossary.rst \
|
||||
doc/user/grpc.rst \
|
||||
doc/user/index.rst \
|
||||
doc/user/installation.rst \
|
||||
doc/user/ipv6.rst \
|
||||
|
Loading…
Reference in New Issue
Block a user