15:50, EEST
January 30, 2014
17:12, EEST
April 17, 2013
Hello,
The AddressSpace.getNode method initializes all kinds of information about the UaNode in question: it reads common attributes of the node and in addition to that, attributes that are specific to the NodeClass in question. The method also browses the properties of the node and initializes the Properties into the node object.
UaClient.readAttributes method instead makes a single read service call to the OPC UA server.
So, if you just need to read some attributes as fast as possible, you should indeed use the UaClient.readAttributes method or actually the UaClient.read which allows for the most customizations. In general case the assumption is that the NodeCache concept and initializations of AddressSpace.getNode pay off and this is the recommended way to use the SDK.
12:48, EEST
January 30, 2014
Thanks, yes in this case fastest as possible as we reduced traversing server address space more then 10 times. Server is on different subnet, via vpn,…
Now traversing with client.readAttributes last less then 5min instead more then 1h. Are there some settings in AddressSpace that can influence getNode to be quicker?
BR,
Goran
14:49, EEST
April 17, 2013
Oh, that is indeed a long time.
Can you provide some information about your application scenario so that we can understand why you are traversing so many nodes and if there’s something in the SDK that just doesn’t work in this situation? How much time does it take to just ping the server from the client machine? If there’s some details that you do not wish to share here on forum, you can contact us by email at uajava-support mailing list.
You can tune the NodeCache size and set the maximum time to keep nodes in the cache which may help with getNode performance in some situations. Please see the methods
16:47, EEST
January 30, 2014
Hi,
sorry for late answer. Scenario is simple I think. It is just collecting of server address space info (mostly about variables) which can be used
later in the form of xml. Program starts from starting node, get all references and go further to next node, …
Ping to server at different network is 60ms.
At one line as I wrote we just replaced getNodeId(nodeId) with readAttributes(…) and program significantly speed up.
As you wrote because of additional readings of getNodeId it is slower than readAttributes but that wasn’t visible in local environment where speed of traversing was ok.
I tried tweak methods for cache but I didn’t see any difference.
Anyway, solution with readAttributes in this scenario is suitable too.
BR,
jev
17:59, EEST
April 17, 2013
Hello,
Thanks for the information. You have a special application scenario and this also leads to special requirements. Just for curiosity, I must ask why are you storing the address space to xml?
For the best performance of browsing and reading available in the Prosys OPC UA Java SDK, I suggest that you only use AddressSpace.browse and UaClient.read methods. These offer only the simplest interface but also no time consuming side effects.
The ping to the server is 60 ms which is not especially slow but still influences the sequential browsing and reading. There’s also asynchronous versions of the above mentioned methods which you should take a look at. These are AddressSpace.browseAsync and UaClient.readAsync.
After talking about the read and browsing performance, in the end I would like to mention that the biggest performance gain would be achieved if the server would generate the file for you without multiple browse and read calls. The specification part 5 defines AddressSpaceFileType with method named ExportNamespace which may be intended for similar kind of purpose what you have in this case. Unfortunately this is not implemented in the Java SDK at the moment but depending on what server application you use, this may be one option for you. And if you control the server application yourself, you could implement similar kind of method yourself.
10:58, EEST
January 30, 2014
Hi,
Thank you for a new tips especially related to AddressSpaceFileType. I will take a look that part. We dill with couple of opcua servers (some of them implements very limited set of opcua spec) and only one is controlled by us. Unfortunately I can conclude that in the world of opcua server providers situation is not very good. Most of them do not follow 100% spec and some of them provides very logic explanation for something which is not by spec but also it is not forbidden by spec:) Maybe because opcua spec grows too much.
>> ust for curiosity, I must ask why are you storing the address space to xml?
For client application design time which is off-line. Besides it is exported in special format suitable for existing tools set.
BR,
jev
22:30, EEST
September 14, 2020
Hi,
We have a similar performance issue when querying the nodes and setting it’s data type but I’m not sure we can get around calling `getNode(nodeId)`. If we do not worry about getting/setting the data type, the tree build takes about 2-3 minutes, but with the data types it will take 25 minutes.
“`
import scala.util.{ Try, Success, Failure }
private def getNode(browser: AddressSpace, nodeId: ExpandedNodeId): UaNode = {
Try(browser.getNode(nodeId)) match {
case Success(node) => node
case Failure(e) => null
}
}
childRefs.addAll(browser.browse(nodeId))
import scala.collection.JavaConversions._
var dataType: String = null
for (ref <- childRefs) {
var uaNode = getNode(browser, ref.getNodeId())
if (uaNode != null && uaNode.supportsAttribute(Attributes.DataType)) {
// First, read the DataType attribute of the specified Node
val nodeType = session.readAttribute(uaNode.getNodeId(), Attributes.DataType)
// DataType attributes reference the Node that specifies the actual DataType. So, the value we need is of type NodeId
val dataTypeId = nodeType.getValue().getValue().asInstanceOf[NodeId];
if (uaNode.supportsAttribute(Attributes.DisplayName)) {
// Now that we have the NodeId of the DataType, we can read the DisplayName which gives us, for example, the value "Int32"
val nodeDataType = session.readAttribute(dataTypeId, Attributes.DisplayName);
dataType = nodeDataType.getValue().toString
}
}
val target = browser.getNamespaceTable.toNodeId(ref.getNodeId)
val childNode = new OpcTreeNode(parent, ref.getNodeId.toString, ref.getDisplayName.getText, ref.getTypeDefinition.getIdType.toString, dataType, parent.getServerUri)
parent.getChildren.add(childNode)
createHierarchy(browser, target, childNode) // recursive call
“`
Is there a way we can achieve better performance?
18:20, EEST
December 21, 2011
Yes, getNode() can end up in quite a number of service calls to the server and therefore it may take quite a while. On the other hand, you are doing some extra stuff here – and also we have a method called getNodes(), which you can use instead to read several nodes at once.
And if you use the UaNode objects, they should have the DataType initialised automatically for you in a more efficient way.
So, in practice, you can do something like this, which reads all variables from the Simulation folder of the Prosys OPC UA Simulation Server and prints their DataTypes. (I added this to the SimpleClient sample of the SDK):
// Find the Simulation Folder ExpandedNodeId id = new ExpandedNodeId("http://www.prosysopc.com/OPCUA/SimulationNodes/", "85/0:Simulation"); FolderType simFolder = client.getAddressSpace().getNode(id, FolderType.class); // Find all targets of Organizes references under the Simulation Folder UaReference[] refs = simFolder.getForwardReferences(Identifiers.Organizes); NodeId[] refTargets = new NodeId[refs.length]; for (int i = 0; i < refs.length; i++) { refTargets[i] = client.getNamespaceTable().toNodeId(refs[i].getTargetId()); } // Find all corresponding nodes UaNode[] nodes = client.getAddressSpace().getNodes(refTargets); for (UaNode n : nodes) { // Print data of all variables that we found if (n instanceof UaVariable) { UaVariable v = (UaVariable) n; System.out.println(String.format("%s: %s DataType=%s", v.getDisplayName().getText(), v.getTypeDefinition().getDisplayName().getText(), v.getDataType().getDisplayName())); } }
This results in just 6 service calls to the server (which you can verify in the ReqRes Log of the Simulation Server).
17:22, EEST
September 14, 2020
18:09, EEST
December 21, 2011
Yes, it is. It’s declared as
public UaNode[] getNodes(final NodeId... nodeIds)
which means that you can give it a list of individual NodeIds or an array of NodeId.
https://docs.oracle.com/javase/8/docs/technotes/guides/language/varargs.html
Most Users Ever Online: 1919
Currently Online:
17 Guest(s)
Currently Browsing this Page:
1 Guest(s)
Top Posters:
Heikki Tahvanainen: 402
hbrackel: 144
rocket science: 88
pramanj: 86
Francesco Zambon: 83
Ibrahim: 78
Sabari: 62
kapsl: 57
gjevremovic: 49
Xavier: 43
Member Stats:
Guest Posters: 0
Members: 735
Moderators: 7
Admins: 1
Forum Stats:
Groups: 3
Forums: 15
Topics: 1523
Posts: 6449
Newest Members:
rust, christamcdowall, redaahern07571, nigelbdhmp, travistimmons, AnnelCib, dalenegettinger, howardkennerley, Thomassnism, biancacraft16Moderators: Jouni Aro: 1026, Pyry: 1, Petri: 0, Bjarne Boström: 1026, Jimmy Ni: 26, Matti Siponen: 346, Lusetti: 0
Administrators: admin: 1