In NETCONF, how does the candidate workflow of edit, <validate>, then <commit> or <discard-changes> change the running datastore?
answer
- nothing is live until one RPC
- constraints deferred on the candidate
- commit copies the whole candidate
- discard resets candidate from running
basics
~10 sEdits to the candidate change nothing on the device. <validate> checks the candidate, <commit> sets running to the candidate's entire contents, and <discard-changes> throws the edits away by resetting the candidate to running.
solid answer
~40 sYou `<edit-config>` with `<candidate/>` as the target, as many times as you need, and the device keeps running on its current configuration. YANG defers constraint checks on the candidate until `<validate>` or `<commit>` (RFC 7950 Section 8.3.3), so `<validate>` with the candidate as source, available when the server advertises `:validate`, reports problems before anything goes live. `<commit>` then sets running to the candidate's contents; if the device cannot commit all of it, running must stay unchanged. If you abandon the change, `<discard-changes>` resets the candidate to running. The catch is that the candidate is shared and is a full configuration, so a commit also carries any edits another session left in it.
code
xml · 11 lines<rpc message-id="201" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
<validate>
<source><candidate/></source>
</validate>
</rpc>
<rpc message-id="202" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
<commit/>
</rpc>
<rpc message-id="203" xmlns="urn:ietf:params:xml:ns:netconf:base:1.0">
<discard-changes/>
</rpc>go deeper
Recall that edits to the candidate are not live, that commit makes them live, and that discard-changes throws them away.
Explain each RPC precisely: validate checks the candidate, commit sets running to the whole candidate, discard-changes resets the candidate to running, and validate needs its own capability.
Show you know the candidate is shared and a full configuration, so you start from a clean candidate, guard it while you work, and read rpc-error replies before committing.
Weigh how a team's automation should share or isolate the candidate across tools, including RESTCONF clients that auto-commit whatever the candidate holds.
## The pieces The workflow needs the `:candidate` capability (RFC 6241 Section 8.3). That capability creates the `<candidate>` datastore and two operations that exist only with it: `<commit>` and `<discard-changes>`. The `<validate>` operation comes from a separate capability, `:validate:1.1` (or `:validate:1.0` on older servers), defined in RFC 6241 Section 8.6. | Step | RPC | What changes | |---|---|---| | stage | `<edit-config>` with target `<candidate/>` | the candidate only; the device's behaviour does not change | | check | `<validate>` with source `<candidate/>` | nothing; the reply is `<ok/>` or an `<rpc-error>` | | apply | `<commit/>` | running is set to the candidate's contents | | abandon | `<discard-changes/>` | the candidate is reset to the contents of running | ## Staging and checking The candidate is a full configuration data set that can be changed without affecting the device. Nothing you write there is active, which is the whole point: a change of hundreds of lines can be built across several `<edit-config>` calls. YANG's constraint enforcement model (RFC 7950 Section 8.3.3) is what makes the multi-step build possible. On running or startup, constraints must hold at the end of every `<edit-config>` or `<copy-config>`. On the candidate, enforcement is delayed until a `<commit>` or `<validate>` takes place. A reference to something added in a later edit is therefore not an error in the middle of staging. `<validate>` asks the server to check a complete configuration. RFC 6241 requires a device advertising the capability to check at least for syntax errors; it lists failures such as missing parameters, references to undefined configuration data and other violations of data-model rules. How deep the semantic check goes beyond syntax is up to the implementation, so a clean `<validate>` is strong evidence, not a guarantee. ## Applying: what `<commit>` promises RFC 6241 defines `<commit>` as setting the running configuration to the current contents of the candidate. It is a distinct operation rather than a copy so that the intent stays visible. The text makes three promises: 1. If the device cannot commit all the changes, **running must remain unchanged**. 2. If it succeeds, running is updated with the contents of the candidate. 3. If running or the candidate is locked by a different session, `<commit>` fails with the error-tag `in-use`. Without `:candidate`, the RFC says, `<commit>` is not available at all. ## Abandoning: what `<discard-changes>` does `<discard-changes>` reverts the **candidate** to the current running configuration. It does not touch running and does not undo an earlier commit: a plain commit leaves no previous running configuration for `<discard-changes>` to return to, so keep your own copy if you may need one. After a discard, the candidate again matches what the device is doing. ## The shared-candidate trap RFC 6241 says the candidate can be shared among sessions, and that unless a client knows otherwise it must assume other sessions can modify it at the same time. Put that together with commit's definition and the consequence is direct: - `<commit>` applies **everything** in the candidate, not "my session's edits". - A candidate left dirty by another tool, or by an aborted run, is committed along with your change. - RESTCONF makes the same point from the other side: RFC 8040 Section 1.4 says that on a server with a candidate and no writable running, each RESTCONF edit is committed immediately, and any edits from other sources already in the candidate are committed too. The defences are simple. Start with `<discard-changes>` (or compare the candidate with running) so you begin from a clean copy, and hold a lock on the candidate while you work. Locking is its own subject, and a lock released with changes outstanding discards them. ## A complete run 1. Read the server's `<hello>` and confirm `:candidate`, and `:validate` if you intend to validate. 2. Send `<discard-changes/>` so the candidate equals running. 3. Send one or more `<edit-config>` calls with `<candidate/>` as the target. 4. Send `<validate>` with `<candidate/>` as the source and read any `<rpc-error>`. 5. On `<ok/>`, send `<commit/>`; on errors, fix and validate again, or send `<discard-changes/>`. 6. Test the device, and save running to startup if the device has a distinct startup. Commit with a timeout that rolls back automatically is a separate capability layered on this workflow and is not needed for the plain sequence above.
- Why send <discard-changes> before staging a change in a NETCONF candidate?The candidate is shared and is a full configuration, and `<commit>` applies all of it. If another session or an aborted run left edits there, your commit would push them live. Discarding first resets the candidate to running, so what you commit is running plus exactly your edits.
- Does a successful NETCONF <validate> guarantee the following <commit> succeeds?No. `<validate>` is required to check at least syntax, and how much semantic checking it does beyond that is implementation-specific. Between the two RPCs another session may change or lock the candidate, and a lock makes `<commit>` fail with `in-use`. If the commit does fail, RFC 6241 requires running to stay unchanged.
- What happens when a RESTCONF client edits a device that has a candidate but no writable running?RFC 8040 Section 1.4 says the edit is made in the candidate and the candidate is committed to running immediately after each successful edit. Any edits from other sources already in the candidate are committed as well, so a half-finished NETCONF session's staging can go live through someone else's RESTCONF call.
saying these in an interview costs you the question
- <commit> applies only the edits made in my own session.
- <discard-changes> rolls running back to the previous commit.
- Edits to the candidate take effect on the device immediately.
- Any device with a candidate also supports <validate>.
- The candidate is private to each NETCONF session.