Skip to content

gRPCurl

gRPCurl overview

gRPCurl is a command-line tool that lets you interact with gRPC servers:

The following examples shows various gRPCurl commands to interact with Arista EOS devices.

Install gRPCurl

Install GO

$ go version
go version go1.16.4 linux/amd64
go env | grep 'GOROOT\|GOPATH'
export GOROOT=/usr/local/go
export GOPATH=$HOME/go
export PATH=$GOPATH/bin:$GOROOT/bin:$PATH

Get gNOI repository

mkdir -p $GOPATH/src/github.com/openconfig
git clone https://github.com/openconfig/gnoi.git $GOPATH/src/github.com/openconfig/gnoi
$ ls $GOPATH/src/github.com/openconfig
gnoi

Install gRPCurl

go get github.com/fullstorydev/grpcurl
ls $GOPATH/pkg/mod/github.com/fullstorydev/
grpcurl@v1.8.1
go install github.com/fullstorydev/grpcurl/cmd/grpcurl@latest
ls $GOPATH/bin/
grpcurl

Device config

interface Management1
   description oob_management
   vrf MGMT
   ip address 192.0.2.118/24

username arista secret 0 arista

management api gnmi
   transport grpc def
      vrf MGMT
DC1-L2LEAF2A#show management api gnmi
Enabled:            Yes
Server:             running on port 6030, in MGMT VRF
SSL Profile:        none
QoS DSCP:           none
DC1-L2LEAF2A#

Before to use gNOI ping and traceroute, let's run these commands locally:

$ ssh arista@192.0.2.118
Password:
Last login: Thu Jun  3 12:06:25 2021 from 192.0.2.3
DC1-L2LEAF2A>en
DC1-L2LEAF2A#bash

Arista Networks EOS shell

[arista@DC1-L2LEAF2A ~]$ ping  172.31.255.0 -c 2
PING 172.31.255.0 (172.31.255.0) 56(84) bytes of data.
64 bytes from 172.31.255.0: icmp_seq=1 ttl=63 time=24.6 ms
64 bytes from 172.31.255.0: icmp_seq=2 ttl=63 time=18.8 ms

--- 172.31.255.0 ping statistics ---
2 packets transmitted, 2 received, 0% packet loss, time 1001ms
rtt min/avg/max/mdev = 18.861/21.738/24.616/2.881 ms
[arista@DC1-L2LEAF2A ~]$
[arista@DC1-L2LEAF2A ~]$ traceroute -A 172.31.255.0
traceroute to 172.31.255.0 (172.31.255.0), 30 hops max, 60 byte packets
 1  10.90.90.1 (10.90.90.1) [!!]  26.636 ms  29.420 ms  32.113 ms
 2  172.31.255.0 (172.31.255.0) [!!]  52.764 ms  53.881 ms  63.213 ms
[arista@DC1-L2LEAF2A ~]$
[arista@DC1-L2LEAF2A ~]$ exit
logout
DC1-L2LEAF2A#exit
Connection to 192.0.2.118 closed.

Use gRPCurl

Describe from a proto file

Describe CancelReboot method

grpcurl --plaintext  --import-path ${GOPATH}/src --proto github.com/openconfig/gnoi/system/system.proto  \
   describe  gnoi.system.System.CancelReboot

Output:

gnoi.system.System.CancelReboot is a method:
// CancelReboot cancels any pending reboot request.
rpc CancelReboot ( .gnoi.system.CancelRebootRequest ) returns ( .gnoi.system.CancelRebootResponse );

Describe System service

$ grpcurl --plaintext  --import-path ${GOPATH}/src --proto github.com/openconfig/gnoi/system/system.proto  \
   describe  gnoi.system.System

Output:

gnoi.system.System is a service:
// The gNOI service is a collection of operational RPC's that allow for the
// management of a target outside of the configuration and telemetry pipeline.
service System {
  // CancelReboot cancels any pending reboot request.
  rpc CancelReboot ( .gnoi.system.CancelRebootRequest ) returns ( .gnoi.system.CancelRebootResponse );
  // Ping executes the ping command on the target and streams back
  // the results.  Some targets may not stream any results until all
  // results are in.  If a packet count is not explicitly provided,
  // 5 is used.
  rpc Ping ( .gnoi.system.PingRequest ) returns ( stream .gnoi.system.PingResponse );
  // Reboot causes the target to reboot, possibly at some point in the future.
  // If the method of reboot is not supported then the Reboot RPC will fail.
  // If the reboot is immediate the command will block until the subcomponents
  // have restarted.
  // If a reboot on the active control processor is pending the service must
  // reject all other reboot requests.
  // If a reboot request for active control processor is initiated with other
  // pending reboot requests it must be rejected.
  rpc Reboot ( .gnoi.system.RebootRequest ) returns ( .gnoi.system.RebootResponse );
  // RebootStatus returns the status of reboot for the target.
  rpc RebootStatus ( .gnoi.system.RebootStatusRequest ) returns ( .gnoi.system.RebootStatusResponse );
  // SetPackage places a software package (possibly including bootable images)
  // on the target. The file is sent in sequential messages, each message
  // up to 64KB of data. A final message must be sent that includes the hash
  // of the data sent. An error is returned if the location does not exist or
  // there is an error writing the data. If no checksum is received, the target
  // must assume the operation is incomplete and remove the partially
  // transmitted file. The target should initially write the file to a temporary
  // location so a failure does not destroy the original file.
  rpc SetPackage ( stream .gnoi.system.SetPackageRequest ) returns ( .gnoi.system.SetPackageResponse );
  // SwitchControlProcessor will switch from the current route processor to the
  // provided route processor. If the current route processor is the same as the
  // one provided it is a NOOP. If the target does not exist an error is
  // returned.
  rpc SwitchControlProcessor ( .gnoi.system.SwitchControlProcessorRequest ) returns ( .gnoi.system.SwitchControlProcessorResponse );
  // Time returns the current time on the target.  Time is typically used to
  // test if a target is actually responding.
  rpc Time ( .gnoi.system.TimeRequest ) returns ( .gnoi.system.TimeResponse );
  // Traceroute executes the traceroute command on the target and streams back
  // the results.  Some targets may not stream any results until all
  // results are in.  If a hop count is not explicitly provided,
  // 30 is used.
  rpc Traceroute ( .gnoi.system.TracerouteRequest ) returns ( stream .gnoi.system.TracerouteResponse );
}

List

List from a proto file

Example 1)

grpcurl --plaintext  --import-path ${GOPATH}/src \
   --proto github.com/openconfig/gnoi/system/system.proto list

Output:

gnoi.system.System

Example 2)

grpcurl --plaintext  --import-path ${GOPATH}/src \
   --proto github.com/openconfig/gnoi/system/system.proto \
   list gnoi.system.System

Output:

gnoi.system.System.CancelReboot
gnoi.system.System.Ping
gnoi.system.System.Reboot
gnoi.system.System.RebootStatus
gnoi.system.System.SetPackage
gnoi.system.System.SwitchControlProcessor
gnoi.system.System.Time
gnoi.system.System.Traceroute

Example 3)

grpcurl --plaintext  --import-path ${GOPATH}/src \
   --proto github.com/openconfig/gnoi/os/os.proto list gnoi.os.OS

Output:

gnoi.os.OS.Activate
gnoi.os.OS.Install
gnoi.os.OS.Verify

List from a gRPC server (EOS device)

$ grpcurl --plaintext 192.0.2.105:6030 list
gnmi.gNMI
gnoi.certificate.CertificateManagement
gnoi.system.System
grpc.reflection.v1alpha.ServerReflection

Execute gNOI RPC with EOS

grpcurl -H 'username: arista'  -H 'password: arista' \
   -d '{"destination": "172.31.255.0", "count": 2, "do_not_resolve":true}' \
   -import-path ${GOPATH}/src -proto github.com/openconfig/gnoi/system/system.proto \
   -plaintext 192.0.2.118:6030 gnoi.system.System/Ping

Output:

{
  "source": "172.31.255.0",
  "time": "29800000",
  "bytes": 64,
  "sequence": 1,
  "ttl": 63
}
{
  "source": "172.31.255.0",
  "time": "25200000",
  "bytes": 64,
  "sequence": 2,
  "ttl": 63
}
{
  "source": "172.31.255.0",
  "time": "1001000000",
  "sent": 2,
  "received": 2,
  "minTime": "25210000",
  "avgTime": "27510000",
  "maxTime": "29810000",
  "stdDev": "2300000"
}
grpcurl -H 'username: arista'  -H 'password: arista' \
    -d '{"destination": "172.31.255.0", "max_ttl": 50, "do_not_resolve":true}' \
    -import-path ${GOPATH}/src -proto github.com/openconfig/gnoi/system/system.proto \
    -plaintext 192.0.2.118:6030 gnoi.system.System/Traceroute

Output:

{
  "destinationName": "172.31.255.0",
  "destinationAddress": "172.31.255.0",
  "hops": 50,
  "packetSize": 60
}
{
  "hop": 1,
  "address": "10.90.90.1",
  "rtt": "16589000"
}
{
  "hop": 1,
  "address": "10.90.90.1",
  "rtt": "17886000"
}
{
  "hop": 1,
  "address": "10.90.90.1",
  "rtt": "23219000"
}
{
  "hop": 2,
  "address": "172.31.255.0",
  "rtt": "46537000"
}
{
  "hop": 2,
  "address": "172.31.255.0",
  "rtt": "47873000"
}
{
  "hop": 2,
  "address": "172.31.255.0",
  "rtt": "55376000"
}