# Gateway Script executing on tag value change

**URL:** <https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001>\
**Category:** Ignition\
**Tags:** ignition81, perspective\
**Created:** [July 6, 2023, 2:52pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001 "2023-07-06T14:52:08Z")\
**Posts on this page:** 19\
**Page:** 1

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 2:52pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/1 "2023-07-06T14:52:08Z")

</div>

Good day, I am trying to get a gateway script to execute via tag value change. I can get it to run when I use a boolean, but I need a memory tag that contains text to execute it. The tag gets changed when my RFID antenna reads the RFID tag.

Here is what I have so far, can anyone help me troubleshoot this?

 ![image](https://us1.discourse-cdn.com/inductiveautomation/original/3X/2/b/2b4d9990cb430b9ed958354c55e489f846dac591.png)

Now heres the script:

```auto
import datetime
python_time = datetime.datetime.now()
sql_datetime = python_time.strftime('%Y-%m-%d %H:%M:%S')
#START of data parse for WS to YSF for ticket number
if system.tag.readBlocking("[default]RFID/Waste Scale/Green Light")[0].value == True:
	TID = system.tag.readBlocking("[default]RFID/Waste Scale/TagID")[0].value #'A2163400' test tag number

	dataset = system.db.runPrepQuery("SELECT TOP 1 * FROM WasteBarrelStatus WHERE TID = ? ORDER BY TIME DESC", [TID], 'IgnitionHud')

	Time = sql_datetime #Time weight was recorded into table
	Status = dataset[0][8]
	MachineNum = dataset[0][6]
	FinishLot = 'O5177I22' #dataset[0][4] test lot
	Dept = dataset[0][5]
	BarrelType = dataset[0][7]
	PosNum = dataset[0][3]
	TID = dataset[0][0]
	BarrelNum = dataset[0][1]
	ComponentNum = dataset[0][10]
	Denier = dataset[0][11]
	GrossWeight = int(system.tag.readBlocking("[default]RFID/Waste Scale/Scale Weight Lbs")[0].value) #200

#END of data parse for WS to YSF for ticket number
	
#START of WS to YSF for ticket number

	if Status == 'newFill':
		system.tag.writeBlocking("[default]RFID/Waste Scale/Red Light", 0)
	wsdata = system.ws.runWebService("YSF/RecordInProcessQA",
	None,
	{
	  'recordInProcessDetailRequest': {
	    'userName': "IGNITION",
	    'department': Dept,             
	# x 'productionDate': "2023-05-23",
	# 'shift': "J", #Use Start or completion shift
			    'machine': MachineNum,
	# x 'employeeNumber': "",
	    'finishedLot': FinishLot,
	# x 'scheduledLot': "",
	# x 'component': "",
	    'reasonCode': "003", # Asp Waste Code = 003
	# x 'positionDesc': "",
	    'buggyType': BarrelType,
	# x 'buggyWeight': 0,
    	'cones': 0, # Leave as zero
    	'detailClass': "wast", # must be lower case
    	'grossWeight': GrossWeight,     
	# x 'netWeight': 0
  	}
	})

	Status = 'Weighed'
	TicketNum = wsdata.getChild(0).toDict()['recordInProcessDetailResponse']['ticketNumber']
#END of WS to YSF for ticket number
	system.db.runPrepUpdate("INSERT INTO WasteBarrelStatus (Time, Status, GrossWeight, MachineNum, FinishLot, Dept, BarrelType, PosNum, TID, BarrelNum, ComponentNum, Denier, TicketNum) Values(?,?,?,?,?,?,?,?,?,?,?,?,?)",[Time, Status, GrossWeight, MachineNum, FinishLot, Dept, BarrelType, PosNum, TID, BarrelNum, ComponentNum, Denier, TicketNum])

#	else:
# system.tag.writeBlocking("[default]RFID/Waste Scale/Red Light", 1)

```

As stated before I can get this to run either with a boolean driving it or executing in the script console, just not when the tag value changes.

---

<div class="post-metadata">

**Author:** ![paul-griffith](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/paul-griffith/32/37249_2.png) [@paul-griffith](https://forum.inductiveautomation.com/u/paul-griffith)\
**Post date:** [July 6, 2023, 3:09pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/2 "2023-07-06T15:09:52Z")

</div>

I'd start with the obvious thing, if the same script works in the script console:  
Decorate your code with logger statements so you can see where in the execution flow things are dropping out. Maybe a string comparison isn't what you expect (leading/trailing spaces? capitalization?) or a value isn't quite matching what you think it is. Initialize a logger at the top of the script with `logger = system.util.getLogger("myscriptdebug")` and then call into it with `logger.info("someString")`.

As a minor aside...

> [@mjohnson0238](#):
>
> ```auto
> import datetime
> python_time = datetime.datetime.now()
> sql_datetime = python_time.strftime('%Y-%m-%d %H:%M:%S')
> 
> ```

Prefer the `system.date` functions over Python's datetime for best interop with other Java parts, such as database insertions.  
And also

> [@mjohnson0238](#):
>
> ```auto
> if system.tag.readBlocking("[default]RFID/Waste Scale/Green Light")[0].value == True:
> TID = system.tag.readBlocking("[default]RFID/Waste Scale/TagID")[0].value #'A2163400' test tag number
> 
> ```

Prefer reading all the tags involved in an operation in one call to `system.tag.readBlocking()`. You're paying way, way more overhead for the serial calls than you are to read an "unnecessary" tag or two in the first read.

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 3:13pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/3 "2023-07-06T15:13:58Z")

</div>

when running the logger in script, I just watch the gateway logs and see what pops up, correct?

---

<div class="post-metadata">

**Author:** ![paul-griffith](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/paul-griffith/32/37249_2.png) [@paul-griffith](https://forum.inductiveautomation.com/u/paul-griffith)\
**Post date:** [July 6, 2023, 3:20pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/4 "2023-07-06T15:20:04Z")

</div>

Yep, when the script is running on the gateway, `system.util.logger` messages will show up directly in the gateway log UI + the wrapper log, if you prefer to watch that.

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 3:24pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/5 "2023-07-06T15:24:00Z")

</div>

I added logs to the code in several places, the logger returned this:

 ![image](https://us1.discourse-cdn.com/inductiveautomation/original/3X/a/f/af5be853dcddee1b3b838c678b4d7235303f9d20.png)

that logger is here:

```auto
logger = system.util.getLogger("RFIDscriptdebug")
import datetime
python_time = datetime.datetime.now()
sql_datetime = python_time.strftime('%Y-%m-%d %H:%M:%S')
#START of data parse for WS to YSF for ticket number
logger.info("RFID_debug_1")
if system.tag.readBlocking("[default]RFID/Waste Scale/Green Light")[0].value == True:

```

Does that mean Im not seeing that tag be true?

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 3:49pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/6 "2023-07-06T15:49:10Z")

</div>

Could it be that when my TagID value changes my GreenLight is still false? It changes to True a few seconds after to gather a stable weight signal. Thats why its not running through the script?

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [July 6, 2023, 3:51pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/7 "2023-07-06T15:51:44Z")

</div>

Quite possible. Even if they change together in the PLC, you can't be sure of the order they will be updated by the OPC subscription. When dealing with synchronization issues, the general solution is for everything except the trigger itself to be obtained with `system.opc.readValues()`, not any kind of tag read.

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 5:59pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/8 "2023-07-06T17:59:44Z")

</div>

It did seem to be a sync problem. I added a "while" loop until the GreenLight became true. After it became True the script ran like it should have.

I really appreciate you guys letting me bounce questions around.

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [July 6, 2023, 6:01pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/9 "2023-07-06T18:01:09Z")

</div>

> [@mjohnson0238](#):
>
> I added a "while" loop until the GreenLight became true

That's a huge no-no for tag events. You can lock up your gateway's tag system.

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 6:02pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/10 "2023-07-06T18:02:25Z")

</div>

How so? I dont wanna lock nothing up, lol

---

<div class="post-metadata">

**Author:** ![Kevin.Herron](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/kevin.herron/32/7259_2.png) [@Kevin.Herron](https://forum.inductiveautomation.com/u/Kevin.Herron)\
**Post date:** [July 6, 2023, 6:03pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/11 "2023-07-06T18:03:35Z")

</div>

This looks like a project tag change script, so while still not recommended, not as dangerous as doing it in a tag event script.

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [July 6, 2023, 6:03pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/12 "2023-07-06T18:03:52Z")

</div>

~~Tag events run on a small thread pool (three, by default). If you have three tag events running simultaneous, either spinning or sleeping, no other tag events will run at all.~~

_Not wrong, just not applicable._

Do note that if your green light tag never becomes true, you will be burning CPU indefinitely. If you were trying to monitor multiple tags with one script, the other tag changes would be blocked.

You should use `system.opc.readValues()`. Really. (This is basically what happens when you set a SQL Bridge transaction group to OPC Read mode. The trigger is still subscribed, but everything else gets a fresh read after the trigger.)

---

<div class="post-metadata">

**Author:** ![mjohnson0238](https://avatars.discourse-cdn.com/v4/letter/m/4bbf92/32.png) [@mjohnson0238](https://forum.inductiveautomation.com/u/mjohnson0238)\
**Post date:** [July 6, 2023, 8:43pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/13 "2023-07-06T20:43:35Z")

</div>

Thanks, I will make the appropriate changes.

---

<div class="post-metadata">

**Author:** ![William\_R](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/william_r/32/32710_2.png) [@William\_R](https://forum.inductiveautomation.com/u/William_R)\
**Post date:** [October 5, 2023, 9:23pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/14 "2023-10-05T21:23:16Z")

</div>

> Prefer reading all the tags involved in an operation in one call to `system.tag.readBlocking()` . You're paying way, way more overhead for the serial calls than you are to read an "unnecessary" tag or two in the first read.

Hi @paul-griffith , can you explain this a bit more? I do readBlocking instructions all the time to single tags. What do you mean reading all tags involved? If I have a Ignition UDT, you mean its better to read the whole UDT at once if I will be using multiple tags from it? If so, how then do you reference the elements in the Ignition UDT? TIA.

---

<div class="post-metadata">

**Author:** ![paul-griffith](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/paul-griffith/32/37249_2.png) [@paul-griffith](https://forum.inductiveautomation.com/u/paul-griffith)\
**Post date:** [October 5, 2023, 9:31pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/15 "2023-10-05T21:31:09Z")

</div>

_Within the context of a single script_, try to read all the individual tags you can in the largest "chunk" possible. That is, instead of running a loop from station 1 to 10, reading the motor speed of each station inside the loop and acting on it, read all 10 motor speeds in one operation and then loop over the resulting values.

**Ignition** UDTs are basically just folders of tags with some window dressing. They don't represent any optimization inside of Ignition with regard to bulk reading or anything; all the tags inside a UDT are (basically) exactly the same as independent Ignition tags.

---

<div class="post-metadata">

**Author:** ![William\_R](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/william_r/32/32710_2.png) [@William\_R](https://forum.inductiveautomation.com/u/William_R)\
**Post date:** [October 6, 2023, 2:03pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/16 "2023-10-06T14:03:09Z")

</div>

Hi @paul-griffith thanks for the response. Just to make sure I am tracking with you, when you say to read the largest chunk possible, do you mean something like below (if not what is a better way to read "chunks":

 ![image](https://us1.discourse-cdn.com/inductiveautomation/original/3X/1/3/13c129508287666b14ed606ed1b9eaf1381b5dea.png)

---

<div class="post-metadata">

**Author:** ![Transistor](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/transistor/32/3380_2.png) [@Transistor](https://forum.inductiveautomation.com/u/Transistor)\
**Post date:** [October 6, 2023, 2:09pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/17 "2023-10-06T14:09:23Z")

</div>

> [@William\_R](#):
>
> ... do you mean something like below ...

Yes, that's the way.

---

<div class="post-metadata">

**Author:** ![paul-griffith](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/paul-griffith/32/37249_2.png) [@paul-griffith](https://forum.inductiveautomation.com/u/paul-griffith)\
**Post date:** [October 6, 2023, 3:06pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/18 "2023-10-06T15:06:12Z")

</div>

Although I'll add that that particular example is needlessly verbose. I think I've had this discussion with the training department before and lost, but basically `for index in range(len(something))` is almost never needed in Python; instead you should just iterate over the sequence object directly:

```python
values = system.tag.readBlocking(paths)
for value in values:
    print value

```

---

<div class="post-metadata">

**Author:** ![pturmel](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pturmel/32/3295_2.png) [@pturmel](https://forum.inductiveautomation.com/u/pturmel)\
**Post date:** [October 6, 2023, 3:18pm UTC](https://forum.inductiveautomation.com/t/gateway-script-executing-on-tag-value-change/76001/19 "2023-10-06T15:18:14Z")

</div>

Also, when there aren't too many `values`, I typically assign to reasonable local variable names (called "unpacking" in python). Like so:

```auto
....
alm1, alm2, alm3 = [x.value for x in values]

print alm1
print alm2
print alm3

```
