# Using variable with custom property in expression

**URL:** <https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936>\
**Category:** Ignition\
**Created:** [January 8, 2024, 6:42pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936 "2024-01-08T18:42:56Z")\
**Posts on this page:** 17\
**Page:** 1

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 6:42pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/1 "2024-01-08T18:42:56Z")

</div>

learning more about expressions; can someone explain why this doesn't work? i have used the same variable construction elsewhere in a script and it chooched just fine. it just isn't as an expression.

```python
if ("{Assets/"+{session.custom.assetName}+"/ONLINE}", \
    "Assets/"+{session.custom.assetName}+"/Voltage".value/100, \
    0)

```

i just get an `Error_Configuration` error. which does not surprise me, i am a n00b.

EDIT: just tweaked to more accurately reflect what i'm trying to do so i get a better response. 🙂

---

<div class="post-metadata">

**Author:** ![pascal.fragnoud](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pascal.fragnoud/32/24728_2.png) [@pascal.fragnoud](https://forum.inductiveautomation.com/u/pascal.fragnoud)\
**Post date:** [January 8, 2024, 6:50pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/2 "2024-01-08T18:50:44Z")

</div>

You can't reference tags or properties like this. If you need to build their path dynamically, you'll need to use the `tag` and `property` functions. Or work around it using temporary properties and such.

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 6:52pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/3 "2024-01-08T18:52:41Z")

</div>

well that sucks. 😛 expressions evaluate faster, so i was trying to use those instead. but i can go back to just binding to a transformed a tag i guess.

---

<div class="post-metadata">

**Author:** ![pascal.fragnoud](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/pascal.fragnoud/32/24728_2.png) [@pascal.fragnoud](https://forum.inductiveautomation.com/u/pascal.fragnoud)\
**Post date:** [January 8, 2024, 6:53pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/4 "2024-01-08T18:53:49Z")

</div>

`tag` and `property` are expression functions.

---

<div class="post-metadata">

**Author:** ![lrose](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/lrose/32/62724_2.png) [@lrose](https://forum.inductiveautomation.com/u/lrose)\
**Post date:** [January 8, 2024, 6:55pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/5 "2024-01-08T18:55:03Z")

</div>

Nested tag references are not allowed in expressions.

You could use the `tag()` expression in this case, but I would avoid that.

Instead create two custom properties bound with an indirect tag binding. Then use those properties in your expression.

```auto
if({asset_online_prop},{voltage_prop}/100, 0)

```

Also, the expression language for the most part ignores white space so the `\` isn't needed if you have that in you actual expression.

---

<div class="post-metadata">

**Author:** ![lrose](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/lrose/32/62724_2.png) [@lrose](https://forum.inductiveautomation.com/u/lrose)\
**Post date:** [January 8, 2024, 6:56pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/6 "2024-01-08T18:56:55Z")

</div>

> [@ian.sebryk](#):
>
> expressions evaluate faster

expressions evaluate faster than scripts, not necessarily bindings. Tag bindings are also pre-compiled, so are just as fast if not faster than expressions.

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 7:13pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/7 "2024-01-08T19:13:03Z")

</div>

um.... so if i want to work directly with tags in scripts, i _ **have** _ to first bind the tag property to a custom prop _and then_ reference _that_??

---

<div class="post-metadata">

**Author:** ![lrose](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/lrose/32/62724_2.png) [@lrose](https://forum.inductiveautomation.com/u/lrose)\
**Post date:** [January 8, 2024, 7:17pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/8 "2024-01-08T19:17:46Z")

</div>

Expressions are different from scripts.

If you want to work directly with tags in expressions, you _ **can** _ use the `tag()` expression. This allows you to provide a string as the path, and returns the value.

For best performance you _ **should** _ prefer indirect bindings over a `tag()` expression.

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 7:25pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/9 "2024-01-08T19:25:40Z")

</div>

> [@lrose](#):
>
> This allows you to provide a string as the path, and returns the value.

i'm not married to the expression idea, i was under the impression they were just faster. but since a tag-tranform-script is precompiled and just as fast: pfft. whatever i can get to work in a streamlined way gets the win. i just don't know how to access a tag's property directly from within a script. which i why i went with indirect expression. so... yeah. this is where i'm at right now.

```python
# indirect binding to Assets/{assetName}/ONLINE, a boolean flag
if value:
  newValue = Assets/{assetName}/superImportantValue + 20
  return newValue
else:
  return 0

```

you can see where i'm stuck. 😕

---

<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:** [January 8, 2024, 7:25pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/10 "2024-01-08T19:25:51Z")

</div>

> [@ian.sebryk](#):
>
> so if i want to work ~~directly~~ _ **efficiently** _ with tags in ~~scripts~~ **expressions** , i ~~have to~~ _ **should** _ first bind the tag property to a custom prop _and then_ reference _that_

As annotated, **yes**.

---

<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:** [January 8, 2024, 7:26pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/11 "2024-01-08T19:26:40Z")

</div>

> [@ian.sebryk](#):
>
> since a tag-tranform-script is precompiled and just as fast

Simply not true.

---

<div class="post-metadata">

**Author:** ![lrose](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/lrose/32/62724_2.png) [@lrose](https://forum.inductiveautomation.com/u/lrose)\
**Post date:** [January 8, 2024, 7:39pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/12 "2024-01-08T19:39:24Z")

</div>

> [@ian.sebryk](#):
>
> but since a tag-tranform-script is precompiled and just as fast: pfft

A transform on a binding is not pre-compiled.

> [@ian.sebryk](#):
>
> ```auto
> # indirect binding to Assets/{assetName}/ONLINE, a boolean flag
> if value:
> newValue = Assets/{assetName}/superImportantValue + 20
> return newValue
> else:
> return 0
> 
> ```
> 
> you can see where i'm stuck. 😕

No, I can't really. This script would not work, unless you're intending it as pseudo code.

To get the value of a tag in a script you must use a call to `system.tag.read*()`

In this case, I would create three custom properties:

- assetName
- onlineState
- voltage

I would create indirect tag bindings on the onlineState and voltage properties using the assetName property. That would look something like this:

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

Now you can reference those custom properties in an expression binding.

```auto
if({this.custom.onlineState},{this.custom.voltage}/100,0)

```

Note, that if this is going to be a popup, embedded view, or docked view where you want to send the asset name, you should make that a view parameter. The rest would still be applicable you would just need to change the paths to assetName.

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 7:52pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/13 "2024-01-08T19:52:30Z")

</div>

\*click|\* ooookay... lightbulbs are turning on! you guys are so helpful. thank you very much. 👍

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 7:57pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/14 "2024-01-08T19:57:13Z")

</div>

@pturmel this is where i got the notion that tag-trasform-script and expressions are they are equally speedy.

> [@lrose](#):
>
> Tag bindings are also pre-compiled, so are just as fast if not faster than expressions.

can you explain the difference for me? is @lrose just referring to the _property_ binding on a view/component and not the subsequent transformations?

---

<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:** [January 8, 2024, 8:37pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/15 "2024-01-08T20:37:23Z")

</div>

Bindings, throughout Ignition user interfaces, deliver values to session/view/window/page properties, custom or otherwise. All bindings are "set up" when a Perspective view or subview or Vision window or template is opened. The setup yields a java collection of objects tightly integrated with each other and with the target component. With the exception of any jython involved, everything is effectively pre-compiled during setup. Information flows from element to element in handsfuls of microseconds or less.

While some bindings are "once and done", like expression bindings that yield constants, or non-polling queries, most bindings are intended to monitor some source of data and deliver updates through the binding. When a source reports a change, the binding completely re-executes.

Transforms are a Perspective-only enhancement to bindings that create a chain of consecutive operations, with one result feeding the next, with the final operation's result providing the value for the target property. {Perspective desperately needed transforms because its complex components' architectures have a severe "impedance mismatch" with Ignition's internal object types, particularly dataset objects.} Transforms, for some unclear reason, introduce substantial overhead, on the order of high tens to low hundreds of microseconds.

Jython, meanwhile, whether invoked in a binding by `runScript()` or by a script transform, adds considerable additional overhead. Again, tens to hundreds of microseconds per invocation, plus the performance penalty of an interpreted language.

For some timing comparisons between script transforms and pure expressions for some common Perspective UI tasks, look at my Integration Toolkit module's topic for some of the testing shown there:

> [@Automation Professionals' Integration Toolkit Module](https://forum.inductiveautomation.com/t/automation-professionals-integration-toolkit-module/74934/5):
>
> I have spent my holiday poking at this. Wanted to provide an efficient replacement for a common use of python transforms: Make a (Perspective) table that dynamically populates both .data and .columns from source dataset that isn't constrained to any particular structure or data types. In Vision, one can achieve this (mostly) by pre-populating the column attributes dataset with all of the possible column names your application might deliver. No such thing in Perspective. But a transform can …

For some benchmarks on transform overhead versus runScript versus no script at all, check out this topic:

> [@Tag binding or expression to read dynamic list of tags](https://forum.inductiveautomation.com/t/tag-binding-or-expression-to-read-dynamic-list-of-tags/76610/16):
>
> Collected some overhead stats. Added a sixth binding for comparison, and made them all trigger from a common reference. The new expression transform looks like this: nanoTime() - {value} It is notably faster than the other transforms. To make the recorder() run smoothly, I made a trigger timestamp with now({this.custom.pace}) and set pace to 200. Then I modified the transforms' first stages to look like this: asList( {this.custom.trigger}, nanoTime() )[1] The non-transform tests of run…

---

<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:** [January 8, 2024, 8:44pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/16 "2024-01-08T20:44:22Z")

</div>

Further elaboration:

When you split a binding into separate custom properties, you are essentially constructing a sub-expression that only has to re-evaluate when one of its dependencies changes. If used in an outer expression, and its dependencies haven't changed, then its usage is nearly free--just the lookup of its latest value.

Tag indirect bindings have some asynchronous delivery advantages over the use of `tag()` functions, on top of eliminating the unnecessary re-evaluation of the tag path expression.

---

<div class="post-metadata">

**Author:** ![ian.sebryk](https://sea1.discourse-cdn.com/inductiveautomation/user_avatar/forum.inductiveautomation.com/ian.sebryk/32/49319_2.png) [@ian.sebryk](https://forum.inductiveautomation.com/u/ian.sebryk)\
**Post date:** [January 8, 2024, 9:15pm UTC](https://forum.inductiveautomation.com/t/using-variable-with-custom-property-in-expression/83936/17 "2024-01-08T21:15:18Z")

</div>

@pturmel not gonna lie, i kinda have some localized increase in blood flow right now... thank you so very much.

###### excellent Christmas reading, btw... ;)
