Variable Indirection

variables

#1

1) Give a description of the problem
Local variable containing the name of a global variable works for retrieving the value but unable to set through the same indirection

2) What is the expected behaviour?
define localVariable="@globalVariableName"

set variable({{localVariable}}) = newValue would set the Global variable who’s name is stored in the local variable to the new value

3) What is happening/not happening?
Only able to pick the actual variable objects in the GUI - there is no expression option to be able to perform this indirection

**4) Post a Green Snapshot of the piston!
N/A

5) Attach logs after turning logging level to Full
N/A


#2

When you place the following code up top in the define section:
define variable localVariable = @globalVariableName
It will force the local variable to capture whatever is stored in the global each time the piston runs

When you place the following code down below in the execute section:
execute set variable {localVariable} = newValue
That command will store “newValue” into the local variable. (until the piston runs again. See above)


Essentially, for any variable that you want to be able to change (or have total control of when it updates), you should leave the define section (not set). This way, you can program your “Set variables” down in the execute section, and they will not change until a new “Set variable” command has executed.

I usually only force data up top when the data is static (non-changing).


#3

So I suppose I need to get into more details here, as I’m not sure you followed where I was going with this… I’m trying to create a reusable dynamic piston for my Ikea Tradfri remotes (5-button ones). I set the remote variable for that piston and the index of the light that it should currently control is stored in a global variable (need a different one for each remote so each one can keep track of the light they are controlling) that saves the index between piston runs. The name of the assigned global variable for that piston’s remote is then set to a local variable at the top so it is easy to set up a new instance of the piston.

The local variable will not change per piston / per run / etc, just the global variable defined by that local variable changes when the left- or right-button on the remote is pushed.

Hopefully that makes sense. I’ve done a lot of variable indirection in other languages and was hoping it wasn’t so difficult here, but I guess it may just not be possible.


#4

I have re-read your last post six times, and understand even less than before… LOL

Please bear with me here…


Do you mean you set a global variable from within the piston?


Does this mean you have five globals, each with different (static) integer?


This sounds like one piston changes a global, and you want another piston to act differently…


The code:
Set localVariable = @globalVariable
does not capture the name of the global. Only the data contained within.


I think SmartThings works best when you go at it in reverse. Changing the locals often, and keeping the globals fairly consistent. (this is because locals are written instantly, and globals are not written until the last line of code has processed)


If you cannot share your pistons, perhaps posting here short textual pistons will better explain your goals, and help us point you in the right direction.


#5

I think I understand what you’re trying to do. You want a generic piston which can handle events from a number of ikea switches, where each switch is allocated a light to control?

I’m not sure exactly how you intend your piston to work, but understand what you mean by variable indirection i.e
string s1=“value 1”, s2=“value 2”
string selected =“s1”
string working_val
The following is the indirection assignment (not sure how/or if to do this in webcore)
working_val = {selected}
working_val will now contain the value “value1”

I had similar design aims with a generic piston to turn lights on when you enter a room. The attached achieves this, It’s not perfect but seems to do the job. To add a new room you just alter the variables. You may be able to use some of the concepts. There are some limitations with webcore variable, arrays in particular. A key one is that you cant add devices to the list of devices in the order you want, they are sorted alphabetically, in my code I have to ensure that the sensors & switches have a naming standard so they both appear in the correct order,


#6

So here’s my hard-coded global variable in the piston. I want to genericise it so I only need to tell it the name of the global variable in the definitions.


#7

Just a reminder… The command on line 50 (set global) does not happen until after the very last line of code has processed. This means that line 51 will always use the old/previous global data…

I should probably also mention that line 51 is totally useless for another reason. By hard coding up top in the define section, it basically makes line 51 pointless.


#8

It seems that line 51 was just left-over from my testing in trying to see what was happening. I will remove it… but it still doesn’t seem that I can set a variable thru indirection, which was the point of this thread. By moving the global variable name into a local variable I would only need to edit one place for the global variable instead of the 2 needed now - 18 and 50 - this doesn’t seem like it would be difficult to change the variable in 2 places, but the easier I can make it on myself the better :slight_smile:

Anyway, I guess I’ll close this out and just stick with direct variables.

Thanks everyone