openconfig / reference

This repository contains reference implementations, specifications and tooling related to OpenConfig-based network management.
Apache License 2.0
157 stars 89 forks source link

Proposal: Adding Optional Extensions to gNMI #78

Closed robshakir closed 6 years ago

robshakir commented 6 years ago

Adding Optional Extensions to gNMI

Contributors: Rob Shakir (robjs@google.com), Carl Lebsack (csl@google.com), Nick Ethier (nethier@jive.com), Anees Shaikh (aashaikh@google.com)
Date: November 2017
Status: New Proposal

Summary

This contribution proposes to modify the gNMI protocol to allow extensions to be added without requiring the core specification to be modified. The intention of this is to allow implementors to add additional functionality to existing gNMI RPCs.

Problem Statement/Motivation

In particular use cases, there are requirements for data that is not currently specified within the existing RPC payloads to be carried. Some examples of this include:

The common requirement of these cases is that they require additional data to be supplied in addition to the existing payload without changing the RPC's semantics. If the semantics of an RPC are to be changed, defining an additional service (e.g., FooGNMIExtService with a new MagicSubscription RPC) provides a clean way to extend the service definition. However, for the cases above, where the semantics stay fundamentally the same, bifurcating RPC paths does not seem an optimal solution.

One proposed solution to this problem is to add additional fields in the gRPC metadata. There are a number of downsides to this approach:

This proposal seeks to define a means by which existing gNMI RPC payloads can be extended using a non-metadata approach.

Proposal

We propose to introduce an additional repeated field to all top-level gNMI RPC messages (i.e., Capability(Request|Response), Get(Request|Response), Set(Request|Response) and and Subscribe(Request|Response)) named extension. This field is defined to a carry an gnmiext.Extension message.

We propose that the Extension message is defined as follows:

message Extension {
    oneof ext {
        ProxyDetails proxy = 1;
        ...
        RegisteredExtension ext = NN;
    }
}

message RegisteredExtension {
    enum ExtensionID {
        UNSET = 0;
        EXPERIMENTAL = 999;
    }
    ExtensionID id = 1;
    bytes msg = 2;
}

This splits gNMI extensions into two sets:

The following example for a ProxyDetails extension is below.

// Credentials stores the authentication information for a proxy.
message Credentials {
  string username = 1;   // The login username.
  string password = 2;   // The authentication password.
  // TODO: Extend to other auth, e.g., SSL certificates.
}

message ProxyDetails {
  string address = 1;           // Address of the proxy.
  Credentials credentials = 2;  // Authentication credentials.
  proto.Any extra = 3;          // Additional (arbitrary) details.
}

If a registered extension becomes popular, it may be promoted to a well-known extension. Initially, we propose that RegisteredExtension IDs are assigned simply through an email request. We do not propose to assign an extension ID to a well known extension. When extensions are promoted to well known, their extension ID will be deprecated over time.

Open Questions

robshakir commented 6 years ago

@tsuna @jsterne @kuvempu, @nileshsimaria @aaronbee -- would be interested in your thoughts here.

kuvempu commented 6 years ago

Overall, useful to include. Some thoughts ...

Proxy-specific considerations:

tsuna commented 6 years ago

LGTM.

Just curious: what's the advantage of registered extensions as opposed to using google.protobuf.Any? To support custom / third-party extensions that may not have protobuf payloads, or to still centrally oversee such extension through the assignment process of extension IDs?

@kuvempu why would you suggest to disallow the proxy to add/modify extensions? Or did you mean it's OK for the proxy to drop an extension it consumes for its own use (such as the ProxyDetails extension suggested above) but not OK to add/modify extensions? I'm sure there are cases where proxies will want to add extensions — for example with a dial-out setup (see #42) a reverse proxy might need to tack on information about where the message originally came from (effectively doing the opposite of ProxyDetails).

robshakir commented 6 years ago

Hi @tsuna -- apologies, have been travelling and missed responding to you.

We wanted to keep some form of curation of what is implemented as an extension vs. something that really requires a new RPC. For example, one could implement Subscribe with a SubscribeRequest that really has all the parameters one expects within an extension, rather than using the existing fields - whereas such new Subscribe semantics should probably be implemented with a different RPC such that it's clear to the consumer. Effectively, we erred this way because it seemed a clearer way to keep a standardised API through gNMI.

Let me know if this doesn't make sense!

r.

robshakir commented 6 years ago

@kuvempu, thanks for the feedback.

For the proxy specific messages, we'll define the semantics in a short doc explaining this extension, but (@gcsl, please keep me honest):

Thanks! r.