Skip to content

Commit

Permalink
Client Read File Transfer Method (#372)
Browse files Browse the repository at this point in the history
* add read file method

* add read file example

* refactor read file method parameters

* update read file example

* restore to original

* add new ua file class

* update ua file example with new class

* updating ua file for more user control

* add __aenter__ and __aexit__

* separate file read class

* make uafile class python
  • Loading branch information
jadamroth authored Dec 28, 2020
1 parent e318ef7 commit f189d87
Show file tree
Hide file tree
Showing 3 changed files with 60 additions and 9 deletions.
9 changes: 0 additions & 9 deletions asyncua/client/client.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@
class Client:
"""
High level client to connect to an OPC-UA server.
This class makes it easy to connect and browse address space.
It attempts to expose as much functionality as possible
but if you want more flexibility it is possible and advised to
Expand All @@ -35,11 +34,9 @@ def __init__(self, url: str, timeout: int = 4, loop=None):
:param url: url of the server.
if you are unsure of url, write at least hostname
and port and call get_endpoints
:param timeout:
Each request sent to the server expects an answer within this
time. The timeout is specified in seconds.
Some other client parameters can be changed by setting
attributes on the constructed object:
See the source code for the exhaustive list.
Expand Down Expand Up @@ -110,17 +107,13 @@ def set_password(self, pwd: str):
async def set_security_string(self, string: str):
"""
Set SecureConnection mode.
:param string: Mode format ``Policy,Mode,certificate,private_key[,server_private_key]``
where:
- ``Policy`` is ``Basic128Rsa15``, ``Basic256`` or ``Basic256Sha256``
- ``Mode`` is ``Sign`` or ``SignAndEncrypt``
- ``certificate`` and ``server_private_key`` are paths to ``.pem`` or ``.der`` files
- ``private_key`` may be a path to a ``.pem`` or ``.der`` file or a conjunction of ``path``::``password`` where
``password`` is the private key password.
Call this before connect()
"""
if not string:
Expand Down Expand Up @@ -542,10 +535,8 @@ async def create_subscription(self, period, handler, publishing=True):
"""
Create a subscription.
Returns a Subscription object which allows to subscribe to events or data changes on server.
:param period: Either a publishing interval in milliseconds or a `CreateSubscriptionParameters` instance.
The second option should be used, if the asyncua-server has problems with the default options.
:param handler: Class instance with data_change and/or event methods (see `SubHandler`
base class for details). Remember not to block the main event loop inside the handler methods.
"""
Expand Down
45 changes: 45 additions & 0 deletions asyncua/client/ua_file.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
from asyncua import ua


class UaFile:

def __init__(self, file_node, open_mode):
self._file_node = file_node
self._handle = None
if open_mode == 'r':
self._init_open = ua.OpenFileMode.Read.value
else:
raise ValueError("file mode is not supported")

async def __aenter__(self):
self._handle = await self.open(self._init_open)
return self

async def __aexit__(self, exc_type, exc_value, traceback):
return await self.close()

async def open(self, open_mode):
""" open file method """
open_node = await self._file_node.get_child("Open")
arg = ua.Variant(open_mode, ua.VariantType.Byte)
return await self._file_node.call_method(open_node, arg)

async def close(self):
""" close file method """
read_node = await self._file_node.get_child("Close")
arg1 = ua.Variant(self._handle, ua.VariantType.UInt32)
return await self._file_node.call_method(read_node, arg1)

async def read(self):
""" reads file contents """
size = await self.get_size()
read_node = await self._file_node.get_child("Read")
arg1 = ua.Variant(self._handle, ua.VariantType.UInt32)
arg2 = ua.Variant(size, ua.VariantType.Int32)
return await self._file_node.call_method(read_node, arg1, arg2)

async def get_size(self):
""" gets size of file """
size_node = await self._file_node.get_child("Size")
return await size_node.read_value()

15 changes: 15 additions & 0 deletions examples/client-file.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import asyncio
from asyncua.client import Client
from asyncua.client.ua_file import UaFile

async def read_file():
""" read file example """

url = "opc.tcp://10.0.0.199:4840"
async with Client(url=url) as client:
file_node = client.get_node("ns=2;s=NameOfNode")
async with UaFile(file_node, 'r') as ua_file:
contents = await ua_file.read() # read file
print(contents)

asyncio.run(read_file())

0 comments on commit f189d87

Please sign in to comment.