Package ietf-yang-patch 56/96856/1
authorRobert Varga <robert.varga@pantheon.tech>
Fri, 9 Jul 2021 12:41:24 +0000 (14:41 +0200)
committerRobert Varga <robert.varga@pantheon.tech>
Fri, 9 Jul 2021 12:54:45 +0000 (14:54 +0200)
This is the model published in RFC8072, which gives us some basic
structural elements. Its value will increase once we can generate
structures for rc:yang-data.

JIRA: NETCONF-788
Change-Id: I063cea05f33cc8191db4320ee686b253b0471679
Signed-off-by: Robert Varga <robert.varga@pantheon.tech>
artifacts/pom.xml
restconf/restconf-models/ietf-yang-patch/pom.xml [new file with mode: 0644]
restconf/restconf-models/ietf-yang-patch/src/main/yang/ietf-yang-patch@2017-02-22.yang [new file with mode: 0644]
restconf/restconf-models/pom.xml
restconf/restconf-nb-rfc8040/pom.xml
restconf/restconf-nb-rfc8040/src/main/java/org/opendaylight/restconf/nb/rfc8040/jersey/providers/patch/XmlPatchStatusBodyWriter.java

index acbd0f90c024cf7703f9d1e3d97e4d68941a5625..d8b019632b49f75a2a20a13432968bd1c8eda8a4 100644 (file)
                 <artifactId>ietf-restconf-monitoring</artifactId>
                 <version>${project.version}</version>
             </dependency>
+            <dependency>
+                <groupId>${project.groupId}</groupId>
+                <artifactId>ietf-yang-patch</artifactId>
+                <version>${project.version}</version>
+            </dependency>
             <dependency>
                 <groupId>${project.groupId}</groupId>
                 <artifactId>restconf-common-models</artifactId>
diff --git a/restconf/restconf-models/ietf-yang-patch/pom.xml b/restconf/restconf-models/ietf-yang-patch/pom.xml
new file mode 100644 (file)
index 0000000..923e65d
--- /dev/null
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!--
+ Copyright (c) 2021 PANTHEON.tech, s.r.o. and others.  All rights reserved.
+
+ This program and the accompanying materials are made available under the
+ terms of the Eclipse Public License v1.0 which accompanies this distribution,
+ and is available at http://www.eclipse.org/legal/epl-v10.html
+-->
+<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
+    <modelVersion>4.0.0</modelVersion>
+
+    <parent>
+        <groupId>org.opendaylight.netconf</groupId>
+        <artifactId>netconf-parent</artifactId>
+        <version>2.0.1-SNAPSHOT</version>
+        <relativePath>../../../parent</relativePath>
+    </parent>
+
+    <artifactId>ietf-yang-patch</artifactId>
+    <packaging>bundle</packaging>
+    <name>${project.artifactId}</name>
+
+    <dependencies>
+        <dependency>
+            <groupId>com.google.guava</groupId>
+            <artifactId>guava</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.opendaylight.yangtools</groupId>
+            <artifactId>concepts</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.opendaylight.yangtools</groupId>
+            <artifactId>yang-common</artifactId>
+        </dependency>
+        <dependency>
+            <groupId>org.opendaylight.netconf</groupId>
+            <artifactId>ietf-restconf</artifactId>
+        </dependency>
+    </dependencies>
+</project>
diff --git a/restconf/restconf-models/ietf-yang-patch/src/main/yang/ietf-yang-patch@2017-02-22.yang b/restconf/restconf-models/ietf-yang-patch/src/main/yang/ietf-yang-patch@2017-02-22.yang
new file mode 100644 (file)
index 0000000..d0029ed
--- /dev/null
@@ -0,0 +1,390 @@
+module ietf-yang-patch {
+  yang-version 1.1;
+  namespace "urn:ietf:params:xml:ns:yang:ietf-yang-patch";
+  prefix "ypatch";
+
+  import ietf-restconf { prefix rc; }
+
+  organization
+    "IETF NETCONF (Network Configuration) Working Group";
+
+  contact
+    "WG Web:   <https://datatracker.ietf.org/wg/netconf/>
+     WG List:  <mailto:netconf@ietf.org>
+
+     Author:   Andy Bierman
+               <mailto:andy@yumaworks.com>
+
+     Author:   Martin Bjorklund
+               <mailto:mbj@tail-f.com>
+
+     Author:   Kent Watsen
+               <mailto:kwatsen@juniper.net>";
+
+  description
+    "This module contains conceptual YANG specifications
+     for the YANG Patch and YANG Patch Status data structures.
+
+     Note that the YANG definitions within this module do not
+     represent configuration data of any kind.
+     The YANG grouping statements provide a normative syntax
+     for XML and JSON message-encoding purposes.
+
+     Copyright (c) 2017 IETF Trust and the persons identified as
+     authors of the code.  All rights reserved.
+
+     Redistribution and use in source and binary forms, with or
+     without modification, is permitted pursuant to, and subject
+     to the license terms contained in, the Simplified BSD License
+     set forth in Section 4.c of the IETF Trust's Legal Provisions
+     Relating to IETF Documents
+     (http://trustee.ietf.org/license-info).
+
+     This version of this YANG module is part of RFC 8072; see
+     the RFC itself for full legal notices.";
+
+  revision 2017-02-22 {
+    description
+      "Initial revision.";
+    reference
+      "RFC 8072: YANG Patch Media Type.";
+  }
+
+  typedef target-resource-offset {
+    type string;
+    description
+      "Contains a data resource identifier string representing
+       a sub-resource within the target resource.
+       The document root for this expression is the
+       target resource that is specified in the
+       protocol operation (e.g., the URI for the PATCH request).
+
+       This string is encoded according to the same rules as those
+       for a data resource identifier in a RESTCONF request URI.";
+    reference
+       "RFC 8040, Section 3.5.3.";
+  }
+
+  rc:yang-data "yang-patch" {
+    uses yang-patch;
+  }
+
+  rc:yang-data "yang-patch-status" {
+    uses yang-patch-status;
+  }
+
+  grouping yang-patch {
+
+    description
+      "A grouping that contains a YANG container representing the
+       syntax and semantics of a YANG Patch edit request message.";
+
+    container yang-patch {
+      description
+        "Represents a conceptual sequence of datastore edits,
+         called a patch.  Each patch is given a client-assigned
+         patch identifier.  Each edit MUST be applied
+         in ascending order, and all edits MUST be applied.
+         If any errors occur, then the target datastore MUST NOT
+         be changed by the YANG Patch operation.
+
+         It is possible for a datastore constraint violation to occur
+         due to any node in the datastore, including nodes not
+         included in the 'edit' list.  Any validation errors MUST
+         be reported in the reply message.";
+
+      reference
+        "RFC 7950, Section 8.3.";
+
+      leaf patch-id {
+        type string;
+        mandatory true;
+        description
+          "An arbitrary string provided by the client to identify
+           the entire patch.  Error messages returned by the server
+           that pertain to this patch will be identified by this
+           'patch-id' value.  A client SHOULD attempt to generate
+           unique 'patch-id' values to distinguish between
+           transactions from multiple clients in any audit logs
+           maintained by the server.";
+      }
+
+      leaf comment {
+        type string;
+        description
+          "An arbitrary string provided by the client to describe
+           the entire patch.  This value SHOULD be present in any
+           audit logging records generated by the server for the
+           patch.";
+      }
+
+      list edit {
+        key edit-id;
+        ordered-by user;
+
+        description
+          "Represents one edit within the YANG Patch request message.
+           The 'edit' list is applied in the following manner:
+
+             - The first edit is conceptually applied to a copy
+               of the existing target datastore, e.g., the
+               running configuration datastore.
+             - Each ascending edit is conceptually applied to
+               the result of the previous edit(s).
+             - After all edits have been successfully processed,
+               the result is validated according to YANG constraints.
+             - If successful, the server will attempt to apply
+               the result to the target datastore.";
+
+        leaf edit-id {
+          type string;
+          description
+            "Arbitrary string index for the edit.
+             Error messages returned by the server that pertain
+             to a specific edit will be identified by this value.";
+        }
+
+        leaf operation {
+          type enumeration {
+            enum create {
+              description
+                "The target data node is created using the supplied
+                 value, only if it does not already exist.  The
+                 'target' leaf identifies the data node to be
+                 created, not the parent data node.";
+            }
+            enum delete {
+              description
+                "Delete the target node, only if the data resource
+                 currently exists; otherwise, return an error.";
+            }
+
+            enum insert {
+              description
+                "Insert the supplied value into a user-ordered
+                 list or leaf-list entry.  The target node must
+                 represent a new data resource.  If the 'where'
+                 parameter is set to 'before' or 'after', then
+                 the 'point' parameter identifies the insertion
+                 point for the target node.";
+            }
+            enum merge {
+              description
+                "The supplied value is merged with the target data
+                 node.";
+            }
+            enum move {
+              description
+                "Move the target node.  Reorder a user-ordered
+                 list or leaf-list.  The target node must represent
+                 an existing data resource.  If the 'where' parameter
+                 is set to 'before' or 'after', then the 'point'
+                 parameter identifies the insertion point to move
+                 the target node.";
+            }
+            enum replace {
+              description
+                "The supplied value is used to replace the target
+                 data node.";
+            }
+            enum remove {
+              description
+                "Delete the target node if it currently exists.";
+            }
+          }
+          mandatory true;
+          description
+            "The datastore operation requested for the associated
+             'edit' entry.";
+        }
+
+        leaf target {
+          type target-resource-offset;
+          mandatory true;
+          description
+            "Identifies the target data node for the edit
+             operation.  If the target has the value '/', then
+             the target data node is the target resource.
+             The target node MUST identify a data resource,
+             not the datastore resource.";
+        }
+
+        leaf point {
+          when "(../operation = 'insert' or ../operation = 'move')"
+             + "and (../where = 'before' or ../where = 'after')" {
+            description
+              "This leaf only applies for 'insert' or 'move'
+               operations, before or after an existing entry.";
+          }
+          type target-resource-offset;
+          description
+            "The absolute URL path for the data node that is being
+             used as the insertion point or move point for the
+             target of this 'edit' entry.";
+        }
+
+        leaf where {
+          when "../operation = 'insert' or ../operation = 'move'" {
+            description
+              "This leaf only applies for 'insert' or 'move'
+               operations.";
+          }
+          type enumeration {
+            enum before {
+              description
+                "Insert or move a data node before the data resource
+                 identified by the 'point' parameter.";
+            }
+            enum after {
+              description
+                "Insert or move a data node after the data resource
+                 identified by the 'point' parameter.";
+            }
+
+            enum first {
+              description
+                "Insert or move a data node so it becomes ordered
+                 as the first entry.";
+            }
+            enum last {
+              description
+                "Insert or move a data node so it becomes ordered
+                 as the last entry.";
+            }
+          }
+          default last;
+          description
+            "Identifies where a data resource will be inserted
+             or moved.  YANG only allows these operations for
+             list and leaf-list data nodes that are
+             'ordered-by user'.";
+        }
+
+        anydata value {
+          when "../operation = 'create' "
+             + "or ../operation = 'merge' "
+             + "or ../operation = 'replace' "
+             + "or ../operation = 'insert'" {
+            description
+              "The anydata 'value' is only used for 'create',
+               'merge', 'replace', and 'insert' operations.";
+          }
+          description
+            "Value used for this edit operation.  The anydata 'value'
+             contains the target resource associated with the
+             'target' leaf.
+
+             For example, suppose the target node is a YANG container
+             named foo:
+
+                 container foo {
+                   leaf a { type string; }
+                   leaf b { type int32; }
+                 }
+
+             The 'value' node contains one instance of foo:
+
+                 <value>
+                    <foo xmlns='example-foo-namespace'>
+                       <a>some value</a>
+                       <b>42</b>
+                    </foo>
+                 </value>
+              ";
+        }
+      }
+    }
+
+  } // grouping yang-patch
+
+  grouping yang-patch-status {
+
+    description
+      "A grouping that contains a YANG container representing the
+       syntax and semantics of a YANG Patch Status response
+       message.";
+
+    container yang-patch-status {
+      description
+        "A container representing the response message sent by the
+         server after a YANG Patch edit request message has been
+         processed.";
+
+      leaf patch-id {
+        type string;
+        mandatory true;
+        description
+          "The 'patch-id' value used in the request.";
+      }
+
+      choice global-status {
+        description
+          "Report global errors or complete success.
+           If there is no case selected, then errors
+           are reported in the 'edit-status' container.";
+
+        case global-errors {
+          uses rc:errors;
+          description
+            "This container will be present if global errors that
+             are unrelated to a specific edit occurred.";
+        }
+        leaf ok {
+          type empty;
+          description
+            "This leaf will be present if the request succeeded
+             and there are no errors reported in the 'edit-status'
+             container.";
+        }
+      }
+
+      container edit-status {
+        description
+          "This container will be present if there are
+           edit-specific status responses to report.
+           If all edits succeeded and the 'global-status'
+           returned is 'ok', then a server MAY omit this
+           container.";
+
+        list edit {
+          key edit-id;
+
+          description
+            "Represents a list of status responses,
+             corresponding to edits in the YANG Patch
+             request message.  If an 'edit' entry was
+             skipped or not reached by the server,
+             then this list will not contain a corresponding
+             entry for that edit.";
+
+          leaf edit-id {
+            type string;
+             description
+               "Response status is for the 'edit' list entry
+                with this 'edit-id' value.";
+          }
+
+          choice edit-status-choice {
+            description
+              "A choice between different types of status
+               responses for each 'edit' entry.";
+            leaf ok {
+              type empty;
+              description
+                "This 'edit' entry was invoked without any
+                 errors detected by the server associated
+                 with this edit.";
+            }
+            case errors {
+              uses rc:errors;
+              description
+                "The server detected errors associated with the
+                 edit identified by the same 'edit-id' value.";
+            }
+          }
+        }
+      }
+    }
+  }  // grouping yang-patch-status
+
+}
index 12054dd03f4c0e55513fcfa29eb2cfdc99326ae7..01da5fd15a21950d1d45af7219fa75f41207b066 100644 (file)
@@ -25,5 +25,6 @@
   <modules>
     <module>ietf-restconf-monitoring</module>
     <module>ietf-restconf</module>
+    <module>ietf-yang-patch</module>
   </modules>
 </project>
index 43bb08d5a76d70c3633ed8d41ca746b61407394e..b8ac2c24f45fe23e0f9ca1eb9d5f6cd519994977 100644 (file)
       <groupId>org.opendaylight.netconf</groupId>
       <artifactId>ietf-restconf-monitoring</artifactId>
     </dependency>
+    <dependency>
+      <groupId>org.opendaylight.netconf</groupId>
+      <artifactId>ietf-yang-patch</artifactId>
+    </dependency>
     <dependency>
       <groupId>org.opendaylight.netconf</groupId>
       <artifactId>netconf-api</artifactId>
index 076b8b531f9dbc882d142512dd70f44a5a90dde2..914f39c0ddc88ab7d5395905837dd8ca5e959356 100644 (file)
@@ -24,10 +24,12 @@ import org.opendaylight.restconf.common.errors.RestconfError;
 import org.opendaylight.restconf.common.patch.PatchStatusContext;
 import org.opendaylight.restconf.common.patch.PatchStatusEntity;
 import org.opendaylight.restconf.nb.rfc8040.MediaTypes;
+import org.opendaylight.yang.gen.v1.urn.ietf.params.xml.ns.yang.ietf.yang.patch.rev170222.yang.patch.status.YangPatchStatus;
 
 @Provider
 @Produces(MediaTypes.APPLICATION_YANG_DATA_XML)
 public class XmlPatchStatusBodyWriter extends AbstractPatchStatusBodyWriter {
+    private static final String XML_NAMESPACE = YangPatchStatus.QNAME.getNamespace().toString();
     private static final XMLOutputFactory XML_FACTORY;
 
     static {
@@ -51,7 +53,7 @@ public class XmlPatchStatusBodyWriter extends AbstractPatchStatusBodyWriter {
 
     private static void writeDocument(final XMLStreamWriter writer, final PatchStatusContext context)
             throws XMLStreamException {
-        writer.writeStartElement("", "yang-patch-status", "urn:ietf:params:xml:ns:yang:ietf-yang-patch");
+        writer.writeStartElement("", "yang-patch-status", XML_NAMESPACE);
         writer.writeStartElement("patch-id");
         writer.writeCharacters(context.getPatchId());
         writer.writeEndElement();