summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorelie <elie>2014-12-15 22:54:56 +0000
committerelie <elie>2014-12-15 22:54:56 +0000
commitd615014c11f3f696fee01d343138cf2bfd105766 (patch)
tree1b53e6a683302c5ced46fd6c306180c376c55980
parentb1176e5d01801eb451db2c2d017f7811193adee6 (diff)
downloadpysnmp-d615014c11f3f696fee01d343138cf2bfd105766.tar.gz
* asyncio transport made compatible with trollius
* check futures for their cancellation status
-rw-r--r--pysnmp/carrier/asyncio/base.py2
-rw-r--r--pysnmp/carrier/asyncio/dgram/base.py16
-rw-r--r--pysnmp/carrier/asyncio/dgram/udp.py13
-rw-r--r--pysnmp/carrier/asyncio/dispatch.py24
-rw-r--r--pysnmp/entity/rfc3413/asyncio/cmdgen.py8
-rw-r--r--pysnmp/entity/rfc3413/asyncio/ntforg.py9
6 files changed, 46 insertions, 26 deletions
diff --git a/pysnmp/carrier/asyncio/base.py b/pysnmp/carrier/asyncio/base.py
index 192343f..200889b 100644
--- a/pysnmp/carrier/asyncio/base.py
+++ b/pysnmp/carrier/asyncio/base.py
@@ -31,5 +31,3 @@ from pysnmp.carrier.base import AbstractTransport
class AbstractAsyncioTransport(AbstractTransport):
protoTransportDispatcher = AsyncioDispatcher
"""Base Asyncio Transport, to be used with AsyncioDispatcher"""
- def __init__(self):
- self._writeQ = []
diff --git a/pysnmp/carrier/asyncio/dgram/base.py b/pysnmp/carrier/asyncio/dgram/base.py
index c45e358..01a9e30 100644
--- a/pysnmp/carrier/asyncio/dgram/base.py
+++ b/pysnmp/carrier/asyncio/dgram/base.py
@@ -25,14 +25,15 @@
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
# THE POSSIBILITY OF SUCH DAMAGE.
#
+import sys
+import traceback
from pysnmp.carrier.asyncio.base import AbstractAsyncioTransport
from pysnmp.carrier import error
from pysnmp import debug
try:
import asyncio
except ImportError:
- from pysnmp.error import PySnmpError
- raise PySnmpError('The asyncio transport is not available')
+ import trollius as asyncio
loop = asyncio.get_event_loop()
@@ -40,6 +41,9 @@ class DgramAsyncioProtocol(asyncio.DatagramProtocol, AbstractAsyncioTransport):
"""Base Asyncio datagram Transport, to be used with AsyncioDispatcher"""
transport = None
+ def __init__(self, *args, **kwargs):
+ self._writeQ = []
+
def datagram_received(self, datagram, transportAddress):
if self._cbFun is None:
raise error.CarrierError('Unable to call cbFun')
@@ -55,8 +59,8 @@ class DgramAsyncioProtocol(asyncio.DatagramProtocol, AbstractAsyncioTransport):
(transportAddress, debug.hexdump(outgoingMessage)))
try:
self.transport.sendto(outgoingMessage, transportAddress)
- except Exception as err:
- raise error.CarrierError() from err
+ except Exception:
+ raise error.CarrierError(';'.join(traceback.format_exception(*sys.exc_info())))
def connection_lost(self, exc):
debug.logger & debug.flagIO and debug.logger('connection_lost: invoked')
@@ -71,5 +75,5 @@ class DgramAsyncioProtocol(asyncio.DatagramProtocol, AbstractAsyncioTransport):
else:
try:
self.transport.sendto(outgoingMessage, transportAddress)
- except Exception as err:
- raise error.CarrierError() from err
+ except Exception:
+ raise error.CarrierError(';'.join(traceback.format_exception(*sys.exc_info())))
diff --git a/pysnmp/carrier/asyncio/dgram/udp.py b/pysnmp/carrier/asyncio/dgram/udp.py
index d29981a..8b752e3 100644
--- a/pysnmp/carrier/asyncio/dgram/udp.py
+++ b/pysnmp/carrier/asyncio/dgram/udp.py
@@ -25,13 +25,14 @@
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
# THE POSSIBILITY OF SUCH DAMAGE.
#
+import sys
+import traceback
from pysnmp.carrier.asyncio.dgram.base import DgramAsyncioProtocol
from pysnmp.carrier import error
try:
import asyncio
except ImportError:
- from pysnmp.error import PySnmpError
- raise PySnmpError('The asyncio transport is not available')
+ import trollius as asyncio
loop = asyncio.get_event_loop()
@@ -44,16 +45,16 @@ class UdpAsyncioTransport(DgramAsyncioProtocol):
try:
c = loop.create_datagram_endpoint(lambda: self, local_addr=iface)
self._lport = asyncio.async(c)
- except Exception as err:
- raise error.CarrierError() from err
+ except Exception:
+ raise error.CarrierError(';'.join(traceback.format_exception(*sys.exc_info())))
return self
def openServerMode(self, iface=('0.0.0.0', 161)):
try:
c = loop.create_datagram_endpoint(lambda: self, local_addr=iface)
self._lport = asyncio.async(c)
- except Exception as err:
- raise error.CarrierError() from err
+ except Exception:
+ raise error.CarrierError(';'.join(traceback.format_exception(*sys.exc_info())))
return self
def closeTransport(self):
diff --git a/pysnmp/carrier/asyncio/dispatch.py b/pysnmp/carrier/asyncio/dispatch.py
index 1d28b66..1a59db2 100644
--- a/pysnmp/carrier/asyncio/dispatch.py
+++ b/pysnmp/carrier/asyncio/dispatch.py
@@ -25,12 +25,14 @@
# ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
# THE POSSIBILITY OF SUCH DAMAGE.
#
+import sys
+import traceback
from pysnmp.carrier.base import AbstractTransportDispatcher
from pysnmp.error import PySnmpError
try:
import asyncio
except ImportError:
- raise PySnmpError('The asyncio transport is not available')
+ import trollius as asyncio
loop = asyncio.get_event_loop()
@@ -46,7 +48,7 @@ class AsyncioDispatcher(AbstractTransportDispatcher):
@asyncio.coroutine
def handle_timeout(self):
while True:
- yield from asyncio.sleep(self.getTimerResolution())
+ yield asyncio.From(asyncio.sleep(self.getTimerResolution()))
self.handleTimerTick(loop.time())
def runDispatcher(self, timeout=0.0):
@@ -55,8 +57,8 @@ class AsyncioDispatcher(AbstractTransportDispatcher):
loop.run_forever()
except KeyboardInterrupt:
raise
- except Exception as err:
- raise PySnmpError('event loop error') from err
+ except Exception:
+ raise error.PySnmpError(';'.join(traceback.format_exception(*sys.exc_info())))
def registerTransport(self, tDomain, transport):
if self.loopingcall is None and self.getTimerResolution() > 0:
@@ -76,3 +78,17 @@ class AsyncioDispatcher(AbstractTransportDispatcher):
if self.__transportCount == 0 and not self.loopingcall.done():
self.loopingcall.cancel()
self.loopingcall = None
+
+# Trollius or Tulip?
+if not hasattr(asyncio, "From"):
+ exec(
+"""\
+@asyncio.coroutine
+def handle_timeout(self):
+ while True:
+ yield from asyncio.sleep(self.getTimerResolution())
+ self.handleTimerTick(loop.time())
+AsyncioDispatcher.handle_timeout = handle_timeout\
+"""
+ )
+
diff --git a/pysnmp/entity/rfc3413/asyncio/cmdgen.py b/pysnmp/entity/rfc3413/asyncio/cmdgen.py
index 6fcf0f2..9e8d603 100644
--- a/pysnmp/entity/rfc3413/asyncio/cmdgen.py
+++ b/pysnmp/entity/rfc3413/asyncio/cmdgen.py
@@ -32,8 +32,7 @@ from pysnmp.proto.api import v2c
try:
import asyncio
except ImportError:
- from pysnmp.error import PySnmpError
- raise PySnmpError('The asyncio transport is not available')
+ import trollius as asyncio
getNextVarBinds = cmdgen.getNextVarBinds
@@ -41,8 +40,9 @@ class AbstractCommandGenerator:
commandGenerator = None
def _cbFunWithFuture(self, snmpEngine, sendRequestHandle, errorIndication,
- errorStatus, errorIndex, varBinds, cbCtx):
- future = cbCtx
+ errorStatus, errorIndex, varBinds, future):
+ if future.cancelled():
+ return
future.set_result(
(snmpEngine, errorIndication, errorStatus, errorIndex, varBinds)
)
diff --git a/pysnmp/entity/rfc3413/asyncio/ntforg.py b/pysnmp/entity/rfc3413/asyncio/ntforg.py
index 6f352ab..03e927d 100644
--- a/pysnmp/entity/rfc3413/asyncio/ntforg.py
+++ b/pysnmp/entity/rfc3413/asyncio/ntforg.py
@@ -31,12 +31,13 @@ from pyasn1.compat.octets import null
try:
import asyncio
except ImportError:
- from pysnmp.error import PySnmpError
- raise PySnmpError('The asyncio transport is not available')
+ import trollius as asyncio
def _cbFunWithFuture(snmpEngine, sendRequestHandle, errorIndication,
- errorStatus, errorIndex, varBinds, cbCtx):
- cbCtx.set_result(
+ errorStatus, errorIndex, varBinds, future):
+ if future.cancelled():
+ return
+ future.set_result(
(snmpEngine, errorIndication, errorStatus, errorIndex, varBinds)
)