Schema reference
Every field netviz accepts, read directly off the models in src/netviz/models/.
This is the lookup table; docs/schema.md is the specification that
explains the design, and docs/yang-mapping.md explains how the
YANG column relates to RFC 8343, RFC 8344 and IEEE 802.1Q.
Reading the tables. Required means the key must be present in the document.
Default is the value netviz uses when it is absent — — for a required field,
unset when the field simply has no value and nothing downstream supplies one. Several
defaults are filled in at load time from elsewhere in the document (an interface's MTU
becomes the address families' MTU, the device's forwarding becomes each family's
forwarding); those are called out in the description. The YANG column names the node
the field maps to, with … standing for
/if:interfaces/if:interface and — meaning the field has no standards counterpart.
Element kinds
kind |
spec model |
Notes |
|---|---|---|
switch |
DeviceSpec | VLAN-aware bridge. Layer-2 by default: forwarding is false/false. |
router |
DeviceSpec | Forwards by default: forwarding is true/true. |
firewall |
DeviceSpec | A router that filters. Forwards by default; drawn as a wall. Structurally identical to router — zones and firewall are available on every layer-3 kind. |
hub |
DeviceSpec | Layer-1 repeater. Rejects vlan, ipv4, ipv6, bridge, vlans and forwarding; every interface must be ethernet. |
computer |
DeviceSpec | End host, drawn as a workstation. |
server |
DeviceSpec | End host, drawn as a rack-mount server. Structurally identical to computer. |
cable |
CableSpec | An undirected link between exactly two interfaces. Owns no interfaces. |
adapter |
AdapterSpec | Presents interfaces over a non-network host port. |
tunnel |
TunnelSpec | An undirected logical link between two or more tunnel interfaces. Owns no interfaces; over nests it inside another tunnel. |
patchpanel |
PatchPanelSpec | A passive cross-connect. Its front/<n> and rear/<n> ports are derived from ports, and a coupler joins each front port to one rear port; it is not a hop. |
pdu |
PduSpec | A power distribution unit. Its numbered outlets are derived from outlets; they are not interfaces, and a device names one in power.inputs rather than being cabled to it. Placed on a rack elevation like any other hardware. |
user |
UserSpec | One identity: a person, a service account or a shared login. Owns no interfaces and terminates no cable; it is drawn only in the identity view. |
group |
GroupSpec | A named set of identities. members may name a user or another group, which is what makes a hierarchy expressible; the nesting must not loop (NV-S012). |
template |
partial DeviceSpec | A named partial device spec, merged into every device that names it in spec.from. Not an element: never drawn, never listed, never validated on its own. |
layout |
LayoutSpec | Diagram geometry for elements declared elsewhere, scoped by view. Not an element: it carries no network facts and is never drawn as a node. See netviz layout. |
testsuite |
TestSuiteSpec | Named assertions about the network the other documents describe, graded by netviz test. Not an element: it declares no device and is never drawn. |
note |
NoteSpec | One free-text callout on the diagram, pinned to a point or anchored to an element or a link. Presentational: it declares no network fact and never changes what validate, path, export or plan conclude. |
area |
AreaSpec | A labelled box drawn behind the nodes, enclosing the elements it names, matches or encircles. The declarative form of --collapse grouping: the same set of elements, boxed rather than folded. |
legend |
LegendSpec | A key: what the colours and line styles of the drawing mean, placed by corner rather than by coordinate. auto: layers derives the entries from what the view drew. |
Document envelope
Every document, whatever its kind, carries these three keys plus a spec whose shape is chosen by kind.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
apiVersion |
netviz.dev/v1alpha1 |
yes | — | Schema version of the document. Only netviz.dev/v1alpha1 is understood by this release; an unknown value is NV-D002. |
— |
kind |
string | yes | — | Which element this document declares. Selects the shape of spec, and is the discriminator of the model union. |
— |
metadata |
Metadata | yes | — | Identity, description, labels and annotations. | — |
specis required and its model is listed in the kind table above.- Unknown keys are rejected anywhere in the document (
NV-D005). A misspelt key that was silently ignored would produce a diagram disagreeing with the file, which is the one failure mode this tool exists to prevent.
metadata
Identity and free-form annotation, shared by every kind.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | yes | — | Element name, unique within its namespace across all kinds (NV-N002). The namespace is the directory the document was found in. |
— |
description |
string | no | unset | Free text, may be multi-line. Rendered as the node's tooltip in SVG output. | — |
location |
Location | no | unset | Where the hardware physically is: site, room, rack and the rack units it occupies. Drives --layer rack and the placement rules NV-U001 to NV-U004. |
— |
labels |
map string → string | no | {} |
Selector-friendly key/value pairs. Keys follow the Kubernetes label grammar; the netviz.dev/ prefix is reserved for the tool. |
— |
annotations |
map string → string | no | {} |
Per-element input to the tooling, not selectable. netviz/ignore suppresses validation rules on this element. |
— |
metadata.location
Where the hardware physically is. Optional, and shared by every kind: a patch panel is racked exactly as a server is.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
site |
string | no | unset | Site the element is installed at, free text. | — |
room |
string | no | unset | Room or floor within the site, free text. | — |
rack |
string | no | unset | Rack identifier, unique within its room. Naming one is what puts the element on an elevation; site, room and rack together identify the rack (NV-U001). |
— |
position |
integer, 1–100 | no | unset | Lowest rack unit the element occupies, counted from 1 at the bottom of the rack. Requires rack (NV-U004). |
— |
height |
integer, 1–100 | no | 1 |
How many rack units the element occupies, upwards from position. |
— |
rack_height |
integer, 1–100 | no | unset | How tall the rack itself is. Any element in the rack may declare it; two that disagree are NV-U003, and nothing may extend past it (NV-U002). |
— |
positionis the lowest rack unit the element occupies andheighthow many it takes, counting upwards; units are numbered from 1 at the bottom of the cabinet, which is how a rack is labelled.site,roomandracktogether identify a rack (NV-U001). Two elements that name the same three share a cabinet and may not overlap; namingpositionorrack_heightwithoutrackisNV-U004.netviz render --layer rackdraws one front elevation per rack, empty units included.
spec — switch, router, firewall, hub, computer, server
The six device kinds share one spec shape. They differ in which fields they permit (a hub rejects bridge, vlans, forwarding and all layer-3 configuration) and in the default value of forwarding.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
vendor |
string | no | unset | Hardware vendor, free text. Documentation only. | — |
model |
string | no | unset | Hardware model designation, free text. | — |
serial |
string | no | unset | Serial or asset number, free text. | — |
location |
string | no | unset | Physical location, free text (site, room, rack unit). | — |
interfaces |
Interface list, ≥ 1 entry | yes | — | Every port and logical interface the device owns. At least one is required. | /if:interfaces/if:interface |
bridge |
BridgeConfig | no | unset | The 802.1Q bridge component this device implements. Absent means the device is not a bridge. | /dot1q:bridges/dot1q:bridge |
vlans |
VlanDefinition list | no | [] |
The device VLAN database: which VLANs exist on this device, and what they are called. | …/dot1q:bridge-vlan/dot1q:vlan |
forwarding |
Forwarding | no | unset | Device-wide default for per-interface IP forwarding. Defaults to true/true on a router and false/false on every other kind; a hub must not declare it. |
— |
netns |
NetnsDefinition list | no | [] |
The network namespaces this machine runs (§23.1). Each is a whole second network stack — its own interfaces, addresses and routing table — and parent nests one inside another, arbitrarily deep. Not a VRF: a VRF partitions one stack's routing table, a namespace is a second stack. |
— |
vrfs |
VrfDefinition list | no | [] |
The routing instances (VRFs) this device implements. An interface binds to one with vrf, and that binding is what partitions the address namespace. |
/ni:network-instances/ni:network-instance |
route_tables |
RouteTable list | no | [] |
The routing tables this device holds beyond main, local and default. A table on its own changes nothing; what reaches it is a rule in routing_policy (§16.4). |
— |
routes |
StaticRoute list | no | [] |
Configured static routes, in the order the device holds them. | …/rt:routing/rt:control-plane-protocols/rt:control-plane-protocol/rt:static-routes |
routing_policy |
PolicyRule list | no | [] |
The routing policy database: the ordered rules deciding which table a packet is routed by, from its source, its firewall mark, its ingress interface or its DSCP. This is policy-based routing (§16.4). | — |
routing |
RoutingConfig | no | unset | The dynamic routing protocols the device takes part in: an OSPF area, a BGP autonomous system, or both. | …/rt:routing/rt:control-plane-protocols/rt:control-plane-protocol |
zones |
Zone list | no | [] |
The security zones the device divides its interfaces into (§24.1). Policy is written between zones rather than between interfaces, so a rule survives a port being renamed, doubled or moved to a LAG. An interface is in at most one zone (NV-B003). |
— |
firewall |
FirewallConfig | no | unset | What the device does to the packets it sees: the filter policy and the address translations (§24.2). Absent records nothing about its filtering, which is not the same as saying it filters nothing. | — |
power |
PowerConfig | no | unset | What the device draws, which PDU outlets feed it, and how much PoE it hands out (§17.2). Absent means the inventory records nothing about its power. | /eo-mib:eoPowerTable/eoPowerEntry |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
from |
element reference | no | unset | Names a kind: template document whose partial spec is merged underneath this one. Consumed by the loader: it is gone before validation, the graph or any renderer sees the device. interfaces is required only when from is absent. |
— |
frommerges a template underneath the device: the device's own keys win,interfacesmerge byname, and every other list the device declares replaces the template's outright. See §6.6 ofschema.md.
spec.forwarding
The device-wide default for per-interface IP forwarding. Both fields are required once the block is written at all.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
ipv4 |
boolean | yes | — | Default for interfaces[].ipv4.forwarding on this device. |
…/ip:ipv4/ip:forwarding (as the default) |
ipv6 |
boolean | yes | — | Default for interfaces[].ipv6.forwarding on this device. |
…/ip:ipv6/ip:forwarding (as the default) |
spec.bridge
The 802.1Q bridge component the device implements.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | no | unset | Name of the bridge component. Defaults to metadata.name once the document is loaded. |
/dot1q:bridges/dot1q:bridge/dot1q:name |
type |
customer-vlan-bridge | provider-bridge | provider-edge-bridge | two-port-mac-relay-bridge | mac-bridge |
no | customer-vlan-bridge |
802.1Q bridge type, which decides the dot1q:port-type of every port on the device. |
/dot1q:bridges/dot1q:bridge/dot1q:bridge-type |
address |
MAC address | no | unset | Bridge address (the bridge's own MAC), used as the spanning-tree bridge identifier. | /dot1q:bridges/dot1q:bridge/dot1q:address |
spec.vlans[]
The device VLAN database. A port may reference a VLAN this list does not declare; that is NV-V004, not an error.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
id |
integer, 1–4094 | yes | — | VLAN identifier. Unique within the device (NV-V001). |
…/dot1q:bridge-vlan/dot1q:vlan/dot1q:vid |
name |
string, ≤ 32 characters | no | unset | Human name of the VLAN. 802.1Q caps it at 32 characters. | …/dot1q:bridge-vlan/dot1q:vlan/dot1q:name |
description |
string | no | unset | Free text. netviz-only; 802.1Q has no such node. | — |
spec.interfaces[]
One entry per port or logical interface. Used by both devices and adapters.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
interface name | yes | — | Interface name as the device itself spells it (eth0, GigabitEthernet0/2). Unique within the element (NV-I001), and the target of a cable endpoint. |
/if:interfaces/if:interface/if:name |
type |
ethernet | wifi | loopback | bridge | vlan | lag | tunnel |
yes | — | What kind of interface this is. Decides which other fields are allowed and whether a cable may terminate here (NV-C009). |
…/if:type |
description |
string | no | unset | Free text describing what the port is for. | …/if:description |
enabled |
boolean | no | true |
Intended administrative state. A disabled interface is exempt from W101. |
…/if:enabled |
mac |
MAC address | no | unset | Hardware address, EUI-48. Accepted in colon, dash or Cisco dotted form and normalised to lower-case colon form. if:phys-address is config false in RFC 8343, so an exporter must not write it to a live datastore. |
…/if:phys-address |
mtu |
integer, 68–65535 | no | unset | Layer-2 MTU in bytes. Propagated to ipv4.mtu and ipv6.mtu when those are not set. RFC 8343 has no layer-2 MTU node. |
— |
ipv4 |
IPv4Config | no | unset | IPv4 configuration. Absent means the interface has no IPv4 stack. | …/ip:ipv4 |
ipv6 |
IPv6Config | no | unset | IPv6 configuration. Absent means the interface has no IPv6 stack. | …/ip:ipv6 |
vlan |
VlanConfig | no | unset | 802.1Q bridge-port configuration. Absent means the port is not VLAN-aware; a host port facing an access port normally omits it. | …/dot1q:bridge-port |
vrf |
element name | no | unset | The routing instance this interface is in. Names an entry of the device's spec.vrfs (NV-F002); unset means the global instance. An address only collides with another address in the same VRF. |
/ni:network-instances/ni:network-instance/ni:name |
wireless |
WirelessConfig | no | unset | Radio configuration of a type: wifi interface: which side of the association it is, which frequency it uses and which BSSs it beacons or joins. Forbidden on every other type (NV-W002). |
…/dot11:wireless-interface |
poe |
PoeConfig | no | unset | This port is power sourcing equipment: it hands power down the cable (§17.3). Only on a type a cable terminates on — ethernet or lag (NV-E006). |
/power-ethernet-mib:pethPsePortTable/pethPsePortEntry |
parent |
interface name | no | unset | The interface this one is stacked on. Required for type: vlan, forbidden otherwise (NV-I002). |
…/if:lower-layer-if |
members |
interface name list | no | unset | The interfaces aggregated by this one. Required for type: lag and type: bridge, forbidden otherwise (NV-I003). |
…/if:lower-layer-if |
netns |
element name | no | unset | The network namespace this interface lives in (§23.1). Names an entry of the device's spec.netns (NV-N022); unset means the machine's initial namespace. Unlike vrf, which partitions one stack's routing table, this places the interface in a different stack entirely — its addresses do not collide with the same addresses elsewhere on the machine. |
— |
peer |
interface name | no | unset | The other end of the veth pair this interface is one end of (§23.2). Names another type: ethernet interface of the same element, which must name this one back (NV-N023). A veth end is ianaift:ethernetCsmacd like any other port; what it has instead of a socket is this peer, so a cable must not terminate on it (NV-N024). |
…/if:lower-layer-if |
range |
string | no | unset | Declares many interfaces at once instead of name, by bracket expansion over one or more numeric spans (GigabitEthernet1/0/[1-48]). Consumed by the loader: the entry is replaced by the interfaces it expands to before anything else sees the document. Exactly one of name and range is written. |
— |
rangeexpands as an odometer, the rightmost span varying fastest, and the width of a span's low bound is its zero padding ([01-12]yields01…12). Indescription,{}and%dstand for the last span and{0},{1}, … for a span by position. See §6.2.5 ofschema.md.- Inside a
specthat declaresfrom, an entry may state onlynameand the fields it overrides; the template suppliestypeand the rest. type: vlanrequiresparentand avlanblock in access mode carrying the encapsulation VID.type: lagandtype: bridgerequiremembers, which must be non-empty, free of duplicates, and must not name the interface itself.- An interface carrying IPv6 addresses must have an MTU of at least 1280 (
NV-I011).
spec.interfaces[].ipv4
RFC 8344's ip:ipv4 container.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
enabled |
boolean | no | true |
Whether the IPv4 stack is active on this interface. | …/ip:ipv4/ip:enabled |
forwarding |
boolean | no | unset | Whether the interface forwards IPv4. Left unset in the document, it inherits spec.forwarding.ipv4; RFC 8344's own default is false. |
…/ip:ipv4/ip:forwarding |
mtu |
integer, 68–65535 | no | unset | IPv4 MTU. Defaults to interfaces[].mtu once the document is loaded. |
…/ip:ipv4/ip:mtu |
addresses |
IPv4Address list | no | [] |
The IPv4 addresses configured on the interface. 10.0.0.1/24 is shorthand for a full entry, and a bare list is shorthand for {addresses: [...]}. |
…/ip:ipv4/ip:address |
gateway |
IPv4 address | no | unset | First hop for off-link IPv4 traffic, as a bare address without a prefix length. It must lie inside one of this interface's own prefixes (NV-A013). |
rt:routing/…/static-routes/v4ur:ipv4/v4ur:route/…/next-hop-address |
- A bare list is shorthand for the container:
ipv4: [10.0.0.1/24]meansipv4: {addresses: [{ip: 10.0.0.1, prefix_length: 24}]}.
spec.interfaces[].ipv4.addresses[]
One IPv4 address. Addresses are unique within the interface (NV-A002).
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
ip |
IPv4 address | yes | — | The address itself, without a prefix and without a zone index. RFC 8344's list key. | …/ip:ipv4/ip:address/ip:ip |
prefix_length |
integer, 0–32 | yes | — | Prefix length. May be written as a dotted-quad netmask instead, which is normalised to a prefix length on load; a non-contiguous mask is rejected (NV-A003). |
…/ip:ipv4/ip:address/ip:prefix-length |
10.0.0.1/24is shorthand for the mapping form.netmask: 255.255.255.0may be written instead ofprefix_length, but not as well as; it is normalised away on load and never appears innetviz showoutput.
spec.interfaces[].ipv6
RFC 8344's ip:ipv6 container.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
enabled |
boolean | no | true |
Whether the IPv6 stack is active on this interface. | …/ip:ipv6/ip:enabled |
forwarding |
boolean | no | unset | Whether the interface forwards IPv6. Inherits spec.forwarding.ipv6 when unset. |
…/ip:ipv6/ip:forwarding |
mtu |
integer, 1280–4294967295 | no | unset | IPv6 MTU. Defaults to interfaces[].mtu, but only when that is at least 1280. |
…/ip:ipv6/ip:mtu |
addresses |
IPv6Address list | no | [] |
The IPv6 addresses configured on the interface. Normalised to RFC 5952 lower-case compressed form. | …/ip:ipv6/ip:address |
gateway |
IPv6 address | no | unset | First hop for off-link IPv6 traffic, as a bare address without a prefix length. It must lie inside one of this interface's own prefixes (NV-A013), unless it is link-local: fe80::1 is on-link by definition and is exempt. |
rt:routing/…/static-routes/v6ur:ipv6/v6ur:route/…/next-hop-address |
spec.interfaces[].ipv6.addresses[]
One IPv6 address. The 2001:db8::1/64 shorthand applies here too.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
ip |
IPv6 address | yes | — | The address itself, zone-free. RFC 8344's list key. | …/ip:ipv6/ip:address/ip:ip |
prefix_length |
integer, 0–128 | yes | — | Prefix length. Mandatory — RFC 8344 has no netmask case for IPv6. | …/ip:ipv6/ip:address/ip:prefix-length |
spec.interfaces[].vlan
The 802.1Q bridge-port configuration of one interface.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
mode |
access | trunk |
yes | — | Access or trunk. 802.1Q has neither concept; netviz expands the mode into a PVID, an acceptable-frame filter and VLAN membership (see docs/yang-mapping.md). | — |
access_vlan |
integer, 1–4094 | no | unset | The VLAN an access port belongs to, and the encapsulation VID of a type: vlan sub-interface. Required in access mode — it defaults to 1 — and forbidden in trunk mode (NV-V002). |
…/dot1q:bridge-port/dot1q:pvid |
trunk_vlans |
VLAN set | no | unset | The tagged VLAN set of a trunk port. Required in trunk mode, forbidden in access mode. | …/dot1q:vlan/dot1q:egress-ports (tagged) |
native_vlan |
integer, 1–4094 | no | unset | The untagged VLAN on a trunk. Trunk mode only (NV-V003); it is implicitly a member of the port's VLAN set. |
…/dot1q:bridge-port/dot1q:pvid |
ingress_filtering |
boolean | no | true |
Drop frames tagged with a VLAN the port is not a member of. | …/dot1q:bridge-port/dot1q:enable-ingress-filtering |
acceptable_frames |
admit-all-frames | admit-only-VLAN-tagged-frames | admit-only-untagged-and-priority-tagged |
no | unset | Which frames the port admits. Derived from mode and native_vlan when not stated. |
…/dot1q:bridge-port/dot1q:acceptable-frame |
- In
accessmode:access_vlanis allowed and defaults to 1;trunk_vlansandnative_vlanare rejected (NV-V002,NV-V003). - In
trunkmode:trunk_vlansis required andaccess_vlanis rejected. trunk_vlansaccepts an id, a list,"10,20,100-110",all(1–4094) ornone, and always serialises back to the coalesced string form.
spec.interfaces[].wireless
The radio configuration of a type: wifi interface: which side of the association it is on, where on the air it is, and which networks it serves.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
role |
ap | station | mesh |
yes | — | Which side of the association this radio is: ap beacons the SSIDs, station and mesh associate to one. A wireless link joins exactly one ap to one client (NV-W007). |
…/dot11:station-config/dot11:desired-bss-type |
band |
2.4GHz | 5GHz | 6GHz |
no | unset | The band the radio operates in: 2.4GHz, 5GHz or 6GHz. Required alongside channel and width_mhz, because both mean different frequencies in different bands. |
…/dot11:phy/dot11:channel-starting-factor |
channel |
integer, 1–233 | no | unset | The primary 20 MHz channel, as the band numbers it (NV-W003). |
…/dot11:phy/dot11:current-channel-number |
width_mhz |
20 | 40 | 80 | 160 | 320 |
no | unset | Total channel width in MHz. 40 is the most 2.4 GHz can bond and 320 is 6 GHz only (NV-W004). |
…/dot11:phy/dot11:current-channel-width |
tx_power_dbm |
number, -30.0–40.0 | no | unset | Radiated power in dBm. The MIB counts abstract power levels per PHY, so the unit is netviz's own. | …/dot11:phy/dot11:current-tx-power-level |
bss |
Bss list | no | [] |
The basic service sets this radio beacons (ap) or is associated to (station, mesh, at most one — NV-W006). |
…/dot11:bss |
channelandwidth_mhzboth requireband: channel numbers repeat between the 2.4 GHz and 6 GHz plans, and 320 MHz exists only at 6 GHz (NV-W003,NV-W004).- A
medium: wirelesscable joins exactly oneapradio to onestationormeshradio (NV-W007); that association is what the layer-2 view labels withSSID @ channel/band.
spec.interfaces[].wireless.bss[]
One basic service set: an SSID the radio beacons, or — on a client radio — the one it is associated to.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
ssid |
string, 1–32 characters | yes | — | The network name, 1 to 32 octets. Unique within one radio (NV-W005), and on a client radio it must be one the AP at the far end advertises (NV-W010). |
…/dot11:bss/dot11:ssid |
bssid |
MAC address | no | unset | MAC address of this BSS — usually the radio's own for the first SSID and a derived one for each further SSID. Unique across the inventory (NV-W008). |
…/dot11:bss/dot11:bssid |
vlan |
integer, 1–4094 | no | unset | The VLAN this SSID's traffic is bridged into. Absent means the radio's untagged domain. Checked against the device's VLAN database (W113) and against the VLANs the access point actually carries (NV-W009). |
— |
security |
open | wpa2-psk | wpa2-eap | wpa3-psk | wpa3-eap |
no | unset | How the BSS authenticates: open, or WPA2/WPA3 with a passphrase (-psk) or an authentication server (-eap). Absent means nobody recorded it. |
…/dot11:bss/dot11:rsna-enabled |
hidden |
boolean | no | false |
The SSID is left out of the beacon. It is still on the air, and still a BSS this radio serves. | — |
- An
apradio lists one entry per SSID it serves; astationormeshradio lists at most one (NV-W006). vlanis where the SSID's traffic goes on the wired side. It has to be a VLAN the access point carries somewhere (NV-W009), or clients associate and reach nothing.
spec.netns[]
One network namespace the machine runs (§23.1) — a whole second network stack, with its own interfaces, addresses and routing table. An interface joins it with netns.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | yes | — | Name of the namespace, as ip netns spells it. Unique within the device (NV-N020), and what interfaces[].netns and another entry's parent refer to. |
— |
parent |
element name | no | unset | The namespace this one was created inside (NV-N021). Unset means the machine's initial namespace. This is the whole of the hierarchy: a namespace has exactly one creator, so nesting is a tree. |
— |
description |
string | no | unset | Free text: what the namespace is for — a tenant, a container, a test harness. | — |
parentnames another entry of the same table, which is how namespaces nest: a namespace is created from inside exactly one other, so the nesting is a tree (NV-N021). Unset means the machine's initial namespace, which no document declares.- Not a VRF. A VRF partitions the routing table of one stack; a namespace is a second stack, so it partitions the interface names, the addresses and the sockets as well. An interface can be in both.
- Namespaces are joined by veth pairs, which are ordinary
type: ethernetinterfaces naming each other withpeer(§23.2). - A namespace no interface is in holds nothing, which is
NV-N026.
spec.vrfs[]
One routing instance — a VRF (§16.1). An interface joins it with vrf, and that binding is what makes an address private to the instance.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | yes | — | Name of the routing instance. Unique within the device (NV-F001), and what an interface's vrf and a route's vrf refer to. Two devices using one name mean one VRF. |
/ni:network-instances/ni:network-instance/ni:name |
rd |
route distinguisher | yes | — | Route distinguisher, in one of the three RFC 4364 §4.2 encodings: 65000:1, 192.0.2.1:1 or 4200000000:1. Quote it — an unquoted 65000:1 is a number to YAML. |
— |
description |
string | no | unset | Free text: what the instance is for. | /ni:network-instances/ni:network-instance/ni:description |
- Two devices that use the same
nameare taken to mean the same VRF; the route distinguisher is recorded because MPLS needs it, not to identify the instance. - A VRF no interface binds to holds nothing, which is
NV-F014.
spec.route_tables[]
One routing table beyond the three every stack has (§16.2). A table is a container routes are placed in; what reaches it is a rule in routing_policy.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | yes | — | Name of the routing table. Unique within the device, and not one of the reserved main, local or default, which exist without being declared (NV-F015). |
— |
id |
integer, 1–4294967295 | yes | — | The number the table is known by, 1-4294967295. Unique within the device, and not 253, 254 or 255 — those are the reserved three under another name (NV-F015). |
— |
description |
string | no | unset | Free text: what the table is for. | — |
main,localanddefaultexist without being declared and may not be declared, by either name or number (NV-F015).- A table nothing looks up is consulted by nothing (
NV-F023); a rule looking up a table nothing is placed in falls through (NV-F022).
spec.routes[]
One configured static route (§16.3).
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
prefix |
IPv4 prefix | IPv6 prefix | yes | — | Destination prefix, either family, in canonical CIDR form. Host bits are rejected: a destination with them set is a typo or a host route, and netviz will not guess which. | …/rt:static-routes/v4ur:ipv4/v4ur:route/v4ur:destination-prefix |
via |
IPv4 address | IPv6 address | no | unset | Next-hop address. Same family as prefix (NV-F003), and on a prefix the device configures (NV-F008). |
…/v4ur:route/v4ur:next-hop/v4ur:next-hop-address |
dev |
interface name | no | unset | Egress interface, for an unnumbered next hop or a route pointed at an interface. Names an interface of this device (NV-F009). |
…/v4ur:route/v4ur:next-hop/v4ur:outgoing-interface |
vrf |
element name | no | unset | The routing instance holding the route. Names an entry of spec.vrfs (NV-F005); unset means the global instance. |
/ni:network-instances/ni:network-instance/ni:name |
table |
element name | no | unset | The routing table holding the route; main when unset. Names an entry of spec.route_tables or a reserved table (NV-F019). A VRF is a table of its own, so vrf and table are alternatives, not a pair (NV-F018). |
— |
metric |
integer, 0–4294967295 | no | unset | Administrative distance or cost, as this device counts it. Documentation only: netviz does not compute a best path. | — |
blackhole |
boolean | no | false |
Discard matching packets. Excludes via and dev (NV-F004). |
…/v4ur:route/v4ur:next-hop/v4ur:special-next-hop |
- At least one of
via,devandblackholeis required, andblackholeexcludes the other two (NV-F004). viais of the same family asprefix(NV-F003) and must be on-link: inside a prefix the device configures, in the same VRF (NV-F008).vrfandtableare alternatives, not a pair: a VRF is a routing table of its own (NV-F018).
spec.routing_policy[]
One rule of the routing policy database (§16.4): which table a packet is routed by, decided from where it came from, what marked it, where it arrived or its DSCP.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
priority |
integer, 0–4294967295 | yes | — | Where the rule sits in the policy database, 0-4294967295. The database is walked from the lowest priority upwards and the first match decides, so this is the rule's position and its identity: unique within the device per family (NV-F020). |
— |
family |
ipv4 | ipv6 |
no | unset | ipv4 or ipv6 — which family's database the rule is installed in. Derived from src/dst when they say, and both families when nothing does. |
— |
src |
IPv4 prefix | IPv6 prefix | no | unset | Match packets from this prefix. The selector policy-based routing exists for: it is what makes a source route a source route. | — |
dst |
IPv4 prefix | IPv6 prefix | no | unset | Match packets to this prefix. | — |
fwmark |
string | no | unset | Match the mark a firewall put on the packet, optionally masked: 0x1, 0x1/0xff, or a plain number. This is how a port, a user or an application reaches the policy database — something marks, and this matches. |
— |
iif |
interface name | no | unset | Match packets that arrived on this interface. Names an interface of this device (NV-F021). |
— |
oif |
interface name | no | unset | Match packets that would leave by this interface — locally originated traffic from a socket bound to it. Names an interface of this device (NV-F021). |
— |
dscp |
integer, 0–63 | no | unset | Match this DSCP code point, 0-63 (RFC 2474 §3) — the six bits, not the whole octet. | — |
invert |
boolean | no | false |
Match everything the selectors do not. Needs a selector to invert (NV-F017). |
— |
action |
lookup | blackhole | unreachable | prohibit | goto |
no | lookup |
What happens to a matching packet: lookup routes it by table, blackhole, unreachable and prohibit discard it, goto jumps to another priority. Default lookup. |
— |
table |
element name | no | unset | The table to route by. Required by lookup and refused by every other action (NV-F016); names an entry of spec.route_tables, a VRF, or a reserved table (NV-F019). |
— |
goto |
integer, 0–4294967295 | no | unset | The priority to jump to. Required by goto and refused by every other action (NV-F016), and strictly greater than this rule's own — the database is walked upwards, so a backwards jump is a loop. |
— |
description |
string | no | unset | Free text: what the rule is for. | — |
- The database is walked from the lowest
priorityupwards and the first match decides, sopriorityis the rule's position and its identity: unique within the device, per family (NV-F020). - A rule with no selector matches every packet, which terminates the database — and makes every rule after it in that family unreachable (
NV-F024). - There is no layer-4 selector. Mark the packet in the firewall and match
fwmarkhere; see §16.7.
spec.routing
The dynamic routing protocols the device takes part in (§16.5). Both blocks are optional and neither implies the other.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
ospf |
OspfConfig | no | unset | The OSPF area this device runs, and on which interfaces. | …/rt:control-plane-protocol[type='ospf'] |
bgp |
BgpConfig | no | unset | The BGP autonomous system this device is in, and its neighbours. | …/rt:control-plane-protocol[type='bgp'] |
spec.routing.ospf
One OSPF area, and the interfaces that run it.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
area |
OSPF area | no | 0.0.0.0 |
Area identifier, written as a dotted quad or as a plain number; 0 and 0.0.0.0 are the same backbone area and both normalise to 0.0.0.0. |
— |
router_id |
IPv4 address | no | unset | Router identifier — a dotted quad even in an IPv6-only network. Unique across the inventory (NV-F012). |
— |
interfaces |
interface name list, ≥ 1 entry | yes | — | The interfaces OSPF runs on. Non-empty, free of duplicates (NV-F006), and each one an interface of this device (NV-F010). |
/if:interfaces/if:interface/if:name |
areaaccepts0and0.0.0.0for the backbone and stores the dotted quad, so two documents that spell one area differently still compare equal.- One area per device: per-interface areas, and therefore area border routers, are deferred (§16.7).
spec.routing.bgp
The autonomous system this device is in, and the sessions it configures.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
asn |
integer, 1–4294967295 | yes | — | Local autonomous system number, 1 to 4294967295. AS 0 is reserved (RFC 7607). | — |
router_id |
IPv4 address | no | unset | BGP identifier — a dotted quad. Unique across the inventory (NV-F012); commonly the same value as the OSPF router id, which is one identity rather than a duplicate. |
— |
neighbors |
BgpNeighbor list | no | [] |
The sessions this device configures. Peers are named by address, never by element name. | — |
spec.routing.bgp.neighbors[]
One BGP session. The peer is an address, which is what the device is configured with — never an element name (§16.6).
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
address |
IPv4 address | IPv6 address | yes | — | Peer address. Resolved against every address the inventory configures; a peer that resolves to nothing is NV-F013, a warning, because an eBGP peer may be external. |
— |
remote_asn |
integer, 1–4294967295 | yes | — | The AS the peer is in. Checked against the peer's own asn when the address resolves (NV-F011). |
— |
description |
string | no | unset | Free text: what the session is for. | — |
- The address is resolved against every address the inventory configures. A peer that resolves to nothing is a warning (
NV-F013), because an eBGP peer may be a transit provider nobody declares here; a peer whose ownasncontradictsremote_asnis an error (NV-F011).
spec.zones[]
One security zone (§24.1): a name, and the interfaces in it. Policy is written between zones rather than between interfaces, so a rule survives a port being renamed.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | yes | — | Name of the zone. Unique within the device, and not local, which is the machine itself and is nameable in a rule without being declared (NV-B001). |
— |
interfaces |
interface name list | no | [] |
The interfaces in this zone. Each names an interface of this device (NV-B002), and no interface is in two zones (NV-B003). A zone holding none is inert (W150). |
— |
description |
string | no | unset | Free text: what the zone is for. | — |
- An interface is in at most one zone (
NV-B003). That is the defining property of a zone, and what makesfrom lana statement about a packet rather than a question. localis the machine itself and may not be declared (NV-B001); it is nameable in a rule without being declared.- A zone holding no interface is inert (
W150); an interface in no zone, on a device that declares zones at all, is worth a second look (W151).
spec.firewall
What the device does to the packets it sees (§24.2): the three defaults, the filter policy and the address translations.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
default_input |
accept | drop | reject | mark | log |
no | drop |
What a packet for this machine gets when no rule decides. One of accept, drop and reject — a default has to decide (NV-B007). Defaults to drop. |
— |
default_forward |
accept | drop | reject | mark | log |
no | drop |
What a packet through this machine gets when no rule decides, on the same terms. Defaults to drop. |
— |
default_output |
accept | drop | reject | mark | log |
no | accept |
What a packet from this machine gets when no rule decides, on the same terms. Defaults to accept: a machine that cannot answer a DNS query cannot be administered either. |
— |
rules |
FirewallRule list | no | [] |
The filter policy, in declaration order. What the device walks is this list in priority order, lowest first, first terminal match deciding (§24.2). | — |
nat |
NatRule list | no | [] |
The address translations, in the order they are tried (§24.4). Apart from rules because a packet is translated and filtered, in different hooks. |
— |
description |
string | no | unset | Free text: what the policy as a whole is for. | — |
- The defaults are deny inbound, deny transit, permit outbound. Each has to decide the packet, so
markandlogare refused there (NV-B007). - Available on every layer-3 kind, not only on
kind: firewall: a router with three rules on it filters, and that is what most networks run. Ahubhas no IP stack and refuses both this andzones(NV-H003).
spec.firewall.rules[]
One filter rule (§24.2): which packets it picks out, and what happens to them. Read it as a sentence — at priority 100, TCP from the lan zone to this machine's port 22 is accepted.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
priority |
integer, 0–4294967295 | yes | — | Unique within the device, per family (NV-B008). The chain is walked from the lowest priority upwards; the first rule whose action is terminal decides, and nothing after it is consulted. |
— |
name |
element name | no | unset | Optional label, for the diagram and for a diagnostic to name the rule by. | — |
src_zone |
element name | no | unset | The zone the packet came from: a declared zone, or local for traffic this machine generated (NV-B004). Unset matches any zone. |
— |
dst_zone |
element name | no | unset | The zone the packet is going to, on the same terms (NV-B004). Together with src_zone this decides the hook: to: local is input, from: local is output, two real zones are forward. |
— |
family |
ipv4 | ipv6 |
no | unset | Which family's chain the rule is in. Omit to install in both, and derive from src, dst or protocol when possible (NV-B005); ipv4 and ipv6 are explicit. |
— |
src |
IPv4 prefix | IPv6 prefix | no | unset | Source prefix selector. Either family; optional. | — |
dst |
IPv4 prefix | IPv6 prefix | no | unset | Destination prefix selector, on the same terms. | — |
protocol |
tcp | udp | icmp | icmpv6 | sctp | esp | ah | gre |
no | unset | The IP protocol. Required by src_ports and dst_ports, which only tcp, udp and sctp have (NV-B005). icmp is IPv4 and icmpv6 is IPv6, and stating one against the other family is refused. |
— |
src_ports |
string list | no | [] |
Source ports: single ports and closed ranges (443, 30000-32767), matched as a set. |
— |
dst_ports |
string list | no | [] |
Destination ports, on the same terms. The usual selector, since it is the one that names the service. | — |
ct_state |
new | established | related | invalid list |
no | [] |
Connection-tracking states, matched as a set. Empty matches any state; one rule accepting established and related replaces the return path of every other rule. |
— |
iif |
interface name | no | unset | Ingress interface selector (NV-B009), for when a zone is too coarse. Rare: the point of a zone is not needing this. |
— |
oif |
interface name | no | unset | Egress interface selector, on the same terms (NV-B009). |
— |
invert |
boolean | no | false |
Match everything the selectors do not. Meaningless without a selector to invert (NV-B005). |
— |
action |
accept | drop | reject | mark | log |
yes | — | accept, drop and reject decide the packet and end the walk; mark writes a firewall mark and log records it, and both carry on to the next rule. Stated, never defaulted. |
— |
mark |
string | no | unset | The mark to write, hexadecimal, optionally masked. Required by action: mark and refused by everything else (NV-B005). This is what spec.routing_policy[].fwmark reads — see §16.9 and §24.3. |
— |
log_prefix |
string, ≤ 64 characters | no | unset | The tag put in front of a logged packet. For action: log only (NV-B005). |
— |
description |
string | no | unset | Free text: what the rule is for. | — |
- The chain is walked from the lowest
priorityupwards and the first terminal match decides, sopriorityis the rule's position and its identity: unique within the device, per family (NV-B008). accept,dropandrejectare terminal;markandlogdo something to the packet and carry on walking, which is what makes them useful.- The hook is derived, never written:
dst_zone: localis input,src_zone: localis output, two real zones are forward. A rule naming one real zone is in both the hooks it could be in. - A rule with no selector matches everything reaching its hooks, which terminates the chain — and makes every rule after it unreachable (
W154). action: markis the half of §16.9 that writes;spec.routing_policy[].fwmarkis the half that reads. A mark written that nothing reads isW152, and one read that nothing writes isW153.
spec.firewall.nat[]
One address translation (§24.4). Apart from the filter rules because it happens apart from them: a packet is translated and filtered, in different hooks.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
element name | no | unset | Optional label, for a diagnostic to name the translation by. | — |
type |
snat | masquerade | dnat | redirect |
yes | — | snat and masquerade rewrite the source on the way out; dnat and redirect rewrite the destination on the way in. Which of the two fields below are required follows from this (NV-B006). |
— |
src_zone |
element name | no | unset | The zone the packet came from (NV-B004). |
— |
dst_zone |
element name | no | unset | The zone it is going to (NV-B004). The usual selector for a source translation: everything leaving towards the wan is masqueraded. |
— |
family |
ipv4 | ipv6 |
no | unset | Which family the translation is in. Derived from any address it names (NV-B006). |
— |
src |
IPv4 prefix | IPv6 prefix | no | unset | Source prefix selector. | — |
dst |
IPv4 prefix | IPv6 prefix | no | unset | Destination prefix selector. | — |
protocol |
tcp | udp | icmp | icmpv6 | sctp | esp | ah | gre |
no | unset | The IP protocol. Required by dst_ports (NV-B006). |
— |
dst_ports |
string list | no | [] |
Destination ports: the published port, not the internal one, which is to_port. |
— |
to_address |
IPv4 address | IPv6 address | no | unset | What the address becomes. Required by snat and dnat; refused by masquerade (whose address is the egress interface's, unknown here) and by redirect (whose address is this machine) — NV-B006. |
— |
to_port |
integer, 1–65535 | no | unset | What the port becomes. Required by redirect, which translates the port and nothing else; on a source translation it needs a dst_ports to be about (NV-B006). |
— |
description |
string | no | unset | Free text: what the translation is for. | — |
- Order in the list is the order the translations are tried, first match winning. There is no
priority: a number that only ever repeated the position would be one more thing to keep in step. snatanddnatstate the address they translate to;masqueradecannot (it is the egress interface's, unknown until the packet leaves) andredirectneed not (it is this machine) —NV-B006.
spec — cable
A cable is an undirected physical link between exactly two interfaces, and a first-class element so that it can carry its own metadata.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
endpoints |
InterfaceRef list | yes | — | Exactly two device:interface references (NV-C001). The link is undirected, so the pair is sorted on load and the order carries no meaning. |
— |
medium |
copper | fiber | wireless |
yes | — | What the link physically is. wireless requires both endpoints to be type: wifi and forbids length_m and category (NV-C006, NV-C007). |
— |
speed |
bit rate | no | unset | Negotiated link rate. Written as bit/s or as 1Gbps; stored in bit/s. Projected onto if:speed of both endpoints, which is config false. |
…/if:speed (on both endpoints) |
duplex |
full | half |
no | full |
Duplex of the link. half outside a hub link is NV-C013. |
— |
length_m |
number, ≥ 0.0 | no | unset | Physical length in metres. Documentation only. | — |
category |
string | no | unset | Cable category, free text (cat6, cat6a, om4). |
— |
connector |
string | no | unset | Connector type, free text (rj45, lc, sc). |
— |
label |
string | no | unset | The identifier printed on the cable or the patch panel. Drawn on the edge. | — |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
spec.endpoints[]
A reference to one port. Written as the string device:interface; the mapping form below is equivalent and both serialise back to the string.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
device |
element reference | yes | — | Name of the element the port belongs to. Resolved in the cable's own namespace first, then upwards (NV-C002). |
— |
interface |
interface name | yes | — | Name of the interface on that element. An adapter's upstream.name counts (NV-C003). |
— |
spec — adapter
An adapter presents network interfaces over a non-network host port: USB dongles, Thunderbolt docks, media converters.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
vendor |
string | no | unset | Hardware vendor, free text. | — |
model |
string | no | unset | Hardware model designation, free text. | — |
serial |
string | no | unset | Serial or asset number, free text. | — |
location |
string | no | unset | Physical location, free text. | — |
form_factor |
string | no | unset | What sort of adapter this is: usb-ethernet, dock, media-converter, sfp-module. Descriptive only. |
— |
passthrough |
boolean | no | true |
May the renderer collapse the adapter into its host? True draws the host and the adapter as one node at layer 2; false keeps them separate. | — |
ports |
integer, ≥ 1 | no | unset | How many downstream ports the hardware physically has. Declaring it lets the validator catch an inventory that outgrew the device (E006). |
— |
upstream |
UpstreamPort | yes | — | The host-facing port: the bus the adapter plugs into. | — |
interfaces |
Interface list, ≥ 1 entry | yes | — | The network ports the adapter presents downstream. Only ethernet, wifi and lag are allowed (NV-X003). |
/if:interfaces/if:interface |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
spec.upstream
The host-facing port of an adapter.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
name |
interface name | yes | — | Name of the host-side port. Shares the interface namespace of the adapter (NV-X004) and may be named by a cable endpoint. |
/if:interfaces/if:interface/if:name |
type |
usb | usb-c | thunderbolt | pcie | m2 | sfp | internal |
yes | — | The host bus. usb and usb-c export as ianaift:usb; everything else as ianaift:other, because IANA registers no Thunderbolt or PCIe identity. |
…/if:type |
speed |
bit rate | no | unset | Host-bus rate, e.g. 5Gbps for USB 3.0. Written as bit/s or with a unit suffix. |
…/if:speed |
attached_to |
element reference | no | unset | The host the adapter is plugged into. A bare device name, never a device:interface reference (NV-X001). This is what joins the adapter to the graph when no cable does. |
— |
- Declaring
attached_toand cabling the upstream port is an error (NV-X005): the host attachment is declared exactly once.
spec — tunnel
A tunnel is an undirected logical link between two or more interfaces of type: tunnel. It is to a logical topology what a cable is to a physical one, and a first-class element for the same reason.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
type |
wireguard | ipsec | openvpn | pptp | l2tp | gre | vxlan | geneve |
yes | — | The encapsulation: wireguard, ipsec, openvpn, pptp, l2tp, gre, vxlan or geneve. It decides the layer carried, the outer transport, the default port, whether the payload is encrypted and how much MTU the headers cost. |
— |
endpoints |
InterfaceRef list | yes | — | Two or more device:interface references, each naming an interface of type: tunnel (NV-T001, NV-T003). The link is undirected, so the list is sorted on load. Three or more endpoints make it multipoint, and it is then drawn as a node rather than a line. |
— |
over |
element reference | no | unset | The tunnel this one is encapsulated in — vxlan over ipsec is written by naming the IPsec tunnel here (NV-T004). Absent means the tunnel runs directly over the physical topology. The chain must not loop (NV-T005). |
— |
mode |
tunnel | transport |
no | unset | IPsec's encapsulation mode, tunnel or transport (RFC 4301). Defaults to tunnel; every other type has only one mode and must not declare it (NV-T008). |
— |
vni |
integer, 0–16777215 | no | unset | The 24-bit VXLAN/Geneve virtual network identifier. Required for those two types and rejected for every other (NV-T007). |
— |
port |
integer, 1–65535 | no | unset | Outer UDP/TCP port. Defaults to the registered port of the type (WireGuard 51820, OpenVPN 1194, L2TP 1701, VXLAN 4789, Geneve 6081) and is rejected for GRE and IPsec, which run directly over IP (NV-T008). |
— |
mtu |
integer, 68–65535 | no | unset | MTU of the tunnel interface. Compared with what the underlay leaves after the encapsulation overhead of the whole stack (NV-T011). |
— |
encrypted |
boolean | no | unset | Whether the payload is protected. Defaults to what the type does — true for WireGuard, IPsec and OpenVPN, false for GRE, VXLAN, Geneve, L2TP and PPTP, whose MPPE is broken. Set it to true to record that the deployment protects an otherwise cleartext type some other way. | — |
cipher |
string | no | unset | Negotiated cipher suite, free text (chacha20-poly1305, aes-256-gcm). Only on a tunnel that encrypts (NV-T009). |
— |
auth |
psk | certificate | public-key | password |
no | unset | How the endpoints authenticate each other: psk, certificate, public-key or password. The method, never the material — netviz stores no secrets (NV-T010). |
— |
label |
string | no | unset | Free-text identifier printed on the edge, as a cable's label is. |
— |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
endpointsuses the samedevice:interfaceform a cable does, and each one must name an interface oftype: tunnel(NV-T003) — the virtual interface the tunnel presents, not the physical port its outer packets leave by.overnests one tunnel inside another:vxlanoveripsecis written by naming the IPsec tunnel there. The chain must not loop (NV-T005).typesupplies the defaults forport,encryptedandmode, and the encapsulation overheadNV-T011measures an MTU against. Materialised on load, so a loaded document states them explicitly.- There is nowhere to put a key, a password or a certificate, and the fields people reach for are rejected by name (
NV-T010).authrecords the method.
spec — patchpanel
A patch panel is a passive cross-connect: numbered positions on the front, the same numbers on the rear, and a coupler joining each front position to one rear position.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
vendor |
string | no | unset | Hardware vendor, free text. Documentation only. | — |
model |
string | no | unset | Hardware model designation, free text. | — |
serial |
string | no | unset | Serial or asset number, free text. | — |
form_factor |
string | no | unset | Descriptive: keystone, fibre-lc, coupler. Documentation only. |
— |
ports |
string, ≥ 1 character | yes | — | The positions the panel has, as a count (24) or as spans (1-12,17-24). Each one becomes a front/<n> and a rear/<n> interface (NV-P006). |
/if:interfaces/if:interface |
couplers |
map string → string | no | unset | Front position to rear position, for a panel that is not wired straight through. Absent means the identity mapping (NV-P007). |
— |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
portsis the only required key. Each position it names becomes two interfaces,front/<n>andrear/<n>, which a cable terminates on exactly as it terminates on a device port (NV-P001).- A panel is not a hop.
netviz render --layer physicaldraws it and both cable segments; every other layer splices the run into the single edge it electrically is, between the two active ports. couplersis only needed for a panel that is cross-wired. The default is the identity mapping, which is what the numbering printed on a real panel promises.
spec — pdu
A power distribution unit: numbered outlets, a rated capacity, and the supply that feeds it. The power half of what a patch panel is for data.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
vendor |
string | no | unset | Hardware vendor, free text. Documentation only. | — |
model |
string | no | unset | Hardware model designation, free text. | — |
serial |
string | no | unset | Serial or asset number, free text. | — |
form_factor |
string | no | unset | Descriptive: vertical, horizontal, 1U, 0U. Documentation only. |
— |
outlets |
string, ≥ 1 character | yes | — | The outlets the unit has, as a count (24) or as spans (1-12,17-24). Referred to by number from a device's power.inputs; at most 512, no repeats (NV-E001). |
/entity-mib:entPhysicalTable/entPhysicalEntry |
capacity_watts |
number, > 0.0, ≤ 1000000.0 | no | unset | How many watts may be drawn through the unit in total. NV-E012 sums the declared loads against it; absent means the rating is not recorded, and nothing is graded. |
/eo-mib:eoPowerTable/eoPowerEntry/eoPowerNameplate |
input_feed |
string, ≤ 64 characters | no | unset | Which supply feeds the unit — A, B, ups-1, utility. Free text, compared only for equality: two PDUs on one feed do not make a device redundant (NV-E015). |
/eo-ctx-mib:eoPowerRelationTable/eoPowerRelationEntry |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
outletsis the only required key, and takes the same count-or-range shorthandportsdoes. An outlet is not an interface: a power cord is not acable, so nothing is cabled to a PDU — a device names an outlet inpower.inputsinstead.- A PDU is placed on a rack elevation through
metadata.location, exactly as a switch is, andnetviz render --layer rackannotates it with its utilisation. input_feedis free text and is compared only for equality. It is what makes A/B redundancy checkable: two units on one feed fail together (NV-E015).
spec.power
What a device draws, which outlets feed it, and how much PoE it hands out. One block for both directions, because they are one question about one box.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
draw_watts |
PowerDraw | no | unset | What the device draws. A bare number is the typical draw; a mapping states typical and optionally maximum. |
/eo-mib:eoPowerTable/eoPowerEntry/eoPower |
inputs |
PowerInput list, ≤ 8 entries | no | [] |
One entry per power supply, naming the PDU outlet feeding it. At most 8. Empty for a device fed over PoE, or one whose feed is not recorded yet (NV-E016). |
/eo-ctx-mib:eoPowerRelationTable/eoPowerRelationEntry |
redundant |
boolean | no | false |
The feeds are meant to be independent: losing one must not lose the device. Needs at least two inputs (NV-E002) that land on different units and different feeds (NV-E015). |
— |
powered_by |
outlet | poe |
no | outlet |
Where the device's own power comes from: outlet (the default) or poe, meaning it takes power over its uplink and declares no inputs (NV-E005, NV-E014). |
— |
poe_budget_watts |
number, > 0.0, ≤ 1000000.0 | no | unset | The PoE power this device can hand out across every PSE port together. NV-E013 checks the ports that hold budget fit inside it. |
/power-ethernet-mib:pethMainPseTable/pethMainPseEntry/pethMainPsePower |
draw_wattsaccepts a bare number as shorthand for{typical: n}. The typical figure is what a load schedule sums;maximumis what a breaker has to survive.redundant: trueneeds at least twoinputs(NV-E002), and they have to land on different units and differentinput_feeds for the claim to hold (NV-E015).powered_by: poeexcludesinputs(NV-E005): a device fed over its uplink has no cord.NV-E014then checks the far end of that uplink actually sources power.
spec.power.draw_watts
The nameplate load of one device, in watts. Written as a bare number when only the typical figure is known.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
typical |
number, > 0.0, ≤ 1000000.0 | yes | — | Steady-state draw of the box as configured, in watts. This is what a load schedule sums. | /eo-mib:eoPowerTable/eoPowerEntry/eoPower |
maximum |
number, > 0.0, ≤ 1000000.0 | no | unset | Nameplate or PSU rating, in watts — what a breaker has to survive. Must not be below typical (NV-E003). |
/eo-mib:eoPowerTable/eoPowerEntry/eoPowerNameplate |
spec.power.inputs[]
One power supply and the outlet feeding it. Accepts the compact form pdu-r1-a:7 and the equivalent mapping, the same grammar a cable endpoint uses.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
pdu |
element reference | yes | — | The PDU feeding this supply. An element reference, so it may be written fully qualified to pick one of several PDUs sharing a short name (NV-E011). |
— |
outlet |
string, 1–16 characters | yes | — | The outlet on it, as the PDU numbers it. Must exist (NV-E011) and must not already feed something else (NV-E010). Writable as the shorthand pdu-r1-a:7. |
— |
psu |
string, ≤ 64 characters | no | unset | Which supply on the device this feeds, e.g. psu1. Documentation only, and worth writing: it is what an operator reads off the back of a chassis. |
— |
interfaces[].poe
This port is power sourcing equipment: it hands power down the cable. Only on a type a cable terminates on — ethernet or lag (NV-E006).
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
standard |
802.3af | 802.3at | 802.3bt |
yes | — | Which IEEE 802.3 amendment the port implements: 802.3af (classes 0-3), 802.3at (adds 4) or 802.3bt (adds 5-8). |
/power-ethernet-mib:pethPsePortTable/pethPsePortEntry/pethPsePortType |
class |
integer, 0–8 | no | unset | The IEEE classification, 0 to 8, written class in YAML. Fixes the reservation; refused above the standard's own ceiling, and exclusive with budget_watts (NV-E004). |
…/pethPsePortEntry/pethPsePortPowerClassifications |
budget_watts |
number, > 0.0, ≤ 1000000.0 | no | unset | An explicit reservation in watts instead of a class, for a vendor that lets an operator cap a port below what its class allows. | …/pethPsePortEntry/pethPsePortPowerLimit |
enabled |
boolean | no | true |
Is the port administratively allowed to source power? A disabled PSE port reserves nothing and powers nothing, which is what NV-E014 reports it for. |
…/pethPsePortEntry/pethPsePortAdminEnable |
- How much the port reserves is said once: a
class, or abudget_watts, never both (NV-E004). With neither, the port reserves its standard's maximum, which is what a switch with no per-port configuration does. - A
poeblock on a port with nothing on it is a capability and takes no budget. A port that feeds something, or one with an explicitbudget_watts, does — seeNV-E013.
spec of a user document
One identity: a person, a service account or a shared login. Owns no interfaces and terminates no cable — a person is not a host — so it appears only in the identity view.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
login |
string, 1–64 characters | no | unset | The account name, when it differs from metadata.name; absent means the two are the same. Estate-wide, so two users claiming one login is NV-S013. |
/ietf-system:system/authentication/user/name |
full_name |
string, ≤ 253 characters | no | unset | The person's name as they write it. Free text: a real name is not a grammar. | — |
email |
string, 3–254 characters | no | unset | Where mail reaches them, local@domain.tld. Also what ties the identity to a directory without netviz having to model the directory. |
— |
uid |
integer, 0–4294967294 | no | unset | POSIX user id, when the estate assigns one. 0 to 4294967294; two users claiming one is NV-S013. |
/ietf-system:system/authentication/user |
type |
person | service | shared |
no | person |
person, service or shared. Decides whether NV-S015 and NV-S016 have anything to say: only a person can depart, and only a person is expected in a group. |
— |
status |
active | suspended | departed |
no | active |
active, suspended or departed. A departed account is kept rather than deleted so the memberships still to be revoked stay visible (NV-S015). |
— |
ssh_keys |
string, ≥ 1 character list, ≤ 32 entries | no | [] |
Public keys the account authenticates with, <algorithm> <base64> [comment]. Normalised to single spaces; a private key is refused (NV-S002). |
/ietf-system:system/authentication/user/authorized-key |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
loginis optional becausemetadata.nameis usually the account name already. Absent means the two are the same; everything downstream reads the materialised value, so nothing has to re-apply the default.- A
departedaccount is kept, not deleted: the group memberships still to be revoked are whatNV-S015reports, and deleting the document would delete them too. - Only public keys. A pasted private key is refused with an explanation (
NV-S002), which is the point of checking the shape at all.
spec of a group document
A named set of identities. members may name a user or another group, which is what makes a hierarchy expressible.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
members |
element reference list, ≤ 4096 entries | no | [] |
The users and nested groups in this group, as element references resolved outwards from the group's own namespace. Must resolve (NV-S010), must be an identity (NV-S011), and the nesting must not loop (NV-S012). |
— |
gid |
integer, 0–4294967294 | no | unset | POSIX group id, when the estate assigns one. 0 to 4294967294; two groups claiming one is NV-S013. |
— |
email |
string, 3–254 characters | no | unset | Where mail to the whole group goes, when the group is also a distribution list. | — |
style |
Style | no | unset | How this element is drawn (§22): fill, stroke, shape, icon and five more. Every field is optional, and an absent one inherits from the theme, then the icon set, then the built-in palette. | — |
- Membership is written on the group and nowhere else. A
userdoes not list its groups: two spellings of one fact are how an inventory starts disagreeing with itself. - A member is an ordinary element reference (§4.1), resolved outwards from the group's own namespace. It must resolve (
NV-S010) and must be an identity (NV-S011). - A group naming itself is refused by the model; a longer loop needs the whole tree and is
NV-S012.
spec of a layout document
Where things are drawn, per view. A sidecar: it carries no network facts, and the elements it places know nothing about it. netviz layout writes it.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
views |
map string → ViewGeometry | no | {} |
Geometry per view, keyed by layer name (l1, l2, l3, routing, ...). The same element sits differently in each, so each gets its own arrangement. |
— |
routing |
spline | orthogonal | straight |
no | unset | How links are drawn across the whole inventory unless a view or a link says otherwise: spline (the curve Graphviz draws), orthogonal (right angles) or straight. |
— |
- Coordinates are points (1/72 inch),
yupwards, origin at the bottom left, and apositionis the centre of what it places — Graphviz's system, so a stored arrangement can be handed straight back to it. - A key is an address, resolved like any other reference. A node the inventory does not declare is keyed by its graph id instead:
subnet:10.0.0.0/24,tunnel:site/wg0,rack:hq/comms/r1. - A key naming something the inventory no longer has is
NV-Y001, a warning;netviz layout --prunedrops it.
spec.views.<view>
One view's arrangement. The view name is a layer netviz draws — physical, l1, l2, l3, overlay, routing, rack, power — because the same device sits somewhere different in each.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
nodes |
map string → NodeGeometry | no | {} |
Where each node is drawn, keyed by its address. A derived node the inventory does not declare is keyed by its graph id, such as subnet:10.0.0.0/24. |
— |
edges |
map string → EdgeGeometry | no | {} |
Bends each link is drawn through, keyed by the link's address. | — |
groups |
map string → GroupGeometry | no | {} |
The box each namespace cluster is drawn as, keyed by namespace. Only drawn when the render groups by namespace. | — |
routing |
spline | orthogonal | straight |
no | unset | How links in this view are drawn when they do not say for themselves. Overrides spec.routing; a link's own routing overrides both. |
— |
spec.views.<view>.nodes.<address>
Where one node is drawn.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
position |
Point | yes | — | Centre of the node, in points. | — |
size |
Size | no | unset | Box the node occupies, in points. Omitted means the label decides, which is what keeps an arrangement valid when a device grows a port. | — |
sizeis optional and is not seeded bynetviz layout --write: Graphviz derives the same box from the same label on every run. It is honoured on read, for an editor that lets somebody resize a box on purpose.
spec.views.<view>.edges.<address>
How one link is drawn: the bends it goes through, the style it is routed in and where its label sits. Bends are not seeded unless netviz layout --write --waypoints is asked for — a computed spline is noise, a hand-placed bend is a decision — but a routing or a label is always written, neither being derivable.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
waypoints |
Point list, ≤ 64 entries | no | () |
The bends the link is drawn through, in points, ordered from its first endpoint to its second. Interior points only: the two ends are the nodes, so a route follows them when they are dragged. | — |
routing |
spline | orthogonal | straight |
no | unset | How this link is drawn between its bends, overriding the view's and the inventory's default: spline, orthogonal or straight. |
— |
label |
LabelGeometry | no | unset | Where the link's annotation sits. Omitted leaves it where the renderer puts it, which is half way along and on the line. | — |
- The waypoints are interior points: the two ends of a route are the nodes themselves, so dragging either endpoint carries the bends along instead of invalidating them.
spec.views.<view>.edges.<address>.label
Where a link's annotation sits, as a position on the link rather than a coordinate — so nudging a VLAN label clear of a crossing cable survives both endpoints moving.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
at |
number, 0.0–1.0 | no | 0.5 |
How far along the route the label sits, from 0 at the first endpoint to 1 at the second. |
— |
offset |
Point | no | unset | How far off the line the label is nudged, in points. This is what makes a dense VLAN diagram legible. | — |
spec.views.<view>.groups.<namespace>
The box one namespace cluster is drawn as. Unlike a node it carries a required size: nothing else decides how big a cluster is.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
position |
Point | yes | — | Centre of the cluster box, in points. | — |
size |
Size | yes | — | Extent of the cluster box, in points. | — |
A point
Two numbers, in points. {x: 240, y: 396} or the shorthand [240, 396]; both mean the same thing and both are read.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
x |
number | yes | — | Points from the left edge of the drawing, growing rightwards. | — |
y |
number | yes | — | Points from the bottom edge of the drawing, growing upwards. | — |
A size
Two positive numbers, in points. {width: 220, height: 90} or [220, 90].
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
width |
number, > 0.0 | yes | — | Width in points; strictly positive. | — |
height |
number, > 0.0 | yes | — | Height in points; strictly positive. | — |
spec of a testsuite document
Named claims about the network the other documents describe. netviz test grades them and exits non-zero when one does not hold.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
description |
string | no | unset | What the suite is for, in one line. Printed as the suite's progress line. | — |
assertions |
Assertion list, 1–1024 entries | yes | — | The claims, graded in the order they are written. At least one: a suite that asserts nothing would report a green run having checked nothing. | — |
- A suite must assert something (
NV-K002). A suite that checked nothing would report a green run, which is worse than having no suite at all. - Assertions are graded in the order they are written, and a failure names the file and line of the assertion so an editor can jump to it.
One assertion
assert chooses the claim; every other key is read in its light. A key that belongs to a different assertion is rejected by name (NV-K003) rather than ignored.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
assert |
reachable | not-reachable | path-shorter-than | same-vlan | distinct-vlan | within-prefix | has-interface | port-count-at-least | unique | count | no-single-point-of-failure | query |
yes | — | What is being claimed: reachable, not-reachable, path-shorter-than, same-vlan, distinct-vlan, within-prefix, has-interface, port-count-at-least, unique, count or no-single-point-of-failure. Every other key is read in its light. |
— |
name |
string, ≤ 200 characters | no | unset | How the claim is reported — a sentence a reader who has never seen the inventory can act on. Defaults to a description built from the other keys. | — |
description |
string | no | unset | Why the claim is made. Printed under a failure, so it is where the ticket number or the standard that demands it belongs. | — |
from |
string, ≥ 1 character | no | unset | Where the trace starts: an element, element:interface, an IP address, or a selector matching several of them. The spellings netviz path accepts. |
— |
to |
string, ≥ 1 character | no | unset | Where the trace ends, in the same four spellings as from. |
— |
max_hops |
integer, 1–64 | no | unset | Abandon a route that crosses more links than this. Defaults to the trace engine's own limit of 16. | — |
hops |
integer, 1–64 | no | unset | path-shorter-than: the exclusive upper bound on the hop count of the shortest path. |
— |
vlan |
integer, 1–4094 | no | unset | Restrict a trace to one VLAN, or pin which VLAN same-vlan means. |
— |
layer |
any | l1 | l2 | l3 | power |
no | unset | Which view the claim is about: any, l2 or l3 for a trace; any, l1, l2, l3 or power for no-single-point-of-failure. |
— |
select |
string, ≥ 1 character | no | unset | Which elements the claim is about, in netviz render's filter vocabulary: kind=switch, namespace=sites/north, name=sw-*. A bare word is a name glob. |
— |
query |
string, ≥ 1 character | no | unset | The same thing said in the selector language (docs/query.md), which can express what the vocabulary above cannot: kind in (switch, router) and not interface[name ~ 'Vlan*' and has address]. Either key supplies the elements a selector assertion is graded over, and both together are ANDed. An assert: query takes this one and grades how much it matches against equals / at_least / at_most, defaulting — with none of them — to the claim that it matches nothing. |
— |
prefix |
string, ≥ 1 character | no | unset | within-prefix: the CIDR every routable address on a selected element must lie inside. |
— |
interface |
string, ≥ 1 character | no | unset | has-interface: the interface name every selected element must declare, or a glob matching it. |
— |
ports |
integer, ≥ 0 | no | unset | port-count-at-least: the inclusive lower bound on how many interfaces each selected element declares. |
— |
field |
string, ≥ 1 character | no | unset | unique: the field expression whose values must all differ, e.g. spec.interfaces[name=mgmt0].ipv4[]. |
— |
equals |
integer, ≥ 0 | no | unset | count and query: how many elements the selector must match, exactly. |
— |
at_least |
integer, ≥ 0 | no | unset | count and query: the inclusive lower bound on how many elements the selector matches. |
— |
at_most |
integer, ≥ 0 | no | unset | count and query: the inclusive upper bound on how many elements the selector matches. |
— |
min_isolated |
integer, ≥ 1 | no | unset | no-single-point-of-failure: ignore a candidate that isolates fewer endpoints than this. 1, the default, reports every one of them. |
— |
reachable,not-reachableandpath-shorter-thantakefromandtoin the spellingsnetviz pathaccepts: an element,element:interface, an IP address, or a selector matching several of them.same-vlan,distinct-vlan,within-prefix,has-interface,port-count-at-least,uniqueandcounttakeselect, innetviz render's filter vocabulary.no-single-point-of-failuretakes neither, and optionally narrows the candidates withselectand the views withlayer.
spec of a note document
One callout on the diagram. Presentational throughout: a note cannot make netviz validate fail, cannot move a hop in netviz path, and never reaches an exported configuration.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
views |
string list | no | () |
Which drawings the note appears in, by layer name. Empty means every one of them, which is what a remark about the site itself wants; [l3] is for a remark that only makes sense once the picture is prefixes rather than cables. |
— |
color |
string | no | unset | Fill colour, #rgb or #rrggbb. Absent lets the renderer pick, which is the one presentational decision it is allowed to make for itself. |
— |
text |
string, 1–4000 characters | yes | — | What the note says, in the markdown subset of §21.1: paragraphs, **bold**, *italic*, `code` and - bullets. Anything else is drawn verbatim, because several very different exporters have to agree about the result. |
— |
anchor |
NoteAnchor | no | unset | What the note is about. An anchored note follows what it is anchored to when the diagram is laid out again; a note with only a position does not. | — |
geometry |
AnnotationGeometry | no | unset | Where the note is drawn, and how big. Required unless anchor says what to attach it to; given as well as an anchor, the point wins and the anchor is what the leader points at — which is what dragging an anchored note produces. |
— |
leader |
boolean | no | true |
Draw a line from the note to what it is anchored to. Inert without an anchor. |
— |
- A note needs somewhere to be: either an
anchor, or ageometrygivingxandy. Both is the shape dragging an anchored note produces — the point places it, the anchor is what the leader line points at. viewsscopes the note to the drawings it makes sense in; empty means all of them. A note naming an element the inventory no longer has isNV-G001, a warning, exactly as a stale layout key is.
spec.anchor
What a note is about: one element, or one link. Exactly one of the two, and what makes the note survive the diagram being laid out again.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
element |
element reference | no | unset | The element the note is about, by reference. Exactly one of element and link is written. |
— |
link |
element reference | no | unset | The cable or tunnel the note is about, by reference. | — |
spec.geometry of an annotation
Where an annotation is drawn and how big it is. Flat rather than §18's nested position/size, because these four numbers are what a drag and a resize produce.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
x |
number | no | unset | Points from the left edge of the drawing to the centre of the annotation. Written with y or not at all: half a position places nothing. |
— |
y |
number | no | unset | Points from the bottom edge of the drawing, growing upwards — §18's system, so a dragged note is stored by the machinery that stores a dragged switch. | — |
width |
number, > 0.0 | no | unset | Width in points. Omitted lets the text decide, which is what keeps a note legible after it is edited. | — |
height |
number, > 0.0 | no | unset | Height in points, omitted for the same reason. | — |
- Coordinates are §18's: points,
yupwards, origin at the bottom left, andx/yis the centre of the box. Both or neither — half a position places nothing.
spec of an area document
A labelled box drawn behind the nodes. It says what it contains with members, a selector or an explicit geometry, and at least one of the three is required.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
views |
string list | no | () |
Which drawings the area appears in, by layer name. Empty means every one of them. | — |
color |
string | no | unset | Fill colour, #rgb or #rrggbb. The box is drawn behind the nodes, so a pale one is the readable choice. |
— |
label |
string | no | unset | The caption drawn on the box. Absent draws it unlabelled, which is legitimate for a purely visual grouping. | — |
members |
element reference list, ≤ 1000 entries | no | () |
The elements the zone encloses, named outright. The box is the hull of wherever they were drawn, so it follows them. | — |
selector |
AreaSelector | no | unset | The elements the zone encloses, said as a query instead of a list — the form that does not go stale when the inventory grows. | — |
geometry |
AnnotationGeometry | no | unset | An explicit rectangle, for a zone that is a region of the canvas rather than a set of devices: "everything below this line is on the UPS". Needs a position and a size. | — |
border |
solid | dashed | dotted | none |
no | dashed |
How the outline is drawn. dashed by default because a zone is a convention rather than a cable, and a solid box reads as a real container. |
— |
padding |
number, 0.0–400.0 | no | 16.0 |
Space in points between the hull of the members and the box drawn round them. Ignored when geometry gives the rectangle outright. |
— |
membersandselectorbox wherever the elements were drawn, so the zone follows them;geometryboxes a region of the canvas instead, for a zone that is about the paper rather than about devices.- An area matching nothing is
NV-G004, a warning: an empty box on a diagram reads as a claim that the zone is empty.
spec.selector
Which elements an area contains, said as a query rather than a list — the form that does not go stale when a rack gains a switch.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
namespace |
string | no | unset | A namespace prefix: sites/hq matches sites/hq and everything under it. At least one clause is required — an empty selector would box the whole inventory. |
— |
labels |
map string → string | no | {} |
Every one of these labels must be present with this value. Combined with the other clauses by and, never by or. | — |
kinds |
string list | no | () |
Element kinds, for a zone that is about a class of thing rather than a place. | — |
- Every clause given must match. A selector with no clause at all is refused: it would silently box the whole inventory.
spec of a legend document
A key: what the colours and the line styles of this drawing mean. Positioned by corner rather than by coordinate, because a key belongs at the edge of the paper and should stay there when the diagram is laid out again.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
views |
string list | no | () |
Which drawings the key appears in, by layer name. Empty means every one of them. | — |
color |
string | no | unset | Background of the key box, #rgb or #rrggbb. |
— |
title |
string | no | unset | Heading of the key. Absent draws the swatches on their own. | — |
corner |
top-left | top-right | bottom-left | bottom-right |
no | bottom-right |
Which corner of the drawing the key sits in. A corner rather than a coordinate, so it stays at the edge of the paper when the diagram is laid out again. | — |
auto |
layers |
no | unset | layers builds the entries from what the view actually drew — the node kinds and link media present — which is the only form of key that cannot go stale. Exclusive with entries. |
— |
entries |
LegendEntry list, ≤ 64 entries | no | () |
The rows, written out. Required unless auto derives them; a key nobody can read is not a key, so there is a ceiling on how many there may be. |
— |
auto: layersbuilds the entries from what the view actually drew — the node kinds present, the media of the links present — which is the only form of key that cannot disagree with the picture. It excludesentries, and one of the two is required.
spec.entries[]
One row of the key: a swatch, and what it means.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
label |
string, 1–200 characters | yes | — | What this swatch means, in the reader's words. | — |
color |
string | no | unset | Colour of the swatch. Absent takes the renderer's colour for whatever the row is about. | — |
shape |
box | line | dashed | dotted | ellipse |
no | box |
What the swatch is drawn as. A line style says the row is about links; a box says it is about nodes. | — |
description |
string | no | unset | A second line, for the row that needs one. | — |
spec.style
How one element is drawn. Optional on every drawable kind and on cables and tunnels; every field is optional in turn, and an absent one inherits from the theme, then the icon set, then the built-in palette.
| Field | Type | Required | Default | Description | YANG |
|---|---|---|---|---|---|
fill |
string | no | unset | Interior colour: a named colour or #rrggbb. none draws an unfilled shape. |
— |
stroke |
string | no | unset | Outline colour, and — on a cable or a tunnel — the colour of the line itself. | — |
strokeWidth |
number, > 0, ≤ 20.0 | no | unset | Outline width in points, greater than 0 and at most 20. | — |
dash |
string | no | unset | Line pattern: solid, dashed, dotted or bold. bold is a width rather than a pattern, spelled as Graphviz spells it because the built-in palette already is. |
— |
fontColor |
string | no | unset | Label colour. | — |
fontSize |
integer, 6–96 | no | unset | Label size in points, between 6 and 96. | — |
shape |
string | no | unset | The glyph the node is drawn as. Ignored on a cable or a tunnel, which has no shape. | — |
icon |
string | no | unset | Picture to draw this one element as, overriding what the --icons theme picks for its kind. A bare name resolved inside the theme directory; none draws the plain shape. |
— |
opacity |
number, 0.0–1.0 | no | unset | How opaque the element is drawn, from 0 (invisible) to 1. | — |
- The vocabulary is closed. A colour is a hex literal or one of the named colours, and every other field is a small enum or a bounded number, because these values end up inside Graphviz attributes and mxGraph style strings and a free-form pass-through would be an injection (
NV-Z001). shapeis ignored on a cable and a tunnel, which have no shape to set.iconnames a picture inside the--iconstheme and is ignored when no theme is in use;icon: nonedraws this one element as a plain shape.
Enumerations
interfaces[].type
Only ethernet, wifi and lag can terminate a cable (NV-C009).
| Value | if:type identity |
Cableable |
|---|---|---|
ethernet |
ianaift:ethernetCsmacd |
yes |
wifi |
ianaift:ieee80211 |
yes |
loopback |
ianaift:softwareLoopback |
no |
bridge |
ianaift:bridge |
no |
vlan |
ianaift:l2vlan |
no |
lag |
ianaift:ieee8023adLag |
yes |
tunnel |
ianaift:tunnel |
no |
vlan.mode
A netviz abstraction; 802.1Q has no equivalent leaf.
| Value |
|---|
access |
trunk |
vlan.acceptable_frames
The values are the 802.1Q identity names, unabbreviated.
| Value |
|---|
admit-all-frames |
admit-only-VLAN-tagged-frames |
admit-only-untagged-and-priority-tagged |
bridge.type
Decides the dot1q:port-type of every port on the device.
| Value |
|---|
customer-vlan-bridge |
provider-bridge |
provider-edge-bridge |
two-port-mac-relay-bridge |
mac-bridge |
cable.medium
wireless constrains the endpoint interface types.
| Value |
|---|
copper |
fiber |
wireless |
cable.duplex
| Value |
|---|
full |
half |
upstream.type
Only usb and usb-c have an IANA interface-type identity.
| Value |
|---|
usb |
usb-c |
thunderbolt |
pcie |
m2 |
sfp |
internal |
tunnel.type
Each type fixes the layer carried, the outer transport and port, whether the payload is encrypted, and the encapsulation overhead. See §14.1 of the schema for the table.
| Value |
|---|
wireguard |
ipsec |
openvpn |
pptp |
l2tp |
gre |
vxlan |
geneve |
tunnel outer transport
Derived from type; gre and esp run directly over IP and carry no port.
| Value |
|---|
udp |
tcp |
gre |
esp |
tunnel.mode
IPsec only; every other type has a single mode.
| Value |
|---|
tunnel |
transport |
firewall.rules[].action
accept, drop and reject decide the packet and end the walk; mark and log do something to it and carry on to the next rule.
| Value |
|---|
accept |
drop |
reject |
mark |
log |
firewall.rules[].protocol
Only tcp, udp and sctp have ports to select on. icmp is IPv4 and icmpv6 is IPv6, so stating either against the other family is refused (NV-B005).
| Value |
|---|
tcp |
udp |
icmp |
icmpv6 |
sctp |
esp |
ah |
gre |
firewall.rules[].ct_state
Connection-tracking states, matched as a set. One rule accepting established and related replaces the return path of every other rule in the file.
| Value |
|---|
new |
established |
related |
invalid |
firewall.nat[].type
snat and masquerade rewrite the source on the way out; dnat and redirect rewrite the destination on the way in.
| Value |
|---|
snat |
masquerade |
dnat |
redirect |
firewall hook
Never written in a document: derived from src_zone and dst_zone, and named here because the three defaults of spec.firewall are one per hook.
| Value |
|---|
input |
forward |
output |
poe.standard
Which IEEE 802.3 amendment the port implements, and therefore which classes exist: 802.3af stops at class 3, 802.3at adds 4, 802.3bt adds 5 to 8.
| Value |
|---|
802.3af |
802.3at |
802.3bt |
power.powered_by
outlet is the default. poe says the device takes power over its uplink and has no cord, so it declares no inputs.
| Value |
|---|
outlet |
poe |
tunnel.auth
The authentication method. netviz never stores key material (NV-T010).
| Value |
|---|
psk |
certificate |
public-key |
password |
user.type
Decides which identity rules apply: only a person can depart (NV-S015), and only a person is expected to be in a group (NV-S016).
| Value |
|---|
person |
service |
shared |
user.status
departed is kept rather than deleted, so the memberships still to be revoked stay visible.
| Value |
|---|
active |
suspended |
departed |
Scalar formats
Values that are normalised on load: what you write and what
netviz show prints back may differ.
| Type | Accepted | Stored as |
|---|---|---|
| Element name | ^[A-Za-z0-9]+(?:[-_.][A-Za-z0-9]+)*$, 1–253 characters |
unchanged |
| Interface name | ^[A-Za-z0-9._/-]+$, 1–64 characters |
unchanged |
| MAC address | 00:1e:8c:00:10:01, 00-1E-8C-00-10-01, 001e.8c00.1001 |
lower-case colon form |
| Bit rate | an integer of bit/s, or <number><unit> with unit bps, kbps, Mbps, Gbps, Tbps |
integer bit/s |
| IPv4 address entry | 10.0.0.1/24, or a mapping with prefix_length or netmask |
{ip, prefix_length} |
| IPv6 address entry | 2001:db8::1/64, or a mapping with prefix_length |
RFC 5952 compressed {ip, prefix_length} |
| VLAN set | 10, [10, 20], "10,20,100-110", all, none |
sorted, coalesced "10,20,100-110" |
| Boolean | true / false only |
unchanged |
Booleans are strict on purpose: a quoted "true" or a YAML 1.1 yes is an error,
not a silently accepted truth value. A MAC address written unquoted can be parsed by
YAML as a sexagesimal integer, which loses the original digits — netviz detects the
case and tells you to quote it.