====Write Values to an Modbus/TCP Slave Device==== ===Description=== This script sets a value inside a Modbus/TCP slave device. This is used if you want to link the form system back into your control or information systems to advise that that a job - such as an isolation - has been completed. In turn, you could use this to indicate isolation in SCADA, route around the isolated equipment in your plant logic, or simply keep a history of events in your historian product without having to add additional data sources. In the example below, the target Modbus address to be set is a //property of the asset//. We read the target address from the ARDI API before we set it. We also set a fixed value (in this case, **1**) to the address. Alternatively, you could set timestamps, strings etc. ===Full Script=== import requests import pymodbus from datetime import datetime import os import sys import traceback import warnings from pymodbus.client.sync import ModbusTcpClient #Set default details #The ARDI server to query server="localhost/s/bm" #The ARDI property containing the Modbus address mbaddressid=47 #Modbus connection details ipaddress="localhost" unit=1 port=502 register=0 offset=0 #The value to write valuetoset=1 asset = "Unknown Asset" checklist = "Unknown Checklist" user = "Unknown User" assetid = "1" tm = datetime.now().strftime("%Y/%m/%d %H:%M:%S") #Get submission details from environment variables try: asset = os.environ["assetname"] except: print "No Asset Provided" sys.exit(0) try: assetid = os.environ["assetid"] except: print "No Asset ID Provided" sys.exit(0) try: checklist = os.environ["checklist"] except: print "No Checklist Provided" sys.exit(0) try: user = os.environ["user"] except: print "No User Provided" sys.exit(0) def Sub(st,ass,chk,usr,dt): return st.replace("{checklist}",chk).replace("{asset}",ass).replace("{user}",usr).replace("{date}",dt) #Get isolation modbus address from server (assumes a Guest Mode server, otherwise we need to authenticate!) url = "http://" + server + "/api/asset/property?id=" + str(assetid) + "&property=" + str(mbaddressid) resp = requests.get(url) data = resp.content #Read the address from ARDI ind = data.find("") if ind > 0: indx = data.find("") totaloffset = ind + 6 value = data[totaloffset:indx] #Adjust the value based on the type of I/O point we are talking about. if len(value) > 3: if value[0] == '1': register = 1 offset = 1000 if len(value) > 4: offset = 10000 if value[0] == '3': register = 3 offset = 3000 if len(value) > 4: offset = 30000 if value[0] == '4': register = 4 offset = 4000 if len(value) > 4: offset = 40000 #Connect to modbus device client=ModbusTcpClient(ipaddress,port=port) client.connect() address = int(value)-offset #Write data at correct location... if register == 3: client.write_input_register(address,int(valuetoset),unit=unit) if register == 4: client.write_register(address,int(valuetoset),unit=unit) if register == 1: if valuetoset == 1: valuetoset = True else: valuetoset = False client.write_discrete_input(address,valuetoset,unit=unit) if register == 0: if valuetoset == 1: valuetoset = True else: valuetoset = False client.write_coil(address,valuetoset,unit=unit) #If everything worked out, send the word 'OK'. print 'OK'