Re: [PATCH] base64 encode all strings before transmitting over xmlrpc

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi,

I realized that I did not quote the original message. Also, my reply
was written too hastily at the end of the day. Here is the correct
patch, tested with a pre and post deep_base64 client.

-Adam

git-diff /home/func-cermaster/func/func/overlord/client.py overlord/client.py
diff --git a/home/func-cermaster/func/func/overlord/client.py
b/overlord/client.py
index b9f8d76..4e924c6 100644
--- a/home/func-cermaster/func/func/overlord/client.py
+++ b/overlord/client.py
@@ -786,7 +786,7 @@ class Overlord(object):
                 if self.interactive:
                     print retval

-                retval = func_utils.deep_base64(retval)
+                retval = func_utils.deep_base64(retval,1)

             except Exception, e:
                 (t, v, tb) = sys.exc_info()




git-diff /home/func-cermaster/func/func/utils.py utils.py
diff --git a/home/func-cermaster/func/func/utils.py b/utils.py
index 011b902..b6e8a6f 100644
--- a/home/func-cermaster/func/func/utils.py
+++ b/utils.py
@@ -168,22 +168,29 @@ def should_log(args):
         return True
     return False

-def deep_base64(ds):
+def deep_base64(ds, mode = 0):
     """
     Run through an arbitrary datastructure of dicts / lists / tuples
     to find all strings and base 64 encode/decode them with
     xmlrpclib.Binary objects.
+
+    mode 0 - flip, 1 - force decode, 2 - force encode
+
     """
     from xmlrpclib import Binary

     if isinstance(ds, Binary):
+        if mode == 2:
+             return ds
         return ds.data

     if isinstance(ds, basestring):
+        if mode == 1:
+             return ds
         return Binary(ds)

     if isinstance(ds, list) or isinstance(ds, tuple):
-        cleaned = map(lambda x: deep_base64(x), ds)
+        cleaned = map(lambda x: deep_base64(x,mode), ds)
         if isinstance(ds, tuple):
             cleaned = tuple(cleaned)
         return cleaned
@@ -191,7 +198,7 @@ def deep_base64(ds):
     if isinstance(ds, dict):
         cleaned = {}
         for k,v in ds.iteritems():
-            cleaned[deep_base64(k)] = deep_base64(v)
+            cleaned[deep_base64(k)] = deep_base64(v,mode)
         return cleaned

     return ds






From: John Eckersberg <jeckersb redhat com>
-------------------------------------
>From http://docs.python.org/library/xmlrpclib.html:

When passing strings, characters special to XML such as <, >, and &
will be automatically escaped. However, it’s the caller’s
responsibility to ensure that the string is free of characters that
aren’t allowed in XML, such as the control characters with ASCII
values between 0 and 31 (except, of course, tab, newline and carriage
return); failing to do this will result in an XML-RPC request that
isn’t well-formed XML. If you have to pass arbitrary strings via
XML-RPC, use the Binary wrapper class
---
 func/minion/server.py   |    9 ++++++++-
 func/overlord/client.py |    4 +++-
 func/utils.py           |   28 ++++++++++++++++++++++++++++
 3 files changed, 39 insertions(+), 2 deletions(-)

diff --git a/func/minion/server.py b/func/minion/server.py
index fbe5c4b..27b4181 100644
--- a/func/minion/server.py
+++ b/func/minion/server.py
@@ -201,7 +201,14 @@ class FuncApiMethod:
             rc = utils.nice_exception(t,v,tb)
         self.logger.debug("Return code for %s: %s" % (self.__name, rc))

-        return rc
+        if self.__name == 'jobs.job_status':
+            # don't double-encode (which ultimately ends up being a no-op,
+            # since deep_base64(deep_base64(foo)) == foo
+            # the return value stored by jobthing is already encoded at this
+            # point
+            return rc
+        else:
+            return futils.deep_base64(rc)


 def serve():
diff --git a/func/overlord/client.py b/func/overlord/client.py
index e011929..4b8c689 100644
--- a/func/overlord/client.py
+++ b/func/overlord/client.py
@@ -649,7 +649,9 @@ class Overlord(object):

                 if self.interactive:
                     print retval
-
+
+                retval = func_utils.deep_base64(retval)
+
             except Exception, e:
                 (t, v, tb) = sys.exc_info()
                 retval = utils.nice_exception(t,v,tb)
diff --git a/func/utils.py b/func/utils.py
index 75ac368..011b902 100644
--- a/func/utils.py
+++ b/func/utils.py
@@ -168,6 +168,34 @@ def should_log(args):
         return True
     return False

+def deep_base64(ds):
+    """
+    Run through an arbitrary datastructure of dicts / lists / tuples
+    to find all strings and base 64 encode/decode them with
+    xmlrpclib.Binary objects.
+    """
+    from xmlrpclib import Binary
+
+    if isinstance(ds, Binary):
+        return ds.data
+
+    if isinstance(ds, basestring):
+        return Binary(ds)
+
+    if isinstance(ds, list) or isinstance(ds, tuple):
+        cleaned = map(lambda x: deep_base64(x), ds)
+        if isinstance(ds, tuple):
+            cleaned = tuple(cleaned)
+        return cleaned
+
+    if isinstance(ds, dict):
+        cleaned = {}
+        for k,v in ds.iteritems():
+            cleaned[deep_base64(k)] = deep_base64(v)
+        return cleaned
+
+    return ds
+
 #################### PROGRESS BAR ##################################
 # The code below can be used for progress bar purposes as we will do
 #it is a combination of http://code.activestate.com/recipes/168639/ and
-- 
1.6.6

_______________________________________________
Func-list mailing list
Func-list@xxxxxxxxxx
https://www.redhat.com/mailman/listinfo/func-list


[Index of Archives]     [Fedora Users]     [Linux Networking]     [Fedora Legacy List]     [Fedora Desktop]     [Fedora SELinux]     [Big List of Linux Books]     [Yosemite News]     [KDE Users]

  Powered by Linux