module ietf-yang-push { yang-version 1.1; namespace "urn:ietf:params:xml:ns:yang:ietf-yang-push"; prefix yp; import ietf-inet-types { prefix inet; } import ietf-yang-types { prefix yang; } import ietf-subscribed-notifications { prefix sn; } import ietf-datastores { prefix ds; } organization "IETF"; contact "WG Web: WG List: Editor: Alexander Clemm Editor: Eric Voit Editor: Alberto Gonzalez Prieto Editor: Ambika Prasad Tripathy Editor: Einar Nilsen-Nygaard Editor: Andy Bierman Editor: Balazs Lengyel "; description "This module contains conceptual YANG specifications for YANG push."; revision 2017-10-23 { description "Initial revision."; reference "YANG Datastore Push, draft-ietf-netconf-yang-push-11"; } /* * EXTENSIONS */ extension notifiable-on-change { argument "value"; description "Indicates whether changes to the data node are reportable in on-change subscriptions. The statement MUST only be a substatement of the leaf, leaf-list, container, list, anyxml, anydata statements. Zero or One notifiable-on-change statement is allowed per parent statement. NO substatements are allowed. The argument is a boolean value indicating whether on-change notifications are supported. If notifiable-on-change is not specified, the default is the same as the parent data node's value. For top level data nodes the default value is false."; } /* * FEATURES */ feature on-change { description "This feature indicates that on-change triggered subscriptions are supported."; } /* * IDENTITIES */ /* Error type identities for datastore subscription */ identity period-unsupported { base sn:error; description "Requested time period is too short. This can be for both periodic and on-change dampening."; } identity qos-unsupported { base sn:error; description "Subscription QoS parameters not supported on this platform."; } identity dscp-unavailable { base sn:error; description "Requested DSCP marking not allocatable."; } identity on-change-unsupported { base sn:error; description "On-change not supported."; } identity on-change-synch-unsupported { base sn:error; description "On-change synch-on-start and resynchonization not supported."; } identity reference-mismatch { base sn:error; description "Mismatch in filter key and referenced yang subtree."; } identity data-unavailable { base sn:error; description "Referenced yang node or subtree doesn't exist, or read access is not permitted."; } identity datatree-size { base sn:error; description "Resulting periodic or on-change push updates may exceed a size limit during normal conditions."; } identity synchronization-size { base sn:error; description "The resulting Synch-on-start or resynchronization would push a datatree which exceeds size limit for a one-time update."; } identity no-such-datastore { base sn:error; description "This is not a subscribable datastore."; } /* Datastore identities */ identity custom-datastore { base ds:datastore; description "A datastore with boundaries not defined within draft-ietf-netmod-revised-datastores"; } /* * TYPE DEFINITIONS */ typedef change-type { type enumeration { enum "create" { description "Create a new data resource if it does not already exist. If it already exists, replace."; } enum "delete" { description "Delete a data resource if it already exists. If it does not exists, take no action."; } enum "insert" { description "Insert a new user-ordered data resource"; } enum "merge" { description "merge the edit value with the target data resource; create if it does not already exist"; } enum "move" { description "Reorder the target data resource"; } enum "replace" { description "Replace the target data resource with the edit value"; } enum "remove" { description "Remove a data resource if it already exists "; } } description "Specifies different types of datastore changes."; reference "RFC 8072 section 2.5, with a delta that it is ok to receive ability create on an existing node, or receive a delete on a missing node."; } typedef selection-filter-ref { type leafref { path "/sn:filters/yp:selection-filter/yp:identifier"; } description "This type is used to reference a selection filter."; } /* * GROUP DEFINITIONS */ grouping datastore-criteria { description "A grouping to define criteria for which selected objects from a targeted datastore should be included in push updates."; leaf source { type identityref { base ds:datastore; } mandatory true; description "Datastore from which to retrieve data."; } uses selection-filter-objects; } grouping selection-filter-types { description "This grouping defines a selector for objects from a datastore."; choice filter-spec { description "The content filter specification for this request."; anydata subtree-filter { description "This parameter identifies the portions of the target datastore to retrieve."; reference "RFC 6241, Section 6."; } leaf xpath-filter { type yang:xpath1.0; description "This parameter contains an XPath expression identifying the portions of the target datastore to retrieve."; reference "http://www.w3.org/TR/1999/REC-xpath-19991116"; } } } grouping selection-filter-objects { description "This grouping defines a selector for objects from a datastore."; choice selected-content { description "The source of the selection filter applied to the subscription. This will come either referenced from a global list, or be provided within the subscription itself."; case by-reference { description "Incorporate a filter that has been configured separately."; leaf selection-filter-ref { type selection-filter-ref; mandatory true; description "References an existing selection filter which is to be applied to the subscription."; } } case within-subscription { description "Local definition allows a filter to have the same lifecycle as the subscription."; uses selection-filter-types; } } } grouping update-policy-modifiable { description "This grouping describes the datastore specific subscription conditions that can be changed during the lifetime of the subscription."; choice update-trigger { description "Defines necessary conditions for sending an event record to the subscriber."; case periodic { description "The agent is requested to notify periodically the current values of the datastore as defined by the selection filter."; leaf period { type yang:timeticks; mandatory true; description "Duration of time which should occur between periodic push updates. Where the anchor-time is available, the push will include the objects and their values which exist at an exact multiple of timeticks aligning to this start-time anchor."; } leaf anchor-time { type yang:date-and-time; description "Designates a timestamp before or after which a series of periodic push updates are determined. The next update will take place at a whole multiple interval from the anchor time. For example, for an anchor time is set for the top of a particular minute and a period interval of a minute, updates will be sent at the top of every minute this subscription is active."; } } case on-change { if-feature "on-change"; description "The agent is requested to notify changes in values in the datastore subset as defined by a selection filter."; leaf dampening-period { type yang:timeticks; mandatory true; description "The shortest time duration which is allowed between the creation of independent yang object update messages. Effectively this is the amount of time that needs to have passed since the last update. Zero indicates no delay."; } } } } grouping update-policy { description "This grouping describes the datastore specific subscription conditions of a subscription."; uses update-policy-modifiable { augment "update-trigger/on-change" { description "Includes objects not modifiable once subscription is established."; leaf no-synch-on-start { type empty; description "The presence of this object restricts an on-change subscription from sending push-update notifications. When present, pushing a full selection per the terms of the selection filter MAY NOT be done for this subscription. Only updates about changes, i.e. only push-change-update notifications are sent. When absent (default behavior), in order to facilitate a receiver's synchronization, a full update is sent when the subscription starts using a push-update notification, just like in the case of a periodic subscription. After that, push-change-update notifications are exclusively sent unless the publisher chooses to resynch the subscription via a new push-update notification."; } leaf-list excluded-change { type change-type; description "Use to restrict which changes trigger an update. For example, if modify is excluded, only creation and deletion of objects is reported."; } } } } grouping update-qos { description "This grouping describes Quality of Service information concerning a subscription. This information is passed to lower layers for transport prioritization and treatment"; leaf dscp { type inet:dscp; default "0"; description "The push update's IP packet transport priority. This is made visible across network hops to receiver. The transport priority is shared for all receivers of a given subscription."; } leaf weighting { type uint8 { range "0 .. 255"; } description "Relative weighting for a subscription. Allows an underlying transport layer perform informed load balance allocations between various subscriptions"; reference "RFC-7540, section 5.3.2"; } leaf dependency { type sn:subscription-id; description "Provides the Subscription ID of a parent subscription which has absolute priority should that parent have push updates ready to egress the publisher. In other words, there should be no streaming of objects from the current subscription if the parent has something ready to push."; reference "RFC-7540, section 5.3.1"; } } grouping update-error-hints { description "Allow return additional negotiation hints that apply specifically to push updates."; leaf period-hint { type yang:timeticks; description "Returned when the requested time period is too short. This hint can assert an viable period for both periodic push cadence and on-change dampening."; } leaf error-path { type string; description "Reference to a YANG path which is associated with the error being returned."; } leaf object-count-estimate { type uint32; description "If there are too many objects which could potentially be returned by the selection filter, this identifies the estimate of the number of objects which the filter would potentially pass."; } leaf object-count-limit { type uint32; description "If there are too many objects which could be returned by the selection filter, this identifies the upper limit of the publisher's ability to service for this subscription."; } leaf kilobytes-estimate { type uint32; description "If the returned information could be beyond the capacity of the publisher, this would identify the data size which could result from this selection filter."; } leaf kilobytes-limit { type uint32; description "If the returned information would be beyond the capacity of the publisher, this identifies the upper limit of the publisher's ability to service for this subscription."; } } /* * RPCs */ rpc resynch-subscription { if-feature "on-change"; description "This RPC allows a subscriber of an active on-change subscription to request a full push of objects in there current state. A successful result would be the set of YANG objects equivalent to a Get using the existing selection criteria. This request may only come from the same subscriber using the establish-subscription RPC."; input { leaf identifier { type sn:subscription-id; mandatory true; description "Identifier of the subscription that is to be resynched."; } } output { leaf subscription-result { type sn:subscription-result; mandatory true; description "Indicates whether the request for the subscription resynch has been accepted, or why it has been denied."; } } } /* * DATA NODES */ augment "/sn:establish-subscription/sn:input" { description "This augmentation adds additional subscription parameters that apply specifically to datastore updates to RPC input."; uses update-policy; uses update-qos; } augment "/sn:establish-subscription/sn:input/sn:target" { description "This augmentation adds the datastore as a valid parameter object for the subscription to RPC input. This provides a target for the filter."; case datastore { uses datastore-criteria; } } augment "/sn:establish-subscription/sn:output/"+ "sn:result/sn:no-success" { description "This augmentation adds datastore specific error info and hints to RPC output."; uses update-error-hints; } augment "/sn:modify-subscription/sn:input" { description "This augmentation adds additional subscription parameters specific to datastore updates."; uses update-policy-modifiable; } augment "/sn:modify-subscription/sn:input/sn:target" { description "This augmentation adds the datastore as a valid parameter object for the subscription to RPC input. This provides a target for the filter."; case datastore { uses selection-filter-objects; } } augment "/sn:modify-subscription/sn:output/"+ "sn:result/sn:no-success" { description "This augmentation adds push datastore error info and hints to RPC output."; uses update-error-hints; } notification push-update { description "This notification contains a push update, containing data subscribed to via a subscription. This notification is sent for periodic updates, for a periodic subscription. It can also be used for synchronization updates of an on-change subscription. This notification shall only be sent to receivers of a subscription; it does not constitute a general-purpose notification."; leaf subscription-id { type sn:subscription-id; description "This references the subscription which drove the notification to be sent."; } leaf time-of-update { type yang:date-and-time; description "This leaf identifies the generation time of the datastore selection within a push-update."; } leaf updates-not-sent { type empty; description "This is a flag which indicates that not all data nodes subscribed to are included with this update. In other words, the publisher has failed to fulfill its full subscription obligations. The result is intermittent loss of synchronization of data at the receiver."; } anydata datastore-contents { description "This contains the updated data. It constitutes a snapshot at the time-of-update of the set of data that has been subscribed to. The format and syntax of the data corresponds to the format and syntax of data that would be returned in a corresponding get operation with the same selection filter parameters applied."; } } notification push-change-update { if-feature "on-change"; description "This notification contains an on-change push update. This notification shall only be sent to the receivers of a subscription; it does not constitute a general-purpose notification."; leaf subscription-id { type sn:subscription-id; description "This references the subscription which drove the notification to be sent."; } leaf time-of-update { type yang:date-and-time; description "This leaf identifies the generation time of the datastore changes extract. If a dampening-period was in effect before the notification message was generated, this may not be the time any of the datastore-changes were actually made."; } leaf updates-not-sent { type empty; description "The presence of this object indicates not all changes which have occurred since the last update are included with this update. In other words, the publisher has failed to fulfill its full subscription obligations, for example in cases where it was not able to keep up with a change burst."; } anydata datastore-changes { description "This contains an incremental set of datastore changes needed to update a remote datastore starting at the time of the previous update, per the terms of the subscription. Changes are encoded analogous to the syntax of a corresponding yang- patch operation, i.e. a yang-patch operation applied to the YANG datastore implied by the previous update to result in the current state."; reference "RFC 8072 section 2.5, with a delta that it is ok to receive ability create on an existing node, or receive a delete on a missing node."; } } augment "/sn:subscription-started" { description "This augmentation adds many yang datastore specific objects to the notification that a subscription has started."; uses update-policy; uses update-qos; } augment "/sn:subscription-started/sn:target" { description "This augmentation allows the datastore to be included as part of the notification that a subscription has started."; case datastore { uses datastore-criteria; } } augment "/sn:filters" { description "This augmentation allows the datastore to be included as part of the selection filtering criteria for a subscription."; list selection-filter { key "identifier"; description "A list of pre-positioned filters that can be applied to datastore subscriptions."; leaf identifier { type sn:filter-id; description "An identifier to differentiate between selection filters."; } uses selection-filter-types; } } augment "/sn:subscription-modified" { description "This augmentation adds many yang datastore specific objects to the notification that a subscription has been modified."; uses update-policy; uses update-qos; } augment "/sn:subscription-modified/sn:target" { description "This augmentation allows the datastore to be included as part of the notification that a subscription has been modified."; case datastore { uses datastore-criteria; } } augment "/sn:subscription-config/sn:subscription" { description "This augmentation adds many yang datastore specific objects which can be configured as opposed to established via RPC."; uses update-policy; uses update-qos; } augment "/sn:subscription-config/sn:subscription/sn:target" { description "This augmentation adds the datastore to the selection filtering criteria for a subscription."; case datastore { uses datastore-criteria; } } augment "/sn:subscriptions/sn:subscription" { yp:notifiable-on-change true; description "This augmentation adds many datastore specific objects to a subscription."; uses update-policy; uses update-qos; } augment "/sn:subscriptions/sn:subscription/sn:target" { description "This augmentation allows the datastore to be included as part of the selection filtering criteria for a subscription."; case datastore { uses datastore-criteria; } } /* YANG Parser Pyang crashing on syntax below, due to fixed bug https://github.com/mbj4668/pyang/issues/300 deviation "/sn:subscriptions/sn:subscription/sn:receivers/" + "sn:receiver/sn:pushed-notifications" { deviate add { yp:notifiable-on-change false; } } deviation "/sn:subscriptions/sn:subscription/sn:receivers/" + "sn:receiver/sn:excluded-notifications" { deviate add { yp:notifiable-on-change false; } } YANG Parser Pyang crashing on syntax above */ }