Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
O
opcua-asyncio
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
1
Merge Requests
1
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Nikola Balog
opcua-asyncio
Commits
ac15d133
Commit
ac15d133
authored
Apr 03, 2015
by
Olivier R-D
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
add high level namespace api, set server namespace array
parent
ef58b9d6
Changes
5
Hide whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
141 additions
and
28 deletions
+141
-28
opcua/client.py
opcua/client.py
+9
-0
opcua/internal_server.py
opcua/internal_server.py
+3
-0
opcua/node.py
opcua/node.py
+83
-9
opcua/server.py
opcua/server.py
+23
-2
tests.py
tests.py
+23
-17
No files found.
opcua/client.py
View file @
ac15d133
...
...
@@ -214,6 +214,15 @@ class Client(object):
params
.
Priority
=
0
return
Subscription
(
self
.
bclient
,
params
,
handler
)
def
get_namespace_array
(
self
):
ns_node
=
self
.
get_node
(
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_NamespaceArray
))
return
ns_node
.
get_value
()
def
get_namespace_index
(
self
,
uri
):
uries
=
self
.
get_namespace_array
()
return
uries
.
index
(
uri
)
opcua/internal_server.py
View file @
ac15d133
...
...
@@ -46,6 +46,9 @@ class InternalServer(object):
self
.
_stopev
=
False
self
.
_timer
=
None
self
.
current_time_node
=
Node
(
self
.
isession
,
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_ServerStatus_CurrentTime
))
uries
=
[
"http://opcfoundation.org/UA/"
]
ns_node
=
Node
(
self
.
isession
,
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_NamespaceArray
))
ns_node
.
set_value
(
uries
)
def
start
(
self
):
self
.
logger
.
info
(
"starting internal server"
)
...
...
opcua/node.py
View file @
ac15d133
...
...
@@ -7,8 +7,8 @@ import opcua.uaprotocol as ua
class
Node
(
object
):
"""
High level node object, to access node attribute
and brows
e address space
High level node object, to access node attribute
,
browse and populat
e address space
"""
def
__init__
(
self
,
server
,
nodeid
):
self
.
server
=
server
...
...
@@ -28,19 +28,27 @@ class Node(object):
return
"Node({})"
.
format
(
self
.
nodeid
)
__repr__
=
__str__
def
get_name
(
self
):
def
get_
browse_
name
(
self
):
result
=
self
.
get_attribute
(
ua
.
AttributeIds
.
BrowseName
)
return
result
.
Value
def
get_
valu
e
(
self
):
result
=
self
.
get_attribute
(
ua
.
AttributeIds
.
Valu
e
)
def
get_
display_nam
e
(
self
):
result
=
self
.
get_attribute
(
ua
.
AttributeIds
.
DisplayNam
e
)
return
result
.
Value
def
_value
(
self
):
def
get_value
(
self
):
"""
Get value of a node. Only variables(properties) have values.
An exception will be generated for other node types.
"""
result
=
self
.
get_attribute
(
ua
.
AttributeIds
.
Value
)
return
result
.
Value
def
set_value
(
self
,
value
,
varianttype
=
None
):
"""
Set value of a node. Only variables(properties) have values.
An exception will be generated for other node types.
"""
variant
=
None
if
type
(
value
)
==
ua
.
Variant
:
variant
=
value
...
...
@@ -49,6 +57,9 @@ class Node(object):
self
.
set_attribute
(
ua
.
AttributeIds
.
Value
,
ua
.
DataValue
(
variant
))
def
set_attribute
(
self
,
attributeid
,
datavalue
):
"""
Set an attribute of a node
"""
attr
=
ua
.
WriteValue
()
attr
.
NodeId
=
self
.
nodeid
attr
.
AttributeId
=
attributeid
...
...
@@ -59,6 +70,9 @@ class Node(object):
result
[
0
].
check
()
def
get_attribute
(
self
,
attr
):
"""
Get an attribute of a node
"""
rv
=
ua
.
ReadValueId
()
rv
.
NodeId
=
self
.
nodeid
rv
.
AttributeId
=
attr
...
...
@@ -68,10 +82,31 @@ class Node(object):
result
[
0
].
StatusCode
.
check
()
return
result
[
0
].
Value
def
get_children
(
self
):
def
get_children
(
self
,
refs
=
ua
.
ObjectIds
.
HierarchicalReferences
):
"""
Get all children of a node. By default hierarchical references are returnes.
Other types may be given:
References = 31
NonHierarchicalReferences = 32
HierarchicalReferences = 33
HasChild = 34
Organizes = 35
HasEventSource = 36
HasModellingRule = 37
HasEncoding = 38
HasDescription = 39
HasTypeDefinition = 40
GeneratesEvent = 41
Aggregates = 44
HasSubtype = 45
HasProperty = 46
HasComponent = 47
HasNotifier = 48
HasOrderedComponent = 49
"""
desc
=
ua
.
BrowseDescription
()
desc
.
BrowseDirection
=
ua
.
BrowseDirection
.
Forward
desc
.
ReferenceTypeId
=
ua
.
TwoByteNodeId
(
ua
.
ObjectIds
.
Reference
s
)
desc
.
ReferenceTypeId
=
ua
.
TwoByteNodeId
(
ref
s
)
desc
.
IncludeSubtypes
=
True
desc
.
NodeClassMask
=
ua
.
NodeClass
.
Unspecified
desc
.
ResultMask
=
ua
.
BrowseResultMask
.
None_
...
...
@@ -87,6 +122,14 @@ class Node(object):
return
nodes
def
get_child
(
self
,
path
):
"""
get a child specified by its path from this node.
A path might be:
* a string representing a qualified name.
* a qualified name
* a list of string
* a list of qualified names
"""
if
type
(
path
)
not
in
(
list
,
tuple
):
path
=
[
path
]
rpath
=
ua
.
RelativePath
()
...
...
@@ -138,6 +181,8 @@ class Node(object):
def
add_object
(
self
,
*
args
):
"""
create a child node object
arguments are nodeid, browsename
or namespace index, name
"""
nodeid
,
qname
=
self
.
_parse_add_args
(
*
args
)
return
self
.
_add_object
(
nodeid
,
qname
)
...
...
@@ -210,7 +255,36 @@ class Node(object):
results
=
self
.
server
.
add_nodes
([
node
])
results
[
0
].
StatusCode
.
check
()
return
Node
(
self
.
server
,
nodeid
)
def
add_method
(
self
,
*
args
):
"""
create a child method object
"""
nodeid
,
qname
=
self
.
_parse_add_args
(
*
args
)
return
self
.
_add_object
(
nodeid
,
qname
)
def
_add_method
(
self
,
nodeid
,
qname
):
node
=
ua
.
AddNodesItem
()
node
.
RequestedNewNodeId
=
nodeid
node
.
BrowseName
=
qname
node
.
NodeClass
=
ua
.
NodeClass
.
Object
node
.
ParentNodeId
=
self
.
nodeid
node
.
ReferenceTypeId
=
ua
.
NodeId
.
from_string
(
"i=35"
)
node
.
TypeDefinition
=
ua
.
NodeId
(
ua
.
ObjectIds
.
BaseObjectType
)
attrs
=
ua
.
MethodAttributes
()
attrs
.
Description
=
ua
.
LocalizedText
(
qname
.
Name
)
attrs
.
DisplayName
=
ua
.
LocalizedText
(
qname
.
Name
)
attrs
.
WriteMask
=
0
attrs
.
UserWriteMask
=
0
self
.
Executable
=
True
self
.
UserExecutable
=
True
node
.
NodeAttributes
=
attrs
results
=
self
.
server
.
add_nodes
([
node
])
results
[
0
].
StatusCode
.
check
()
return
Node
(
self
.
server
,
nodeid
)
def
_vtype_to_uatype
(
self
,
vtype
):
return
eval
(
"ua.NodeId(ua.ObjectIds.{})"
.
format
(
vtype
.
name
))
...
...
opcua/server.py
View file @
ac15d133
...
...
@@ -30,8 +30,14 @@ class Server(object):
def
set_endpoint
(
self
,
url
):
self
.
endpoint
=
urlparse
(
url
)
def
_set
_endpoint
s
(
self
):
def
_set
up_server_node
s
(
self
):
#to be called just before starting server since it needs all parameters to be setup
self
.
_set_endpoints
()
self
.
register_namespace
(
self
.
server_uri
)
sa_node
=
self
.
get_node
(
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_ServerArray
))
sa_node
.
set_value
([
self
.
server_uri
])
def
_set_endpoints
(
self
):
idtoken
=
ua
.
UserTokenPolicy
()
idtoken
.
PolicyId
=
'anonymous'
idtoken
.
TokenType
=
ua
.
UserTokenType
.
Anonymous
...
...
@@ -58,7 +64,7 @@ class Server(object):
def
start
(
self
):
self
.
iserver
.
start
()
self
.
_set
_endpoint
s
()
self
.
_set
up_server_node
s
()
self
.
bserver
=
BinaryServer
(
self
.
iserver
,
self
.
endpoint
.
hostname
,
self
.
endpoint
.
port
)
self
.
bserver
.
start
()
...
...
@@ -94,6 +100,21 @@ class Server(object):
params
.
Priority
=
0
return
Subscription
(
self
.
iserver
.
isession
,
params
,
handler
)
def
get_namespace_array
(
self
):
ns_node
=
self
.
get_node
(
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_NamespaceArray
))
return
ns_node
.
get_value
()
def
register_namespace
(
self
,
uri
):
ns_node
=
self
.
get_node
(
ua
.
NodeId
(
ua
.
ObjectIds
.
Server_NamespaceArray
))
uries
=
ns_node
.
get_value
()
uries
.
append
(
uri
)
ns_node
.
set_value
(
uries
)
return
(
len
(
uries
)
-
1
)
def
get_namespace_index
(
self
,
uri
):
uries
=
self
.
get_namespace_array
()
return
uries
.
index
(
uri
)
...
...
tests.py
View file @
ac15d133
...
...
@@ -185,13 +185,13 @@ class CommonTests(object):
def
test_root
(
self
):
root
=
self
.
opc
.
get_root_node
()
self
.
assertEqual
(
ua
.
QualifiedName
(
'Root'
,
0
),
root
.
get_name
())
self
.
assertEqual
(
ua
.
QualifiedName
(
'Root'
,
0
),
root
.
get_
browse_
name
())
nid
=
ua
.
NodeId
(
84
,
0
)
self
.
assertEqual
(
nid
,
root
.
nodeid
)
def
test_objects
(
self
):
objects
=
self
.
opc
.
get_objects_node
()
self
.
assertEqual
(
ua
.
QualifiedName
(
'Objects'
,
0
),
objects
.
get_name
())
self
.
assertEqual
(
ua
.
QualifiedName
(
'Objects'
,
0
),
objects
.
get_
browse_
name
())
nid
=
ua
.
NodeId
(
85
,
0
)
self
.
assertEqual
(
nid
,
objects
.
nodeid
)
...
...
@@ -242,13 +242,13 @@ class CommonTests(object):
#sub.delete()
#def test_get_
N
amespaceIndex(self):
#idx = self.opc.get_
N
amespaceIndex('http://freeua.github.io')
#def test_get_
browse_n
amespaceIndex(self):
#idx = self.opc.get_
browse_n
amespaceIndex('http://freeua.github.io')
#self.assertEqual(idx, 1)
#def test_use_namespace(self):
#root = self.opc.get_root_node()
#idx = self.opc.get_
N
amespaceIndex('http://freeua.github.io')
#idx = self.opc.get_
browse_n
amespaceIndex('http://freeua.github.io')
#o = root.add_object(idx, 'test_namespace')
#self.assertEqual(idx, o.nodeid.NamespaceIndex)
#o2 = root.get_child('{}:test_namespace'.format(idx))
...
...
@@ -286,7 +286,7 @@ class CommonTests(object):
nid
=
ua
.
NodeId
(
888
,
3
)
qn
=
ua
.
QualifiedName
(
'numericnodefromstring'
,
3
)
self
.
assertEqual
(
nid
,
v
.
nodeid
)
self
.
assertEqual
(
qn
,
v
.
get_name
())
self
.
assertEqual
(
qn
,
v
.
get_
browse_
name
())
def
test_add_string_variable
(
self
):
objects
=
self
.
opc
.
get_objects_node
()
...
...
@@ -294,7 +294,7 @@ class CommonTests(object):
nid
=
ua
.
NodeId
(
'stringid'
,
3
)
qn
=
ua
.
QualifiedName
(
'stringnodefromstring'
,
3
)
self
.
assertEqual
(
nid
,
v
.
nodeid
)
self
.
assertEqual
(
qn
,
v
.
get_name
())
self
.
assertEqual
(
qn
,
v
.
get_
browse_
name
())
def
test_add_string_array_variable
(
self
):
objects
=
self
.
opc
.
get_objects_node
()
...
...
@@ -302,7 +302,7 @@ class CommonTests(object):
nid
=
ua
.
NodeId
(
'stringarrayid'
,
3
)
qn
=
ua
.
QualifiedName
(
'stringarray'
,
9
)
self
.
assertEqual
(
nid
,
v
.
nodeid
)
self
.
assertEqual
(
qn
,
v
.
get_name
())
self
.
assertEqual
(
qn
,
v
.
get_
browse_
name
())
val
=
v
.
get_value
()
self
.
assertEqual
([
'l'
,
'b'
],
val
)
...
...
@@ -312,7 +312,7 @@ class CommonTests(object):
qn
=
ua
.
QualifiedName
(
'AddNodeVar1'
,
3
)
v1
=
objects
.
add_variable
(
nid
,
qn
,
0
)
self
.
assertEqual
(
nid
,
v1
.
nodeid
)
self
.
assertEqual
(
qn
,
v1
.
get_name
())
self
.
assertEqual
(
qn
,
v1
.
get_
browse_
name
())
def
test_add_string_node
(
self
):
objects
=
self
.
opc
.
get_objects_node
()
...
...
@@ -320,7 +320,7 @@ class CommonTests(object):
nid
=
ua
.
NodeId
(
'AddNodeVar2Id'
,
3
)
v2
=
objects
.
add_variable
(
nid
,
qn
,
0
)
self
.
assertEqual
(
nid
,
v2
.
nodeid
)
self
.
assertEqual
(
qn
,
v2
.
get_name
())
self
.
assertEqual
(
qn
,
v2
.
get_
browse_
name
())
def
test_add_find_node_
(
self
):
objects
=
self
.
opc
.
get_objects_node
()
...
...
@@ -341,7 +341,7 @@ class CommonTests(object):
nid
=
ua
.
NodeId
(
102
,
2
)
self
.
assertEqual
(
o
.
nodeid
,
nid
)
qn
=
ua
.
QualifiedName
(
'AddReadObject'
,
2
)
self
.
assertEqual
(
o
.
get_name
(),
qn
)
self
.
assertEqual
(
o
.
get_
browse_
name
(),
qn
)
def
test_simple_value
(
self
):
o
=
self
.
opc
.
get_objects_node
()
...
...
@@ -438,6 +438,13 @@ class CommonTests(object):
sub
.
unsubscribe
(
handle
)
sub
.
delete
()
def
test_use_namespace
(
self
):
idx
=
self
.
opc
.
get_namespace_index
(
"urn:freeopcua:python:server"
)
self
.
assertEqual
(
idx
,
1
)
root
=
self
.
opc
.
get_root_node
()
myvar
=
root
.
add_variable
(
idx
,
'var_in_custom_namespace'
,
[
5
])
myid
=
myvar
.
nodeid
self
.
assertEqual
(
idx
,
myid
.
NamespaceIndex
)
...
...
@@ -501,7 +508,7 @@ class TestClient(unittest.TestCase, CommonTests):
# new one before this one is really stopped
self
.
srv
.
join
()
"""
class
TestServer
(
unittest
.
TestCase
,
CommonTests
):
'''
...
...
@@ -527,11 +534,11 @@ class TestServer(unittest.TestCase, CommonTests):
self
.
assertTrue
(
v
in
childs
)
self
.
assertTrue
(
p
in
childs
)
'''
def
test_register_namespace
(
self
):
uri
=
'http://mycustom.Namespace.com'
idx1
=
self
.
opc
.
register_namespace
(
uri
)
idx2 = self.opc.get_
NamespaceI
ndex(uri)
idx2
=
self
.
opc
.
get_
namespace_i
ndex
(
uri
)
self
.
assertEqual
(
idx1
,
idx2
)
def
test_register_use_namespace
(
self
):
...
...
@@ -541,9 +548,8 @@ class TestServer(unittest.TestCase, CommonTests):
myvar
=
root
.
add_variable
(
idx
,
'var_in_custom_namespace'
,
[
5
])
myid
=
myvar
.
nodeid
self
.
assertEqual
(
idx
,
myid
.
NamespaceIndex
)
#self.assertEqual(uri, myid.Namespace_uri) #FIXME: should return uri!!!
'''
"""
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment