As @bkarabinchak.psi pointed out even though the structure “looks” like a dict
it isn’t actually a dict
.
Actually the type of a perspective property when accessed from a script is:com.inductiveautomation.perspective.gateway.script.PropertyTreeScriptWrapper.ObjectWrapper.
Thus deepcopy chokes when it runs into an object that it doesn’t know how to handle.
If you need a true deepcopy, then you have couple of options.
- Write a function which recursively loops through the structure and correctly maps objects to dictionaries, and arrays to lists.
- Encode to JSON and de-encode to guarantee you’re dealing with native Python objects
I have done both of those things in the past.
Note: Option 1 will work for “perspective properties”, it doesn’t account for other possible types that aren’t handled by deepcopy. The assumption I have made here is that if it isn’t an object, or array, then it is a basic type (string,integer,float,etc…). The function can/should be modified to handle other types if you need that particular thing.
Code for option 1:
def recursiveCopy(original):
from copy import deepcopy
from com.inductiveautomation.ignition.common.script.abc import AbstractMutableJythonMap,AbstractMutableJythonSequence
if isinstance(original,AbstractMutableJythonMap):
return {key:recursiveCopy(value) for key,value in original.iteritems()}
if isinstance(original,AbstractMutableJythonSequence):
return [recursiveCopy(item) for item in original]
return deepcopy(original)
Code for Option 2:
from copy import deepcopy
pen = deepcopy(system.util.jsonDecode(system.util.jsonEncode(self.view.custom.penEjemplo)))
There are reasons to go with option 1 over option 2, but for what it looks like you’re trying to do either will work.
I will say though, that if I were trying to modify a pen in a power chart, I would just modify the pen, not sure why you need a copy for that.