Update Invalid Data of Tag in AVEVA PI Data Archive
This example shows you how to manage invalid data present in a tag in the AVEVA® PI Data Archive by updating data with the correct values from the OPC UA server.
For this example, consider any data with status bad
as invalid. You fetch the correct data for the invalid data instances from the backup data stored in an OPC UA server. You then write the correct values in the AVEVA PI Data Archive at the required time instances.
The write capability of Industrial Communication Toolbox™ for PI provides a variety of options and flexible ways to update data to an existing tag in PI Data Archive. Running this example assumes a PI Data Archive is available for connection and Prosys OPC UA Simulation Server is installed and running. The demo tags used in this example were provided by AVEVA and can be downloaded from AVEVA sharefile.
Create Client/Server Connection and Retrieve Required Tags
Connect to the PI Data Archive using the piclient
function. This example uses the name of the Windows® computer name as the PI Data Archive name, which might vary depending on the PI System configuration.
host = getenv("COMPUTERNAME");
client = piclient(host);
Find a list of tag names that start with "Flynn I
" using the tags
function. For more information, see Get Started Accessing a PI Data Archive.
tagsFlynnI = tags(client, Name="Flynn I.*")
tagsFlynnI=3×1 table
Tags
______________________________________________________________________________
"Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f"
"Flynn I.Hydro Unit Attention Percentage.fb72102e-7bae-5b4d-0c63-1a95b1062dab"
"Flynn I.Hydro Unit Condition.eabe7033-cd1c-5fe8-36cc-3d172e7ca0dd"
Read Value of Tag
Read the data recorded in a tag using the read
function. To read data of a tag over a period of time, first define the period. For example, to read the data from 09-Dec-2023 in UTC timezone, use the DateRange
name-value argument to specify a starting datetime
and ending datetime
.
startDate=datetime("09-12-2023", InputFormat="dd-MM-uuuu", TimeZone="UTC"); endDate = startDate + days(1); activePowerGenFlynnI = read(client, tagsFlynnI.Tags(1), DateRange=[startDate endDate])
activePowerGenFlynnI=8×3 timetable
Time Tag Value Status
________________________ _____________________________________________________________________ ______ ______
09-Dec-2023 04:40:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" NaN Bad
09-Dec-2023 05:35:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" NaN Bad
09-Dec-2023 06:09:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" NaN Bad
09-Dec-2023 13:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 95.14 Good
09-Dec-2023 14:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 96.22 Good
09-Dec-2023 15:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 98.236 Good
09-Dec-2023 16:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 99.11 Good
09-Dec-2023 17:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 95.3 Good
In this example, the data in rows 1, 2 and 3 is considered as invalid because of the Bad
status.
Retrieve Correct Value from OPC UA Server
Create a client object using the endpoint URL of the OPC UA server that you are connecting to and the opcua
function. Connect the client to the server using the connect
function. For more information, see Access Data from OPC UA Servers.
uaClient = opcua("opc.tcp://BGL-SSAHA.dhcp.mathworks.com:53530/OPCUA/SimulationServer");
connect(uaClient);
Get the handle to the node containing the backup data using the findNodeById
function.
nodeOfInterest = findNodeById(uaClient.Namespace, 3, 1005);
Retrieve the time instances where invalid data is present in the PI tag.
invalidDataTimestamp = activePowerGenFlynnI.Time(activePowerGenFlynnI.Status == "Bad")
invalidDataTimestamp = 3×1 datetime
09-Dec-2023 04:40:00 UTC
09-Dec-2023 05:35:00 UTC
09-Dec-2023 06:09:00 UTC
Retrieve the values of the node at the specific time instances from the OPC UA server using the readAtTime
function.
correctValue = readAtTime(uaClient, nodeOfInterest, invalidDataTimestamp)
correctValue = 1-by-1 OPC UA Data object array: Timestamp Sinusoid ----------------------- -------------------------- 2023-12-09 10:10:00.000 88.535900 [Good (Raw)] 2023-12-09 11:05:00.000 90.000000 [Good (Raw)] 2023-12-09 11:39:00.000 95.236070 [Good (Raw)]
Update Invalid Value of Tag
Update the invalid data using the write
function. You can overwrite the invalid data with correct data by setting the Overwrite
name-value argument to true
. You can write data to a tag at a specific timestamp by setting the TimeInstance
name-value argument to the required datetime
.
write(client, tagsFlynnI.Tags(1), correctValue.Value, TimeInstance=invalidDataTimestamp, Overwrite=true)
Verify updated values by waiting for one second before using the read
function.
pause(1); activePowerGenFlynnI = read(client, tagsFlynnI.Tags(1), DateRange=[startDate endDate])
activePowerGenFlynnI=8×3 timetable
Time Tag Value Status
________________________ _____________________________________________________________________ ______ ______
09-Dec-2023 04:40:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 88.536 Good
09-Dec-2023 05:35:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 90 Good
09-Dec-2023 06:09:00 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 95.236 Good
09-Dec-2023 13:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 95.14 Good
09-Dec-2023 14:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 96.22 Good
09-Dec-2023 15:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 98.236 Good
09-Dec-2023 16:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 99.11 Good
09-Dec-2023 17:23:22 UTC "Flynn I.Active Power Generated.4780df36-9354-5eda-28b0-f7a67582c48f" 95.3 Good
You can see that the invalid data in rows 1, 2, and 3 is replaced with the correct data from the OPC UA server.