You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@plc4x.apache.org by cd...@apache.org on 2020/02/26 11:10:03 UTC
[plc4x] branch develop updated: Refactor PlcDriverManager as
context manager
This is an automated email from the ASF dual-hosted git repository.
cdutz pushed a commit to branch develop
in repository https://gitbox.apache.org/repos/asf/plc4x.git
The following commit(s) were added to refs/heads/develop by this push:
new 7b556a1 Refactor PlcDriverManager as context manager
new 44f0ebc Merge pull request #124 from nuclearpinguin/feature/plc4py
7b556a1 is described below
commit 7b556a12ee18daa7d06e90327c212fe773b666a7
Author: Tomek Urbaszek <to...@polidea.com>
AuthorDate: Sun Feb 23 12:49:29 2020 +0100
Refactor PlcDriverManager as context manager
---
.gitignore | 1 +
sandbox/plc4py/README.md | 23 ++-----
.../python/org/apache/plc4x/PlcDriverManager.py | 74 +++++++++++++++-------
3 files changed, 55 insertions(+), 43 deletions(-)
diff --git a/.gitignore b/.gitignore
index 282586c..6691622 100644
--- a/.gitignore
+++ b/.gitignore
@@ -96,6 +96,7 @@ plc4cpp/cmake-build-debug/
plc4py/venv/
**/__pycache__/**/*
/plc4cpp/.vscode/ipch
+*.egg-info
# Exclude gradle stuff
.gradle
diff --git a/sandbox/plc4py/README.md b/sandbox/plc4py/README.md
index 41f5545..05bf569 100644
--- a/sandbox/plc4py/README.md
+++ b/sandbox/plc4py/README.md
@@ -30,29 +30,14 @@ Some tests can be found in `test/test_PlcDriverManager.py`.
Here is some example code:
```python
-try:
- manager = PlcDriverManager()
-
- connection = None
- try:
- connection = manager.get_connection("s7://192.168.167.210/0/1")
+with PlcDriverManager() as manager:
+ with manager.connection("s7://192.168.167.210/0/1") as conn:
for _ in range(100):
- result = connection.execute(Request(fields={"field1": "%M0:USINT"}))
+ result = conn.execute(Request(fields={"field1": "%M0:USINT"}))
print("Response Code is " + str(result.get_field("field1").get_response_code()))
- # We now that we want to get an int...
+ # We know that we want to get an int...
print("Response Value is " + str(result.get_field("field1").get_int_value()))
-
- except PlcException as e:
- raise Exception(str(e.url))
- finally:
- if connection is not None:
- connection.close()
-finally:
- manager.close()
```
-the `PlcDriverManager` spawns an interop server in the background, thus it is important to close it afterwards.
-Otherwise this process keeps alive and you have to kill by yourself.
-
All generated files (from thrift) are in `org.apache.plc4x.interop`.
I built a very simple Python API in `org.apache.plc4x`.
diff --git a/sandbox/plc4py/src/main/python/org/apache/plc4x/PlcDriverManager.py b/sandbox/plc4py/src/main/python/org/apache/plc4x/PlcDriverManager.py
index aa68418..f818bdf 100644
--- a/sandbox/plc4py/src/main/python/org/apache/plc4x/PlcDriverManager.py
+++ b/sandbox/plc4py/src/main/python/org/apache/plc4x/PlcDriverManager.py
@@ -18,6 +18,7 @@
import subprocess
import time
import warnings
+from contextlib import contextmanager
from generated.org.apache.plc4x.interop.InteropServer import Client, PlcException
from thrift.protocol import TBinaryProtocol
@@ -28,41 +29,44 @@ from org.apache.plc4x.PlcConnection import PlcConnection
class PlcDriverManager:
-
"""
- constructor, initialize the server
+ Constructor, initialize the server
"""
def __init__(self, embedded_server=True):
self.embedded_server = embedded_server
+ self.interop_proc = None
# Start the Server in the background
if embedded_server:
- self.interop_proc = subprocess.Popen(
- ["java", "-Dlog4j.configurationFile=../lib/log4j2.xml",
- "-jar", "../lib/interop-server.jar"])
- try:
- print("Started server under pid " + str(self.interop_proc.pid))
- except:
- print("Encountered an Exception while starting Interop Server")
- raise PlcException("Unable to start the Interop Server!")
+ self.start_server()
- time.sleep(2)
- poll = self.interop_proc.poll()
- if poll is None:
- print("Sucesfully started the Interop Server...")
- else:
- warnings.warn("Interop Server died after starting up...")
- raise PlcException(
- "Unable to start the Interop Server. Is another Server still running under the same port?")
+ transport = TSocket.TSocket('localhost', 9090)
+ self.transport = TTransport.TBufferedTransport(transport)
+ self.protocol = TBinaryProtocol.TBinaryProtocol(self.transport)
- self.transport = TSocket.TSocket('localhost', 9090)
- self.transport = TTransport.TBufferedTransport(self.transport)
+ def __enter__(self):
+ self.open()
+ return self
- self.protocol = TBinaryProtocol.TBinaryProtocol(self.transport)
+ def __exit__(self, *args):
+ self.close()
+ def start_server(self):
+ self.interop_proc = subprocess.Popen(
+ ["java", "-Dlog4j.configurationFile=../lib/log4j2.xml", "-jar", "../lib/interop-server.jar"]
+ )
try:
- self.transport.open()
- except TTransportException:
- raise PlcException("Unable to connect to the Interop Server, is the Server really running???")
+ print("Started server under pid " + str(self.interop_proc.pid))
+ except:
+ print("Encountered an Exception while starting Interop Server")
+ raise PlcException("Unable to start the Interop Server!")
+ time.sleep(2)
+ poll = self.interop_proc.poll()
+ if poll is None:
+ print("Sucesfully started the Interop Server...")
+ else:
+ warnings.warn("Interop Server died after starting up...")
+ raise PlcException(
+ "Unable to start the Interop Server. Is another Server still running under the same port?")
def _get_client(self):
return Client(self.protocol)
@@ -70,6 +74,28 @@ class PlcDriverManager:
def get_connection(self, url):
return PlcConnection(self._get_client(), url)
+ @contextmanager
+ def connection(self, url):
+ """
+ Context manager to handle connection.
+ """
+ conn = None
+ try:
+ conn = self.get_connection(url)
+ yield conn
+ except PlcException as e:
+ raise Exception(str(e.url))
+ finally:
+ if conn is not None:
+ conn.close()
+
+ def open(self):
+ try:
+ self.transport.open()
+ except TTransportException:
+ self.close() # Handle failure on enter
+ raise PlcException("Unable to connect to the Interop Server, is the Server really running?")
+
def close(self):
print("Closing the Interop Server")
try: