On Fri, 23 Aug 2013 13:42:54 +0900 (JST)
yamam...@valinux.co.jp (YAMAMOTO Takashi) wrote:

>> On Fri, 23 Aug 2013 12:18:31 +0900 (JST)
>> yamam...@valinux.co.jp (YAMAMOTO Takashi) wrote:
>> 
>>>> On Fri, 16 Aug 2013 15:29:22 +0900
>>>> YAMAMOTO Takashi <yamam...@valinux.co.jp> wrote:
>>>> 
>>>>> Signed-off-by: YAMAMOTO Takashi <yamam...@valinux.co.jp>
>>>>> ---
>>>>>  ryu/ofproto/ofproto_v1_0_parser.py | 6 +++++-
>>>>>  1 file changed, 5 insertions(+), 1 deletion(-)
>>>>> 
>>>>> diff --git a/ryu/ofproto/ofproto_v1_0_parser.py 
>>>>> b/ryu/ofproto/ofproto_v1_0_parser.py
>>>>> index 3fae86d..e1951c8 100644
>>>>> --- a/ryu/ofproto/ofproto_v1_0_parser.py
>>>>> +++ b/ryu/ofproto/ofproto_v1_0_parser.py
>>>>> @@ -18,6 +18,7 @@ import struct
>>>>>  import binascii
>>>>>  
>>>>>  from ofproto_parser import StringifyMixin, MsgBase, msg_pack_into, 
>>>>> msg_str_attr
>>>>> +from ryu.lib import addrconv
>>>>>  from ryu.lib import mac
>>>>>  from . import ofproto_parser
>>>>>  from . import ofproto_v1_0
>>>>> @@ -86,6 +87,9 @@ class 
>>>>> OFPPhyPort(ofproto_parser.namedtuple('OFPPhyPort', (
>>>>>      def parser(cls, buf, offset):
>>>>>          port = struct.unpack_from(ofproto_v1_0.OFP_PHY_PORT_PACK_STR,
>>>>>                                    buf, offset)
>>>>> +        i = cls._fields.index('hw_addr')
>>>>> +        port = list(port)
>>>>> +        port[i] = addrconv.mac.bin_to_text(port[i])
>>>>>          return cls(*port)
>>>> 
>>>> Can we use unicode type here? Then _encode_value() in stringfy.py just
>>> 
>>> are you talking about "name", not "hw_addr"?
>> 
>> hw_addr.
> 
> then i'm not sure if i understand what you mean.
> do you mean to use different python types (str vs unicode) to
> tell the encoder do base64 or not?  it can work for encoding
> but not for decoding.

_JSON_FORMATER thing in this patchset describes the type of members in
a class. Then you can know how to decode.

I thought that we could use unicode for 'string' type however looks
like it needs more changes than I want. Scratch that.

I like to simply use 'type' attribute rather than allowing own
encoder/decoder. We use JSON so it's just about string or binary. I
like a simpler like the following. I don't like to use class attribute
though. I prefer to use the attribute of each member.


diff --git a/ryu/lib/stringify.py b/ryu/lib/stringify.py
index 5766f4a..00b2558 100644
--- a/ryu/lib/stringify.py
+++ b/ryu/lib/stringify.py
@@ -43,6 +43,7 @@ _RESERVED_KEYWORD = dir(__builtin__)
 
 _mapdict = lambda f, d: dict([(k, f(v)) for k, v in d.items()])
 _mapdict_key = lambda f, d: dict([(f(k), v) for k, v in d.items()])
+_mapdict_kv = lambda f, d: dict([(k, f(k, v)) for k, v in d.items()])
 
 
 class StringifyMixin(object):
@@ -78,9 +79,17 @@ class StringifyMixin(object):
         return False
 
     @classmethod
-    def _encode_value(cls, v, encode_string=base64.b64encode):
-        encode = lambda x: cls._encode_value(x, encode_string)
-        if isinstance(v, (bytes, unicode)):
+    def _is_string_type(cls, k):
+        if hasattr(cls, '_STRING') and k in cls._STRING:
+            return True
+        return False
+
+    @classmethod
+    def _encode_value(cls, k, v, encode_string=base64.b64encode):
+        encode = lambda x: cls._encode_value(k, x, encode_string)
+        if cls._is_string_type(k):
+            json_value = v.encode('utf')
+        elif isinstance(v, (bytes, unicode)):
             json_value = encode_string(v)
         elif isinstance(v, list):
             json_value = map(encode, v)
@@ -101,9 +110,9 @@ class StringifyMixin(object):
         """returns an object to feed json.dumps()
         """
         dict_ = {}
-        encode = lambda x: self._encode_value(x, encode_string)
+        encode = lambda k, x: self._encode_value(k, x, encode_string)
         for k, v in obj_attrs(self):
-            dict_[k] = encode(v)
+            dict_[k] = encode(k, v)
         return {self.__class__.__name__: dict_}
 
     @classmethod
@@ -121,9 +130,11 @@ class StringifyMixin(object):
             return obj_cls.from_jsondict(v)
 
     @classmethod
-    def _decode_value(cls, json_value, decode_string=base64.b64decode):
-        decode = lambda x: cls._decode_value(x, decode_string)
-        if isinstance(json_value, (bytes, unicode)):
+    def _decode_value(cls, k, json_value, decode_string=base64.b64decode):
+        decode = lambda x: cls._decode_value(k, x, decode_string)
+        if cls._is_string_type(k):
+            v = json_value
+        elif isinstance(json_value, (bytes, unicode)):
             v = decode_string(json_value)
         elif isinstance(json_value, list):
             v = map(decode, json_value)
@@ -155,8 +166,8 @@ class StringifyMixin(object):
                       **additional_args):
         """create an instance from a result of json.loads()
         """
-        decode = lambda x: cls._decode_value(x, decode_string)
-        kwargs = cls._restore_args(_mapdict(decode, dict_))
+        decode = lambda k, x: cls._decode_value(k, x, decode_string)
+        kwargs = cls._restore_args(_mapdict_kv(decode, dict_))
         try:
             return cls(**dict(kwargs, **additional_args))
         except TypeError:
diff --git a/ryu/ofproto/ofproto_v1_0_parser.py 
b/ryu/ofproto/ofproto_v1_0_parser.py
index 3fae86d..897efe4 100644
--- a/ryu/ofproto/ofproto_v1_0_parser.py
+++ b/ryu/ofproto/ofproto_v1_0_parser.py
@@ -18,6 +18,7 @@ import struct
 import binascii
 
 from ofproto_parser import StringifyMixin, MsgBase, msg_pack_into, msg_str_attr
+from ryu.lib import addrconv
 from ryu.lib import mac
 from . import ofproto_parser
 from . import ofproto_v1_0
@@ -82,10 +83,15 @@ class OFPPhyPort(ofproto_parser.namedtuple('OFPPhyPort', (
         'port_no', 'hw_addr', 'name', 'config', 'state', 'curr', 'advertised',
         'supported', 'peer'))):
 
+    _STRING = ('hw_addr')
+
     @classmethod
     def parser(cls, buf, offset):
         port = struct.unpack_from(ofproto_v1_0.OFP_PHY_PORT_PACK_STR,
                                   buf, offset)
+        i = cls._fields.index('hw_addr')
+        port = list(port)
+        port[i] = addrconv.mac.bin_to_text(port[i])
         return cls(*port)
 
 
@@ -2109,7 +2115,7 @@ class OFPPortMod(MsgBase):
     def _serialize_body(self):
         msg_pack_into(ofproto_v1_0.OFP_PORT_MOD_PACK_STR,
                       self.buf, ofproto_v1_0.OFP_HEADER_SIZE,
-                      self.port_no, self.hw_addr,
+                      self.port_no, addrconv.mac.text_to_bin(self.hw_addr),
                       self.config, self.mask, self.advertise)
 
 
diff --git 
a/ryu/tests/unit/ofproto/json/of10/1-6-ofp_switch_features.packet.json 
b/ryu/tests/unit/ofproto/json/of10/1-6-ofp_switch_features.packet.json
index 4084ba5..aa8180e 100644
--- a/ryu/tests/unit/ofproto/json/of10/1-6-ofp_switch_features.packet.json
+++ b/ryu/tests/unit/ofproto/json/of10/1-6-ofp_switch_features.packet.json
@@ -11,7 +11,7 @@
                "advertised": 640, 
                "config": 0, 
                "curr": 648, 
-               "hw_addr": "8gukffjq", 
+               "hw_addr": "f2:0b:a4:7d:f8:ea", 
                "name": "UG9ydAYAAAAAAAAAAAAAAA==", 
                "peer": 648, 
                "port_no": 6, 
@@ -24,7 +24,7 @@
                "advertised": 640, 
                "config": 0, 
                "curr": 648, 
-               "hw_addr": "8guk0D9w", 
+               "hw_addr": "f2:0b:a4:d0:3f:70", 
                "name": "UG9ydAcAAAAAAAAAAAAAAA==", 
                "peer": 648, 
                "port_no": 7, 
diff --git a/ryu/tests/unit/ofproto/test_parser_v10.py 
b/ryu/tests/unit/ofproto/test_parser_v10.py
index 29e7d28..81b96de 100644
--- a/ryu/tests/unit/ofproto/test_parser_v10.py
+++ b/ryu/tests/unit/ofproto/test_parser_v10.py
@@ -20,6 +20,7 @@ import logging
 from nose.tools import *
 from ryu.ofproto.ofproto_v1_0_parser import *
 from ryu.ofproto import ofproto_v1_0_parser
+from ryu.lib import addrconv
 
 
 LOG = logging.getLogger('test_ofproto_v10')
@@ -33,7 +34,7 @@ class TestOFPPhyPort(unittest.TestCase):
     # '!H6s16sIIIIII'... port_no, hw_addr, name, config, state
     #                    curr, advertised, supported, peer
     port_no = {'buf': '\xe7\x6b', 'val': 59243}
-    hw_addr = '\x52\x54\x54\x10\x20\x99'
+    hw_addr = '52:54:54:10:20:99'
     name = 'name'.ljust(16)
     config = {'buf': '\x84\xb6\x8c\x53', 'val': 2226555987}
     state = {'buf': '\x64\x07\xfb\xc9', 'val': 1678244809}
@@ -43,7 +44,7 @@ class TestOFPPhyPort(unittest.TestCase):
     peer = {'buf': '\xa4\x5b\x8b\xed', 'val': 2757463021}
 
     buf = port_no['buf'] \
-        + hw_addr \
+        + addrconv.mac.text_to_bin(hw_addr) \
         + name \
         + config['buf'] \
         + state['buf'] \
@@ -3384,7 +3385,7 @@ class TestOFPSwitchFeatures(unittest.TestCase):
         # '!H6s16sIIIIII'... port_no, hw_addr, name, config, state
         #                    curr, advertised, supported, peer
         port_no = {'buf': '\xe7\x6b', 'val': 59243}
-        hw_addr = '\x3c\xd1\x2b\x8d\x3f\xd6'
+        hw_addr = '3c:d1:2b:8d:3f:d6'
         name = 'name'.ljust(16)
         config = {'buf': '\x84\xb6\x8c\x53', 'val': 2226555987}
         state = {'buf': '\x64\x07\xfb\xc9', 'val': 1678244809}
@@ -3404,7 +3405,7 @@ class TestOFPSwitchFeatures(unittest.TestCase):
             + capabilities['buf'] \
             + actions['buf'] \
             + port_no['buf'] \
-            + hw_addr \
+            + addrconv.mac.text_to_bin(hw_addr) \
             + name \
             + config['buf'] \
             + state['buf'] \
@@ -3433,7 +3434,7 @@ class TestOFPSwitchFeatures(unittest.TestCase):
         # port
         port = res.ports[port_no['val']]
         eq_(port_no['val'], port.port_no)
-        eq_(hw_addr, port.hw_addr)
+        eq_(hw_addr, hw_addr)
         eq_(name, port.name)
         eq_(config['val'], port.config)
         eq_(state['val'], port.state)
@@ -3480,7 +3481,7 @@ class TestOFPPortStatus(unittest.TestCase):
         reason = {'buf': '\x71', 'val': 113}
         zfill = '\x00' * 7
         port_no = {'buf': '\x48\xd8', 'val': 18648}
-        hw_addr = '\x41\xf7\xa3\x52\x8f\x6b'
+        hw_addr = '41:f7:a3:52:8f:6b'
         name = 'name'.ljust(16)
         config = {'buf': '\xae\x73\x90\xec', 'val': 2926809324}
         state = {'buf': '\x41\x37\x32\x1d', 'val': 1094136349}
@@ -3496,7 +3497,7 @@ class TestOFPPortStatus(unittest.TestCase):
             + reason['buf'] \
             + zfill \
             + port_no['buf'] \
-            + hw_addr \
+            + addrconv.mac.text_to_bin(hw_addr) \
             + name \
             + config['buf'] \
             + state['buf'] \

------------------------------------------------------------------------------
Introducing Performance Central, a new site from SourceForge and 
AppDynamics. Performance Central is your source for news, insights, 
analysis and resources for efficient Application Performance Management. 
Visit us today!
http://pubads.g.doubleclick.net/gampad/clk?id=48897511&iu=/4140/ostg.clktrk
_______________________________________________
Ryu-devel mailing list
Ryu-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/ryu-devel

Reply via email to