Closed AndreasHeine closed 3 years ago
???
They are in the Nodeset, but aren't loaded?
EDIT: Ah I understand now what you mean...but this sounds strange indeed
Does this problem only appear with the Machinery nodesets or are other affected as well? Does it only appear if you import both xmls?
actually you need DI for Machinery and i want the namplate stuff... tbh i have not tested it with other nodesets!
I tried to build the stuff like mentionede in the README in the folder schemas (first time ever and it seems that there have been some changes been made, like the Folder name is now "UA-Nodeset" and not "UA-Nodeset-master" anymore, as well there has been an issue with standard_address_space_part3, an indent would be missing).
I used the server-minimal.py example code and added both Schemas into it.
Beside of issues like:
there have been Nodes being added normally, but it crashed at:
If I just added the Machinery part, the not implemented tags logs are there as well and it crashes as well:
Is it just me (in that case I would open another issue) or could this being caused by this issue?
"UA-Nodeset-master" thats from me!
check VDMA-Prototype1 there you see my code!
"UA-Nodeset-master" thats from me!
We may have to change the README then, so that if others want to import stuff as well, we don't get problems (or make it more understandable for beginners like me ^^).
I tried your code and got this:
If the parent is missing, all child nodes may not appear.
Btw. is it allowed that a Node of both XMLs can have the same NodeId (here BlockType and IMachineryItemVendorNameplateType)? May this cause problems as well?
But I am even wondering why it expects a parent for that Node (as example). There is no parent mentioned in the xml files (for both sets).
If the parent is missing, all child nodes may not appear.
the weird thing is in some cases it did....
But I am even wondering why it expects a parent for that Node (as example). There is no parent mentioned in the xml files (for both sets).
the parent in those cases is mostly a standard addressspace node!
@oroulet 0.9.0 / 0.8.4 some thing in the xml import broke!
in 0.9.0 i am not able to import Opc.Ua.Machinery.NodeSet2.xml without missing nodes, in 0.8.4 everything is fine... does anything else change then load_type_definition() -> load_data_type_definition() in connection to the XML-Importer?
I did not manage to understand. You mean some nodes are not imported?
I can confirm that Nodes are missing with 0.9.
@oroulet invite for the repo is out!
after importing Opc.Ua.Di.NodeSet2.xml and Opc.Ua.Machinery.NodeSet2.xml
0.8.4: also missing nodes
0.9.0:
Siemens SIOME:
Sorry I am very busy currently. The easiest way to debug that is probably to identify a commit that works an use 'git bisect' to find what commit break things. Maybe it gets way to fix then..
No worries time is a rare ressource...
the error is not in python-opcua v0.98.12 and not in asyncua 0.8.4 one difference is the add missing parents part
update:
I am a step closer to a solution for this issue it happens when importing "Opc.Ua.Di.NodeSet2.xml"
failure adding node NodeData(nodeid:ns=2;i=6017)
Non array Variant of type VariantType.NodeId cannot have value None
original:
<UAVariable NodeId="ns=1;i=6017" BrowseName="1:<ParameterIdentifier>" SymbolicName="ParameterIdentifier" ParentNodeId="ns=1;i=5002">
<DisplayName><ParameterIdentifier></DisplayName>
<Description>A parameter which belongs to the topology element.</Description>
<References>
<Reference ReferenceType="HasTypeDefinition">i=63</Reference>
<Reference ReferenceType="HasModellingRule">i=11510</Reference>
<Reference ReferenceType="HasComponent" IsForward="false">ns=1;i=5002</Reference>
</References>
</UAVariable>
next step is to check spec and see if a NodeId can be Null. ..... if needed we can modify code to accept it. Otherwise there is a bug in that spec OR we should write a default NodeId value in that case
this raise causes that the import is been stopped (i am not sure if we shloud just continue?)
@AndreasHeine What error has been raised?
i am not sure if we shloud just continue?
I am fighting with myself, if it should raise (since the "mission" of this Coroutine is to import an xml file, not just the Nodes who work) or continue with a better error handling (not just a logged warning/error, perhaps another return value about missing/faulty Nodes?).
Py:
Siemens:
next step is to check spec and see if a NodeId can be Null. ..... if needed we can modify code to accept it. Otherwise there is a bug in that spec OR we should write a default NodeId value in that case
@oroulet NodeId cant be Null!
OK. but we can define a NodeId(0,0) which is invalid and can be a default value. (It is btw used as a kind of Null NodeId a few places in code). Since you are looking at that import code you can probably fix it there (instead of raising an exception)
for nodedata in nodes_parsed: # self.parser:
try:
node = await self._add_node_data(nodedata)
except Exception:
print(nodedata.nodeid)
print(nodedata.nodetype)
_logger.warning("failure adding node %s", nodedata)
raise
print returns id: ns=2;i=6017 type: UAVariable
so we have a node id! but we dont handle it right i guess!?
async def add_variable(self, obj):
node = self._get_add_node_item(obj)
attrs = ua.VariableAttributes()
if obj.desc:
attrs.Description = ua.LocalizedText(obj.desc)
attrs.DisplayName = ua.LocalizedText(obj.displayname)
attrs.DataType = obj.datatype
if obj.value is not None:
attrs.Value = self._add_variable_value(obj,)
if obj.rank:
attrs.ValueRank = obj.rank
if obj.accesslevel:
attrs.AccessLevel = obj.accesslevel
if obj.useraccesslevel:
attrs.UserAccessLevel = obj.useraccesslevel
if obj.minsample:
attrs.MinimumSamplingInterval = obj.minsample
if obj.dimensions:
attrs.ArrayDimensions = obj.dimensions
node.NodeAttributes = attrs
print("Node: ", node)
res = await self._get_server().add_nodes([node])
print("Res: ", res)
await self._add_refs(obj)
res[0].StatusCode.check()
return res[0].AddedNodeId
Node: AddNodesItem(ParentNodeId:ns=2;i=6094, ReferenceTypeId:i=46, RequestedNewNodeId:ns=2;i=6095, BrowseName:QualifiedName(2:OnlineAccess), NodeClass:2, NodeAttributes:VariableAttributes(SpecifiedAttributes:4002419, DisplayName:LocalizedText(Encoding:2, Locale:None, Text:OnlineAccess), Description:LocalizedText(Encoding:2, Locale:None, Text:Hint of whether the Server is currently able to communicate to Devices in the topology.), WriteMask:0, UserWriteMask:0, Value:Variant(val:None,type:VariantType.Null), DataType:i=1, ValueRank:-1, ArrayDimensions:[], AccessLevel:1, UserAccessLevel:1, MinimumSamplingInterval:0, Historizing:False), TypeDefinition:i=68)
Res: [AddNodesResult(StatusCode:StatusCode(Good), AddedNodeId:ns=2;i=6095)]
Node: AddNodesItem(ParentNodeId:ns=2;i=5002, ReferenceTypeId:i=47, RequestedNewNodeId:ns=2;i=6017, BrowseName:QualifiedName(2:<ParameterIdentifier>), NodeClass:2, NodeAttributes:VariableAttributes(SpecifiedAttributes:4002419, DisplayName:LocalizedText(Encoding:2, Locale:None, Text:<ParameterIdentifier>), Description:LocalizedText(Encoding:2, Locale:None, Text:A parameter which belongs to the topology element.), WriteMask:0, UserWriteMask:0,
Value:Variant(val:None,type:VariantType.Null), DataType:None, ValueRank:-1, ArrayDimensions:[], AccessLevel:1, UserAccessLevel:1, MinimumSamplingInterval:0, Historizing:False), TypeDefinition:i=63)
failure adding node NodeData(nodeid:ns=2;i=6017)
Non array Variant of type VariantType.NodeId cannot have value None
you have a nodedata of type UAVaiable but its value is None and this is wrong. so at some places (maybe in a new function here: since all fix functions are there) . Go through all nodes and if you get a nodedata of type UAVariable and type is NodeId and value is None then add that default NodeId(0, 0) as a value) https://github.com/FreeOpcUa/opcua-asyncio/blob/9925e7d098f8949d3f928ac8fb72fe469c4c07c1/asyncua/common/xmlimporter.py#L61
call that method fix_missing_values() for example
@oroulet
as shown above and here it should look like:
<UAVariable NodeId="ns=1;i=6017" BrowseName="1:<ParameterIdentifier>" SymbolicName="ParameterIdentifier" ParentNodeId="ns=1;i=5002">
<DisplayName><ParameterIdentifier></DisplayName>
<Description>A parameter which belongs to the topology element.</Description>
<References>
<Reference ReferenceType="HasTypeDefinition">i=63</Reference>
<Reference ReferenceType="HasModellingRule">i=11510</Reference>
<Reference ReferenceType="HasComponent" IsForward="false">ns=1;i=5002</Reference>
</References>
</UAVariable>
i=63 -> BaseDataVariableType i=11510 -> ModellingRule_MandatoryPlaceholder
you have a nodedata of type UAVaiable but its value is None and this is wrong. so at some places (maybe in a new function here: since all fix functions are there) . Go through all nodes and if you get a nodedata of type UAVariable and type is NodeId and value is None then add that default NodeId(0, 0) as a value)
None is a valid value for a Variable in OPC UA!
the node id of this node is:
failure adding node NodeData(nodeid:ns=2;i=6017)
<--- initial error
following error because its not writen as VariantType.Null that leads to:
Non array Variant of type VariantType.NodeId cannot have value None
if self.Value is None and not self.is_array and self.VariantType not in (VariantType.Null, VariantType.String, VariantType.DateTime, VariantType.ExtensionObject):
raise UaError(f"Non array Variant of type {self.VariantType} cannot have value None")
None is a valid value for a Variable in OPC UA!
I thought you wrote the opposite above. If none is valid then we just accept it then
NodeId cant be Null! NodeValue can be Null! if its VariantType.Null
the initial error is not because of the nodeid :) maybe missunderstanding.
AddNodesItem(ParentNodeId:ns=2;i=5002, ReferenceTypeId:i=47, RequestedNewNodeId:ns=2;i=6017, BrowseName:QualifiedName(2:<ParameterIdentifier>), NodeClass:2, NodeAttributes:VariableAttributes(SpecifiedAttributes:4002419, DisplayName:LocalizedText(Encoding:2, Locale:None, Text:<ParameterIdentifier>), Description:LocalizedText(Encoding:2, Locale:None, Text:A parameter which belongs to the topology element.), WriteMask:0, UserWriteMask:0, Value:Variant(val:None,type:VariantType.Null), DataType:None, ValueRank:-1, ArrayDimensions:[], AccessLevel:1, UserAccessLevel:1, MinimumSamplingInterval:0, Historizing:False), TypeDefinition:i=63)
failure adding node NodeData(nodeid:ns=2;i=6017)
nodedata: NodeData(nodeid:ns=2;i=6017) nodetype: UAVariable nodeid : ns=2;i=6017 browsename : QualifiedName(1:
) displayname : parent : ns=2;i=5002 parentlink : i=47 desc : A parameter which belongs to the topology element. typedef : i=63 refs : [RefStruct((NumericNodeId(i=40), True, NumericNodeId(i=63))), RefStruct((NumericNodeId(i=37), True, NumericNodeId(i=11510))), RefStruct((NumericNodeId(i=47), False, NumericNodeId(ns=2;i=5002)))] nodeclass : None eventnotifier : 0 datatype : None rank : -1 value : None valuetype : None dimensions : None accesslevel : None useraccesslevel : None minsample : None inversename : abstract : False symmetric : False definitions : [] failure adding node NodeData(nodeid:ns=2;i=6017)
@oroulet added your suggestion to #323 but still some nodes missing...
I had a closer look and I propose the following fix
https://github.com/FreeOpcUa/opcua-asyncio/pull/325
That should make us support many strange things
Missing nodes from: Opc.Ua.Machinery.NodeSet2.xml MachineryItemIdentificationType -> parent is ITagNameplateType (from DI nodeset) IMachineryItemVendorNameplateType -> parent is IVendorNameplateType (from DI nodeset)
it appears that we dont update the references from parent nodes importet earlier!
C:\Users\andre\Desktop\python import>C:/Users/andre/AppData/Local/Programs/Python/Python37/python.exe "c:/Users/andre/Desktop/python import/server.py"
No user manager specified. Using default permissive manager instead.
Parsing value of type 'QualifiedName' not implemented
NOT DEFINITON i=22 NodeData(nodeid:ns=2;i=6522)
Registring Enum ns=2;i=6244 QualifiedName(2:DeviceHealthEnumeration)
Registring data type ns=2;i=6244 QualifiedName(2:DeviceHealthEnumeration)
CODE
class DeviceHealthEnumeration(IntEnum):
'''
DeviceHealthEnumeration EnumInt autogenerated from EnumDefinition
'''
NORMAL = 0
FAILURE = 1
CHECK_FUNCTION = 2
OFF_SPEC = 3
MAINTENANCE_REQUIRED = 4
Registring data type i=258 QualifiedName(0:Node)
Registring data type i=285 QualifiedName(0:ReferenceNode)
Registring data type ns=2;i=6522 QualifiedName(2:FetchResultDataType)
Registring data type ns=2;i=6525 QualifiedName(2:ParameterResultDataType)
CODE
class ParameterResultDataType:
'''
ParameterResultDataType structure autogenerated from StructureDefinition object
'''
data_type = ua.NodeId(6525, 2)
ua_types = [
('NodePath', 'ListOfQualifiedName'),
('StatusCode', 'StatusCode'),
('Diagnostics', 'DiagnosticInfo'),
]
def __str__(self):
vals = [f"{name}:{val}" for name, val in self.__dict__.items()]
return f"ParameterResultDataType({','.join(vals)})"
__repr__ = __str__
def __init__(self):
self.NodePath = []
self.StatusCode = ua.StatusCode()
self.Diagnostics = ua.DiagnosticInfo()
Parsing value of type 'QualifiedName' not implemented
Registring data type i=258 QualifiedName(0:Node)
Registring data type i=285 QualifiedName(0:ReferenceNode)
Registring data type ns=2;i=6522 QualifiedName(2:FetchResultDataType)
Endpoints other than open requested but private key and certificate are not set.
the nodes are actually there but not with all references like hassubtype and some other which leads to differences in node tree structure!
and got a "Unexpected structure" -_-°
INFO:asyncua.common.xmlimporter:Importing xml node (QualifiedName(1:ParameterSet), ns=2;i=5002) as (QualifiedName(2:ParameterSet) ns=2;i=5002)
DEBUG:asyncua.server.address_space:Adding node ns=2;i=5002 QualifiedName(2:ParameterSet)
ID: ns=2;i=6017 Type: UAVariable Val: None Typedef: i=63 Ref: [RefStruct((NumericNodeId(i=40), True, NumericNodeId(i=63))), RefStruct((NumericNodeId(i=37), True, NumericNodeId(i=11510))), RefStruct((NumericNodeId(i=47), False, NumericNodeId(ns=2;i=5002)))]
INFO:asyncua.common.xmlimporter:Importing xml node (QualifiedName(1:<ParameterIdentifier>), ns=2;i=6017) as (QualifiedName(2:<ParameterIdentifier>) ns=2;i=6017)
DEBUG:asyncua.server.address_space:Adding node ns=2;i=6017 QualifiedName(2:<ParameterIdentifier>)
WARNING:asyncua.common.xmlimporter:failure adding node NodeData(nodeid:ns=2;i=6017)
Non array Variant of type VariantType.NodeId cannot have value None
ID: ns=2;i=6017
Type: UAVariable
Val: None
Ref: [
#HasTypeDefinition: BaseDataVariableType
RefStruct((NumericNodeId(i=40), True, NumericNodeId(i=63))),
#HasModellingRule: ModellingRule_MandatoryPlaceholder
RefStruct((NumericNodeId(i=37), True, NumericNodeId(i=11510))),
#HasComponent: ParameterSet
RefStruct((NumericNodeId(i=47), False, NumericNodeId(ns=2;i=5002)))
]
@oroulet update i am in adress_space.py -> _add_node() and uncomented some debug logs
i put the content in a try/except and got 'NoneType' object has no attribute 'StatusCode'
lets see what weve got ;)
adress_space.py -> _add_node() -> self._add_node_attributes() -> _add_node_attributes() -> _add_nodeattributes() -> _add_node_attr() -> ERROR
ID: ns=2;i=6017 Type: UAVariable Val: None Typedef: i=63 Ref: [RefStruct((NumericNodeId(i=40), True, NumericNodeId(i=63))), RefStruct((NumericNodeId(i=37), True, NumericNodeId(i=11510))), RefStruct((NumericNodeId(i=47), False, NumericNodeId(ns=2;i=5002)))]
INFO:asyncua.common.xmlimporter:Importing xml node (QualifiedName(1:<ParameterIdentifier>), ns=2;i=6017) as (QualifiedName(2:<ParameterIdentifier>) ns=2;i=6017)
DEBUG:asyncua.server.address_space:Adding node ns=2;i=6017 QualifiedName(2:<ParameterIdentifier>)
VariantType.Byte
VariantType.UInt32
VariantType.NodeId
Non array Variant of type VariantType.NodeId cannot have value None
WARNING:asyncua.common.xmlimporter:failure adding node NodeData(nodeid:ns=2;i=6017)
'NoneType' object has no attribute 'StatusCode'
WARNING:asyncua.server.server:Endpoints other than open requested but private key and certificate are not set.
INFO:asyncua.server.internal_server:starting internal server
@oroulet to sum it all up:
it is better to fix it in variant class like below (in #323) https://github.com/FreeOpcUa/opcua-asyncio/blob/9925e7d098f8949d3f928ac8fb72fe469c4c07c1/asyncua/ua/uatypes.py#L720
if self.Value is None and not self.is_array and self.VariantType not in (VariantType.Null, VariantType.String, VariantType.DateTime, VariantType.ExtensionObject):
if self.Value == None and self.VariantType == VariantType.NodeId:
self.Value = NodeId(0,0)
else:
raise UaError(f"Non array Variant of type {self.VariantType} cannot have value None")
if i follow the error there is no place to fix it better then above adress_space.py -> _add_node() -> self._add_node_attributes() -> _add_node_attributes() -> _add_nodeattributes() -> _add_node_attr() -> ERROR
it only happens for such placeholder nodes in CS nodesets
@jcbastosportela can you verify if it solves #308
STATUS: with the fix it is "CLOSED"
"missing nodes" the nodes arent missing with the fix above but there are missing references especialy if the second imported nodeset/node has a references to the first imported nodeset/node
STATUS: OPEN
Problem: Browsing BaseDataType -> Structure -> "Unexpected structure" Solution: on browse it should responde with "BadAttributeIdInvalid"
STATUS: OPEN
one problem solved and got two new, live is good (sarcasm!)
Non array Variant of type VariantType.NodeId cannot have value None That is the old error. Why do you get it?
Also if you want to know exactly where the error happens, you can add logging: logger.exception("whatever") and you get the trace.
Also how does th xml code you import looks like for the failing structure?
Also how does th xml code you import looks like for the failing structure?
not only those who got imported also the NS=0 structures return for the TypeDefinition "Unexpected structure" but i guess it should be "BadAttributeIdInvalid" Examples: i=465 [ActivateSessionRequest] ns=2;i=6522 (FetchResultDataType)
I am on it, to remove lxml (#299) and fix that kind of stuff (#308 and here) ... that will take a while, I guess.
If somebody is missing a feature for that or want to make some hints, now would be the right time to mention this, before I yeet my table later. 😄
create early a merge request so you can get feedback @swamper123
Got the same error running server-robotics.py example from 9925e7d, which imports
DI/Opc.Ua.Di.NodeSet2.xml Robotics/Opc.Ua.Robotics.NodeSet2.xml
@pbertoni89 could you test it with version 0.8.4 ?
@pbertoni89 could you test it with version 0.8.4 ?
So strange. First, imports pass with no errors, just some lines worth of attention (showing just one, they're ~50 instances)
INFO:asyncua.common.xmlparser:Parsing node: ns=1;i=16794 1:PowerTrainType INFO:asyncua.common.xmlparser:Not implemented tag: <Element '{http://opcfoundation.org/UA/2011/03/UANodeSet.xsd}Documentation' at 0x7fc5b6508ea0> INFO:asyncua.common.xmlparser:Could not find parent for node 'ns=1;i=16794'
But it's at connection time that things get broken with a TimeoutError
. Using opcua-client
from master
, after few seconds it surrenders with
uaclient.uaclient - INFO - Connecting to opc.tcp://localhost:4840 with parameters None, None, None, None') uaclient.mainwindow - WARNING - showing error: %s') uawidgets.utils - ERROR - ') Traceback (most recent call last): File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/site-packages/uawidgets/utils.py", line 21, in wrapper result = func(self, *args) File "/media/xnext/DATAEXT/git_repos/FreeOpcUa/opcua-client-gui/uaclient/mainwindow.py", line 339, in connect self.uaclient.connect(uri) File "/media/xnext/DATAEXT/git_repos/FreeOpcUa/opcua-client-gui/uaclient/uaclient.py", line 93, in connect self.client.connect() File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/site-packages/opcua/client/client.py", line 274, in connect self.send_hello() File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/site-packages/opcua/client/client.py", line 316, in send_hello ack = self.uaclient.send_hello(self.server_url.geturl(), self.max_messagesize, self.max_chunkcount) File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/site-packages/opcua/client/ua_client.py", line 272, in send_hello return self._uasocket.send_hello(url, max_messagesize, max_chunkcount) File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/site-packages/opcua/client/ua_client.py", line 190, in send_hello ack = future.result(self.timeout) File "/media/xnext/DATAEXT/opt/miniconda/envs/opc-vanilla-38/lib/python3.8/concurrent/futures/_base.py", line 441, in result raise TimeoutError() concurrent.futures._base.TimeoutError uaclient.mainwindow - WARNING - showing error: %s')
Running Python 3.8.5 from conda 4.9.2 inside Ubuntu 20.04
@pbertoni89 There are existing parser problems with some tags. I tumbled over them as well while trying to understand the whole Parser thing ("just" replacing objectify may not lead to a better goal). There are other Tags missing like "Documentation" (Part 100-5.5.5.3).
Beside of that, you may have other Problems with your connection, which would be better in another Issue. :)
Hey,
i am kind of confused, i looked for quite some time to find the issue but i did not found it yet... maybe someone sees what i dont!
???