Aller au contenu principal

Creating Enriched Documentation

Every node in the model can have a description attribute containing documentation as detailed as you wish.

  • Short form: a single sentence that populates the description attribute of the OPC UA node in the address space.
  • Long form: a multi-line Markdown text. The first line populates the OPC UA description attribute; the rest is added to the auto-generated online documentation in the Markdown file produced by the generator.
Rich description on a method
objectTypes:
- browseName: TemperatureSensorType
methods:
- browseName: Calibrate
description: |
Initiate the calibration of the sensor. This line will go into the `description`
attribute of the OPCUA node.

The Calibrate method initiates the calibration of the **temperature sensor**
on the physical device. This method takes __two__ arguments that define
the linear interpolation `T = A*x + B`.

| key | value |
|-----|-------|
| A | B |
inputArguments:
- name: CoefficientA
dataType: ua:Double
description: Slope coefficient A for linear interpolation
- name: CoefficientB
dataType: ua:Double
description: Offset coefficient B for linear interpolation
outputArguments:
- name: PreviousA
dataType: ua:Double
- name: PreviousB
dataType: ua:Double

!include(path) — embedding external files

New in v3.41.0

For long documentation blocks, keep the content in a separate Markdown file and embed it using the !include(path) directive inside a description field:

!include directive
objectTypes:
- browseName: ReactorType
description: |
Main reactor vessel type.
!include(./docs/reactor-type.md)

The path is relative to the directory containing the .model.yaml file. The included file's content is inserted verbatim and header levels are automatically normalised so they fit correctly within the generated documentation hierarchy.

This is useful when:

  • A type has extensive operational documentation that would clutter the YAML file
  • The same documentation block is shared across multiple types
  • Technical writers maintain Markdown files separately from the model authors

Recommended project layout:

your-project/
├── model.yaml
└── docs/
├── reactor-type.md
└── safety-notes.md
Multiple !include directives
objectTypes:
- browseName: SafetyControllerType
description: |
Safety controller.
!include(./docs/safety-notes.md)
📄 Full working example — enriching-documentation.model.yaml
enriching-documentation.model.yaml
# yaml-language-server: $schema=../../../../schemas/nodeset2.schema.json
#
# Living documentation example for: s99_enriching-documentation.md
# Validate: opcua-modeler generate --input enriching-documentation.model.yaml

namespaceUri: http://example.com/doc/enriching-documentation/
version: 1.0.0

objectTypes:
- browseName: TemperatureSensorType
methods:
- browseName: Calibrate
description: |
Initiate the calibration of the sensor. This line will go into the `description`
attribute of the OPCUA node.

The Calibrate method initiates the calibration of the **temperature sensor**
on the physical device. This method takes __two__ arguments that define
the linear interpolation `T = A*x + B`.

| key | value |
|-----|-------|
| A | B |
inputArguments:
- name: CoefficientA
dataType: ua:Double
description: Slope coefficient A for linear interpolation
- name: CoefficientB
dataType: ua:Double
description: Offset coefficient B for linear interpolation
outputArguments:
- name: PreviousA
dataType: ua:Double
- name: PreviousB
dataType: ua:Double

- browseName: ReactorType
description: |
Main reactor vessel type.
!include(./docs/reactor-type.md)

- browseName: SafetyControllerType
description: |
Safety controller.
!include(./docs/safety-notes.md)
📄 Generated NodeSet2.xml — enriching-documentation.model.Nodeset2.xml
enriching-documentation.model.Nodeset2.xml
<?xml version="1.0"?>
<UANodeSet xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:uax="http://opcfoundation.org/UA/2008/02/Types.xsd" xmlns="http://opcfoundation.org/UA/2011/03/UANodeSet.xsd" xmlns:ns1="http://example.com/doc/enriching-documentation/Type.xsd">
<NamespaceUris>
<Uri>http://example.com/doc/enriching-documentation/</Uri>
</NamespaceUris>
<Models>
<Model ModelUri="http://example.com/doc/enriching-documentation/" Version="1.0.0" PublicationDate="2026-06-02T17:00:00.000Z">
<RequiredModel ModelUri="http://opcfoundation.org/UA/" Version="1.05.06" PublicationDate="2025-11-08T00:00:00.000Z"/>
</Model>
</Models>
<Aliases>
<Alias Alias="Argument">i=296</Alias>
<Alias Alias="HasComponent">i=47</Alias>
<Alias Alias="HasModellingRule">i=37</Alias>
<Alias Alias="HasProperty">i=46</Alias>
<Alias Alias="HasSubtype">i=45</Alias>
<Alias Alias="HasTypeDefinition">i=40</Alias>
</Aliases>
<!--ReferenceTypes-->
<!--ObjectTypes-->
<!--ObjectType - 1:TemperatureSensorType {{{{ -->
<UAObjectType NodeId="ns=1;i=1000" BrowseName="1:TemperatureSensorType">
<DisplayName>TemperatureSensorType</DisplayName>
<References>
<Reference ReferenceType="HasSubtype" IsForward="false">i=58</Reference>
<Reference ReferenceType="HasComponent">ns=1;i=1001</Reference>
</References>
</UAObjectType>
<UAMethod NodeId="ns=1;i=1001" BrowseName="1:Calibrate" ParentNodeId="ns=1;i=1000">
<DisplayName>Calibrate</DisplayName>
<Description>Initiate the calibration of the sensor. This line will go into the `description`</Description>
<References>
<Reference ReferenceType="HasModellingRule">i=78</Reference>
<Reference ReferenceType="HasProperty">ns=1;i=1002</Reference>
<Reference ReferenceType="HasProperty">ns=1;i=1003</Reference>
</References>
</UAMethod>
<UAVariable NodeId="ns=1;i=1002" BrowseName="InputArguments" ParentNodeId="ns=1;i=1001" ValueRank="1" ArrayDimensions="2" DataType="Argument">
<DisplayName>InputArguments</DisplayName>
<Description>the definition of the input argument of method 1:TemperatureSensorType.1:Calibrate</Description>
<References>
<Reference ReferenceType="HasTypeDefinition">i=68</Reference>
<Reference ReferenceType="HasModellingRule">i=78</Reference>
</References>
<Value>
<ListOfExtensionObject xmlns="http://opcfoundation.org/UA/2008/02/Types.xsd">
<ExtensionObject>
<TypeId>
<Identifier>i=297</Identifier>
</TypeId>
<Body>
<Argument>
<Name>CoefficientA</Name>
<DataType>
<Identifier>i=11</Identifier>
</DataType>
<ValueRank>-1</ValueRank>
<ArrayDimensions/>
<Description>
<Text>Slope coefficient A for linear interpolation</Text>
</Description>
</Argument>
</Body>
</ExtensionObject>
<ExtensionObject>
<TypeId>
<Identifier>i=297</Identifier>
</TypeId>
<Body>
<Argument>
<Name>CoefficientB</Name>
<DataType>
<Identifier>i=11</Identifier>
</DataType>
<ValueRank>-1</ValueRank>
<ArrayDimensions/>
<Description>
<Text>Offset coefficient B for linear interpolation</Text>
</Description>
</Argument>
</Body>
</ExtensionObject>
</ListOfExtensionObject>
</Value>
</UAVariable>
<UAVariable NodeId="ns=1;i=1003" BrowseName="OutputArguments" ParentNodeId="ns=1;i=1001" ValueRank="1" ArrayDimensions="2" DataType="Argument">
<DisplayName>OutputArguments</DisplayName>
<Description>the definition of the output arguments of method 1:TemperatureSensorType.1:Calibrate</Description>
<References>
<Reference ReferenceType="HasTypeDefinition">i=68</Reference>
<Reference ReferenceType="HasModellingRule">i=78</Reference>
</References>
<Value>
<ListOfExtensionObject xmlns="http://opcfoundation.org/UA/2008/02/Types.xsd">
<ExtensionObject>
<TypeId>
<Identifier>i=297</Identifier>
</TypeId>
<Body>
<Argument>
<Name>PreviousA</Name>
<DataType>
<Identifier>i=11</Identifier>
</DataType>
<ValueRank>-1</ValueRank>
<ArrayDimensions/>
<Description>
<Text/>
</Description>
</Argument>
</Body>
</ExtensionObject>
<ExtensionObject>
<TypeId>
<Identifier>i=297</Identifier>
</TypeId>
<Body>
<Argument>
<Name>PreviousB</Name>
<DataType>
<Identifier>i=11</Identifier>
</DataType>
<ValueRank>-1</ValueRank>
<ArrayDimensions/>
<Description>
<Text/>
</Description>
</Argument>
</Body>
</ExtensionObject>
</ListOfExtensionObject>
</Value>
</UAVariable>
<!--ObjectType - 1:TemperatureSensorType }}}}-->
<!--ObjectType - 1:ReactorType {{{{ -->
<UAObjectType NodeId="ns=1;i=1004" BrowseName="1:ReactorType">
<DisplayName>ReactorType</DisplayName>
<Description>Main reactor vessel type.</Description>
<References>
<Reference ReferenceType="HasSubtype" IsForward="false">i=58</Reference>
</References>
</UAObjectType>
<!--ObjectType - 1:ReactorType }}}}-->
<!--ObjectType - 1:SafetyControllerType {{{{ -->
<UAObjectType NodeId="ns=1;i=1005" BrowseName="1:SafetyControllerType">
<DisplayName>SafetyControllerType</DisplayName>
<Description>Safety controller.</Description>
<References>
<Reference ReferenceType="HasSubtype" IsForward="false">i=58</Reference>
</References>
</UAObjectType>
<!--ObjectType - 1:SafetyControllerType }}}}-->
<!--VariableTypes-->
<!--Other Nodes-->
</UANodeSet>