VTScada Agent MIB Representation and Manipulation
Prior to version 12.1, the internal MIB configuration of tags was persisted in an XML file. This proved to require heavy processing for large MIBs.
It is now persisted within a valid JSON file containing an array of JSON objects, where each tag is represented by a single JSON string (or object). The JSON file is processed one line (object) at a time and is not loaded in its entirety. JSON formatting tools may be used to verify the validity of the data in the file.
The file may be modified as explained in the following notes, so long as the format of the file respects three rules:
-
The first line is always (and only) an opening square bracket: [
-
The last line is always (and only) a closing square bracket: ]
-
Between the first and last lines, each JSON object representing a tag must be on a single line.
The file is processed line by line, assuming that a JSON object occupies a single line.
Backward compatibility support:
If an XML configuration file exists when an application is launched, that file is read, an internal configuration is generated, and then immediately written to a JSON configuration file. Following this, the XML file is deleted. If the XML file causes any error reports at loading, no internal configuration is generated, no JSON file is generated, and the XML file is not deleted.
Problems in the XML file must be fixed and the application restarted (or the agent disabled then enabled). Note that extremely large XML files may cause a freeze or crash. These must be deleted and a new JSON file created by triggering the generation of a new MIB.
Manipulation of the MIB:
MIB files are generated and persisted as a JSON file for all OPC-enabled tags. For each tag, the properties to be exposed via SNMP are set via the application configuration property, SNMPAgentTagExposedProperties.
It is possible to manipulate the MIB manually by editing the JSON file and the generated MIB file in parallel (Both must be edited simultaneously so that the change in the MIB file is reflected in the internal MIB.)
For example assume you have three I/O tags (IO1, IO2, IO3). Assume also that you set "SNMPAgentTagExposedProperties" to the CSV template: "name,value,timestamp". This means that you want to expose only name, value, and timestamp via the SNMPAgent. After pressing the button, Generate New MIB you will get the following:
[ {"id":"io1","TagName":"IO1","SubId":1,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io1Name"},{"field":"value","id":"io1Value"},{"field":"timestamp","id":"io1Timestamp"}]}, {"id":"io2","TagName":"IO2","SubId":2,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io2Name"},{"field":"value","id":"io2Value"},{"field":"timestamp","id":"io2Timestamp"}]}, {"id":"io3","TagName":"IO3","SubId":3,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io3Name"},{"field":"value","id":"io3Value"},{"field":"timestamp","id":"io3Timestamp"}]} ]
The main part of the MIB related to the tags will look like the following:
-- Application tags appTags OBJECT IDENTIFIER ::= { vtscada 3 } io1 OBJECT IDENTIFIER ::= { appTags 1 } io1Name OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Name of the tag for discovery" ::= { io1 1 } io1Value OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Value of the tag if quality is good" ::= { io1 2 } io1Timestamp OBJECT-TYPE SYNTAX Unsigned32 MAX-ACCESS read-only STATUS current DESCRIPTION "UTC timestamp associated with the tag value (POSIX time)" ::= { io1 4 } io2 OBJECT IDENTIFIER ::= { appTags 2 } io2Name OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Name of the tag for discovery" ::= { io2 1 } io2Value OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Value of the tag if quality is good" ::= { io2 2 } io2Timestamp OBJECT-TYPE SYNTAX Unsigned32 MAX-ACCESS read-only STATUS current DESCRIPTION "UTC timestamp associated with the tag value (POSIX time)" ::= { io2 4 } io3 OBJECT IDENTIFIER ::= { appTags 3 } io3Name OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Name of the tag for discovery" ::= { io3 1 } io3Value OBJECT-TYPE SYNTAX DisplayString MAX-ACCESS read-only STATUS current DESCRIPTION "Value of the tag if quality is good" ::= { io3 2 } io3Timestamp OBJECT-TYPE SYNTAX Unsigned32 MAX-ACCESS read-only STATUS current DESCRIPTION "UTC timestamp associated with the tag value (POSIX time)" ::= { io3 4 } END
Suppose that you decide not to expose the timestamp for IO1. Then you can make the following edit:
-
In the MIB file remove the following OBJECT-TYPE definition:
io1Timestamp OBJECT-TYPE SYNTAX Unsigned32 MAX-ACCESS read-only STATUS current DESCRIPTION "UTC timestamp associated with the tag value (POSIX time)" ::= { io1 4 }
-
In the file, SNMPAgentConfig.JSON, remove the timestamp member for IO1
Do so by removing: {"field":"timestamp","id":"io1Timestamp"}. The JSON file would look like the following:
[ {"id":"io1","TagName":"IO1","SubId":1,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io1Name"},{"field":"value","id":"io1Value"}]}, {"id":"io2","TagName":"IO2","SubId":2,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io2Name"},{"field":"value","id":"io2Value"},{"field":"timestamp","id":"io2Timestamp"}]}, {"id":"io3","TagName":"IO3","SubId":3,"DataType":"DisplayString","Access":"read-only","TagFields":[{"field":"name","id":"io3Name"},{"field":"value","id":"io3Value"},{"field":"timestamp","id":"io3Timestamp"}]} ]
Note that step 2 is mandatory in order for IO1's timestamp to be removed from the internal MIB.
-
Import file changes for the app.
The internal MIB would look like this in the Source Debugger, notice how there is no more entry for the IO1 timestamp. So now a read for the object a OID 1.3.6.1.4.1.42905.1.3.1.4.0 will fail.
Cautions:
-
If the XML contains an error, it must be fixed or no MIB will exist in the app.
-
If an application configuration is changed (for example I/O tags added or removed) and a Generate New MIB is triggered, there is no guarantee that the I/Os will preserve the same OIDs.