From ba8e5937ab708e1afbe23b5c22dc5236e24e0ac0 Mon Sep 17 00:00:00 2001 From: Johannes Mueller Date: Wed, 18 Nov 2015 19:51:31 +0100 Subject: [PATCH 1/2] Add support for "h" type tag --- txosc/osc.py | 37 ++++++++++++++++++++++++++++++++++++- 1 file changed, 36 insertions(+), 1 deletion(-) diff --git a/txosc/osc.py b/txosc/osc.py index 6e074ce..d25f3f1 100644 --- a/txosc/osc.py +++ b/txosc/osc.py @@ -396,13 +396,46 @@ def fromBinary(data): def __int__(self): return int(self.value) +class Int64Argument(Argument): + """An L{Argument} representing a 64-bit signed integer. + + This is derived from IntArgument of the txosc module. Will place a + pullrequest to txosc soon. + """ + typeTag = "h" + + def _check_type(self): + if type(self.value) not in [int, long]: + raise TypeError("Value %s must be an integer or a long, not a %s." % (self.value, type(self.value).__name__)) + + def toBinary(self): + if self.value >= 1<<63: + raise OverflowError("Integer too large: %d" % self.value) + if self.value < -1<<63: + raise OverflowError("Integer too small: %d" % self.value) + return struct.pack(">i", int(self.value)) + + + @staticmethod + def fromBinary(data): + try: + i = struct.unpack(">q", data[:8])[0] + leftover = data[8:] + except struct.error: + raise OscError("Too few bytes left to get an int from %s." % (data)) + #FIXME: do not raise error and return leftover anyways ? + return Int64Argument(i), leftover + + def __int__(self): + return int(self.value) + class FloatArgument(Argument): """ An L{Argument} representing a 32-bit floating-point value. """ typeTag = "f" - + def _check_type(self): if type(self.value) not in [float, int, long]: raise TypeError("Value %s must be a float, an int or a long, not a %s." % (self.value, type(self.value).__name__)) @@ -614,6 +647,7 @@ def fromBinary(data): float: FloatArgument, str: StringArgument, int: IntArgument, + long: Int64Argument, bool: BooleanArgument, type(None): NullArgument, } @@ -622,6 +656,7 @@ def fromBinary(data): "b": BlobArgument, "f": FloatArgument, "i": IntArgument, + "h": Int64Argument, "s": StringArgument, "t": TimeTagArgument, } From 583e1b07f56580f8ce755d271e8832562c51800f Mon Sep 17 00:00:00 2001 From: Johannes Mueller Date: Wed, 18 Nov 2015 23:31:07 +0100 Subject: [PATCH 2/2] Added unit tests ... ... and fixed some issues :) --- txosc/osc.py | 5 ++++- txosc/test/test_osc.py | 23 +++++++++++++++++++++-- 2 files changed, 25 insertions(+), 3 deletions(-) diff --git a/txosc/osc.py b/txosc/osc.py index d25f3f1..c61af7b 100644 --- a/txosc/osc.py +++ b/txosc/osc.py @@ -413,7 +413,7 @@ def toBinary(self): raise OverflowError("Integer too large: %d" % self.value) if self.value < -1<<63: raise OverflowError("Integer too small: %d" % self.value) - return struct.pack(">i", int(self.value)) + return struct.pack(">q", int(self.value)) @staticmethod @@ -695,6 +695,9 @@ def createArgument(value, type_tag=None): else: # Guess the argument type based on the type of the value + if kind == int: + if value > 1<<31: + return _types[long](value) if kind in _types.keys(): return _types[kind](value) diff --git a/txosc/test/test_osc.py b/txosc/test/test_osc.py index 6b4ccd9..3d1045a 100644 --- a/txosc/test/test_osc.py +++ b/txosc/test/test_osc.py @@ -34,12 +34,13 @@ class TestArgumentCreation(unittest.TestCase): """ Test the L{osc.CreateArgument} function. """ - + def testCreateFromValue(self): self.assertEquals(type(osc.createArgument(True)), osc.BooleanArgument) self.assertEquals(type(osc.createArgument(False)), osc.BooleanArgument) self.assertEquals(type(osc.createArgument(None)), osc.NullArgument) self.assertEquals(type(osc.createArgument(123)), osc.IntArgument) + self.assertEquals(type(osc.createArgument(1<<32+1)), osc.Int64Argument) self.assertEquals(type(osc.createArgument(3.14156)), osc.FloatArgument) # Unicode is not supported. self.assertRaises(osc.OscError, osc.createArgument, u'test') @@ -50,6 +51,7 @@ def testCreateFromTypeTag(self): self.assertEquals(type(osc.createArgument(123, "N")), osc.NullArgument) self.assertEquals(type(osc.createArgument(123, "I")), osc.ImpulseArgument) self.assertEquals(type(osc.createArgument(123, "i")), osc.IntArgument) + self.assertEquals(type(osc.createArgument(123, "h")), osc.Int64Argument) self.assertEquals(type(osc.createArgument(123, "f")), osc.FloatArgument) self.assertRaises(osc.OscError, osc.createArgument, 123, "?") @@ -145,13 +147,30 @@ def test(value): test(1) test(-1) test(1<<31-1) - test(-1<<31) + test(-1<<31) self.assertRaises(osc.OscError, osc.IntArgument.fromBinary, "\0\0\0") # invalid value def testIntOverflow(self): self.assertRaises(OverflowError, osc.IntArgument(1<<31).toBinary) self.assertRaises(OverflowError, osc.IntArgument((-1<<31) - 1).toBinary) +class TestInt64Argument(unittest.TestCase): + + def testToAndFromBinary(self): + def test(value): + int_arg = osc.Int64Argument.fromBinary(osc.Int64Argument(value).toBinary())[0] + self.assertEquals(int_arg.value, value) + test(0) + test(1) + test(-1) + test(1<<63-1) + test(-1<<63) + self.assertRaises(osc.OscError, osc.IntArgument.fromBinary, "\0\0\0") # invalid value + + def testIntOverflow(self): + self.assertRaises(OverflowError, osc.IntArgument(1<<63).toBinary) + self.assertRaises(OverflowError, osc.IntArgument((-1<<63) - 1).toBinary) + class TestColorArgument(unittest.TestCase):