You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@qpid.apache.org by kp...@apache.org on 2020/07/13 17:58:41 UTC

[qpid-interop-test] branch master updated: QPIDIT-139: Updated tests for Python3. Updated shims to receive and send base64-encoded binary, as JSON cannot send binary. Other tidy-ups and small optimizations.

This is an automated email from the ASF dual-hosted git repository.

kpvdr pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/qpid-interop-test.git


The following commit(s) were added to refs/heads/master by this push:
     new 0ee6a0a  QPIDIT-139: Updated tests for Python3. Updated shims to receive and send base64-encoded binary, as JSON cannot send binary. Other tidy-ups and small optimizations.
0ee6a0a is described below

commit 0ee6a0ab67c15e350a23bde1b3212f3f6ce48426
Author: Kim van der Riet <kp...@apache.org>
AuthorDate: Mon Jul 13 13:58:22 2020 -0400

    QPIDIT-139: Updated tests for Python3. Updated shims to receive and send base64-encoded binary, as JSON cannot send binary. Other tidy-ups and small optimizations.
---
 .gitignore                                         |   1 +
 config.sh.in                                       |   4 +-
 .../src/amqp_types_test/Receiver/Receiver.cs       | 262 ++++---
 .../src/amqp_types_test/Sender/Sender.cs           |  12 +-
 .../interop_test/jms_hdrs_props_test/Receiver.java |  17 +-
 .../interop_test/jms_hdrs_props_test/Sender.java   |  37 +-
 .../interop_test/jms_messages_test/Receiver.java   |  20 +-
 .../interop_test/jms_messages_test/Sender.java     |  41 +-
 shims/qpid-proton-cpp/src/CMakeLists.txt           |   2 +
 shims/qpid-proton-cpp/src/qpidit/Base64.cpp        | 125 ++++
 shims/qpid-proton-cpp/src/qpidit/Base64.hpp        |  32 +
 shims/qpid-proton-cpp/src/qpidit/QpidItErrors.cpp  |   4 +-
 shims/qpid-proton-cpp/src/qpidit/QpidItErrors.hpp  |   2 +-
 .../src/qpidit/amqp_complex_types_test/Common.cpp  |   3 -
 .../src/qpidit/amqp_complex_types_test/Common.hpp  |   1 -
 .../qpidit/amqp_large_content_test/Receiver.cpp    |   9 +-
 .../src/qpidit/amqp_large_content_test/Sender.cpp  |  18 +-
 .../src/qpidit/amqp_types_test/Receiver.cpp        | 127 ++--
 .../src/qpidit/amqp_types_test/Receiver.hpp        |   3 -
 .../src/qpidit/amqp_types_test/Sender.cpp          | 152 +---
 .../src/qpidit/amqp_types_test/Sender.hpp          |   9 -
 .../src/qpidit/jms_hdrs_props_test/Receiver.cpp    |  41 +-
 .../src/qpidit/jms_hdrs_props_test/Sender.cpp      |  50 +-
 .../src/qpidit/jms_hdrs_props_test/Sender.hpp      |   2 +-
 .../src/qpidit/jms_messages_test/Receiver.cpp      |  35 +-
 .../src/qpidit/jms_messages_test/Sender.cpp        |  45 +-
 .../src/qpidit/jms_messages_test/Sender.hpp        |   2 +-
 .../src/amqp_complex_types_test/Common.py          |   9 +-
 .../src/amqp_complex_types_test/Receiver.py        |  27 +-
 .../src/amqp_types_test/Receiver.py                |  46 +-
 .../src/amqp_types_test/Sender.py                  |  70 +-
 .../src/jms_hdrs_props_test/Receiver.py            |  32 +-
 .../src/jms_hdrs_props_test/Sender.py              |  15 +-
 .../src/jms_messages_test/Receiver.py              |  29 +-
 .../src/jms_messages_test/Sender.py                |  13 +-
 shims/rhea-js/amqp_types_test/Receiver.js          |  21 +-
 shims/rhea-js/amqp_types_test/Sender.js            |  28 +-
 .../amqp_complex_types_test.array.json             |   2 +-
 .../qpid_interop_test/amqp_complex_types_test.py   |  17 +-
 .../amqp_complex_types_test_generator.py           | 771 +++++++++++----------
 .../qpid_interop_test/amqp_large_content_test.py   |   9 +-
 src/python/qpid_interop_test/amqp_types_test.py    | 149 +---
 .../qpid_interop_test/jms_hdrs_props_test.py       |  52 +-
 src/python/qpid_interop_test/jms_messages_test.py  |  40 +-
 src/python/qpid_interop_test/qit_broker_props.py   |  20 +-
 src/python/qpid_interop_test/qit_common.py         |  15 +-
 src/python/qpid_interop_test/qit_errors.py         |   2 -
 src/python/qpid_interop_test/qit_jms_types.py      |   2 +-
 src/python/qpid_interop_test/qit_shim.py           |  23 +-
 src/python/qpid_interop_test/qit_xunit_log.py      |   5 +-
 src/python/qpid_interop_test/run_all.py            |   2 +-
 51 files changed, 1165 insertions(+), 1290 deletions(-)

diff --git a/.gitignore b/.gitignore
index c52634a..cac0800 100644
--- a/.gitignore
+++ b/.gitignore
@@ -19,6 +19,7 @@
 /target/
 /build/
 /docs/users-guide.html
+/src/python/qpid_interop_test/amqp_complex_types_test_data.*
 .project
 .cproject
 .pydevproject
diff --git a/config.sh.in b/config.sh.in
index 18b34a7..3ab336c 100644
--- a/config.sh.in
+++ b/config.sh.in
@@ -37,8 +37,8 @@ if [[ "${py3_found_str#*-}" == "NOTFOUND" ]]; then
 else
     export PYTHON3PATH=@CMAKE_INSTALL_PREFIX@/lib64/proton/bindings/python3:@CMAKE_INSTALL_PREFIX@/lib/@PYTHON3_SITE_DIR_NAME@/site-packages:@CMAKE_INSTALL_PREFIX@/libexec/qpid_interop_test/shims/qpid-proton-python
 fi
-# To run the main program use python 2
-export PYTHONPATH=$PYTHON2PATH
+# To run the main program use python 3
+export PYTHONPATH=$PYTHON3PATH
 
 export LD_LIBRARY_PATH=@CMAKE_INSTALL_PREFIX@/lib64:$LD_LIBRARY_PATH
 export PATH=@CMAKE_INSTALL_PREFIX@/lib/@PYTHON_DIR_NAME@/site-packages/qpid_interop_test:$PATH
diff --git a/shims/amqpnetlite/src/amqp_types_test/Receiver/Receiver.cs b/shims/amqpnetlite/src/amqp_types_test/Receiver/Receiver.cs
index 0443606..abfb269 100644
--- a/shims/amqpnetlite/src/amqp_types_test/Receiver/Receiver.cs
+++ b/shims/amqpnetlite/src/amqp_types_test/Receiver/Receiver.cs
@@ -216,152 +216,126 @@ namespace Qpidit
             }
 
             liteType = messageValue.GetType().Name;
-            if (liteType == "List")
-            {
-                qpiditType = "list";
-                valueList = new List<MessageValue>();
-                List list = (List)messageValue;
-                foreach (var item in list)
-                {
-                    MessageValue itemValue = new Qpidit.MessageValue(item);
-                    itemValue.Decode();
-                    valueList.Add(itemValue);
-                }
-            }
-            else if (liteType == "Map")
-            {
-                qpiditType = "map";
-                valueMapKeys = new List<MessageValue>();
-                valueMapValues = new List<MessageValue>();
-                Map map = (Map)messageValue;
-                foreach (var key in map.Keys)
-                {
-                    MessageValue valueKey = new Qpidit.MessageValue(key);
-                    valueKey.Decode();
-                    MessageValue valueValue = new Qpidit.MessageValue(map[key]);
-                    valueValue.Decode();
-                    valueMapKeys.Add(valueKey);
-                    valueMapValues.Add(valueValue);
-                }
+            if (liteType == "List" || liteType == "Map") {
+                        throw new ApplicationException(String.Format(
+                            "Unsupported complex AMQP type {0}", liteType));
             }
-            else
+
+            //Console.WriteLine("MessageValue singleton type : {0}", liteType);
+            switch (liteType)
             {
-                //Console.WriteLine("MessageValue singleton type : {0}", liteType);
-                switch (liteType)
-                {
-                    case "Boolean":
-                        qpiditType = "boolean";
-                        valueString = (Boolean)messageValue ? "True" : "False";
-                        break;
-                    case "Byte":
-                        qpiditType = "ubyte";
-                        valueString = String.Format("0x{0:x}", (Byte)messageValue);
-                        break;
-                    case "UInt16":
-                        qpiditType = "ushort";
-                        valueString = String.Format("0x{0:x}", (UInt16)messageValue);
-                        break;
-                    case "UInt32":
-                        qpiditType = "uint";
-                        valueString = String.Format("0x{0:x}", (UInt32)messageValue);
-                        break;
-                    case "UInt64":
-                        qpiditType = "ulong";
-                        valueString = String.Format("0x{0:x}", (UInt64)messageValue);
-                        break;
-                    case "SByte":
-                        qpiditType = "byte";
-                        SByte mySbyte = (SByte)messageValue;
-                        if (mySbyte >= 0)
-                        {
-                            valueString = String.Format("0x{0:x}", mySbyte);
-                        }
-                        else
-                        {
-                            mySbyte = (SByte) (-mySbyte);
-                            valueString = String.Format("-0x{0:x}", mySbyte);
-                        }
-                        break;
-                    case "Int16":
-                        qpiditType = "short";
-                        Int16 myInt16 = (Int16)messageValue;
-                        if (myInt16 >= 0)
-                        {
-                            valueString = String.Format("0x{0:x}", myInt16);
-                        }
-                        else
-                        {
-                            myInt16 = (Int16)(-myInt16);
-                            valueString = String.Format("-0x{0:x}", myInt16);
-                        }
-                        break;
-                    case "Int32":
-                        qpiditType = "int";
-                        Int32 myInt32 = (Int32)messageValue;
-                        if (myInt32 >= 0)
-                        {
-                            valueString = String.Format("0x{0:x}", myInt32);
-                        }
-                        else
-                        {
-                            myInt32 = (Int32)(-myInt32);
-                            valueString = String.Format("-0x{0:x}", myInt32);
-                        }
-                        break;
-                    case "Int64":
-                        qpiditType = "long";
-                        Int64 myInt64 = (Int64)messageValue;
-                        if (myInt64 >= 0)
-                        {
-                            valueString = String.Format("0x{0:x}", myInt64);
-                        }
-                        else
-                        {
-                            myInt64 = (Int64)(-myInt64);
-                            valueString = String.Format("-0x{0:x}", myInt64);
-                        }
-                        break;
-                    case "Single":
-                        byte[] sbytes = BitConverter.GetBytes((Single)messageValue);
-                        qpiditType = "float";
-                        valueString = "0x" + BytesReversedToString(sbytes);
-                        break;
-                    case "Double":
-                        byte[] dbytes = BitConverter.GetBytes((Double)messageValue);
-                        qpiditType = "double";
-                        valueString = "0x" + BytesReversedToString(dbytes);
-                        break;
-                    case "DateTime":
-                        // epochTicks is the number of 100uSec ticks between 01/01/0001
-                        // and 01/01/1970. Used to adjust between DateTime and unix epoch.
-                        const long epochTicks = 621355968000000000;
-                        byte[] dtbytes = BitConverter.GetBytes(
-                            (((DateTime)messageValue).Ticks - epochTicks) / TimeSpan.TicksPerMillisecond);
-                        qpiditType = "timestamp";
-                        valueString = "0x" + BytesReversedToString(dtbytes, true);
-                        break;
-                    case "Guid":
-                        qpiditType = "uuid";
-                        valueString = messageValue.ToString();
-                        break;
-                    case "Byte[]":
-                        qpiditType = "binary";
-                        byte[] binstr = (byte[])messageValue;
-                        valueString = SerializeBytes(binstr);
-                        break;
-                    case "String":
-                        qpiditType = "string";
-                        valueString = SerializeString(messageValue);
-                        break;
-                    case "Symbol":
-                        qpiditType = "symbol";
-                        valueString = SerializeString(messageValue);
-                        break;
-                    default:
-                        qpiditType = "unknown";
-                        valueString = String.Format("Unknown AMQP type: {0}", liteType);
-                        throw new ApplicationException(valueString);
-                }
+                case "Boolean":
+                    qpiditType = "boolean";
+                    valueString = (Boolean)messageValue ? "True" : "False";
+                    break;
+                case "Byte":
+                    qpiditType = "ubyte";
+                    valueString = String.Format("0x{0:x}", (Byte)messageValue);
+                    break;
+                case "UInt16":
+                    qpiditType = "ushort";
+                    valueString = String.Format("0x{0:x}", (UInt16)messageValue);
+                    break;
+                case "UInt32":
+                    qpiditType = "uint";
+                    valueString = String.Format("0x{0:x}", (UInt32)messageValue);
+                    break;
+                case "UInt64":
+                    qpiditType = "ulong";
+                    valueString = String.Format("0x{0:x}", (UInt64)messageValue);
+                    break;
+                case "SByte":
+                    qpiditType = "byte";
+                    SByte mySbyte = (SByte)messageValue;
+                    if (mySbyte >= 0)
+                    {
+                        valueString = String.Format("0x{0:x}", mySbyte);
+                    }
+                    else
+                    {
+                        mySbyte = (SByte) (-mySbyte);
+                        valueString = String.Format("-0x{0:x}", mySbyte);
+                    }
+                    break;
+                case "Int16":
+                    qpiditType = "short";
+                    Int16 myInt16 = (Int16)messageValue;
+                    if (myInt16 >= 0)
+                    {
+                        valueString = String.Format("0x{0:x}", myInt16);
+                    }
+                    else
+                    {
+                        myInt16 = (Int16)(-myInt16);
+                        valueString = String.Format("-0x{0:x}", myInt16);
+                    }
+                    break;
+                case "Int32":
+                    qpiditType = "int";
+                    Int32 myInt32 = (Int32)messageValue;
+                    if (myInt32 >= 0)
+                    {
+                        valueString = String.Format("0x{0:x}", myInt32);
+                    }
+                    else
+                    {
+                        myInt32 = (Int32)(-myInt32);
+                        valueString = String.Format("-0x{0:x}", myInt32);
+                    }
+                    break;
+                case "Int64":
+                    qpiditType = "long";
+                    Int64 myInt64 = (Int64)messageValue;
+                    if (myInt64 >= 0)
+                    {
+                        valueString = String.Format("0x{0:x}", myInt64);
+                    }
+                    else
+                    {
+                        myInt64 = (Int64)(-myInt64);
+                        valueString = String.Format("-0x{0:x}", myInt64);
+                    }
+                    break;
+                case "Single":
+                    byte[] sbytes = BitConverter.GetBytes((Single)messageValue);
+                    qpiditType = "float";
+                    valueString = "0x" + BytesReversedToString(sbytes);
+                    break;
+                case "Double":
+                    byte[] dbytes = BitConverter.GetBytes((Double)messageValue);
+                    qpiditType = "double";
+                    valueString = "0x" + BytesReversedToString(dbytes);
+                    break;
+                case "DateTime":
+                    // epochTicks is the number of 100uSec ticks between 01/01/0001
+                    // and 01/01/1970. Used to adjust between DateTime and unix epoch.
+                    const long epochTicks = 621355968000000000;
+                    byte[] dtbytes = BitConverter.GetBytes(
+                        (((DateTime)messageValue).Ticks - epochTicks) / TimeSpan.TicksPerMillisecond);
+                    qpiditType = "timestamp";
+                    valueString = "0x" + BytesReversedToString(dtbytes, true);
+                    break;
+                case "Guid":
+                    qpiditType = "uuid";
+                    valueString = messageValue.ToString();
+                    break;
+                case "Byte[]":
+                    qpiditType = "binary";
+                    byte[] binstr = (byte[])messageValue;
+                    valueString = Convert.ToBase64String(binstr);
+                    break;
+                case "String":
+                    qpiditType = "string";
+                    valueString = SerializeString(messageValue);
+                    break;
+                case "Symbol":
+                    qpiditType = "symbol";
+                    valueString = SerializeString(messageValue);
+                    break;
+                default:
+                    qpiditType = "unknown";
+                    valueString = String.Format("Unknown AMQP type: {0}", liteType);
+                    throw new ApplicationException(valueString);
             }
         }
     }
diff --git a/shims/amqpnetlite/src/amqp_types_test/Sender/Sender.cs b/shims/amqpnetlite/src/amqp_types_test/Sender/Sender.cs
index 979900f..0545c66 100644
--- a/shims/amqpnetlite/src/amqp_types_test/Sender/Sender.cs
+++ b/shims/amqpnetlite/src/amqp_types_test/Sender/Sender.cs
@@ -172,17 +172,11 @@ namespace Qpidit
                         qpiditType = "symbol";
                         break;
                     case "Array":
-                        qpiditType = "list";
-                        break;
                     case "ArrayList":
-                        qpiditType = "list";
-                        break;
                     case "Dictionary":
-                        qpiditType = "map";
-                        break;
                     case "Dictionary`2":
-                        qpiditType = "map";
-                        break;
+                         throw new ApplicationException(String.Format(
+                            "Unsupported complex AMQP type {0}", typename));
                     default:
                         throw new ApplicationException(String.Format(
                             "Can not translate system type {0} to a QpidIT type", typename));
@@ -372,7 +366,7 @@ namespace Qpidit
                     case "binary":
                         // TODO: fix this
                         value = (string)baseValue;
-                        byte[] binval = Encoding.ASCII.GetBytes(value);
+                        byte[] binval = Convert.FromBase64String(value);
                         valueDirect = binval;
                         break;
                     case "string":
diff --git a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Receiver.java b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Receiver.java
index 00d2e4c..1b06df7 100644
--- a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Receiver.java
+++ b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Receiver.java
@@ -24,6 +24,7 @@ import java.io.StringWriter;
 import java.text.SimpleDateFormat;
 import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.Base64;
 import java.util.Collections;
 import java.util.Enumeration;
 import java.util.List;
@@ -210,15 +211,15 @@ public class Receiver {
                 byte[] bytesBuff = new byte[65536];
                 int numBytesRead = ((BytesMessage)message).readBytes(bytesBuff);
                 if (numBytesRead >= 0) {
-                    jasonTestValuesArrayBuilder.add(new String(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
+                    jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
                 } else {
                     // NOTE: For this case, an empty byte array has nothing to return
-                    jasonTestValuesArrayBuilder.add(new String());
+                    jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString("".getBytes()));
                 }
             }
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((BytesMessage)message).readChar()));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((BytesMessage)message).readChar()).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((BytesMessage)message).readDouble());
@@ -269,10 +270,10 @@ public class Receiver {
             jasonTestValuesArrayBuilder.add(formatByte(((MapMessage)message).getByte(name)));
             break;
         case "bytes":
-            jasonTestValuesArrayBuilder.add(new String(((MapMessage)message).getBytes(name)));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString((((MapMessage)message).getBytes(name))));
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((MapMessage)message).getChar(name)));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((MapMessage)message).getChar(name)).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((MapMessage)message).getDouble(name));
@@ -319,14 +320,14 @@ public class Receiver {
             byte[] bytesBuff = new byte[65536];
             int numBytesRead = ((StreamMessage)message).readBytes(bytesBuff);
             if (numBytesRead >= 0) {
-                jasonTestValuesArrayBuilder.add(new String(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
+                jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
             } else {
                 System.out.println("StreamMessage.readBytes() returned " + numBytesRead);
                 jasonTestValuesArrayBuilder.add("<bytes error>");
             }
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((StreamMessage)message).readChar()));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((StreamMessage)message).readChar()).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((StreamMessage)message).readDouble());
@@ -423,7 +424,7 @@ public class Receiver {
     protected void addMessageHeaderByteArray(String headerName, byte[] value) {
         if (value != null) {
             JsonObjectBuilder valueMap = Json.createObjectBuilder();
-            valueMap.add("bytes", new String(value));
+            valueMap.add("bytes", Base64.getEncoder().encodeToString(value));
             _jsonMessageHeaderMapBuilder.add(headerName, valueMap);
         }        
     }
diff --git a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Sender.java b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Sender.java
index 2f38991..15d14f5 100644
--- a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Sender.java
+++ b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_hdrs_props_test/Sender.java
@@ -20,7 +20,9 @@ import java.io.Serializable;
 import java.io.StringReader;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
+import java.nio.ByteBuffer;
 import java.util.ArrayList;
+import java.util.Base64;
 import java.util.Collections;
 import java.util.List;
 import javax.jms.BytesMessage;
@@ -185,7 +187,7 @@ public class Sender {
                 if (subMapKey.compareTo("string") == 0) {
                     msg.setJMSCorrelationID(subMapVal);
                 } else if (subMapKey.compareTo("bytes") == 0) {
-                    msg.setJMSCorrelationIDAsBytes(subMapVal.getBytes());
+                    msg.setJMSCorrelationIDAsBytes(Base64.getDecoder().decode(subMapVal.getBytes()));
                 } else {
                     throw new Exception("Internal exception: Invalid message header type \"" + subMapKey + "\" for message header \"" + key + "\"");
                 }
@@ -275,13 +277,14 @@ public class Sender {
             message.writeByte(Byte.decode(testValue));
             break;
         case "bytes":
-            message.writeBytes(testValue.getBytes());
+            message.writeBytes(Base64.getDecoder().decode(testValue));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X" or "\xNN"
-                message.writeChar(testValue.charAt(0));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X" or "\xNN"
+                message.writeChar((char)decodedValue[0]);
             } else {
-                throw new Exception("JmsSenderShim.createJMSBytesMessage() Malformed char string: \"" + testValue + "\" of length " + testValue.length());
+                throw new Exception("JmsSenderShim.createJMSBytesMessage() Malformed char string: \"" + decodedValue + "\" of length " + decodedValue.length);
             }
             break;
         case "double":
@@ -326,15 +329,16 @@ public class Sender {
             message.setByte(name, Byte.decode(testValue));
             break;
         case "bytes":
-            message.setBytes(name, testValue.getBytes());
+            message.setBytes(name, Base64.getDecoder().decode(testValue));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X"
-                message.setChar(name, testValue.charAt(0));
-            } else if (testValue.length() == 6) { // Char format: "\xNNNN"
-                message.setChar(name, (char)Integer.parseInt(testValue.substring(2), 16));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X" or "\xNN"
+                message.setChar(name, (char)decodedValue[0]);
+            } else if (decodedValue.length == 6) { // Char format: "\xNNNN"
+                message.setChar(name, ByteBuffer.wrap(decodedValue).getChar());
             } else {
-                throw new Exception("JmsSenderShim.createJMSMapMessage() Malformed char string: \"" + testValue + "\"");
+                throw new Exception("JmsSenderShim.createJMSMapMessage() Malformed char string: \"" + decodedValue + "\"");
             }
             break;
         case "double":
@@ -390,15 +394,16 @@ public class Sender {
             message.writeByte(Byte.decode(testValue));
             break;
         case "bytes":
-            message.writeBytes(testValue.getBytes());
+            message.writeBytes(Base64.getDecoder().decode(testValue.getBytes()));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X"
-                message.writeChar(testValue.charAt(0));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X"
+                message.writeChar((char)decodedValue[0]);
             } else if (testValue.length() == 6) { // Char format: "\xNNNN"
-                message.writeChar((char)Integer.parseInt(testValue.substring(2), 16));
+                message.writeChar(ByteBuffer.wrap(decodedValue).getChar());
             } else {
-                throw new Exception("JmsSenderShim.createJMSStreamMessage() Malformed char string: \"" + testValue + "\"");
+                throw new Exception("JmsSenderShim.createJMSStreamMessage() Malformed char string: \"" + decodedValue + "\"");
             }
             break;
         case "double":
diff --git a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Receiver.java b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Receiver.java
index 07d1f06..3d7c074 100644
--- a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Receiver.java
+++ b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Receiver.java
@@ -23,13 +23,12 @@ import java.io.StringReader;
 import java.io.StringWriter;
 import java.util.ArrayList;
 import java.util.Arrays;
+import java.util.Base64;
 import java.util.Collections;
-import java.util.Enumeration;
 import java.util.List;
 import javax.jms.BytesMessage;
 import javax.jms.Connection;
 import javax.jms.ConnectionFactory;
-import javax.jms.Destination;
 import javax.jms.ExceptionListener;
 import javax.jms.JMSException;
 import javax.jms.MapMessage;
@@ -40,9 +39,7 @@ import javax.jms.Queue;
 import javax.jms.Session;
 import javax.jms.StreamMessage;
 import javax.jms.TextMessage;
-import javax.jms.Topic;
 import javax.json.Json;
-import javax.json.JsonArray;
 import javax.json.JsonArrayBuilder;
 import javax.json.JsonObject;
 import javax.json.JsonObjectBuilder;
@@ -60,7 +57,6 @@ public class Receiver {
                                                                  "JMS_OBJECTMESSAGE_TYPE",
                                                                  "JMS_STREAMMESSAGE_TYPE",
                                                                  "JMS_TEXTMESSAGE_TYPE"};
-    private static enum JMS_DESTINATION_TYPE {JMS_QUEUE, JMS_TEMPORARY_QUEUE, JMS_TOPIC, JMS_TEMPORARY_TOPIC};
     
     Connection _connection;
     Session _session;
@@ -189,15 +185,15 @@ public class Receiver {
                 byte[] bytesBuff = new byte[65536];
                 int numBytesRead = ((BytesMessage)message).readBytes(bytesBuff);
                 if (numBytesRead >= 0) {
-                    jasonTestValuesArrayBuilder.add(new String(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
+                    jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
                 } else {
                     // NOTE: For this case, an empty byte array has nothing to return
-                    jasonTestValuesArrayBuilder.add(new String());
+                    jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString("".getBytes()));
                 }
             }
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((BytesMessage)message).readChar()));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((BytesMessage)message).readChar()).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((BytesMessage)message).readDouble());
@@ -248,10 +244,10 @@ public class Receiver {
             jasonTestValuesArrayBuilder.add(formatByte(((MapMessage)message).getByte(name)));
             break;
         case "bytes":
-            jasonTestValuesArrayBuilder.add(new String(((MapMessage)message).getBytes(name)));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString((((MapMessage)message).getBytes(name))));
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((MapMessage)message).getChar(name)));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((MapMessage)message).getChar(name)).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((MapMessage)message).getDouble(name));
@@ -298,14 +294,14 @@ public class Receiver {
             byte[] bytesBuff = new byte[65536];
             int numBytesRead = ((StreamMessage)message).readBytes(bytesBuff);
             if (numBytesRead >= 0) {
-                jasonTestValuesArrayBuilder.add(new String(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
+                jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(Arrays.copyOfRange(bytesBuff, 0, numBytesRead)));
             } else {
                 System.out.println("StreamMessage.readBytes() returned " + numBytesRead);
                 jasonTestValuesArrayBuilder.add("<bytes error>");
             }
             break;
         case "char":
-            jasonTestValuesArrayBuilder.add(formatChar(((StreamMessage)message).readChar()));
+            jasonTestValuesArrayBuilder.add(Base64.getEncoder().encodeToString(formatChar(((StreamMessage)message).readChar()).getBytes()));
             break;
         case "double":
             long l = Double.doubleToRawLongBits(((StreamMessage)message).readDouble());
diff --git a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Sender.java b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Sender.java
index 0cccc97..c77d36d 100644
--- a/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Sender.java
+++ b/shims/qpid-jms/src/main/java/org/apache/qpid/interop_test/jms_messages_test/Sender.java
@@ -20,7 +20,9 @@ import java.io.Serializable;
 import java.io.StringReader;
 import java.lang.reflect.Constructor;
 import java.lang.reflect.InvocationTargetException;
+import java.nio.ByteBuffer;
 import java.util.ArrayList;
+import java.util.Base64;
 import java.util.Collections;
 import java.util.List;
 import javax.jms.BytesMessage;
@@ -44,8 +46,6 @@ import javax.json.JsonReader;
 import org.apache.qpid.jms.JmsConnectionFactory;
 
 public class Sender {
-    private static final String USER = "guest";
-    private static final String PASSWORD = "guest";
     private static final String[] SUPPORTED_JMS_MESSAGE_TYPES = {"JMS_MESSAGE_TYPE",
                                                                  "JMS_BYTESMESSAGE_TYPE",
                                                                  "JMS_MAPMESSAGE_TYPE",
@@ -174,13 +174,14 @@ public class Sender {
             message.writeByte(Byte.decode(testValue));
             break;
         case "bytes":
-            message.writeBytes(testValue.getBytes());
+            message.writeBytes(Base64.getDecoder().decode(testValue));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X" or "\xNN"
-                message.writeChar(testValue.charAt(0));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X" or "\xNN"
+                message.writeChar((char)decodedValue[0]);
             } else {
-                throw new Exception("JmsSenderShim.createJMSBytesMessage() Malformed char string: \"" + testValue + "\" of length " + testValue.length());
+                throw new Exception("JmsSenderShim.createJMSBytesMessage() Malformed char string: \"" + decodedValue + "\" of length " + decodedValue.length);
             }
             break;
         case "double":
@@ -225,15 +226,16 @@ public class Sender {
             message.setByte(name, Byte.decode(testValue));
             break;
         case "bytes":
-            message.setBytes(name, testValue.getBytes());
+            message.setBytes(name, Base64.getDecoder().decode(testValue));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X"
-                message.setChar(name, testValue.charAt(0));
-            } else if (testValue.length() == 6) { // Char format: "\xNNNN"
-                message.setChar(name, (char)Integer.parseInt(testValue.substring(2), 16));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X" or "\xNN"
+                message.setChar(name, (char)decodedValue[0]);
+            } else if (decodedValue.length == 6) { // Char format: "\xNNNN"
+                message.setChar(name, ByteBuffer.wrap(decodedValue).getChar());
             } else {
-                throw new Exception("JmsSenderShim.createJMSMapMessage() Malformed char string: \"" + testValue + "\"");
+                throw new Exception("JmsSenderShim.createJMSMapMessage() Malformed char string: \"" + decodedValue + "\"");
             }
             break;
         case "double":
@@ -289,15 +291,16 @@ public class Sender {
             message.writeByte(Byte.decode(testValue));
             break;
         case "bytes":
-            message.writeBytes(testValue.getBytes());
+            message.writeBytes(Base64.getDecoder().decode(testValue.getBytes()));
             break;
         case "char":
-            if (testValue.length() == 1) { // Char format: "X"
-                message.writeChar(testValue.charAt(0));
+            byte[] decodedValue = Base64.getDecoder().decode(testValue);
+            if (decodedValue.length == 1) { // Char format: "X"
+                message.writeChar((char)decodedValue[0]);
             } else if (testValue.length() == 6) { // Char format: "\xNNNN"
-                message.writeChar((char)Integer.parseInt(testValue.substring(2), 16));
+                message.writeChar(ByteBuffer.wrap(decodedValue).getChar());
             } else {
-                throw new Exception("JmsSenderShim.createJMSStreamMessage() Malformed char string: \"" + testValue + "\"");
+                throw new Exception("JmsSenderShim.createJMSStreamMessage() Malformed char string: \"" + decodedValue + "\"");
             }
             break;
         case "double":
@@ -336,7 +339,7 @@ public class Sender {
         try {
             Class<?> c = Class.forName(className);
             if (className.compareTo("java.lang.Character") == 0) {
-                Constructor ctor = c.getConstructor(char.class);
+                Constructor<?> ctor = c.getConstructor(char.class);
                 if (testValue.length() == 1) {
                     // Use first character of string
                     obj = (Serializable)ctor.newInstance(testValue.charAt(0));
@@ -348,7 +351,7 @@ public class Sender {
                 }
             } else {
                 // Use string constructor
-                Constructor ctor = c.getConstructor(String.class);
+                Constructor<?> ctor = c.getConstructor(String.class);
                 obj = (Serializable)ctor.newInstance(testValue);
             }
         }
diff --git a/shims/qpid-proton-cpp/src/CMakeLists.txt b/shims/qpid-proton-cpp/src/CMakeLists.txt
index 221b912..6bcc310 100644
--- a/shims/qpid-proton-cpp/src/CMakeLists.txt
+++ b/shims/qpid-proton-cpp/src/CMakeLists.txt
@@ -116,6 +116,8 @@ endfunction(addJmsTest testName)
 # --- Common files and libs ---
 
 set(Common_SOURCES
+    qpidit/Base64.hpp
+    qpidit/Base64.cpp
     qpidit/QpidItErrors.hpp
     qpidit/QpidItErrors.cpp
 )
diff --git a/shims/qpid-proton-cpp/src/qpidit/Base64.cpp b/shims/qpid-proton-cpp/src/qpidit/Base64.cpp
new file mode 100644
index 0000000..18dc6d8
--- /dev/null
+++ b/shims/qpid-proton-cpp/src/qpidit/Base64.cpp
@@ -0,0 +1,125 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+
+/*
+ * Based on René Nyffenegger rene.nyffenegger@adp-gmbh.ch
+ * https://renenyffenegger.ch/notes/development/Base64/Encoding-and-decoding-base-64-with-cpp/
+ */
+#include "Base64.hpp"
+#include <iostream>
+
+static const std::string b64_chars = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+
+static inline bool is_base64(uint8_t c) {
+	return (isalnum(c) || (c == '+') || (c == '/'));
+}
+
+std::string b64_encode(proton::binary const& str_buf) {
+	uint8_t const* buf = &str_buf[0];
+	uint16_t bufLen = str_buf.size();
+	std::string ret;
+	int i = 0;
+	int j = 0;
+	uint8_t char_array_3[3];
+	uint8_t char_array_4[4];
+
+	while (bufLen--) {
+		char_array_3[i++] = *(buf++);
+		if (i == 3) {
+			char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
+			char_array_4[1] = ((char_array_3[0] & 0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
+			char_array_4[2] = ((char_array_3[1] & 0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
+			char_array_4[3] = char_array_3[2] & 0x3f;
+
+			for(i = 0; (i <4) ; i++) {
+				ret += b64_chars[char_array_4[i]];
+			}
+			i = 0;
+		}
+	}
+
+	if (i) {
+		for(j = i; j < 3; j++) {
+			char_array_3[j] = '\0';
+		}
+
+		char_array_4[0] = (char_array_3[0] & 0xfc) >> 2;
+		char_array_4[1] = ((char_array_3[0] & 0x03) << 4) + ((char_array_3[1] & 0xf0) >> 4);
+		char_array_4[2] = ((char_array_3[1] & 0x0f) << 2) + ((char_array_3[2] & 0xc0) >> 6);
+		char_array_4[3] = char_array_3[2] & 0x3f;
+
+		for (j = 0; (j < i + 1); j++) {
+			ret += b64_chars[char_array_4[j]];
+		}
+
+		while((i++ < 3))
+			ret += '=';
+	}
+
+	return ret;
+}
+
+proton::binary b64_decode(std::string const& encoded_string) {
+	int in_len = encoded_string.size();
+	int i = 0;
+	int j = 0;
+	int in_ = 0;
+	uint8_t char_array_4[4], char_array_3[3];
+	proton::binary ret;
+
+	while (in_len-- && ( encoded_string[in_] != '=') && is_base64(encoded_string[in_])) {
+		char_array_4[i++] = encoded_string[in_]; in_++;
+		if (i ==4) {
+			for (i = 0; i <4; i++) {
+				char_array_4[i] = b64_chars.find(char_array_4[i]);
+			}
+
+			char_array_3[0] = (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
+			char_array_3[1] = ((char_array_4[1] & 0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
+			char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
+
+			for (i = 0; (i < 3); i++) {
+				ret.push_back(char_array_3[i]);
+			}
+			i = 0;
+		}
+	}
+
+	if (i) {
+		for (j = i; j <4; j++) {
+			char_array_4[j] = 0;
+		}
+
+		for (j = 0; j <4; j++) {
+			char_array_4[j] = b64_chars.find(char_array_4[j]);
+		}
+
+		char_array_3[0] = (char_array_4[0] << 2) + ((char_array_4[1] & 0x30) >> 4);
+		char_array_3[1] = ((char_array_4[1] & 0xf) << 4) + ((char_array_4[2] & 0x3c) >> 2);
+		char_array_3[2] = ((char_array_4[2] & 0x3) << 6) + char_array_4[3];
+
+		for (j = 0; (j < i - 1); j++) {
+			ret.push_back(char_array_3[j]);
+		}
+	}
+
+	return ret;
+}
diff --git a/shims/qpid-proton-cpp/src/qpidit/Base64.hpp b/shims/qpid-proton-cpp/src/qpidit/Base64.hpp
new file mode 100644
index 0000000..d4a80bd
--- /dev/null
+++ b/shims/qpid-proton-cpp/src/qpidit/Base64.hpp
@@ -0,0 +1,32 @@
+/*
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ *
+ */
+
+#ifndef SRC_QPIDIT_BASE64_HPP_
+#define SRC_QPIDIT_BASE64_HPP_
+
+#include <vector>
+#include <string>
+#include <proton/binary.hpp>
+
+std::string b64_encode(proton::binary const&);
+proton::binary b64_decode(std::string const&);
+
+#endif /* SRC_QPIDIT_BASE64_HPP_ */
diff --git a/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.cpp b/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.cpp
index 76936e6..1e76dcc 100644
--- a/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.cpp
@@ -163,8 +163,8 @@ namespace qpidit
 
     // --- JsonParserError ---
 
-    JsonParserError::JsonParserError(const Json::Reader& jsonReader) :
-                    std::runtime_error(MSG("JSON test values failed to parse: " << jsonReader.getFormattedErrorMessages()))
+    JsonParserError::JsonParserError(const std::string& parseErrors) :
+                    std::runtime_error(MSG("JSON test values failed to parse: " << parseErrors))
     {}
 
     JsonParserError::~JsonParserError() throw() {}
diff --git a/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.hpp b/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.hpp
index f34b26b..d6ad864 100644
--- a/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/QpidItErrors.hpp
@@ -129,7 +129,7 @@ namespace qpidit
     class JsonParserError: public std::runtime_error
     {
     public:
-        explicit JsonParserError(const Json::Reader& jsonReader);
+        explicit JsonParserError(const std::string& parseErrors);
         virtual ~JsonParserError() throw();
     };
 
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.cpp b/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.cpp
index 34bb33c..eeeab48 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.cpp
@@ -70,9 +70,6 @@ namespace qpidit
             return _testDataMap.size();
         }
 
-        const TestDataList_t& Common::testDataList() const {
-
-        }
         bool Common::isAmqpSubType(const proton::value& protonValue) const {
             TestDataList_t valueList;
             proton::get(protonValue, valueList);
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.hpp b/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.hpp
index 4c65e19..53d1648 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_complex_types_test/Common.hpp
@@ -51,7 +51,6 @@ namespace qpidit
             void initializeDataMap(); // Generated function
             static void setUuid(proton::uuid& val, const std::string& uuidStr);
             std::size_t size() const;
-            const TestDataList_t& testDataList() const;
 
             template<size_t N> static void hexStringToBytearray(proton::byte_array<N>& ba, const std::string& s, size_t fromArrayIndex = 0, size_t arrayLen = N) {
                 size_t len = (s.size()/2 > arrayLen) ? arrayLen : s.size()/2;
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Receiver.cpp b/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Receiver.cpp
index c28ad07..ee24985 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Receiver.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Receiver.cpp
@@ -134,6 +134,7 @@ namespace qpidit
             if (_amqpType.compare("symbol") == 0) {
                 return proton::get<proton::symbol>(testString).size() / 1024 / 1024;
             }
+            return 0;
         }
 
         void Receiver::appendListMapSize(Json::Value& numEltsList, std::pair<uint32_t, uint32_t> val) {
@@ -172,8 +173,12 @@ int main(int argc, char** argv) {
         proton::container(receiver).run();
 
         std::cout << argv[3] << std::endl;
-        Json::FastWriter fw;
-        std::cout << fw.write(receiver.getReceivedValueList());
+        Json::StreamWriterBuilder wbuilder;
+        wbuilder["indentation"] = "";
+        std::unique_ptr<Json::StreamWriter> writer(wbuilder.newStreamWriter());
+        std::ostringstream oss;
+        writer->write(receiver.getReceivedValueList(), &oss);
+        std::cout << oss.str() << std::endl;
     } catch (const std::exception& e) {
         std::cerr << "amqp_large_content_test receiver error: " << e.what() << std::endl;
         exit(-1);
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Sender.cpp b/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Sender.cpp
index cf871f1..3b13493 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Sender.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_large_content_test/Sender.cpp
@@ -150,16 +150,18 @@ namespace qpidit
  */
 
 int main(int argc, char** argv) {
-    // TODO: improve arg management a little...
-    if (argc != 5) {
-        throw qpidit::ArgumentError("Incorrect number of arguments");
-    }
-
     try {
+        // TODO: improve arg management a little...
+        if (argc != 5) {
+            throw qpidit::ArgumentError("Incorrect number of arguments");
+        }
+
         Json::Value testValues;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testValues, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder builder;
+        Json::CharReader* jsonReader = builder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testValues, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
         qpidit::amqp_large_content_test::Sender sender(argv[1], argv[2], argv[3], testValues);
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.cpp b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.cpp
index 6b6f2ba..5755ad3 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.cpp
@@ -20,6 +20,7 @@
  */
 
 #include <qpidit/amqp_types_test/Receiver.hpp>
+#include "qpidit/Base64.hpp"
 
 #include <iostream>
 #include <json/json.h>
@@ -111,79 +112,32 @@ namespace qpidit
         //static
         std::string Receiver::getAmqpType(const proton::value& val) {
             switch(val.type()) {
-            case proton::NULL_TYPE: return "null";
-            case proton::BOOLEAN: return "boolean";
-            case proton::UBYTE: return "ubyte";
-            case proton::USHORT: return "ushort";
-            case proton::UINT: return "uint";
-            case proton::ULONG: return "ulong";
-            case proton::BYTE: return "byte";
-            case proton::SHORT: return "short";
-            case proton::INT: return "int";
-            case proton::LONG: return "long";
-            case proton::FLOAT: return "float";
-            case proton::DOUBLE: return "double";
-            case proton::DECIMAL32: return "decimal32";
-            case proton::DECIMAL64: return "decimal64";
-            case proton::DECIMAL128: return "decimal128";
-            case proton::CHAR: return "char";
-            case proton::TIMESTAMP: return "timestamp";
-            case proton::UUID: return "uuid";
-            case proton::BINARY: return "binary";
-            case proton::STRING: return "string";
-            case proton::SYMBOL: return "symbol";
-            case proton::LIST: return "list";
-            case proton::MAP: return "map";
-            case proton::ARRAY: return "array";
-            //default: throw qpidit::UnknownAmqpTypeError(val);
+                case proton::NULL_TYPE: return "null";
+                case proton::BOOLEAN: return "boolean";
+                case proton::UBYTE: return "ubyte";
+                case proton::USHORT: return "ushort";
+                case proton::UINT: return "uint";
+                case proton::ULONG: return "ulong";
+                case proton::BYTE: return "byte";
+                case proton::SHORT: return "short";
+                case proton::INT: return "int";
+                case proton::LONG: return "long";
+                case proton::FLOAT: return "float";
+                case proton::DOUBLE: return "double";
+                case proton::DECIMAL32: return "decimal32";
+                case proton::DECIMAL64: return "decimal64";
+                case proton::DECIMAL128: return "decimal128";
+                case proton::CHAR: return "char";
+                case proton::TIMESTAMP: return "timestamp";
+                case proton::UUID: return "uuid";
+                case proton::BINARY: return "binary";
+                case proton::STRING: return "string";
+                case proton::SYMBOL: return "symbol";
+                case proton::LIST: return "list";
+                case proton::MAP: return "map";
+                case proton::ARRAY: return "array";
             }
-        }
-
-        //static
-        Json::Value& Receiver::getMap(Json::Value& jsonMap, const proton::value& val) {
-            std::map<proton::value, proton::value> msgMap;
-            proton::get(val, msgMap);
-            for (std::map<proton::value, proton::value>::const_iterator i = msgMap.begin(); i != msgMap.end(); ++i) {
-
-                // Process key
-                Json::Value mapKey;
-                if (i->first.type() == proton::LIST || i->first.type() == proton::MAP || i->first.type() == proton::ARRAY) {
-                    mapKey = getValue(i->first);
-                } else {
-                    std::ostringstream oss;
-                    oss << getAmqpType(i->first) << ":" << getValue(i->first).asString();
-                    mapKey = oss.str();
-                }
-
-                // Process value
-                Json::Value mapValue;
-                if (i->second.type() == proton::LIST || i->second.type() == proton::MAP || i->second.type() == proton::ARRAY) {
-                    mapValue = getValue(i->second);
-                } else {
-                    std::ostringstream oss;
-                    oss << getAmqpType(i->second) << ":" << getValue(i->second).asString();
-                    mapValue = oss.str();
-                }
-
-                jsonMap[mapKey.asString()] = mapValue;
-            }
-            return jsonMap;
-        }
-
-        //static
-        Json::Value& Receiver::getSequence(Json::Value& jsonList, const proton::value& val) {
-            std::vector<proton::value> msgList;
-            proton::get(val, msgList);
-            for (std::vector<proton::value>::const_iterator i=msgList.begin(); i!=msgList.end(); ++i) {
-                if (i->type() == proton::LIST || i->type() == proton::MAP || i->type() == proton::ARRAY) {
-                    jsonList.append(getValue(*i));
-                } else {
-                    std::ostringstream oss;
-                    oss << getAmqpType(*i) << ":" << getValue(*i).asString();
-                    jsonList.append(oss.str());
-                }
-            }
-            return jsonList;
+            return "unknown";
         }
 
         //static
@@ -280,7 +234,8 @@ namespace qpidit
             }
             if (amqpType.compare("binary") == 0) {
                 checkMessageType(val, proton::BINARY);
-                return std::string(proton::get<proton::binary>(val));
+                // Encode binary to base64 before returning value as string
+                return b64_encode(proton::get<proton::binary>(val));
             }
             if (amqpType.compare("string") == 0) {
                 checkMessageType(val, proton::STRING);
@@ -291,14 +246,10 @@ namespace qpidit
                 return proton::get<proton::symbol>(val);
             }
             if (amqpType.compare("list") == 0) {
-                checkMessageType(val, proton::LIST);
-                Json::Value jsonList(Json::arrayValue);
-                return getSequence(jsonList, val);
+                throw qpidit::UnsupportedAmqpTypeError(amqpType);
             }
             if (amqpType.compare("map") == 0) {
-                checkMessageType(val, proton::MAP);
-                Json::Value jsonMap(Json::objectValue);
-                return getMap(jsonMap, val);
+                throw qpidit::UnsupportedAmqpTypeError(amqpType);
             }
             if (amqpType.compare("array") == 0) {
                 throw qpidit::UnsupportedAmqpTypeError(amqpType);
@@ -319,18 +270,22 @@ namespace qpidit
  */
 
 int main(int argc, char** argv) {
-    // TODO: improve arg management a little...
-    if (argc != 5) {
-        throw qpidit::ArgumentError("Incorrect number of arguments");
-    }
-
     try {
+        // TODO: improve arg management a little...
+        if (argc != 5) {
+            throw qpidit::ArgumentError("Incorrect number of arguments");
+        }
+
         qpidit::amqp_types_test::Receiver receiver(argv[1], argv[2], argv[3], std::strtoul(argv[4], NULL, 0));
         proton::container(receiver).run();
 
         std::cout << argv[3] << std::endl;
-        Json::FastWriter fw;
-        std::cout << fw.write(receiver.getReceivedValueList());
+        Json::StreamWriterBuilder wbuilder;
+        wbuilder["indentation"] = "";
+        std::unique_ptr<Json::StreamWriter> writer(wbuilder.newStreamWriter());
+        std::ostringstream oss;
+        writer->write(receiver.getReceivedValueList(), &oss);
+        std::cout << oss.str() << std::endl;
     } catch (const std::exception& e) {
         std::cerr << "AmqpReceiver error: " << e.what() << std::endl;
         exit(-1);
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.hpp b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.hpp
index 8b5b32d..157fc8a 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Receiver.hpp
@@ -55,11 +55,8 @@ namespace qpidit
             void on_transport_error(proton::transport &t);
             void on_error(const proton::error_condition &c);
         protected:
-            //static void checkMessageType(const proton::message& msg, const proton::type_id amqpType);
             static void checkMessageType(const proton::value& val, const proton::type_id amqpType);
             static std::string getAmqpType(const proton::value& val);
-            static Json::Value& getMap(Json::Value& jsonMap, const proton::value& val);
-            static Json::Value& getSequence(Json::Value& jsonList, const proton::value& val);
             static Json::Value getValue(const proton::value& val);
             static Json::Value getValue(const std::string& amqpType, const proton::value& val);
 
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.cpp b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.cpp
index 7b47827..abefb5d 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.cpp
@@ -20,6 +20,7 @@
  */
 
 #include "qpidit/amqp_types_test/Sender.hpp"
+#include "qpidit/Base64.hpp"
 
 #include <cstdlib>
 #include <iomanip>
@@ -71,16 +72,6 @@ namespace qpidit
         }
 
         //static
-        std::string Sender::bytearrayToHexStr(const char* src, int len) {
-            std::ostringstream oss;
-            oss << "0x" << std::hex;
-            for (int i=0; i<len; ++i) {
-                oss <<  std::setw(2) << std::setfill('0') << ((int)src[i] & 0xff);
-            }
-            return oss.str();
-        }
-
-        //static
         proton::value Sender::convertAmqpValue(const std::string& amqpType, const Json::Value& testValue) {
             if (amqpType.compare("null") == 0) {
                 std::string testValueStr(testValue.asString());
@@ -184,7 +175,8 @@ namespace qpidit
                 return val;
             }
             if (amqpType.compare("binary") == 0) {
-                return proton::binary(testValue.asString());
+                // Base64 decode to binary string
+                return b64_decode(testValue.asString());
             }
             if (amqpType.compare("string") == 0) {
                 return std::string(testValue.asString());
@@ -193,129 +185,17 @@ namespace qpidit
                 return proton::symbol(testValue.asString());
             }
             if (amqpType.compare("list") == 0) {
-                std::vector<proton::value> list;
-                processList(list, testValue);
-                return list;
-            } else if (amqpType.compare("map") == 0) {
-                std::map<proton::value, proton::value> map;
-                processMap(map, testValue);
-                return map;
+                throw qpidit::UnsupportedAmqpTypeError(amqpType);
+            }
+            if (amqpType.compare("map") == 0) {
+                throw qpidit::UnsupportedAmqpTypeError(amqpType);
             }
             if (amqpType.compare("array") == 0) {
-/*
-                std::vector<proton::value> array;
-                processArray(array, testValue);
-                return proton::as<proton::ARRAY>(array);
-*/
                 throw qpidit::UnsupportedAmqpTypeError(amqpType);
             }
             throw qpidit::UnknownAmqpTypeError(amqpType);
         }
 
-//        //static
-//        Json::Value::ValueType getArrayType(const Json::Value& val) {
-//            if (val.size()) > 0) {
-//                return val[0].type();
-//            } else {
-//                return Json::Value::nullValue; // TODO: find a way to represent empty array
-//            }
-//        }
-
-        //static
-        void Sender::processArray(std::vector<proton::value>& array, const Json::Value& testValues) {
-            for (Json::Value::const_iterator i = testValues.begin(); i != testValues.end(); ++i) {
-                if ((*i).isArray()) {
-                    std::vector<proton::value> subArray;
-                    processArray(subArray, *i);
-                    array.push_back(proton::value(subArray));
-                } else if ((*i).isObject()) {
-                    std::map<proton::value, proton::value> subMap;
-                    processMap(subMap, *i);
-                    array.push_back(proton::value(subMap));
-                } else {
-                    proton::value v;
-                    if ((*i).isNull())
-                        ;
-                    else if ((*i).isBool())
-                        v = (*i).asBool();
-                    else if ((*i).isInt())
-                        v = (*i).asInt();
-                    else if ((*i).isUInt())
-                        v = (*i).asUInt();
-                    else if ((*i).isDouble())
-                        v = (*i).asDouble();
-                    else if ((*i).isString())
-                        v = (*i).asString();
-                    else
-                        ; // TODO handle this case
-                    array.push_back(v);
-                }
-            }
-        }
-
-        //static
-        proton::value Sender::processElement(const Json::Value& testValue) {
-            const std::string testValueStr(testValue.asString());
-            // testValue has the format amqp-type:amqp-str-value
-            const std::size_t splitIndex = testValueStr.find_first_of(':');
-            if (splitIndex == std::string::npos) {
-                throw qpidit::InvalidTestValueError(testValueStr);
-            }
-            const std::string amqpType = testValueStr.substr(0, splitIndex);
-            const std::string amqpValueAsStr = testValueStr.substr(splitIndex + 1);
-            return convertAmqpValue(amqpType, amqpValueAsStr);
-        }
-
-        //static
-        void Sender::processList(std::vector<proton::value>& list, const Json::Value& testValues) {
-            for (Json::Value::const_iterator i = testValues.begin(); i != testValues.end(); ++i) {
-                if ((*i).isArray()) {
-                    std::vector<proton::value> subList;
-                    processList(subList, *i);
-                    list.push_back(proton::value(subList));
-                } else if ((*i).isObject()) {
-                    std::map<proton::value, proton::value> subMap;
-                    processMap(subMap, *i);
-                    list.push_back(proton::value(subMap));
-                } else {
-                    list.push_back(processElement(*i));
-                }
-            }
-        }
-
-        //static
-        void Sender::processMap(std::map<proton::value, proton::value>& map, const Json::Value& testValues) {
-            Json::Value::Members keys = testValues.getMemberNames();
-            for (std::vector<std::string>::const_iterator i=keys.begin(); i!=keys.end(); ++i) {
-                proton::value key = processElement(*i);
-                Json::Value mapVal = testValues[*i];
-                if (mapVal.isArray()) {
-                    std::vector<proton::value> subList;
-                    processList(subList, mapVal);
-                    map[key] = subList;
-                } else if (mapVal.isObject()) {
-                    std::map<proton::value, proton::value> subMap;
-                    processMap(subMap, mapVal);
-                    map[key] = subMap;
-                } else {
-                    map[key] = processElement(mapVal);
-                }
-            }
-        }
-
-        //static
-        void Sender::revMemcpy(char* dest, const char* src, int n) {
-            for (int i = 0; i < n; ++i) {
-                *(dest + i) = *(src + n - i - 1);
-            }
-        }
-
-        //static
-        void Sender::uint64ToChar16(char* dest, uint64_t upper, uint64_t lower) {
-            revMemcpy(dest, (const char*)&upper, sizeof(uint64_t));
-            revMemcpy(dest + 8, (const char*)&lower, sizeof(uint64_t));
-        }
-
     } /* namespace amqp_types_test */
 } /* namespace qpidit */
 
@@ -329,16 +209,18 @@ namespace qpidit
  */
 
 int main(int argc, char** argv) {
-    // TODO: improve arg management a little...
-    if (argc != 5) {
-        throw qpidit::ArgumentError("Incorrect number of arguments");
-    }
-
     try {
+        // TODO: improve arg management a little...
+        if (argc != 5) {
+            throw qpidit::ArgumentError("Incorrect number of arguments");
+        }
+
         Json::Value testValues;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testValues, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder rbuilder;
+        Json::CharReader* jsonReader = rbuilder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testValues, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
         qpidit::amqp_types_test::Sender sender(argv[1], argv[2], argv[3], testValues);
diff --git a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.hpp b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.hpp
index 88b81df..da9e721 100644
--- a/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/amqp_types_test/Sender.hpp
@@ -47,16 +47,7 @@ namespace qpidit
         protected:
             proton::message& setMessage(proton::message& msg, const Json::Value& testValue);
 
-            static std::string bytearrayToHexStr(const char* src, int len);
-            static void revMemcpy(char* dest, const char* src, int n);
-            static void uint64ToChar16(char* dest, uint64_t upper, uint64_t lower);
-
             static proton::value convertAmqpValue(const std::string& amqpType, const Json::Value& testValue);
-            //static Json::Value::ValueType getArrayType(const Json::Value& val);
-            static void processArray(std::vector<proton::value>& array, const Json::Value& testValues);
-            static proton::value processElement(const Json::Value& testValue);
-            static void processList(std::vector<proton::value>& list, const Json::Value& testValues);
-            static void processMap(std::map<proton::value, proton::value>& map, const Json::Value& testValues);
 
             template<size_t N> static void hexStringToBytearray(proton::byte_array<N>& ba, const std::string s, size_t fromArrayIndex = 0, size_t arrayLen = N) {
                 for (size_t i=0; i<arrayLen; ++i) {
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Receiver.cpp b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Receiver.cpp
index c1093e5..cb275a6 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Receiver.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Receiver.cpp
@@ -20,6 +20,7 @@
  */
 
 #include "qpidit/jms_hdrs_props_test/Receiver.hpp"
+#include "qpidit/Base64.hpp"
 
 #include <ctime>
 #include <iostream>
@@ -174,11 +175,11 @@ namespace qpidit
                 } else if (subType.compare("byte") == 0) {
                     _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(proton::get<int8_t>(val))));
                 } else if (subType.compare("bytes") == 0) {
-                    _receivedSubTypeList.append(Json::Value(std::string(proton::get<proton::binary>(val))));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::get<proton::binary>(val))));
                 } else if (subType.compare("char") == 0) {
                     std::ostringstream oss;
                     oss << (char)proton::get<wchar_t>(val);
-                    _receivedSubTypeList.append(Json::Value(oss.str()));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
                 } else if (subType.compare("double") == 0) {
                     double d = proton::get<double>(val);
                     _receivedSubTypeList.append(Json::Value(toHexStr<int64_t>(*((int64_t*)&d), true, false)));
@@ -213,14 +214,14 @@ namespace qpidit
                 int8_t val = *((int8_t*)body.data());
                 _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(val)));
             } else if (subType.compare("bytes") == 0) {
-                _receivedSubTypeList.append(Json::Value(std::string(body)));
+                _receivedSubTypeList.append(Json::Value(b64_encode(body)));
             } else if (subType.compare("char") == 0) {
                 if (body.size() != sizeof(uint16_t)) throw IncorrectMessageBodyLengthError("JmsReceiver::receiveJmsBytesMessage, subType=char", sizeof(uint16_t), body.size());
                 // TODO: This is ugly: ignoring first byte - handle UTF-16 correctly
                 char c = body[1];
                 std::ostringstream oss;
                 oss << c;
-                _receivedSubTypeList.append(Json::Value(oss.str()));
+                _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
             } else if (subType.compare("double") == 0) {
                 if (body.size() != sizeof(int64_t)) throw IncorrectMessageBodyLengthError("JmsReceiver::receiveJmsBytesMessage, subType=double", sizeof(int64_t), body.size());
                 int64_t val = be64toh(*((int64_t*)body.data()));
@@ -262,11 +263,11 @@ namespace qpidit
                 } else if (subType.compare("byte") == 0) {
                     _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(proton::get<int8_t>(*i))));
                 } else if (subType.compare("bytes") == 0) {
-                    _receivedSubTypeList.append(Json::Value(std::string(proton::get<proton::binary>(*i))));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::get<proton::binary>(*i))));
                 } else if (subType.compare("char") == 0) {
                     std::ostringstream oss;
                     oss << (char)proton::get<wchar_t>(*i);
-                    _receivedSubTypeList.append(Json::Value(oss.str()));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
                 } else if (subType.compare("double") == 0) {
                     double d = proton::get<double>(*i);
                     _receivedSubTypeList.append(Json::Value(toHexStr<int64_t>(*((int64_t*)&d), true, false)));
@@ -381,7 +382,7 @@ namespace qpidit
         void Receiver::addMessageHeaderByteArray(const std::string& headerName, const proton::binary ba) {
             if (!ba.empty()) { // TODO: Remove this test when PROTON-1288 is fixed as empty binaries are allowed in headers
                 Json::Value valueMap(Json::objectValue);
-                valueMap["bytes"] = std::string(ba);
+                valueMap["bytes"] = b64_encode(ba);
                 _receivedHeadersMap[headerName] = valueMap;
             }
         }
@@ -467,28 +468,34 @@ namespace qpidit
  *       4: JSON Test parameters containing 2 maps: [testValuesMap, flagMap]
  */
 int main(int argc, char** argv) {
-    // TODO: improve arg management a little...
-    if (argc != 5) {
-        throw qpidit::ArgumentError("Incorrect number of arguments");
-    }
-
     try {
+        // TODO: improve arg management a little...
+        if (argc != 5) {
+            throw qpidit::ArgumentError("Incorrect number of arguments");
+        }
+
         Json::Value testParams;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testParams, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder rbuilder;
+        Json::CharReader* jsonReader = rbuilder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testParams, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
         qpidit::jms_hdrs_props_test::Receiver receiver(argv[1], argv[2], argv[3], testParams[0], testParams[1]);
         proton::container(receiver).run();
 
-        Json::FastWriter fw;
         std::cout << argv[3] << std::endl;
         Json::Value returnList(Json::arrayValue);
         returnList.append(receiver.getReceivedValueMap());
         returnList.append(receiver.getReceivedHeadersMap());
         returnList.append(receiver.getReceivedPropertiesMap());
-        std::cout << fw.write(returnList);
+        Json::StreamWriterBuilder wbuilder;
+        wbuilder["indentation"] = "";
+        std::unique_ptr<Json::StreamWriter> writer(wbuilder.newStreamWriter());
+        std::ostringstream oss;
+        writer->write(returnList, &oss);
+        std::cout << oss.str() << std::endl;
     } catch (const std::exception& e) {
         std::cout << "JmsReceiver error: " << e.what() << std::endl;
     }
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.cpp b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.cpp
index ec8b024..2ef0d07 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.cpp
@@ -20,6 +20,7 @@
  */
 
 #include "qpidit/jms_hdrs_props_test/Sender.hpp"
+#include "qpidit/Base64.hpp"
 
 #include <cerrno>
 #include <iomanip>
@@ -136,13 +137,14 @@ namespace qpidit
                 uint8_t val = getIntegralValue<int8_t>(testValueStr);
                 bin.push_back(char(val));
             } else if (subType.compare("bytes") == 0) {
-                bin.assign(testValueStr.begin(), testValueStr.end());
+                bin = b64_decode(testValueStr);
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 bin.push_back(char(0));
                 if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    bin.push_back(getIntegralValue<char>(testValueStr.substr(2)));
+                    bin.push_back(getIntegralValue<char>(decodedStr.substr(2)));
                 } else { // Format: 'c'
-                    bin.push_back(testValueStr[0]);
+                    bin.push_back(decodedStr[0]);
                 }
             } else if (subType.compare("double") == 0) {
                 uint64_t val;
@@ -203,13 +205,14 @@ namespace qpidit
             } else if (subType.compare("byte") == 0) {
                 m[mapKey] = int8_t(getIntegralValue<int8_t>(testValueStr));
             } else if (subType.compare("bytes") == 0) {
-                m[mapKey] = proton::binary(testValueStr);
+                m[mapKey] = b64_decode(testValueStr);
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 wchar_t val;
-                if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    val = (wchar_t)getIntegralValue<wchar_t>(testValueStr.substr(2));
+                if (decodedStr[0] == '\\') { // Format: '\xNN'
+                    val = (wchar_t)getIntegralValue<wchar_t>(decodedStr.substr(2));
                 } else { // Format: 'c'
-                    val = testValueStr[0];
+                    val = decodedStr[0];
                 }
                 m[mapKey] = val;
             } else if (subType.compare("double") == 0) {
@@ -250,13 +253,14 @@ namespace qpidit
             } else if (subType.compare("byte") == 0) {
                 l.push_back(int8_t(getIntegralValue<int8_t>(testValueStr)));
             } else if (subType.compare("bytes") == 0) {
-                l.push_back(proton::binary(testValueStr));
+                l.push_back(b64_decode(testValueStr));
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 wchar_t val;
-                if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    val = (wchar_t)getIntegralValue<wchar_t>(testValueStr.substr(2));
+                if (decodedStr[0] == '\\') { // Format: '\xNN'
+                    val = (wchar_t)getIntegralValue<wchar_t>(decodedStr.substr(2));
                 } else { // Format: 'c'
-                    val = testValueStr[0];
+                    val = decodedStr[0];
                 }
                 l.push_back(val);
             } else if (subType.compare("double") == 0) {
@@ -297,7 +301,7 @@ namespace qpidit
                     setJmsTypeHeader(msg, val);
                 } else if (i->compare("JMS_CORRELATIONID_HEADER") == 0) {
                     if (headerValueType.compare("bytes") == 0) {
-                        setJmsCorrelationId(msg, proton::binary(val));
+                        setJmsCorrelationId(msg, b64_decode(val));
                     } else {
                         setJmsCorrelationId(msg, val);
                     }
@@ -424,19 +428,21 @@ namespace qpidit
  */
 
 int main(int argc, char** argv) {
-    // TODO: improve arg management a little...
-    if (argc != 5) {
-        throw qpidit::ArgumentError("Incorrect number of arguments");
-    }
+    try {
+        // TODO: improve arg management a little...
+        if (argc != 5) {
+            throw qpidit::ArgumentError("Incorrect number of arguments");
+        }
 
-    std::ostringstream oss;
-    oss << argv[1] << "/" << argv[2];
+        std::ostringstream oss;
+        oss << argv[1] << "/" << argv[2];
 
-    try {
         Json::Value testParams;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testParams, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder builder;
+        Json::CharReader* jsonReader = builder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testParams, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
         qpidit::jms_hdrs_props_test::Sender sender(oss.str(), argv[3], testParams);
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.hpp b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.hpp
index 4b5d6e7..ebeba48 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_hdrs_props_test/Sender.hpp
@@ -76,7 +76,7 @@ namespace qpidit
             static proton::binary getJavaObjectBinary(const std::string& javaClassName, const std::string& valAsString);
             static uint32_t getTotalNumMessages(const Json::Value& testValueMap);
 
-            template<typename T> static T numToBinary(T n, proton::binary& b) {
+            template<typename T> static void numToBinary(T n, proton::binary& b) {
                 for (int i=0; i<sizeof(n); ++i) {
                     b.push_back(* ((char*)&n + i));
                 }
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Receiver.cpp b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Receiver.cpp
index ebbdfe4..0682225 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Receiver.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Receiver.cpp
@@ -20,6 +20,7 @@
  */
 
 #include "qpidit/jms_messages_test/Receiver.hpp"
+#include "qpidit/Base64.hpp"
 
 #include <iostream>
 #include <json/json.h>
@@ -156,11 +157,11 @@ namespace qpidit
                 } else if (subType.compare("byte") == 0) {
                     _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(proton::get<int8_t>(val))));
                 } else if (subType.compare("bytes") == 0) {
-                    _receivedSubTypeList.append(Json::Value(std::string(proton::get<proton::binary>(val))));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::get<proton::binary>(val))));
                 } else if (subType.compare("char") == 0) {
                     std::ostringstream oss;
                     oss << (char)proton::get<wchar_t>(val);
-                    _receivedSubTypeList.append(Json::Value(oss.str()));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
                 } else if (subType.compare("double") == 0) {
                     double d = proton::get<double>(val);
                     _receivedSubTypeList.append(Json::Value(toHexStr<int64_t>(*((int64_t*)&d), true, false)));
@@ -195,14 +196,14 @@ namespace qpidit
                 int8_t val = *((int8_t*)body.data());
                 _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(val)));
             } else if (subType.compare("bytes") == 0) {
-                _receivedSubTypeList.append(Json::Value(std::string(body)));
+                _receivedSubTypeList.append(Json::Value(b64_encode(body)));
             } else if (subType.compare("char") == 0) {
                 if (body.size() != sizeof(uint16_t)) throw IncorrectMessageBodyLengthError("JmsReceiver::receiveJmsBytesMessage, subType=char", sizeof(uint16_t), body.size());
                 // TODO: This is ugly: ignoring first byte - handle UTF-16 correctly
                 char c = body[1];
                 std::ostringstream oss;
                 oss << c;
-                _receivedSubTypeList.append(Json::Value(oss.str()));
+                _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
             } else if (subType.compare("double") == 0) {
                 if (body.size() != sizeof(int64_t)) throw IncorrectMessageBodyLengthError("JmsReceiver::receiveJmsBytesMessage, subType=double", sizeof(int64_t), body.size());
                 int64_t val = be64toh(*((int64_t*)body.data()));
@@ -244,11 +245,11 @@ namespace qpidit
                 } else if (subType.compare("byte") == 0) {
                     _receivedSubTypeList.append(Json::Value(toHexStr<int8_t>(proton::get<int8_t>(*i))));
                 } else if (subType.compare("bytes") == 0) {
-                    _receivedSubTypeList.append(Json::Value(std::string(proton::get<proton::binary>(*i))));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::get<proton::binary>(*i))));
                 } else if (subType.compare("char") == 0) {
                     std::ostringstream oss;
                     oss << (char)proton::get<wchar_t>(*i);
-                    _receivedSubTypeList.append(Json::Value(oss.str()));
+                    _receivedSubTypeList.append(Json::Value(b64_encode(proton::binary(oss.str()))));
                 } else if (subType.compare("double") == 0) {
                     double d = proton::get<double>(*i);
                     _receivedSubTypeList.append(Json::Value(toHexStr<int64_t>(*((int64_t*)&d), true, false)));
@@ -293,21 +294,27 @@ int main(int argc, char** argv) {
             throw qpidit::ArgumentError("Incorrect number of arguments (expected 4):\n\t1. Broker TCP address(ip-addr:port)\n\t2. Queue name\n\t3. JMS message type\n\t4. JSON data string\n");
         }
 
-        std::ostringstream oss;
-        oss << argv[1] << "/" << argv[2];
+        std::ostringstream oss1;
+        oss1 << argv[1] << "/" << argv[2];
 
         Json::Value testParams;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testParams, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder rbuilder;
+        Json::CharReader* jsonReader = rbuilder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testParams, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
-        qpidit::jms_messages_test::Receiver receiver(oss.str(), argv[3], testParams);
+        qpidit::jms_messages_test::Receiver receiver(oss1.str(), argv[3], testParams);
         proton::container(receiver).run();
 
-        Json::FastWriter fw;
         std::cout << argv[3] << std::endl;
-        std::cout << fw.write(receiver.getReceivedValueMap());
+        Json::StreamWriterBuilder wbuilder;
+        wbuilder["indentation"] = "";
+        std::unique_ptr<Json::StreamWriter> writer(wbuilder.newStreamWriter());
+        std::ostringstream oss2;
+        writer->write(receiver.getReceivedValueMap(), &oss2);
+        std::cout << oss2.str() << std::endl;
     } catch (const std::exception& e) {
         std::cout << "JmsReceiver error: " << e.what() << std::endl;
     }
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.cpp b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.cpp
index 5266dcf..5a61be5 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.cpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.cpp
@@ -20,6 +20,7 @@
  */
 
 #include "qpidit/jms_messages_test/Sender.hpp"
+#include "qpidit/Base64.hpp"
 
 #include <cerrno>
 #include <iomanip>
@@ -132,13 +133,14 @@ namespace qpidit
                 uint8_t val = getIntegralValue<int8_t>(testValueStr);
                 bin.push_back(char(val));
             } else if (subType.compare("bytes") == 0) {
-                bin.assign(testValueStr.begin(), testValueStr.end());
+                bin = b64_decode(testValueStr);
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 bin.push_back(char(0));
-                if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    bin.push_back(getIntegralValue<char>(testValueStr.substr(2)));
+                if (decodedStr[0] == '\\') { // Format: '\xNN'
+                    bin.push_back(getIntegralValue<char>(decodedStr.substr(2)));
                 } else { // Format: 'c'
-                    bin.push_back(testValueStr[0]);
+                    bin.push_back(decodedStr[0]);
                 }
             } else if (subType.compare("double") == 0) {
                 uint64_t val;
@@ -146,30 +148,21 @@ namespace qpidit
                     val = htobe64(std::strtoul(testValueStr.data(), NULL, 16));
                 } catch (const std::exception& e) { throw qpidit::InvalidTestValueError("double", testValueStr); }
                 numToBinary(val, bin);
-               //for (int i=0; i<sizeof(val); ++i) {
-               //     bin.push_back(* ((char*)&val + i));
-               // }
             } else if (subType.compare("float") == 0) {
                 uint32_t val;
                 try {
                     val = htobe32((uint32_t)std::strtoul(testValueStr.data(), NULL, 16));
                 } catch (const std::exception& e) { throw qpidit::InvalidTestValueError("float", testValueStr); }
                 numToBinary(val, bin);
-                //for (int i=0; i<sizeof(val); ++i) {
-                //    bin.push_back(* ((char*)&val + i));
-                //}
             } else if (subType.compare("long") == 0) {
                 uint64_t val = htobe64(getIntegralValue<uint64_t>(testValueStr));
                 numToBinary(val, bin);
-                //bin.assign(sizeof(val), val);
             } else if (subType.compare("int") == 0) {
                 uint32_t val = htobe32(getIntegralValue<uint32_t>(testValueStr));
                 numToBinary(val, bin);
-                //bin.assign(sizeof(val), val);
             } else if (subType.compare("short") == 0) {
                 uint16_t val = htobe16(getIntegralValue<int16_t>(testValueStr));
                 numToBinary(val, bin);
-                //bin.assign(sizeof(val), val);
             } else if (subType.compare("string") == 0) {
                 std::ostringstream oss;
                 uint16_t strlen = htobe16((uint16_t)testValueStr.size());
@@ -199,13 +192,14 @@ namespace qpidit
             } else if (subType.compare("byte") == 0) {
                 m[mapKey] = int8_t(getIntegralValue<int8_t>(testValueStr));
             } else if (subType.compare("bytes") == 0) {
-                m[mapKey] = proton::binary(testValueStr);
+                m[mapKey] = b64_decode(testValueStr);
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 wchar_t val;
-                if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    val = (wchar_t)getIntegralValue<wchar_t>(testValueStr.substr(2));
+                if (decodedStr[0] == '\\') { // Format: '\xNN'
+                    val = (wchar_t)getIntegralValue<wchar_t>(decodedStr.substr(2));
                 } else { // Format: 'c'
-                    val = testValueStr[0];
+                    val = decodedStr[0];
                 }
                 m[mapKey] = val;
             } else if (subType.compare("double") == 0) {
@@ -246,13 +240,14 @@ namespace qpidit
             } else if (subType.compare("byte") == 0) {
                 l.push_back(int8_t(getIntegralValue<int8_t>(testValueStr)));
             } else if (subType.compare("bytes") == 0) {
-                l.push_back(proton::binary(testValueStr));
+                l.push_back(b64_decode(testValueStr));
             } else if (subType.compare("char") == 0) {
+                std::string decodedStr = b64_decode(testValueStr);
                 wchar_t val;
-                if (testValueStr[0] == '\\') { // Format: '\xNN'
-                    val = (wchar_t)getIntegralValue<wchar_t>(testValueStr.substr(2));
+                if (decodedStr[0] == '\\') { // Format: '\xNN'
+                    val = (wchar_t)getIntegralValue<wchar_t>(decodedStr.substr(2));
                 } else { // Format: 'c'
-                    val = testValueStr[0];
+                    val = decodedStr[0];
                 }
                 l.push_back(val);
             } else if (subType.compare("double") == 0) {
@@ -334,9 +329,11 @@ int main(int argc, char** argv) {
         oss << argv[1] << "/" << argv[2];
 
         Json::Value testParams;
-        Json::Reader jsonReader;
-        if (not jsonReader.parse(argv[4], testParams, false)) {
-            throw qpidit::JsonParserError(jsonReader);
+        Json::CharReaderBuilder builder;
+        Json::CharReader* jsonReader = builder.newCharReader();
+        std::string parseErrors;
+        if (not jsonReader->parse(argv[4], argv[4] + ::strlen(argv[4]), &testParams, &parseErrors)) {
+            throw qpidit::JsonParserError(parseErrors);
         }
 
         qpidit::jms_messages_test::Sender sender(oss.str(), argv[3], testParams);
diff --git a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.hpp b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.hpp
index b808aec..cb47b1f 100644
--- a/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.hpp
+++ b/shims/qpid-proton-cpp/src/qpidit/jms_messages_test/Sender.hpp
@@ -66,7 +66,7 @@ namespace qpidit
             static proton::binary getJavaObjectBinary(const std::string& javaClassName, const std::string& valAsString);
             static uint32_t getTotalNumMessages(const Json::Value& testValueMap);
 
-            template<typename T> static T numToBinary(T n, proton::binary& b) {
+            template<typename T> static void numToBinary(T n, proton::binary& b) {
                 for (int i=0; i<sizeof(n); ++i) {
                     b.push_back(* ((char*)&n + i));
                 }
diff --git a/shims/qpid-proton-python/src/amqp_complex_types_test/Common.py b/shims/qpid-proton-python/src/amqp_complex_types_test/Common.py
index 6b8103a..e297f10 100644
--- a/shims/qpid-proton-python/src/amqp_complex_types_test/Common.py
+++ b/shims/qpid-proton-python/src/amqp_complex_types_test/Common.py
@@ -50,7 +50,12 @@ class AmqpComplexTypesTestShim(proton.handlers.MessagingHandler):
     def get_array(self, array_data):
         """Get AMQP array from array_data"""
         for array in array_data:
-            if array.type == self.proton_type(self.amqp_subtype):
+            # Empty arrays are of type proton.Data.NULL, but have no elements
+            if self.amqp_subtype == 'None' and array.type == self.proton_type(self.amqp_subtype) and not array.elements:
+                return array
+            if self.amqp_subtype == 'null' and array.type == self.proton_type(self.amqp_subtype) and array.elements:
+                return array
+            if self.amqp_subtype not in ['None', 'null'] and array.type == self.proton_type(self.amqp_subtype):
                 return array
         print('%s: get_array(): Unable to find array subtype "%s" in array test data' %
               (self.role, self.amqp_subtype), file=sys.stderr)
@@ -142,7 +147,7 @@ class AmqpComplexTypesTestShim(proton.handlers.MessagingHandler):
             print('%s: get_class(): Unknown subtype "%s"' % (self.role, amqp_subtype), file=sys.stderr)
             sys.exit(1)
 
-    PROTON_TYPE_MAP = {'None': None,
+    PROTON_TYPE_MAP = {'None': proton.Data.NULL,
                        'null': proton.Data.NULL,
                        'boolean': proton.Data.BOOL,
                        'ubyte': proton.Data.UBYTE,
diff --git a/shims/qpid-proton-python/src/amqp_complex_types_test/Receiver.py b/shims/qpid-proton-python/src/amqp_complex_types_test/Receiver.py
index 331a5a1..fbeea3e 100644
--- a/shims/qpid-proton-python/src/amqp_complex_types_test/Receiver.py
+++ b/shims/qpid-proton-python/src/amqp_complex_types_test/Receiver.py
@@ -107,19 +107,20 @@ class AmqpComplexTypesTestReceiver(amqp_complex_types_test.Common.AmqpComplexTyp
         if len(arr1.elements) != len(arr2.elements):
             return False
         # Check each element is the same value
-        for elt1, elt2 in zip(arr1.elements, arr2.elements):
-            if arr1.type == proton.Data.ARRAY and isinstance(elt1, proton.Array):
-                if not AmqpComplexTypesTestReceiver.check_arrays_equal(elt1, elt2):
-                    return False
-            elif arr1.type == proton.Data.LIST and isinstance(elt1, list):
-                if not AmqpComplexTypesTestReceiver.check_lists_equal(elt1, elt2):
-                    return False
-            elif arr1.type == proton.Data.MAP and isinstance(elt1, dict):
-                if not AmqpComplexTypesTestReceiver.check_maps_equal(elt1, elt2):
-                    return False
-            else:
-                if not AmqpComplexTypesTestReceiver.check_simple_values_equal(elt1, elt2):
-                    return False
+        if len(arr1.elements) > 0:
+            for elt1, elt2 in zip(arr1.elements, arr2.elements):
+                if arr1.type == proton.Data.ARRAY and isinstance(elt1, proton.Array):
+                    if not AmqpComplexTypesTestReceiver.check_arrays_equal(elt1, elt2):
+                        return False
+                elif arr1.type == proton.Data.LIST and isinstance(elt1, list):
+                    if not AmqpComplexTypesTestReceiver.check_lists_equal(elt1, elt2):
+                        return False
+                elif arr1.type == proton.Data.MAP and isinstance(elt1, dict):
+                    if not AmqpComplexTypesTestReceiver.check_maps_equal(elt1, elt2):
+                        return False
+                else:
+                    if not AmqpComplexTypesTestReceiver.check_simple_values_equal(elt1, elt2):
+                        return False
         return True
 
     @staticmethod
diff --git a/shims/qpid-proton-python/src/amqp_types_test/Receiver.py b/shims/qpid-proton-python/src/amqp_types_test/Receiver.py
index 5067de2..b4f50dd 100755
--- a/shims/qpid-proton-python/src/amqp_types_test/Receiver.py
+++ b/shims/qpid-proton-python/src/amqp_types_test/Receiver.py
@@ -23,6 +23,7 @@ AMQP type test receiver shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import json
 import os.path
 import signal
@@ -32,7 +33,6 @@ import sys
 import traceback
 import uuid
 
-import proton
 import proton.handlers
 import proton.reactor
 import _compat
@@ -126,18 +126,13 @@ class AmqpTypesTestReceiver(proton.handlers.MessagingHandler):
         if amqp_type == 'uuid':
             return str(amqp_value)
         if amqp_type == 'binary':
-            return amqp_value.decode('utf-8')
+            return base64.b64encode(amqp_value).decode('utf-8')
         if amqp_type == 'string':
             return amqp_value
         if amqp_type == 'symbol':
             return amqp_value
-        if amqp_type == 'list':
-            return AmqpTypesTestReceiver.decode_amqp_list(amqp_value)
-        if amqp_type == 'map':
-            return AmqpTypesTestReceiver.decode_amqp_map(amqp_value)
-        if amqp_type == 'array':
-            #return AmqpTypesTestReceiver.decode_amqp_array(amqp_value)
-            print('receive: Unsupported AMQP type "%s"' % amqp_type)
+        if amqp_type in ['array', 'list', 'map']:
+            print('receive: Complex AMQP type "%s" unsupported, see amqp_complex_types_test' % amqp_type)
             return None
         print('receive: Unknown AMQP type "%s"' % amqp_type)
         return None
@@ -206,39 +201,6 @@ class AmqpTypesTestReceiver(proton.handlers.MessagingHandler):
 
         print('receive: Unmapped AMQP type: %s:%s' % (type(amqp_value), amqp_value))
 
-    @staticmethod
-    def decode_complex_amqp_element(amqp_value):
-        """Decode an element from a complex AMQP type from its Python value"""
-        amqp_type = AmqpTypesTestReceiver.get_amqp_type(amqp_value)
-        if amqp_type == "list":
-            return AmqpTypesTestReceiver.decode_amqp_list(amqp_value)
-        if amqp_type == "map":
-            return AmqpTypesTestReceiver.decode_amqp_map(amqp_value)
-        return "%s:%s" % (amqp_type, AmqpTypesTestReceiver.decode_amqp_type(amqp_type, amqp_value))
-
-    @staticmethod
-    def decode_amqp_list(amqp_value):
-        """Decode amqp list type"""
-#        print('LIST:%s' % amqp_value)
-        amqp_list = []
-        for list_item in amqp_value:
-            amqp_list.append(AmqpTypesTestReceiver.decode_complex_amqp_element(list_item))
-        return amqp_list
-
-    @staticmethod
-    def decode_amqp_map(amqp_value):
-        """Decode amqp map type"""
-        amqp_map = {}
-        for key, value in amqp_value.items():
-            amqp_map[AmqpTypesTestReceiver.decode_complex_amqp_element(key)] = \
-                    AmqpTypesTestReceiver.decode_complex_amqp_element(value)
-        return amqp_map
-
-    @staticmethod
-    def decode_amqp_array(amqp_value):
-        """Decode amqp array type"""
-        return amqp_value
-
     def on_transport_error(self, event):
         print('Receiver: Broker not found at %s' % self.broker_url)
 
diff --git a/shims/qpid-proton-python/src/amqp_types_test/Sender.py b/shims/qpid-proton-python/src/amqp_types_test/Sender.py
index 034cfc5..7e7f800 100755
--- a/shims/qpid-proton-python/src/amqp_types_test/Sender.py
+++ b/shims/qpid-proton-python/src/amqp_types_test/Sender.py
@@ -23,6 +23,7 @@ AMQP type test sender shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import json
 import os.path
 import signal
@@ -31,7 +32,6 @@ import sys
 import traceback
 import uuid
 
-import proton
 import proton.handlers
 import proton.reactor
 import _compat
@@ -121,77 +121,19 @@ class AmqpTypesTestSender(proton.handlers.MessagingHandler):
         if amqp_type == 'uuid':
             return uuid.UUID(test_value)
         if amqp_type == 'binary':
-            return test_value.encode('utf-8')
+            return base64.b64decode(test_value)
+        if amqp_type == 'binarystr':
+            return _compat.unicode(test_value)
         if amqp_type == 'string':
             return _compat.unicode(test_value)
         if amqp_type == 'symbol':
             return proton.symbol(test_value)
-        if amqp_type == 'list':
-            return AmqpTypesTestSender.encode_amqp_list(test_value)
-        if amqp_type == 'map':
-            return AmqpTypesTestSender.encode_amqp_map(test_value)
-        if amqp_type == 'array':
-            #return AmqpTypesTestSender.encode_amqp_array(test_value)
-            print('send: Unsupported AMQP type "%s"' % amqp_type)
+        if amqp_type in ['array', 'list', 'map']:
+            print('send: Complex AMQP type "%s" unsupported, see amqp_complex_types_test' % amqp_type)
             return None
         print('send: Unknown AMQP type "%s"' % amqp_type)
         return None
 
-    @staticmethod
-    def encode_complex_amqp_element(test_element, make_hashable=False):
-        """
-        Encode a single complex AMQP element (ie list or array member, map key or value)
-        A complex element may be one of:
-        str/unicode: 'amqp_type:amqp_value'
-        list: [...]
-        dict: {...}
-        """
-        if _compat.IS_PY3:
-            is_string = isinstance(test_element, str)
-        else:
-            is_string = isinstance(test_element, unicode)
-        if is_string:
-            split_list = test_element.split(':', 1)
-            return AmqpTypesTestSender.encode_amqp_type(split_list[0], split_list[1])
-        if isinstance(test_element, list):
-            enc_list = AmqpTypesTestSender.encode_amqp_list(test_element)
-            if make_hashable:
-                return tuple(enc_list) # Convert list to tuple
-            return enc_list
-        if isinstance(test_element, dict):
-            enc_dict = AmqpTypesTestSender.encode_amqp_map(test_element)
-            if make_hashable:
-                return tuple(enc_dict.items()) # Convert to tuple of k,v pairs
-            return enc_dict
-        else:
-            print('Unexpected complex amqp element type: %s, value=%s' % (type(test_element), str(test_element)))
-
-    @staticmethod
-    def encode_amqp_list(test_value):
-        """
-        Encode an AMQP list from the format [val1, val2, ...]
-        Each val is in the string format amqp_type:amqp_val_as_str
-        """
-        val_list = []
-        for val in test_value:
-            val_list.append(AmqpTypesTestSender.encode_complex_amqp_element(val))
-        return val_list
-
-    @staticmethod
-    def encode_amqp_map(test_value):
-        """Encode an AMQP map from the format {key1:val1, key2:val2, ...}"""
-        val_map = {}
-        for key, val in test_value.items():
-            encoded_key = AmqpTypesTestSender.encode_complex_amqp_element(key, True) # make keys hashable
-            encoded_val = AmqpTypesTestSender.encode_complex_amqp_element(val)
-            val_map[encoded_key] = encoded_val
-        return val_map
-
-    @staticmethod
-    def encode_amqp_array(test_value):
-        """Encode an AMQP array"""
-        return test_value
-
     def on_accepted(self, event):
         """Event callback for when a sent message is accepted by the broker"""
         self.confirmed += 1
diff --git a/shims/qpid-proton-python/src/jms_hdrs_props_test/Receiver.py b/shims/qpid-proton-python/src/jms_hdrs_props_test/Receiver.py
index 2cabf10..3642149 100755
--- a/shims/qpid-proton-python/src/jms_hdrs_props_test/Receiver.py
+++ b/shims/qpid-proton-python/src/jms_hdrs_props_test/Receiver.py
@@ -23,6 +23,7 @@ JMS message headers and properties test receiver shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import json
 import signal
 import struct
@@ -31,11 +32,12 @@ import sys
 import time
 import traceback
 
+from qpid_interop_test.qit_errors import InteropTestError
+from qpid_interop_test.qit_jms_types import QPID_JMS_TYPE_ANNOTATION_NAME
+
 import proton
 import proton.handlers
 import proton.reactor
-from qpid_interop_test.qit_errors import InteropTestError
-from qpid_interop_test.qit_jms_types import QPID_JMS_TYPE_ANNOTATION_NAME
 import _compat
 
 
@@ -160,12 +162,12 @@ class JmsHdrsPropsTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(struct.unpack('b', message.body)[0])
         if self.current_subtype == 'bytes':
-            return message.body.decode('utf-8')
+            return base64.b64encode(message.body).decode('utf-8')
         if self.current_subtype == 'char':
             if len(message.body) == 2: # format 'a' or '\xNN'
                 if _compat.IS_PY3:
-                    return chr(message.body[1]) # strip leading '\x00' char
-                return str(message.body[1]) # strip leading '\x00' char
+                    return base64.b64encode(bytes([message.body[1]])).decode('utf-8') # strip leading '\x00' char
+                return base64.b64encode(bytes(message.body[1])).decode('utf-8') # strip leading '\x00' char
             raise InteropTestError('Unexpected strring length for type char: %d' % len(message.body))
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', message.body)[0]
@@ -186,9 +188,8 @@ class JmsHdrsPropsTestReceiver(proton.handlers.MessagingHandler):
                     raise InteropTestError('String length mismatch: size=%d, but len(\'%s\')=%d' %
                                            (str_len, str_body, len(str_body)))
                 return str_body
-            else:
-                raise InteropTestError('Malformed string binary: len(\'%s\')=%d' %
-                                       (repr(message.body), len(message.body)))
+            raise InteropTestError('Malformed string binary: len(\'%s\')=%d' %
+                                   (repr(message.body), len(message.body)))
         raise InteropTestError('JMS message type %s: Unknown or unsupported subtype \'%s\'' %
                                (self.jms_msg_type, self.current_subtype))
 
@@ -203,9 +204,11 @@ class JmsHdrsPropsTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(value)
         if self.current_subtype == 'bytes':
-            return value.decode('utf-8')
+            return base64.b64encode(value).decode('utf-8')
         if self.current_subtype == 'char':
-            return str(value)
+            if _compat.IS_PY3:
+                return base64.b64encode(bytes(value, 'utf-8')).decode('utf-8')
+            return base64.b64encode(bytes(value)).decode('utf-8')
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', struct.pack('!d', value))[0]
         if self.current_subtype == 'float':
@@ -266,9 +269,11 @@ class JmsHdrsPropsTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(value)
         if self.current_subtype == 'bytes':
-            return value.decode('utf-8')
+            return base64.b64encode(value).decode('utf-8')
         if self.current_subtype == 'char':
-            return str(value)
+            if _compat.IS_PY3:
+                return base64.b64encode(bytes(value, 'utf-8')).decode('utf-8')
+            return base64.b64encode(bytes(value)).decode('utf-8')
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', struct.pack('!d', value))[0]
         if self.current_subtype == 'float':
@@ -302,7 +307,8 @@ class JmsHdrsPropsTestReceiver(proton.handlers.MessagingHandler):
         correlation_id = message.correlation_id
         if correlation_id is not None:
             if 'JMS_CORRELATIONID_AS_BYTES' in self.flag_map and self.flag_map['JMS_CORRELATIONID_AS_BYTES']:
-                self.jms_header_map['JMS_CORRELATIONID_HEADER'] = {'bytes': correlation_id.decode('utf-8')}
+                bytes_val = base64.b64encode(correlation_id).decode('utf-8')
+                self.jms_header_map['JMS_CORRELATIONID_HEADER'] = {'bytes': bytes_val}
             else:
                 self.jms_header_map['JMS_CORRELATIONID_HEADER'] = {'string': correlation_id}
 
diff --git a/shims/qpid-proton-python/src/jms_hdrs_props_test/Sender.py b/shims/qpid-proton-python/src/jms_hdrs_props_test/Sender.py
index 076920c..e19949d 100755
--- a/shims/qpid-proton-python/src/jms_hdrs_props_test/Sender.py
+++ b/shims/qpid-proton-python/src/jms_hdrs_props_test/Sender.py
@@ -23,6 +23,7 @@ JMS message headers and properties test sender shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import os.path
 import signal
 import struct
@@ -175,10 +176,10 @@ class JmsHdrsPropsTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             body_bytes = struct.pack('b', int(test_value, 16))
         elif test_value_type == 'bytes':
-            body_bytes = test_value.encode('utf-8')
+            body_bytes = base64.b64decode(test_value)
         elif test_value_type == 'char':
             # JMS expects two-byte chars, ASCII chars can be prefixed with '\x00'
-            body_bytes = b'\x00' + test_value.encode('utf-8')
+            body_bytes = b'\x00' + base64.b64decode(test_value)
         elif test_value_type == 'double' or test_value_type == 'float':
             body_bytes = test_value[2:].decode('hex')
         elif test_value_type == 'int':
@@ -209,9 +210,9 @@ class JmsHdrsPropsTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             value = proton.byte(int(test_value, 16))
         elif test_value_type == 'bytes':
-            value = test_value.encode('utf-8')
+            value = base64.b64decode(test_value)
         elif test_value_type == 'char':
-            value = proton.char(test_value)
+            value = proton.char(base64.b64decode(test_value).decode('utf-8'))
         elif test_value_type == 'double':
             value = struct.unpack('!d', test_value[2:].decode('hex'))[0]
         elif test_value_type == 'float':
@@ -266,9 +267,9 @@ class JmsHdrsPropsTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             body_list = [proton.byte(int(test_value, 16))]
         elif test_value_type == 'bytes':
-            body_list = [test_value.encode('utf-8')]
+            body_list = [base64.b64decode(test_value)]
         elif test_value_type == 'char':
-            body_list = [proton.char(test_value)]
+            body_list = [proton.char(base64.b64decode(test_value).decode('utf-8'))]
         elif test_value_type == 'double':
             body_list = [struct.unpack('!d', test_value[2:].decode('hex'))[0]]
         elif test_value_type == 'float':
@@ -317,7 +318,7 @@ class JmsHdrsPropsTestSender(proton.handlers.MessagingHandler):
                 if value_type == 'string':
                     hdr_kwargs['correlation_id'] = value
                 elif value_type == 'bytes':
-                    hdr_kwargs['correlation_id'] = value.encode('utf-8')
+                    hdr_kwargs['correlation_id'] = base64.b64decode(value)
                 else:
                     raise InteropTestError('JmsSenderShim._get_jms_message_header_kwargs(): ' +
                                            'JMS_CORRELATIONID_HEADER requires value type "string" or "bytes", ' +
diff --git a/shims/qpid-proton-python/src/jms_messages_test/Receiver.py b/shims/qpid-proton-python/src/jms_messages_test/Receiver.py
index c2d27bf..b457369 100755
--- a/shims/qpid-proton-python/src/jms_messages_test/Receiver.py
+++ b/shims/qpid-proton-python/src/jms_messages_test/Receiver.py
@@ -23,6 +23,7 @@ JMS receiver shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import json
 import signal
 import struct
@@ -30,11 +31,12 @@ import subprocess
 import sys
 import traceback
 
+from qpid_interop_test.qit_errors import InteropTestError
+from qpid_interop_test.qit_jms_types import QPID_JMS_TYPE_ANNOTATION_NAME
+
 import proton
 import proton.handlers
 import proton.reactor
-from qpid_interop_test.qit_errors import InteropTestError
-from qpid_interop_test.qit_jms_types import QPID_JMS_TYPE_ANNOTATION_NAME
 import _compat
 
 class JmsMessagesTestReceiver(proton.handlers.MessagingHandler):
@@ -145,12 +147,12 @@ class JmsMessagesTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(struct.unpack('b', message.body)[0])
         if self.current_subtype == 'bytes':
-            return message.body.decode('utf-8')
+            return base64.b64encode(message.body).decode('utf-8')
         if self.current_subtype == 'char':
             if len(message.body) == 2: # format 'a' or '\xNN'
                 if _compat.IS_PY3:
-                    return chr(message.body[1]) # strip leading '\x00' char
-                return str(message.body[1]) # strip leading '\x00' char
+                    return base64.b64encode(bytes([message.body[1]])).decode('utf-8') # strip leading '\x00' char
+                return base64.b64encode(bytes(message.body[1])).decode('utf-8') # strip leading '\x00' char
             raise InteropTestError('Unexpected string length for type char: %d' % len(message.body))
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', message.body)[0]
@@ -171,9 +173,8 @@ class JmsMessagesTestReceiver(proton.handlers.MessagingHandler):
                     raise InteropTestError('String length mismatch: size=%d, but len(\'%s\')=%d' %
                                            (str_len, str_body, len(str_body)))
                 return str_body
-            else:
-                raise InteropTestError('Malformed string binary: len(\'%s\')=%d' %
-                                       (repr(message.body), len(message.body)))
+            raise InteropTestError('Malformed string binary: len(\'%s\')=%d' %
+                                   (repr(message.body), len(message.body)))
         raise InteropTestError('JMS message type %s: Unknown or unsupported subtype \'%s\'' %
                                (self.jms_msg_type, self.current_subtype))
 
@@ -188,9 +189,11 @@ class JmsMessagesTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(value)
         if self.current_subtype == 'bytes':
-            return value.decode('utf-8')
+            return base64.b64encode(value).decode('utf-8')
         if self.current_subtype == 'char':
-            return str(value)
+            if _compat.IS_PY3:
+                return base64.b64encode(bytes(value, 'utf-8')).decode('utf-8')
+            return base64.b64encode(bytes(value)).decode('utf-8')
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', struct.pack('!d', value))[0]
         if self.current_subtype == 'float':
@@ -251,9 +254,11 @@ class JmsMessagesTestReceiver(proton.handlers.MessagingHandler):
         if self.current_subtype == 'byte':
             return hex(value)
         if self.current_subtype == 'bytes':
-            return value.decode('utf-8')
+            return base64.b64encode(value).decode('utf-8')
         if self.current_subtype == 'char':
-            return str(value)
+            if _compat.IS_PY3:
+                return base64.b64encode(bytes(value, 'utf-8')).decode('utf-8')
+            return base64.b64encode(bytes(value)).decode('utf-8')
         if self.current_subtype == 'double':
             return '0x%016x' % struct.unpack('!Q', struct.pack('!d', value))[0]
         if self.current_subtype == 'float':
diff --git a/shims/qpid-proton-python/src/jms_messages_test/Sender.py b/shims/qpid-proton-python/src/jms_messages_test/Sender.py
index 931da10..3707707 100755
--- a/shims/qpid-proton-python/src/jms_messages_test/Sender.py
+++ b/shims/qpid-proton-python/src/jms_messages_test/Sender.py
@@ -23,6 +23,7 @@ JMS sender shim for qpid-interop-test
 # under the License.
 #
 
+import base64
 import json
 import signal
 import subprocess
@@ -156,10 +157,10 @@ class JmsMessagesTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             body_bytes = struct.pack('b', int(test_value, 16))
         elif test_value_type == 'bytes':
-            body_bytes = test_value.encode('utf-8')
+            body_bytes = base64.b64decode(test_value)
         elif test_value_type == 'char':
             # JMS expects two-byte chars, ASCII chars can be prefixed with '\x00'
-            body_bytes = b'\x00' + test_value.encode('utf-8')
+            body_bytes = b'\x00' + base64.b64decode(test_value)
         elif test_value_type == 'double' or test_value_type == 'float':
             body_bytes = _compat.decode_hex(test_value[2:])
         elif test_value_type == 'int':
@@ -189,9 +190,9 @@ class JmsMessagesTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             value = proton.byte(int(test_value, 16))
         elif test_value_type == 'bytes':
-            value = test_value.encode('utf-8')
+            value = base64.b64decode(test_value)
         elif test_value_type == 'char':
-            value = proton.char(test_value)
+            value = proton.char(base64.b64decode(test_value).decode('utf-8'))
         elif test_value_type == 'double':
             value = struct.unpack('!d', _compat.decode_hex(test_value[2:]))[0]
         elif test_value_type == 'float':
@@ -242,9 +243,9 @@ class JmsMessagesTestSender(proton.handlers.MessagingHandler):
         elif test_value_type == 'byte':
             body_list = [proton.byte(int(test_value, 16))]
         elif test_value_type == 'bytes':
-            body_list = [test_value.encode('utf-8')]
+            body_list = [base64.b64decode(test_value)]
         elif test_value_type == 'char':
-            body_list = [proton.char(test_value)]
+            body_list = [proton.char(base64.b64decode(test_value).decode('utf-8'))]
         elif test_value_type == 'double':
             body_list = [struct.unpack('!d', _compat.decode_hex(test_value[2:]))[0]]
         elif test_value_type == 'float':
diff --git a/shims/rhea-js/amqp_types_test/Receiver.js b/shims/rhea-js/amqp_types_test/Receiver.js
index 94f886d..b445f73 100755
--- a/shims/rhea-js/amqp_types_test/Receiver.js
+++ b/shims/rhea-js/amqp_types_test/Receiver.js
@@ -72,9 +72,9 @@ function Receiver(brokerAddr, brokerPort, queueName, amqpType, numTestValues) {
         case "binary": this.receivedValueList.push(this.decodeBinary(msgBody)); break;
         case "string": this.receivedValueList.push(this.decodeString(msgBody)); break;
         case "symbol": this.receivedValueList.push(this.decodeSymbol(msgBody)); break;
-        case "list": this.receivedValueList.push(this.decodeList(msgBody)); break;
-        case "map": this.receivedValueList.push(this.decodeMap(msgBody)); break;
-        case "array": this.receivedValueList.push(this.decodeArray(msgBody)); break;
+        case "list":
+        case "map":
+        case "array": throw "Unsupported complex AMQP type: \"" + this.amqpType + "\"";
         default: throw "Unknown AMQP type: " + this.amqpType;
         }
     };
@@ -136,7 +136,8 @@ function Receiver(brokerAddr, brokerPort, queueName, amqpType, numTestValues) {
     };
 
     this.decodeBinary = function(msgBody) {
-        return msgBody.toString();
+        var buff = new Buffer(msgBody)
+        return buff.toString('base64');
     };
 
     this.decodeString = function(msgBody) {
@@ -147,18 +148,6 @@ function Receiver(brokerAddr, brokerPort, queueName, amqpType, numTestValues) {
         return msgBody;
     };
 
-    this.decodeList = function(msgBody) {
-        return msgBody; // TODO: decode list
-    };
-
-    this.decodeMap = function(msgBody) {
-        return msgBody; // TODO: decode map
-    };
-
-    this.decodeArray = function(msgBody) {
-        return msgBody; // TODO: decode array
-    };
-
     this.buffer2HexString = function(buff, pad) {
         var hexStr = "";
         var first = true;
diff --git a/shims/rhea-js/amqp_types_test/Sender.js b/shims/rhea-js/amqp_types_test/Sender.js
index f663365..2293747 100755
--- a/shims/rhea-js/amqp_types_test/Sender.js
+++ b/shims/rhea-js/amqp_types_test/Sender.js
@@ -98,9 +98,9 @@ function Sender(brokerAddr, brokerPort, queueName, amqpType, testValues) {
         case "binary": return {body: amqp_types.wrap_binary(this.encodeBinary(testValue))};
         case "string": return {body: amqp_types.wrap_string(this.encodeString(testValue))};
         case "symbol": return {body: amqp_types.wrap_symbol(this.encodeSymbol(testValue))};
-        case "list": return {body: amqp_types.wrap_list(this.encodeList(testValue))};
-        case "map": return {body: amqp_types.wrap_map(this.encodeMap(testValue))};
-        case "array": return {body: amqp_types.wrap_array(this.encodeArray(testValue.slice(1), AmqpArrayTypes[testValue[0]]))};
+        case "list":
+        case "map":
+        case "array": throw "Unsupported complex AMQP type: \"" + this.amqpType + "\"";
         default: throw "Unknown AMQP type: \"" + this.amqpType + "\"";
         }
     };
@@ -129,9 +129,9 @@ function Sender(brokerAddr, brokerPort, queueName, amqpType, testValues) {
         case "binary": return this.encodeBinary(testValue);
         case "string": return this.encodeString(testValue);
         case "symbol": return this.encodeSymbol(testValue);
-        case "list": return this.encodeList(testValue);
-        case "map": return this.encodeMap(testValue);
-        case "array": return this.encodeArray(testValue);
+        case "list":
+        case "map":
+        case "array": throw "Unsupported complex AMQP type: \"" + this.amqpType + "\"";
         default: throw "Unknown AMQP type: \"" + this.amqpType + "\"";
         }
     };
@@ -256,7 +256,8 @@ function Sender(brokerAddr, brokerPort, queueName, amqpType, testValues) {
     };
 
     this.encodeBinary = function(testValue) {
-        return testValue;
+        var buff = new Buffer(testValue, 'base64')
+        return buff;
     };
 
     this.encodeString = function(testValue) {
@@ -267,19 +268,6 @@ function Sender(brokerAddr, brokerPort, queueName, amqpType, testValues) {
         return testValue;
     };
 
-    this.encodeList = function(testValue) {
-        return testValue; // TODO: encode list
-    };
-
-    this.encodeMap = function(testValue) {
-        return testValue; // TODO: encode map
-    };
-
-    // testValue format for arrays: ['type', 'val1', 'val2', ... ]
-    this.encodeArray = function(testValue) {
-        return testValue.slice(1); // TODO: encode array
-    };
-
     this.handleEncodeError = function(amqpType, testValue, err) {
         var errStr = "Invalid string value for type " + amqpType + ": \"" + testValue + "\"";
         if (err) {
diff --git a/src/python/qpid_interop_test/amqp_complex_types_test.array.json b/src/python/qpid_interop_test/amqp_complex_types_test.array.json
index d2d5833..3573321 100644
--- a/src/python/qpid_interop_test/amqp_complex_types_test.array.json
+++ b/src/python/qpid_interop_test/amqp_complex_types_test.array.json
@@ -28,7 +28,7 @@
  ["array", [["byte", -128],
             ["byte", -1],
             ["byte", 0],
-            ["byte", 255]]],
+            ["byte", 127]]],
  ["array", [["short", "-0x8000"],
             ["short", -1],
             ["short", 0],
diff --git a/src/python/qpid_interop_test/amqp_complex_types_test.py b/src/python/qpid_interop_test/amqp_complex_types_test.py
index a63e581..e68667a 100755
--- a/src/python/qpid_interop_test/amqp_complex_types_test.py
+++ b/src/python/qpid_interop_test/amqp_complex_types_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Module to test AMQP complex types across different clients
@@ -33,7 +33,7 @@ import itertools
 import qpid_interop_test.qit_common
 from qpid_interop_test.qit_errors import InteropTestError, InteropTestTimeout
 
-DEFAULT_TEST_TIMEOUT = 10 # seconds
+DEFAULT_TEST_TIMEOUT = 20 # seconds
 
 class AmqpComplexTypes(qpid_interop_test.qit_common.QitTestTypeMap):
     """
@@ -89,6 +89,7 @@ class AmqpComplexTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 
     client_skip = {}
 
+    #pylint: disable=too-many-branches
     def get_types(self, args):
         """Return the list of types"""
         if "include_type" in args and args.include_type is not None:
@@ -139,6 +140,8 @@ class AmqpComplexTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 class AmqpComplexTypeTestCase(qpid_interop_test.qit_common.QitTestCase):
     """Abstract base class for AMQP Complex Type test cases"""
 
+    #pylint: disable=too-many-arguments
+    #pylint: disable=too-many-locals
     def run_test(self, sender_addr, receiver_addr, amqp_type, amqp_subtype, send_shim, receive_shim, timeout):
         """
         Runs this test by invoking the shim send method to send the test values, followed by the shim receive method
@@ -219,8 +222,10 @@ class AmqpComplexTypesTest(qpid_interop_test.qit_common.QitTest):
             if self.args.exclude_type is None or amqp_type not in self.args.exclude_type:
                 for amqp_subtype in self.types.get_subtype_list():
                     if amqp_type != 'array' or amqp_subtype != '*': # array type does not support mixed types (*)
-                        test_case_class = self.create_testcase_class(amqp_type, amqp_subtype,
-                                                                     itertools.product(self.shim_map.values(), repeat=2),
+                        test_case_class = self.create_testcase_class(amqp_type,
+                                                                     amqp_subtype,
+                                                                     itertools.product(self.shim_map.values(),
+                                                                                       repeat=2),
                                                                      int(self.args.timeout))
                         self.test_suite.addTest(unittest.makeSuite(test_case_class))
 
@@ -237,9 +242,9 @@ class AmqpComplexTypesTest(qpid_interop_test.qit_common.QitTest):
             @unittest.skipIf(self.types.skip_test(amqp_subtype, self.broker),
                              self.types.skip_test_message(amqp_subtype, self.broker))
             @unittest.skipIf(self.types.skip_client_test(amqp_subtype, send_shim.NAME),
-                             self.types.skip_client_test_message(amqp_subtype, send_shim.NAME, u'SENDER'))
+                             self.types.skip_client_test_message(amqp_subtype, send_shim.NAME, 'SENDER'))
             @unittest.skipIf(self.types.skip_client_test(amqp_subtype, receive_shim.NAME),
-                             self.types.skip_client_test_message(amqp_subtype, receive_shim.NAME, u'RECEIVER'))
+                             self.types.skip_client_test_message(amqp_subtype, receive_shim.NAME, 'RECEIVER'))
             def inner_test_method(self):
                 self.run_test(self.sender_addr,
                               self.receiver_addr,
diff --git a/src/python/qpid_interop_test/amqp_complex_types_test_generator.py b/src/python/qpid_interop_test/amqp_complex_types_test_generator.py
index 21de6df..4e66e34 100755
--- a/src/python/qpid_interop_test/amqp_complex_types_test_generator.py
+++ b/src/python/qpid_interop_test/amqp_complex_types_test_generator.py
@@ -30,7 +30,7 @@ import sys
 import time
 from abc import abstractmethod
 
-COPYRIGHT_TEXT = u"""Licensed to the Apache Software Foundation (ASF) under one
+COPYRIGHT_TEXT = """Licensed to the Apache Software Foundation (ASF) under one
 or more contributor license agreements.  See the NOTICE file
 distributed with this work for additional information
 regarding copyright ownership.  The ASF licenses this file
@@ -48,19 +48,20 @@ specific language governing permissions and limitations
 under the License."""
 
 DEFAULT_PATH = os.path.dirname(os.path.realpath(__file__))
-DEFAULT_JSON_BASE_NAME = u'amqp_complex_types_test'
-GENERATOR_TARGETS = [u'python', u'cpp', u'javascript', u'dotnet', u'ALL']
-AMQP_COMPEX_TYPES = [u'array', u'list', u'map', u'ALL']
+DEFAULT_JSON_BASE_NAME = 'amqp_complex_types_test'
+GENERATOR_TARGETS = ['python', 'cpp', 'javascript', 'dotnet', 'ALL']
+AMQP_COMPEX_TYPES = ['array', 'list', 'map', 'ALL']
 INDENT_LEVEL_SIZE = 4
 
-class JsonReader(object):
+#pylint: disable=too-few-public-methods
+class JsonReader:
     """Class to read the JSON data file"""
     def __init__(self, args):
         self.args = args
 
     def generate(self):
         """Generate the output files based on command-line argument choices"""
-        if self.args.gen == u'ALL':
+        if self.args.gen == 'ALL':
             gen_targets = GENERATOR_TARGETS[:-1]
         else:
             gen_targets = [self.args.gen]
@@ -68,35 +69,35 @@ class JsonReader(object):
         for target in gen_targets:
             target_file_name = None
             if target == GENERATOR_TARGETS[0]: # Python
-                target_file_name = os.path.join(gen_path, u'%s_data.py' % self.args.json_base_name)
+                target_file_name = os.path.join(gen_path, '%s_data.py' % self.args.json_base_name)
                 with PythonGenerator(target_file_name) as generator:
                     self._generate_target(target, generator)
             elif target == GENERATOR_TARGETS[1]: # C++
-                target_file_name = os.path.join(gen_path, u'%s_data.cpp' % self.args.json_base_name)
+                target_file_name = os.path.join(gen_path, '%s_data.cpp' % self.args.json_base_name)
                 with CppGenerator(target_file_name) as generator:
                     self._generate_target(target, generator)
             elif target == GENERATOR_TARGETS[2]: # JavaScript
-                target_file_name = os.path.join(gen_path, u'%s_data.js' % self.args.json_base_name)
+                target_file_name = os.path.join(gen_path, '%s_data.js' % self.args.json_base_name)
                 with JavaScriptGenerator(target_file_name) as generator:
                     self._generate_target(target, generator)
             elif target == GENERATOR_TARGETS[3]: # DotNet
-                target_file_name = os.path.join(gen_path, u'%s_data.cs' % self.args.json_base_name)
+                target_file_name = os.path.join(gen_path, '%s_data.cs' % self.args.json_base_name)
                 with DotNetGenerator(target_file_name) as generator:
                     self._generate_target(target, generator)
             else:
-                raise RuntimeError(u'Unknown target %s' % target)
+                raise RuntimeError('Unknown target %s' % target)
 
     def _generate_target(self, target, generator):
         """Generate the output file for target type"""
-        print(u'amqp_complex_types_test_generator: target=%s generator=%s' % (target, generator.__class__.__name__))
+        print('amqp_complex_types_test_generator: target=%s generator=%s' % (target, generator.__class__.__name__))
         generator.write_prefix()
-        if self.args.type == u'ALL':
+        if self.args.type == 'ALL':
             amqp_test_types = AMQP_COMPEX_TYPES[:-1]
         else:
             amqp_test_types = [self.args.type]
         # First parse
         for amqp_test_type in amqp_test_types:
-            json_file_name = os.path.join(os.path.abspath(self.args.src_dir), u'%s.%s.json' %
+            json_file_name = os.path.join(os.path.abspath(self.args.src_dir), '%s.%s.json' %
                                           (self.args.json_base_name, amqp_test_type))
             generator.write_code(amqp_test_type, JsonReader._read_file(json_file_name))
         generator.write_postfix()
@@ -104,31 +105,30 @@ class JsonReader(object):
     @staticmethod
     def _read_file(json_file_name):
         """Read the file into a Python data structure"""
-        #print(u'reading file %s' % os.path.basename(json_file_name))
         try:
-            json_file = open(json_file_name, u'r')
+            json_file = open(json_file_name, 'r')
             json_file_data = json_file.read()
             json_file.close()
             return json.loads(json_file_data)
         except IOError:
-            print(u'ERROR: Unable to read JSON source file "%s"' % json_file_name)
+            print('ERROR: Unable to read JSON source file "%s"' % json_file_name)
             sys.exit(1)
 
     @staticmethod
     def _target_file_extension(target):
-        file_extension_map = {u'python': u'py',
-                              u'cpp': u'cpp',
-                              u'javascript': u'js',
-                              u'dotnet': u'cs'}
+        file_extension_map = {'python': 'py',
+                              'cpp': 'cpp',
+                              'javascript': 'js',
+                              'dotnet': 'cs'}
         if target in file_extension_map:
             return file_extension_map[target]
-        raise RuntimeError(u'Unknown target: %s' % target)
+        raise RuntimeError('Unknown target: %s' % target)
 
 
-class Generator(object):
+class Generator:
     """Abstract code generator class"""
     def __init__(self, target_file_name):
-        self.target_file = open(target_file_name, u'w')
+        self.target_file = open(target_file_name, 'w')
 
     def __enter__(self):
         return self
@@ -156,211 +156,221 @@ class PythonGenerator(Generator):
 
     def write_prefix(self):
         """Write comments, copyright, etc at top of Python source file"""
-        self.target_file.write(u'#!/usr/bin/env python\n\n')
-        self.target_file.write(u'"""Data used for qpid_interop_test.amqp_complex_types_test"""\n\n')
+        self.target_file.write('#!/usr/bin/env python3\n\n')
+        self.target_file.write('"""Data used for qpid_interop_test.amqp_complex_types_test"""\n\n')
         for line in iter(COPYRIGHT_TEXT.splitlines()):
-            self.target_file.write(u'# %s\n' % line)
-        self.target_file.write(u'\n# *** THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY ***\n')
-        self.target_file.write(u'# Generated by building qpid_interop_test\n')
-        self.target_file.write(u'# Generated: %s\n\n' % time.strftime(u'%Y-%m-%d %H:%M:%S', time.gmtime()))
-        self.target_file.write(u'import uuid\nimport proton\nimport _compat\n\n')
-        self.target_file.write(u'TEST_DATA = {\n')
+            if line:
+                self.target_file.write('# %s\n' % line)
+            else:
+                self.target_file.write('#')
+        self.target_file.write('\n# *** THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY ***\n')
+        self.target_file.write('# Generated by building qpid_interop_test\n')
+        self.target_file.write('# Generated: %s\n\n' % time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime()))
+        self.target_file.write('import uuid\nimport proton\nimport _compat\n\n')
+        self.target_file.write('TEST_DATA = {\n')
 
     def write_code(self, amqp_test_type, json_data):
         """Write Python code from json_data"""
-        hdr_line = u'=' * (19 + len(amqp_test_type))
-        self.target_file.write(u'\n    # %s\n' % hdr_line)
-        self.target_file.write(u'    # *** AMQP type: %s ***\n' % amqp_test_type)
-        self.target_file.write(u'    # %s\n\n' % hdr_line)
-        self.target_file.write(u'    \'%s\': [\n' % amqp_test_type)
+        hdr_line = '=' * (19 + len(amqp_test_type))
+        self.target_file.write('\n    # %s\n' % hdr_line)
+        self.target_file.write('    # *** AMQP type: %s ***\n' % amqp_test_type)
+        self.target_file.write('    # %s\n\n' % hdr_line)
+        self.target_file.write('    \'%s\': [\n' % amqp_test_type)
         for data_pair in json_data:
             self._write_data_pair(2, data_pair)
-        self.target_file.write(u'    ], # end: AMQP type %s\n' % amqp_test_type)
+        self.target_file.write('    ], # end: AMQP type %s\n' % amqp_test_type)
 
     #pylint: disable=too-many-branches
     #pylint: disable=too-many-statements
-    def _write_data_pair(self, indent_level, data_pair, separator=u',', eol=True, indent=True):
+    #pylint: disable=too-many-arguments
+    def _write_data_pair(self, indent_level, data_pair, separator=',', eol=True, indent=True):
         """Write a JOSN pair ['amqp_type', value]"""
-        indent_str = u' ' * (indent_level * INDENT_LEVEL_SIZE) if indent else u''
-        post_indent_str = u' ' * (indent_level * INDENT_LEVEL_SIZE)
-        eol_char = u'\n' if eol else u''
+        indent_str = ' ' * (indent_level * INDENT_LEVEL_SIZE) if indent else ''
+        post_indent_str = ' ' * (indent_level * INDENT_LEVEL_SIZE)
+        eol_char = '\n' if eol else ''
         amqp_type, value = data_pair
-        if amqp_type == u'null':
-            self.target_file.write(u'%sNone%s%s' % (indent_str, separator, eol_char))
-        elif amqp_type == u'boolean':
-            self.target_file.write(u'%s%s%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'ubyte':
-            self.target_file.write(u'%sproton.ubyte(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'byte':
-            self.target_file.write(u'%sproton.byte(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'ushort':
-            self.target_file.write(u'%sproton.ushort(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'short':
-            self.target_file.write(u'%sproton.short(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'uint':
-            self.target_file.write(u'%sproton.uint(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'int':
-            self.target_file.write(u'%sproton.int32(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'ulong':
-            self.target_file.write(u'%sproton.ulong(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'long':
+        if amqp_type == 'null':
+            self.target_file.write('%sNone%s%s' % (indent_str, separator, eol_char))
+        elif amqp_type == 'boolean':
+            self.target_file.write('%s%s%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'ubyte':
+            self.target_file.write('%sproton.ubyte(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'byte':
+            self.target_file.write('%sproton.byte(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'ushort':
+            self.target_file.write('%sproton.ushort(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'short':
+            self.target_file.write('%sproton.short(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'uint':
+            self.target_file.write('%sproton.uint(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'int':
+            self.target_file.write('%sproton.int32(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'ulong':
+            self.target_file.write('%sproton.ulong(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'long':
             if isinstance(value, str):
-                if (len(value) > 2 and value[:2] == u'0x') or (len(value) > 3 and value[:3] == u'-0x'):
-                    self.target_file.write(u'%s_compat.str2long(u\'%s\', 16)%s%s' %
+                if (len(value) > 2 and value[:2] == '0x') or (len(value) > 3 and value[:3] == '-0x'):
+                    self.target_file.write('%s_compat.str2long(u\'%s\', 16)%s%s' %
                                            (indent_str, value, separator, eol_char))
                 else:
-                    self.target_file.write(u'%s_compat.str2long(u\'%s\', 10)%s%s' %
+                    self.target_file.write('%s_compat.str2long(u\'%s\', 10)%s%s' %
                                            (indent_str, value, separator, eol_char))
             else:
-                self.target_file.write(u'%s_compat.long(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'float':
-            if isinstance(value, str) and (value[-3:] == u'inf' or value[-3:] == u'NaN'):
-                self.target_file.write(u'%sproton.float32(u\'%s\')%s%s' % (indent_str, value, separator, eol_char))
+                self.target_file.write('%s_compat.long(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'float':
+            if isinstance(value, str) and (value[-3:] == 'inf' or value[-3:] == 'NaN'):
+                self.target_file.write('%sproton.float32(u\'%s\')%s%s' % (indent_str, value, separator, eol_char))
             else:
-                self.target_file.write(u'%sproton.float32(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'double':
-            if isinstance(value, str) and (value[-3:] == u'inf' or value[-3:] == u'NaN'):
-                self.target_file.write(u'%sfloat(u\'%s\')%s%s' % (indent_str, value, separator, eol_char))
+                self.target_file.write('%sproton.float32(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'double':
+            if isinstance(value, str) and (value[-3:] == 'inf' or value[-3:] == 'NaN'):
+                self.target_file.write('%sfloat(u\'%s\')%s%s' % (indent_str, value, separator, eol_char))
             else:
-                self.target_file.write(u'%sfloat(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'decimal32':
-            self.target_file.write(u'%sproton.decimal32(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'decimal64':
-            self.target_file.write(u'%sproton.decimal64(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'decimal128':
+                self.target_file.write('%sfloat(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'decimal32':
+            self.target_file.write('%sproton.decimal32(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'decimal64':
+            self.target_file.write('%sproton.decimal64(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'decimal128':
             byte_itr = iter(value[2:])
-            self.target_file.write(u'%sproton.decimal128(b\'' % indent_str)
+            self.target_file.write('%sproton.decimal128(b\'' % indent_str)
             for char_ in byte_itr:
-                self.target_file.write(u'\\x%c%c' % (char_, next(byte_itr)))
-            self.target_file.write(u'\')%s%s' % (separator, eol_char))
-        elif amqp_type == u'char':
-            self.target_file.write(u'%sproton.char(' % indent_str)
+                self.target_file.write('\\x%c%c' % (char_, next(byte_itr)))
+            self.target_file.write('\')%s%s' % (separator, eol_char))
+        elif amqp_type == 'char':
+            self.target_file.write('%sproton.char(' % indent_str)
             if len(value) == 1: # single char
-                self.target_file.write(u'u\'%s\'' % value)
+                self.target_file.write('u\'%s\'' % value)
             else:
-                self.target_file.write(u'_compat.unichr(int(u\'%s\', 16))' % value)
-            self.target_file.write(u')%s%s' % (separator, eol_char))
-        elif amqp_type == u'timestamp':
-            self.target_file.write(u'%sproton.timestamp(%s)%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'uuid':
-            self.target_file.write(u'%suuid.UUID(' % indent_str)
-            if value[:2] == u'0x':
-                self.target_file.write(u'int=%s' % value)
+                self.target_file.write('_compat.unichr(int(u\'%s\', 16))' % value)
+            self.target_file.write(')%s%s' % (separator, eol_char))
+        elif amqp_type == 'timestamp':
+            self.target_file.write('%sproton.timestamp(%s)%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'uuid':
+            self.target_file.write('%suuid.UUID(' % indent_str)
+            if value[:2] == '0x':
+                self.target_file.write('int=%s' % value)
             else:
-                self.target_file.write(u'u\'{%s}\'' % value)
-            self.target_file.write(u')%s%s' % (separator, eol_char))
-        elif amqp_type == u'binary':
+                self.target_file.write('u\'{%s}\'' % value)
+            self.target_file.write(')%s%s' % (separator, eol_char))
+        elif amqp_type == 'binary':
             if isinstance(value, int):
                 value = hex(value)
             if isinstance(value, str):
-                self.target_file.write(u'%sb\'' % indent_str)
-                if value[:2] == u'0x':
+                self.target_file.write('%sb\'' % indent_str)
+                if value[:2] == '0x':
                     value = value[2:]
                     if len(value) % 2 > 0:
                         value = '0' + value
                     byte_itr = iter(value)
                     for char_ in byte_itr:
-                        self.target_file.write(u'\\x%c%c' % (char_, next(byte_itr)))
+                        self.target_file.write('\\x%c%c' % (char_, next(byte_itr)))
                 else:
                     for char_ in value:
-                        if char_ == u'\'':
-                            self.target_file.write(u'\\')
+                        if char_ == '\'':
+                            self.target_file.write('\\')
                         self.target_file.write(char_)
-                self.target_file.write(u'\'%s%s' % (separator, eol_char))
+                self.target_file.write('\'%s%s' % (separator, eol_char))
             else:
-                self.target_file.write(u'%s%d%s%s' % (indent_str, value, separator, eol_char))
-        elif amqp_type == u'string':
-            self.target_file.write(u'%su\'' % indent_str)
+                self.target_file.write('%s%d%s%s' % (indent_str, value, separator, eol_char))
+        elif amqp_type == 'string':
+            self.target_file.write('%su\'' % indent_str)
             for char_ in value:
-                if char_ == u'\'':
-                    self.target_file.write(u'\\')
+                if char_ == '\'':
+                    self.target_file.write('\\')
                 self.target_file.write(char_)
-            self.target_file.write(u'\'%s%s' % (separator, eol_char))
-        elif amqp_type == u'symbol':
-            self.target_file.write(u'%sproton.symbol(u\'' % indent_str)
+            self.target_file.write('\'%s%s' % (separator, eol_char))
+        elif amqp_type == 'symbol':
+            self.target_file.write('%sproton.symbol(u\'' % indent_str)
             for char_ in value:
-                if char_ == u'\'':
-                    self.target_file.write(u'\\')
+                if char_ == '\'':
+                    self.target_file.write('\\')
                 self.target_file.write(char_)
-            self.target_file.write(u'\')%s%s' % (separator, eol_char))
-        elif amqp_type == u'array':
+            self.target_file.write('\')%s%s' % (separator, eol_char))
+        elif amqp_type == 'array':
             if not isinstance(value, list):
-                raise RuntimeError(u'AMQP array value not a list, found %s' % type(value))
+                raise RuntimeError('AMQP array value not a list, found %s' % type(value))
             amqp_type = None
             if value:
                 amqp_type = value[0][0]
-            self.target_file.write(u'%sproton.Array(proton.UNDESCRIBED, %s, [\n' %
+            self.target_file.write('%sproton.Array(proton.UNDESCRIBED, %s' %
                                    (indent_str, PythonGenerator._proton_type_code(amqp_type)))
+            if amqp_type:
+                self.target_file.write(', \n')
             for value_data_pair in value:
                 if value_data_pair[0] != amqp_type:
-                    raise RuntimeError(u'AMQP array of type %s has element of type %s' %
+                    raise RuntimeError('AMQP array of type %s has element of type %s' %
                                        (amqp_type, value_data_pair[0]))
                 self._write_data_pair(indent_level+1, value_data_pair)
-            self.target_file.write(u'%s]),%s' % (post_indent_str, eol_char))
-        elif amqp_type == u'list':
+            if amqp_type:
+                self.target_file.write('%s),%s' % (post_indent_str, eol_char))
+            else:
+                self.target_file.write('),%s' % eol_char)
+        elif amqp_type == 'list':
             if not isinstance(value, list):
-                raise RuntimeError(u'AMQP list value not a list, found %s' % type(value))
-            self.target_file.write(u'%s[\n' % indent_str)
+                raise RuntimeError('AMQP list value not a list, found %s' % type(value))
+            self.target_file.write('%s[\n' % indent_str)
             for value_data_pair in value:
                 self._write_data_pair(indent_level+1, value_data_pair)
-            self.target_file.write(u'%s],%s' % (post_indent_str, eol_char))
-        elif amqp_type == u'map':
+            self.target_file.write('%s],%s' % (post_indent_str, eol_char))
+        elif amqp_type == 'map':
             if not isinstance(value, list):
-                raise RuntimeError(u'AMQP map value not a list, found %s' % type(value))
+                raise RuntimeError('AMQP map value not a list, found %s' % type(value))
             if len(value) % 2 != 0:
-                raise RuntimeError(u'AMQP map value list not even, contains %d items' % len(value))
-            self.target_file.write(u'%s{\n' % indent_str)
+                raise RuntimeError('AMQP map value list not even, contains %d items' % len(value))
+            self.target_file.write('%s{\n' % indent_str)
             # consume list in pairs (key, value)
             value_iter = iter(value)
             for value_data_pair in value_iter:
-                self._write_data_pair(indent_level+1, value_data_pair, separator=u': ', eol=False)
+                self._write_data_pair(indent_level+1, value_data_pair, separator=': ', eol=False)
                 value_data_pair = next(value_iter)
                 self._write_data_pair(indent_level+1, value_data_pair, indent=False)
-            self.target_file.write(u'%s},%s' % (post_indent_str, eol_char))
+            self.target_file.write('%s},%s' % (post_indent_str, eol_char))
         else:
-            raise RuntimeError(u'Unknown AMQP type \'%s\'' % amqp_type)
+            raise RuntimeError('Unknown AMQP type \'%s\'' % amqp_type)
 
     @staticmethod
     def _proton_type_code(amqp_type):
         amqp_types = {
-            None: None,
-            u'null': u'proton.Data.NULL',
-            u'boolean': u'proton.Data.BOOL',
-            u'byte': u'proton.Data.BYTE',
-            u'ubyte': u'proton.Data.UBYTE',
-            u'short': u'proton.Data.SHORT',
-            u'ushort': u'proton.Data.USHORT',
-            u'int': u'proton.Data.INT',
-            u'uint': u'proton.Data.UINT',
-            u'char': u'proton.Data.CHAR',
-            u'long': u'proton.Data.LONG',
-            u'ulong': u'proton.Data.ULONG',
-            u'timestamp': u'proton.Data.TIMESTAMP',
-            u'float': u'proton.Data.FLOAT',
-            u'double': u'proton.Data.DOUBLE',
-            u'decimal32': u'proton.Data.DECIMAL32',
-            u'decimal64': u'proton.Data.DECIMAL64',
-            u'decimal128': u'proton.Data.DECIMAL128',
-            u'uuid': u'proton.Data.UUID',
-            u'binary': u'proton.Data.BINARY',
-            u'string': u'proton.Data.STRING',
-            u'symbol': u'proton.Data.SYMBOL',
-            u'described': u'proton.Data.DESCRIBED',
-            u'array': u'proton.Data.ARRAY',
-            u'list': u'proton.Data.LIST',
-            u'map': u'proton.Data.MAP'
+            None: 'proton.Data.NULL',
+            'null': 'proton.Data.NULL',
+            'boolean': 'proton.Data.BOOL',
+            'byte': 'proton.Data.BYTE',
+            'ubyte': 'proton.Data.UBYTE',
+            'short': 'proton.Data.SHORT',
+            'ushort': 'proton.Data.USHORT',
+            'int': 'proton.Data.INT',
+            'uint': 'proton.Data.UINT',
+            'char': 'proton.Data.CHAR',
+            'long': 'proton.Data.LONG',
+            'ulong': 'proton.Data.ULONG',
+            'timestamp': 'proton.Data.TIMESTAMP',
+            'float': 'proton.Data.FLOAT',
+            'double': 'proton.Data.DOUBLE',
+            'decimal32': 'proton.Data.DECIMAL32',
+            'decimal64': 'proton.Data.DECIMAL64',
+            'decimal128': 'proton.Data.DECIMAL128',
+            'uuid': 'proton.Data.UUID',
+            'binary': 'proton.Data.BINARY',
+            'string': 'proton.Data.STRING',
+            'symbol': 'proton.Data.SYMBOL',
+            'described': 'proton.Data.DESCRIBED',
+            'array': 'proton.Data.ARRAY',
+            'list': 'proton.Data.LIST',
+            'map': 'proton.Data.MAP'
             }
         return amqp_types[amqp_type]
 
     def write_postfix(self):
         """Write postfix at bottom of Python source file"""
-        self.target_file.write(u'}\n\n# <eof>\n')
+        self.target_file.write('}\n\n# <eof>\n')
 
 
+#pylint: disable=too-many-instance-attributes
 class CppGenerator(Generator):
     """C++ code generator"""
 
-    CODE_SEGMET_A = u'''#include <iostream>
+    CODE_SEGMET_A = '''#include <iostream>
 #include <qpidit/amqp_complex_types_test/Common.hpp>
 
 namespace qpidit {
@@ -371,7 +381,7 @@ namespace qpidit {
                 try {
 '''
 
-    CODE_SEGMENT_B = u'''                } catch (const std::exception& e) {
+    CODE_SEGMENT_B = '''                } catch (const std::exception& e) {
                     std::cerr << e.what() << std::endl;
                 }
             } // if (_dataMap.empty())
@@ -381,8 +391,8 @@ namespace qpidit {
 } // namespace qpidit
 '''
 
-    PROTON_TYPES = [u'decimal32', u'decimal64', u'decimal128', u'timestamp', u'uuid', u'binary', u'symbol']
-    COMPLEX_TYPES = [u'array', u'list', u'map']
+    PROTON_TYPES = ['decimal32', 'decimal64', 'decimal128', 'timestamp', 'uuid', 'binary', 'symbol']
+    COMPLEX_TYPES = ['array', 'list', 'map']
 
     class ComplexInstanceContext:
         """Context used for writing complex type instances"""
@@ -424,37 +434,37 @@ namespace qpidit {
 
     def write_prefix(self):
         """Write comments, copyright, etc. at top of C++ source file"""
-        self.target_file.write(u'/*\n')
+        self.target_file.write('/*\n')
         for line in iter(COPYRIGHT_TEXT.splitlines()):
-            self.target_file.write(u' * %s\n' % line)
-        self.target_file.write(u' */\n\n')
-        self.target_file.write(u'/*\n')
-        self.target_file.write(u' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
-        self.target_file.write(u' * Generated by building qpid_interop_test\n')
-        self.target_file.write(u' * Generated: %s\n' % time.strftime(u'%Y-%m-%d %H:%M:%S', time.gmtime()))
-        self.target_file.write(u' */\n\n')
-        self.target_file.write(u'/**\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
+            self.target_file.write(' * %s\n' % line)
+        self.target_file.write(' */\n\n')
+        self.target_file.write('/*\n')
+        self.target_file.write(' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
+        self.target_file.write(' * Generated by building qpid_interop_test\n')
+        self.target_file.write(' * Generated: %s\n' % time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime()))
+        self.target_file.write(' */\n\n')
+        self.target_file.write('/**\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
         self.target_file.write(CppGenerator.CODE_SEGMET_A)
 
     def write_code(self, amqp_test_type, json_data):
         """Write C++ code from json_data"""
         indent_level = 5
-        indent_str = u' ' * (indent_level * INDENT_LEVEL_SIZE)
-        container_name = u'%s_list' % amqp_test_type
-        container_type = u'std::vector<proton::value>'
-        hdr_line = u'*' * (17 + len(amqp_test_type))
-        self.target_file.write(u'\n%s/*%s\n' % (indent_str, hdr_line))
-        self.target_file.write(u'%s*** AMQP type: %s ***\n' % (indent_str, amqp_test_type))
-        self.target_file.write(u'%s%s*/\n\n' % (indent_str, hdr_line))
-        self.target_file.write(u'%s%s %s;\n\n' % (indent_str, container_type, container_name))
+        indent_str = ' ' * (indent_level * INDENT_LEVEL_SIZE)
+        container_name = '%s_list' % amqp_test_type
+        container_type = 'std::vector<proton::value>'
+        hdr_line = '*' * (17 + len(amqp_test_type))
+        self.target_file.write('\n%s/*%s\n' % (indent_str, hdr_line))
+        self.target_file.write('%s*** AMQP type: %s ***\n' % (indent_str, amqp_test_type))
+        self.target_file.write('%s%s*/\n\n' % (indent_str, hdr_line))
+        self.target_file.write('%s%s %s;\n\n' % (indent_str, container_type, container_name))
         self._pre_write_list(indent_level, container_name, json_data, True)
-        self.target_file.write(u'%s_testDataMap.insert(std::pair<const std::string, %s >("%s", %s));\n\n' %
+        self.target_file.write('%s_testDataMap.insert(std::pair<const std::string, %s >("%s", %s));\n\n' %
                                (indent_str, container_type, amqp_test_type, container_name))
 
     def write_postfix(self):
         """Write postfix at bottom of C++ source file"""
         self.target_file.write(CppGenerator.CODE_SEGMENT_B)
-        self.target_file.write(u'// <eof>\n')
+        self.target_file.write('// <eof>\n')
 
     def _pre_write_list(self, indent_level, container_name, value, push_flag=False):
         """If a value in a list is a complex or proton type, write instances before the list itself is written"""
@@ -471,73 +481,73 @@ namespace qpidit {
         """Generate c++ code for a complex instance"""
         amqp_type, value = data_pair
         if amqp_type not in CppGenerator.COMPLEX_TYPES:
-            raise RuntimeError(u'AMQP type %s is not complex (one of %s)' % (amqp_type, CppGenerator.COMPLEX_TYPES))
+            raise RuntimeError('AMQP type %s is not complex (one of %s)' % (amqp_type, CppGenerator.COMPLEX_TYPES))
         if not isinstance(value, list):
-            raise RuntimeError(u'AMQP %s value not a list, found %s' % (amqp_type, type(value)))
+            raise RuntimeError('AMQP %s value not a list, found %s' % (amqp_type, type(value)))
         CppGenerator.INSTANCE_GENERATE_FN[amqp_type](self, value, context)
 
     def _write_array_instance(self, value, context):
         """Generate c++ code for an array instance"""
-        indent_str = u' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
+        indent_str = ' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
         inner_instance_name_list = self._pre_write_list(context.indent_level(), context.container_name(), value)
         self.arr_count += 1
         array_cpp_type = CppGenerator._array_cpp_type(value)
-        self.target_file.write(u'%s%s array_%d = {' %
-                               (indent_str, CppGenerator._cpp_type(u'array', array_cpp_type), self.arr_count))
-        context.instance_name_list().append(u'pv_array_%d' % self.arr_count)
+        self.target_file.write('%s%s array_%d = {' %
+                               (indent_str, CppGenerator._cpp_type('array', array_cpp_type), self.arr_count))
+        context.instance_name_list().append('pv_array_%d' % self.arr_count)
         for value_data_pair in value:
             self._write_data_pair(value_data_pair, inner_instance_name_list)
         if value and value[0][0] in CppGenerator.COMPLEX_TYPES:
-            self.target_file.write(u'};\n%sproton::value pv_array_%d;\n' % (indent_str, self.arr_count))
-            self.target_file.write(u'%sproton::codec::encoder(pv_array_%d) << '
-                                   u'proton::codec::encoder::array(array_%d, %s);\n' %
+            self.target_file.write('};\n%sproton::value pv_array_%d;\n' % (indent_str, self.arr_count))
+            self.target_file.write('%sproton::codec::encoder(pv_array_%d) << '
+                                   'proton::codec::encoder::array(array_%d, %s);\n' %
                                    (indent_str, self.arr_count, self.arr_count,
                                     CppGenerator._array_proton_type(value)))
         else:
-            self.target_file.write(u'};\n%sproton::value pv_array_%d = array_%d;\n' %
+            self.target_file.write('};\n%sproton::value pv_array_%d = array_%d;\n' %
                                    (indent_str, self.arr_count, self.arr_count))
         if context.push_flag():
-            self.target_file.write(u'%s%s.push_back(pv_array_%d);\n\n' %
+            self.target_file.write('%s%s.push_back(pv_array_%d);\n\n' %
                                    (indent_str, context.container_name(), self.arr_count))
 
     def _write_list_instance(self, value, context):
         """Generate c++ code for a list instance"""
-        indent_str = u' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
+        indent_str = ' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
         inner_instance_name_list = self._pre_write_list(context.indent_level(), context.container_name(), value)
         self.list_count += 1
-        self.target_file.write(u'%sstd::vector<proton::value> list_%d = {' % (indent_str, self.list_count))
-        context.instance_name_list().append(u'pv_list_%d' % self.list_count)
+        self.target_file.write('%sstd::vector<proton::value> list_%d = {' % (indent_str, self.list_count))
+        context.instance_name_list().append('pv_list_%d' % self.list_count)
         for value_data_pair in value:
             self._write_data_pair(value_data_pair, inner_instance_name_list)
-        self.target_file.write(u'};\n%sproton::value pv_list_%d = list_%d;\n' %
+        self.target_file.write('};\n%sproton::value pv_list_%d = list_%d;\n' %
                                (indent_str, self.list_count, self.list_count))
         if context.push_flag():
-            self.target_file.write(u'%s%s.push_back(list_%d);\n\n' %
+            self.target_file.write('%s%s.push_back(list_%d);\n\n' %
                                    (indent_str, context.container_name(), self.list_count))
 
     def _write_map_instance(self, value, context):
         """Generate c++ code for a map instance"""
-        indent_str = u' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
+        indent_str = ' ' * (context.indent_level() * INDENT_LEVEL_SIZE)
         if len(value) % 2 != 0:
-            raise RuntimeError(u'AMQP map value list not even, contains %d items' % len(value))
+            raise RuntimeError('AMQP map value list not even, contains %d items' % len(value))
         inner_instance_name_list = self._pre_write_list(context.indent_level(), context.container_name(), value)
         self.map_count += 1
-        self.target_file.write(u'%sstd::vector<std::pair<proton::value, proton::value> > map_%d = {' %
+        self.target_file.write('%sstd::vector<std::pair<proton::value, proton::value> > map_%d = {' %
                                (indent_str, self.map_count))
-        context.instance_name_list().append(u'pv_map_%d' % self.map_count)
+        context.instance_name_list().append('pv_map_%d' % self.map_count)
         # consume list in pairs (key, value)
         value_iter = iter(value)
         for value_data_pair in value_iter:
-            self.target_file.write(u'std::pair<proton::value, proton::value>(')
+            self.target_file.write('std::pair<proton::value, proton::value>(')
             self._write_data_pair(value_data_pair, inner_instance_name_list)
             value_data_pair = next(value_iter)
             self._write_data_pair(value_data_pair, inner_instance_name_list, False)
-            self.target_file.write(u'), ')
-        self.target_file.write(u'};\n%sproton::value pv_map_%d;\n' % (indent_str, self.map_count))
-        self.target_file.write(u'%sproton::codec::encoder(pv_map_%d) << proton::codec::encoder::map(map_%d);\n' %
+            self.target_file.write('), ')
+        self.target_file.write('};\n%sproton::value pv_map_%d;\n' % (indent_str, self.map_count))
+        self.target_file.write('%sproton::codec::encoder(pv_map_%d) << proton::codec::encoder::map(map_%d);\n' %
                                (indent_str, self.map_count, self.map_count))
         if context.push_flag():
-            self.target_file.write(u'%s%s.push_back(map_%d);\n\n' %
+            self.target_file.write('%s%s.push_back(map_%d);\n\n' %
                                    (indent_str, context.container_name(), self.map_count))
 
     @staticmethod
@@ -545,22 +555,22 @@ namespace qpidit {
         """Return a cpp type string for use in array type encoding"""
         if data_list: # List not empty
             if data_list[0][0] in CppGenerator.COMPLEX_TYPES:
-                return u'proton::value'
+                return 'proton::value'
             # The type of the first element is assumed to be the type of the array
             return CppGenerator._cpp_type(data_list[0][0])
-        return u'std::nullptr_t'
+        return 'std::nullptr_t'
 
     @staticmethod
     def _array_proton_type(data_list):
         """Return a Proton cpp type string used in the proton::codec::encoder::array() function"""
         if data_list:
             data_list_type = data_list[0][0]
-            if data_list_type == u'array':
-                return u'proton::ARRAY'
-            if data_list_type == u'list':
-                return u'proton::LIST'
-            if data_list_type == u'map':
-                return u'proton::MAP'
+            if data_list_type == 'array':
+                return 'proton::ARRAY'
+            if data_list_type == 'list':
+                return 'proton::LIST'
+            if data_list_type == 'map':
+                return 'proton::MAP'
         return None
 
     def _write_proton_instance(self, indent_level, data_pair, instance_name_list):
@@ -568,58 +578,58 @@ namespace qpidit {
         Proton types do not yet support literals. Write proton values as instances, place assigned variable name
         onto instance_name_list so they can be placed into the AMQP complex type container.
         """
-        indent_str = u' ' * (indent_level * INDENT_LEVEL_SIZE)
+        indent_str = ' ' * (indent_level * INDENT_LEVEL_SIZE)
         amqp_type, value = data_pair
         CppGenerator.INSTANCE_GENERATE_FN[amqp_type](self, indent_str, value, instance_name_list)
 
     def _write_decimal32_instance(self, indent_str, value, instance_name_list):
         """Write proton::decimal32 instance"""
         self.d32_count += 1
-        self.target_file.write(u'%sproton::decimal32 d32_%d;\n' % (indent_str, self.d32_count))
-        self.target_file.write(u'%shexStringToBytearray(d32_%d, "%s");\n' %
+        self.target_file.write('%sproton::decimal32 d32_%d;\n' % (indent_str, self.d32_count))
+        self.target_file.write('%shexStringToBytearray(d32_%d, "%s");\n' %
                                (indent_str, self.d32_count, value[2:]))
-        instance_name_list.append(u'd32_%d' % self.d32_count)
+        instance_name_list.append('d32_%d' % self.d32_count)
 
     def _write_decimal64_instance(self, indent_str, value, instance_name_list):
         """Write proton::decimal64 instance"""
         self.d64_count += 1
-        self.target_file.write(u'%sproton::decimal64 d64_%d;\n' % (indent_str, self.d64_count))
-        self.target_file.write(u'%shexStringToBytearray(d64_%d, "%s");\n' %
+        self.target_file.write('%sproton::decimal64 d64_%d;\n' % (indent_str, self.d64_count))
+        self.target_file.write('%shexStringToBytearray(d64_%d, "%s");\n' %
                                (indent_str, self.d64_count, value[2:]))
-        instance_name_list.append(u'd64_%d' % self.d64_count)
+        instance_name_list.append('d64_%d' % self.d64_count)
 
     def _write_decimal128_instance(self, indent_str, value, instance_name_list):
         """Write proton::decimal128 instance"""
         self.d128_count += 1
-        self.target_file.write(u'%sproton::decimal128 d128_%d;\n' % (indent_str, self.d128_count))
-        self.target_file.write(u'%shexStringToBytearray(d128_%d, "%s");\n' %
+        self.target_file.write('%sproton::decimal128 d128_%d;\n' % (indent_str, self.d128_count))
+        self.target_file.write('%shexStringToBytearray(d128_%d, "%s");\n' %
                                (indent_str, self.d128_count, value[2:]))
-        instance_name_list.append(u'd128_%d' % self.d128_count)
+        instance_name_list.append('d128_%d' % self.d128_count)
 
     def _write_timestamp_instance(self, indent_str, value, instance_name_list):
         """Write proton::timestamp instance"""
         self.ts_count += 1
-        radix = 16 if isinstance(value, str) and len(value) > 2 and value[:2] == u'0x' else 10
+        radix = 16 if isinstance(value, str) and len(value) > 2 and value[:2] == '0x' else 10
         if radix == 16: # hex string
-            self.target_file.write(u'%sproton::timestamp ts_%d(std::strtoul(' % (indent_str, self.ts_count) +
-                                   u'std::string("%s").data(), nullptr, 16));\n' % value[2:])
+            self.target_file.write('%sproton::timestamp ts_%d(std::strtoul(' % (indent_str, self.ts_count) +
+                                   'std::string("%s").data(), nullptr, 16));\n' % value[2:])
         else:
-            self.target_file.write(u'%sproton::timestamp ts_%d(%s);\n' % (indent_str, self.ts_count, value))
-        instance_name_list.append(u'ts_%d' % self.ts_count)
+            self.target_file.write('%sproton::timestamp ts_%d(%s);\n' % (indent_str, self.ts_count, value))
+        instance_name_list.append('ts_%d' % self.ts_count)
 
     def _write_uuid_instance(self, indent_str, value, instance_name_list):
         """Write proton::uuid instance"""
         self.uuid_count += 1
-        self.target_file.write(u'%sproton::uuid uuid_%d;\n' % (indent_str, self.uuid_count))
-        if isinstance(value, str) and len(value) > 2 and value[:2] == u'0x': # Hex string "0x..."
+        self.target_file.write('%sproton::uuid uuid_%d;\n' % (indent_str, self.uuid_count))
+        if isinstance(value, str) and len(value) > 2 and value[:2] == '0x': # Hex string "0x..."
             # prefix hex strings < 32 chars (16 bytes) with 0s to make exactly 32 chars long
             fill_size = 32 - len(value[2:])
-            uuid_hex_str = u'%s%s' % (u'0' * fill_size, value[2:])
-            self.target_file.write(u'%shexStringToBytearray(uuid_%d, "%s");\n' %
+            uuid_hex_str = '%s%s' % ('0' * fill_size, value[2:])
+            self.target_file.write('%shexStringToBytearray(uuid_%d, "%s");\n' %
                                    (indent_str, self.uuid_count, uuid_hex_str))
         else: # UUID format "00000000-0000-0000-0000-000000000000"
-            self.target_file.write(u'%ssetUuid(uuid_%d, "%s");\n' % (indent_str, self.uuid_count, value))
-        instance_name_list.append(u'uuid_%d' % self.uuid_count)
+            self.target_file.write('%ssetUuid(uuid_%d, "%s");\n' % (indent_str, self.uuid_count, value))
+        instance_name_list.append('uuid_%d' % self.uuid_count)
 
     @staticmethod
     def _get_delimited_string_length(mixed_string):
@@ -653,27 +663,28 @@ namespace qpidit {
     def _write_binary_instance(self, indent_str, value, instance_name_list):
         """Write proton::binary instance"""
         self.bin_count += 1
-        if isinstance(value, int) or ((isinstance(value, str) and len(value) > 2 and value[:2] == u'0x')): # numeric
-            hex_str = u'{:02x}'.format(value) if isinstance(value, int) else value[2:]
+        if isinstance(value, int) or ((isinstance(value, str) and len(value) > 2 and value[:2] == '0x')): # numeric
+            hex_str = '{:02x}'.format(value) if isinstance(value, int) else value[2:]
             if len(hex_str) % 2 > 0: # make string even no. of hex chars, prefix with '0' if needed
-                hex_str = u'0%s' % hex_str
-            self.target_file.write(u'%sproton::binary bin_%d(std::string("' % (indent_str, self.bin_count))
+                hex_str = '0%s' % hex_str
+            self.target_file.write('%sproton::binary bin_%d(std::string("' % (indent_str, self.bin_count))
+            #pylint: disable=consider-using-enumerate
             for i in range(len(hex_str)):
                 if not i % 2:
-                    self.target_file.write(u'\\x')
+                    self.target_file.write('\\x')
                 self.target_file.write(hex_str[i])
-            self.target_file.write(u'", %d));\n' % (len(hex_str)/2))
+            self.target_file.write('", %d));\n' % (len(hex_str)/2))
         else: # string
-            self.target_file.write(u'%sproton::binary bin_%d(std::string("%s", %d));\n' %
+            self.target_file.write('%sproton::binary bin_%d(std::string("%s", %d));\n' %
                                    (indent_str, self.bin_count, value,
                                     CppGenerator._get_delimited_string_length(value)))
-        instance_name_list.append(u'bin_%d' % self.bin_count)
+        instance_name_list.append('bin_%d' % self.bin_count)
 
     def _write_symbol_instance(self, indent_str, value, instance_name_list):
         """Write proton::symbol instance"""
         self.sym_count += 1
-        self.target_file.write(u'%sproton::symbol sym_%d("%s");\n' % (indent_str, self.sym_count, value))
-        instance_name_list.append(u'sym_%d' % self.sym_count)
+        self.target_file.write('%sproton::symbol sym_%d("%s");\n' % (indent_str, self.sym_count, value))
+        instance_name_list.append('sym_%d' % self.sym_count)
 
     #pylint: disable=too-many-branches
     #pylint: disable=too-many-statements
@@ -682,137 +693,137 @@ namespace qpidit {
         Write a JOSN pair ['amqp_type', value]. If amqp_type is complex or a proton type, pop instance name from
         intance_name_list (which has been previously declared).
         """
-        trailing_comma_string = u', ' if trailing_comma_flag else u''
+        trailing_comma_string = ', ' if trailing_comma_flag else ''
         amqp_type, value = data_pair
-        if amqp_type == u'null':
-            self.target_file.write(u'nullptr%s' % trailing_comma_string)
-        elif amqp_type == u'boolean':
-            self.target_file.write(u'%s%s' % (str(value).lower(), trailing_comma_string))
-        elif amqp_type == u'ubyte':
-            self.target_file.write(u'uint8_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'byte':
-            self.target_file.write(u'int8_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'ushort':
-            self.target_file.write(u'uint16_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'short':
-            self.target_file.write(u'int16_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'uint':
-            self.target_file.write(u'uint32_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'int':
-            self.target_file.write(u'int32_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'ulong':
-            self.target_file.write(u'uint64_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'long':
-            self.target_file.write(u'int64_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'float':
+        if amqp_type == 'null':
+            self.target_file.write('nullptr%s' % trailing_comma_string)
+        elif amqp_type == 'boolean':
+            self.target_file.write('%s%s' % (str(value).lower(), trailing_comma_string))
+        elif amqp_type == 'ubyte':
+            self.target_file.write('uint8_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'byte':
+            self.target_file.write('int8_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'ushort':
+            self.target_file.write('uint16_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'short':
+            self.target_file.write('int16_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'uint':
+            self.target_file.write('uint32_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'int':
+            self.target_file.write('int32_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'ulong':
+            self.target_file.write('uint64_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'long':
+            self.target_file.write('int64_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'float':
             if isinstance(value, str):
-                if value == u'inf':
-                    self.target_file.write(u'std::numeric_limits<float>::infinity()%s' % trailing_comma_string)
-                elif value == u'-inf':
-                    self.target_file.write(u'-std::numeric_limits<float>::infinity()%s' % trailing_comma_string)
-                elif value == u'NaN':
-                    self.target_file.write(u'std::numeric_limits<float>::quiet_NaN()%s' % trailing_comma_string)
+                if value == 'inf':
+                    self.target_file.write('std::numeric_limits<float>::infinity()%s' % trailing_comma_string)
+                elif value == '-inf':
+                    self.target_file.write('-std::numeric_limits<float>::infinity()%s' % trailing_comma_string)
+                elif value == 'NaN':
+                    self.target_file.write('std::numeric_limits<float>::quiet_NaN()%s' % trailing_comma_string)
                 else:
-                    self.target_file.write(u'float(%s)%s' % (value, trailing_comma_string))
+                    self.target_file.write('float(%s)%s' % (value, trailing_comma_string))
             else:
-                self.target_file.write(u'float(%s)%s' % (str(value), trailing_comma_string))
-        elif amqp_type == u'double':
+                self.target_file.write('float(%s)%s' % (str(value), trailing_comma_string))
+        elif amqp_type == 'double':
             if isinstance(value, str):
-                if value == u'inf':
-                    self.target_file.write(u'std::numeric_limits<double>::infinity()%s' % trailing_comma_string)
-                elif value == u'-inf':
-                    self.target_file.write(u'-std::numeric_limits<double>::infinity()%s' % trailing_comma_string)
-                elif value == u'NaN':
-                    self.target_file.write(u'std::numeric_limits<double>::quiet_NaN()%s' % trailing_comma_string)
+                if value == 'inf':
+                    self.target_file.write('std::numeric_limits<double>::infinity()%s' % trailing_comma_string)
+                elif value == '-inf':
+                    self.target_file.write('-std::numeric_limits<double>::infinity()%s' % trailing_comma_string)
+                elif value == 'NaN':
+                    self.target_file.write('std::numeric_limits<double>::quiet_NaN()%s' % trailing_comma_string)
                 else:
-                    self.target_file.write(u'double(%s)%s' % (value, trailing_comma_string))
+                    self.target_file.write('double(%s)%s' % (value, trailing_comma_string))
             else:
-                self.target_file.write(u'double(%s)%s' % (str(value), trailing_comma_string))
-        elif amqp_type == u'decimal32':
+                self.target_file.write('double(%s)%s' % (str(value), trailing_comma_string))
+        elif amqp_type == 'decimal32':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'decimal64':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'decimal64':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'decimal128':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'decimal128':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'char':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'char':
             if len(value) == 1: # single char
-                self.target_file.write(u'wchar_t(\'%s\')%s' % (value, trailing_comma_string))
+                self.target_file.write('wchar_t(\'%s\')%s' % (value, trailing_comma_string))
             else:
-                self.target_file.write(u'wchar_t(%s)%s' % (value, trailing_comma_string))
-        elif amqp_type == u'timestamp':
+                self.target_file.write('wchar_t(%s)%s' % (value, trailing_comma_string))
+        elif amqp_type == 'timestamp':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'uuid':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'uuid':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'binary':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'binary':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'string':
-            self.target_file.write(u'std::string("')
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'string':
+            self.target_file.write('std::string("')
             for char_ in value:
-                if char_ == u'\'' or char_ == u'"':
-                    self.target_file.write(u'\\')
+                if char_ in ('\'', '"'):
+                    self.target_file.write('\\')
                 self.target_file.write(char_)
-            self.target_file.write(u'")%s' % trailing_comma_string)
-        elif amqp_type == u'symbol':
+            self.target_file.write('")%s' % trailing_comma_string)
+        elif amqp_type == 'symbol':
             if instance_name_list is not None:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'array':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'array':
             if instance_name_list is not None and instance_name_list:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'list':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'list':
             if instance_name_list is not None and instance_name_list:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
-        elif amqp_type == u'map':
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+        elif amqp_type == 'map':
             if instance_name_list is not None and instance_name_list:
-                self.target_file.write(u'%s%s' % (instance_name_list.pop(0), trailing_comma_string))
+                self.target_file.write('%s%s' % (instance_name_list.pop(0), trailing_comma_string))
 
     @staticmethod
     def _cpp_type(amqp_type, amqp_sub_type=None):
         cpp_types = {
-            None: u'NULL',
-            u'null': u'std::nullptr_t',
-            u'boolean': u'bool',
-            u'byte': u'int8_t',
-            u'ubyte': u'uint8_t',
-            u'short': u'int16_t',
-            u'ushort': u'uint16_t',
-            u'int': u'int32_t',
-            u'uint': u'uint32_t',
-            u'char': u'wchar_t',
-            u'long': u'int64_t',
-            u'ulong': u'uint64_t',
-            u'timestamp': u'proton::timestamp',
-            u'float': u'float',
-            u'double': u'double',
-            u'decimal32': u'proton::decimal32',
-            u'decimal64': u'proton::decimal64',
-            u'decimal128': u'proton::decimal128',
-            u'uuid': u'proton::uuid',
-            u'binary': u'proton::binary',
-            u'string': u'std::string',
-            u'symbol': u'proton::symbol',
-            u'described': u'proton::described',
-            u'array': u'std::vector<%s> ' % amqp_sub_type,
-            u'list': u'std::vector<proton::value> ',
-            u'map': u'std::map<proton::value, proton::value> '
+            None: 'NULL',
+            'null': 'std::nullptr_t',
+            'boolean': 'bool',
+            'byte': 'int8_t',
+            'ubyte': 'uint8_t',
+            'short': 'int16_t',
+            'ushort': 'uint16_t',
+            'int': 'int32_t',
+            'uint': 'uint32_t',
+            'char': 'wchar_t',
+            'long': 'int64_t',
+            'ulong': 'uint64_t',
+            'timestamp': 'proton::timestamp',
+            'float': 'float',
+            'double': 'double',
+            'decimal32': 'proton::decimal32',
+            'decimal64': 'proton::decimal64',
+            'decimal128': 'proton::decimal128',
+            'uuid': 'proton::uuid',
+            'binary': 'proton::binary',
+            'string': 'std::string',
+            'symbol': 'proton::symbol',
+            'described': 'proton::described',
+            'array': 'std::vector<%s> ' % amqp_sub_type,
+            'list': 'std::vector<proton::value> ',
+            'map': 'std::map<proton::value, proton::value> '
             }
         return cpp_types[amqp_type]
 
-    INSTANCE_GENERATE_FN = {u'decimal32': _write_decimal32_instance,
-                            u'decimal64': _write_decimal64_instance,
-                            u'decimal128': _write_decimal128_instance,
-                            u'timestamp': _write_timestamp_instance,
-                            u'uuid': _write_uuid_instance,
-                            u'binary': _write_binary_instance,
-                            u'symbol': _write_symbol_instance,
-                            u'array': _write_array_instance,
-                            u'list': _write_list_instance,
-                            u'map': _write_map_instance,
+    INSTANCE_GENERATE_FN = {'decimal32': _write_decimal32_instance,
+                            'decimal64': _write_decimal64_instance,
+                            'decimal128': _write_decimal128_instance,
+                            'timestamp': _write_timestamp_instance,
+                            'uuid': _write_uuid_instance,
+                            'binary': _write_binary_instance,
+                            'symbol': _write_symbol_instance,
+                            'array': _write_array_instance,
+                            'list': _write_list_instance,
+                            'map': _write_map_instance,
                            }
 
 
@@ -821,25 +832,24 @@ class JavaScriptGenerator(Generator):
 
     def write_prefix(self):
         """Write comments, copyright, etc at top of JavaScript source file"""
-        self.target_file.write(u'#!/usr/bin/env node\n\n')
-        self.target_file.write(u'/*\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
-        self.target_file.write(u'/*\n')
+        self.target_file.write('#!/usr/bin/env node\n\n')
+        self.target_file.write('/*\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
+        self.target_file.write('/*\n')
         for line in iter(COPYRIGHT_TEXT.splitlines()):
-            self.target_file.write(u' * %s\n' % line)
-        self.target_file.write(u' */\n\n')
-        self.target_file.write(u'/*\n')
-        self.target_file.write(u' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
-        self.target_file.write(u' * Generated by building qpid_interop_test\n')
-        self.target_file.write(u' * Generated: %s\n'% time.strftime(u'%Y-%m-%d %H:%M:%S', time.gmtime()))
-        self.target_file.write(u' */\n\n')
+            self.target_file.write(' * %s\n' % line)
+        self.target_file.write(' */\n\n')
+        self.target_file.write('/*\n')
+        self.target_file.write(' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
+        self.target_file.write(' * Generated by building qpid_interop_test\n')
+        self.target_file.write(' * Generated: %s\n'% time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime()))
+        self.target_file.write(' */\n\n')
 
     def write_code(self, amqp_test_type, json_data):
         """Write JavaScript code from json_data"""
-        pass
 
     def write_postfix(self):
         """Write postfix at bottom of JavaScript source file"""
-        self.target_file.write(u'// <eof>\n')
+        self.target_file.write('// <eof>\n')
 
 
 class DotNetGenerator(Generator):
@@ -847,41 +857,40 @@ class DotNetGenerator(Generator):
 
     def write_prefix(self):
         """Write comments, copyright, etc at top of DotNet source file"""
-        self.target_file.write(u'/*\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
-        self.target_file.write(u'/*\n')
+        self.target_file.write('/*\n * Data used for qpid_interop_test.amqp_complex_types_test\n */\n\n')
+        self.target_file.write('/*\n')
         for line in iter(COPYRIGHT_TEXT.splitlines()):
-            self.target_file.write(u' * %s\n' % line)
-        self.target_file.write(u' */\n\n')
-        self.target_file.write(u'/*\n')
-        self.target_file.write(u' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
-        self.target_file.write(u' * Generated by building qpid_interop_test\n')
-        self.target_file.write(u' * Generated: %s\n'% time.strftime(u'%Y-%m-%d %H:%M:%S', time.gmtime()))
-        self.target_file.write(u' */\n\n')
+            self.target_file.write(' * %s\n' % line)
+        self.target_file.write(' */\n\n')
+        self.target_file.write('/*\n')
+        self.target_file.write(' * THIS IS A GENERATED FILE, DO NOT EDIT DIRECTLY\n')
+        self.target_file.write(' * Generated by building qpid_interop_test\n')
+        self.target_file.write(' * Generated: %s\n'% time.strftime('%Y-%m-%d %H:%M:%S', time.gmtime()))
+        self.target_file.write(' */\n\n')
 
     def write_code(self, amqp_test_type, json_data):
         """Write DotNet code from json_data"""
-        pass
 
     def write_postfix(self):
         """Write postfix at bottom of DotNet source file"""
-        self.target_file.write(u'// <eof>\n')
+        self.target_file.write('// <eof>\n')
 
 
-class GeneratorOptions(object):
+class GeneratorOptions:
     """Class to handle generator options"""
     def __init__(self):
-        self._parser = argparse.ArgumentParser(description=u'AMQP Complex Types Test: test data generator')
-        self._parser.add_argument(u'--type', choices=AMQP_COMPEX_TYPES, default=u'ALL', metavar=u'TYPE',
-                                  help=u'AMQP complex type to test %s' % AMQP_COMPEX_TYPES)
-        self._parser.add_argument(u'--json-base-name', action=u'store', default=DEFAULT_JSON_BASE_NAME,
-                                  metavar=u'BASENAME',
-                                  help=u'JSON data file base name [%s]' % DEFAULT_JSON_BASE_NAME)
-        self._parser.add_argument(u'--gen', choices=GENERATOR_TARGETS, default=u'ALL', metavar=u'TARGET',
-                                  help=u'Generate for target %s' % GENERATOR_TARGETS)
-        self._parser.add_argument(u'--gen-dir', action=u'store', default=u'.', metavar=u'DIR',
-                                  help=u'Directory in which to generate source files [.]')
-        self._parser.add_argument(u'--src-dir', action=u'store', default=u'.', metavar=u'DIR',
-                                  help=u'Directory containing JSON data files [.]')
+        self._parser = argparse.ArgumentParser(description='AMQP Complex Types Test: test data generator')
+        self._parser.add_argument('--type', choices=AMQP_COMPEX_TYPES, default='ALL', metavar='TYPE',
+                                  help='AMQP complex type to test %s' % AMQP_COMPEX_TYPES)
+        self._parser.add_argument('--json-base-name', action='store', default=DEFAULT_JSON_BASE_NAME,
+                                  metavar='BASENAME',
+                                  help='JSON data file base name [%s]' % DEFAULT_JSON_BASE_NAME)
+        self._parser.add_argument('--gen', choices=GENERATOR_TARGETS, default='ALL', metavar='TARGET',
+                                  help='Generate for target %s' % GENERATOR_TARGETS)
+        self._parser.add_argument('--gen-dir', action='store', default='.', metavar='DIR',
+                                  help='Directory in which to generate source files [.]')
+        self._parser.add_argument('--src-dir', action='store', default='.', metavar='DIR',
+                                  help='Directory containing JSON data files [.]')
 
     def args(self):
         """Return the parsed args"""
diff --git a/src/python/qpid_interop_test/amqp_large_content_test.py b/src/python/qpid_interop_test/amqp_large_content_test.py
index cb55e6a..e9a9eda 100755
--- a/src/python/qpid_interop_test/amqp_large_content_test.py
+++ b/src/python/qpid_interop_test/amqp_large_content_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Module to test AMQP messages with large content (bodies and headers/properties) across different clients
@@ -33,7 +33,7 @@ from json import dumps
 import qpid_interop_test.qit_common
 from qpid_interop_test.qit_errors import InteropTestError, InteropTestTimeout
 
-DEFAULT_TEST_TIMEOUT = 180 # seconds
+DEFAULT_TEST_TIMEOUT = 300 # seconds
 
 
 class AmqpVariableSizeTypes(qpid_interop_test.qit_common.QitTestTypeMap):
@@ -74,6 +74,7 @@ class AmqpVariableSizeTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 class AmqpLargeContentTestCase(qpid_interop_test.qit_common.QitTestCase):
     """Abstract base class for AMQP large content tests"""
 
+    #pylint: disable=too-many-arguments
     def run_test(self, sender_addr, receiver_addr, amqp_type, test_value_list, send_shim, receive_shim, timeout):
         """
         Run this test by invoking the shim send method to send the test values, followed by the shim receive method
@@ -124,9 +125,9 @@ class AmqpLargeContentTestCase(qpid_interop_test.qit_common.QitTestCase):
     @staticmethod
     def get_num_messages(amqp_type, test_value_list):
         """Find the total number of messages to be sent for this test"""
-        if amqp_type == 'binary' or amqp_type == 'string' or amqp_type == 'symbol':
+        if amqp_type in ('binary', 'string', 'symbol'):
             return len(test_value_list)
-        if amqp_type == 'list' or amqp_type == 'map':
+        if amqp_type in ('list', 'map'):
             tot_len = 0
             for test_item in test_value_list:
                 tot_len += len(test_item[1])
diff --git a/src/python/qpid_interop_test/amqp_types_test.py b/src/python/qpid_interop_test/amqp_types_test.py
index 2404757..b0e316f 100755
--- a/src/python/qpid_interop_test/amqp_types_test.py
+++ b/src/python/qpid_interop_test/amqp_types_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Module to test AMQP primitive types across different clients
@@ -27,6 +27,7 @@ import signal
 import sys
 import unittest
 
+from base64 import b64encode
 from itertools import product
 from json import dumps
 from time import mktime, time
@@ -35,7 +36,7 @@ from uuid import UUID, uuid4
 import qpid_interop_test.qit_common
 from qpid_interop_test.qit_errors import InteropTestError, InteropTestTimeout
 
-DEFAULT_TEST_TIMEOUT = 10 # seconds
+DEFAULT_TEST_TIMEOUT = 20 # seconds
 
 class AmqpPrimitiveTypes(qpid_interop_test.qit_common.QitTestTypeMap):
     """
@@ -137,21 +138,21 @@ class AmqpPrimitiveTypes(qpid_interop_test.qit_common.QitTestTypeMap):
                       '0xffefffffffffffff'],
         'decimal128': ['0x00000000000000000000000000000000',
                        '0xff0102030405060708090a0b0c0d0e0f'],
-        'char': [u' ', # single ASCII chars
-                 u'A',
-                 u'z',
-                 u'0',
-                 u'9',
-                 u'}',
-                 u'0x0', # Hex representation
-                 u'0x1',
-                 u'0x7f',
-                 u'0x80',
-                 u'0xff',
-                 u'0x16b5', # Rune 'G'
-                 u'0x10203',
-                 u'0x10ffff',
-                 #u'0x12345678' # 32-bit number, not real char # Disabled until Python can handle it
+        'char': [' ', # single ASCII chars
+                 'A',
+                 'z',
+                 '0',
+                 '9',
+                 '}',
+                 '0x0', # Hex representation
+                 '0x1',
+                 '0x7f',
+                 '0x80',
+                 '0xff',
+                 '0x16b5', # Rune 'G'
+                 '0x10203',
+                 '0x10ffff',
+                 #'0x12345678' # 32-bit number, not real char # Disabled until Python can handle it
                 ],
         # timestamp: Must be in milliseconds since the Unix epoch
         'timestamp': ['0x0',
@@ -162,96 +163,23 @@ class AmqpPrimitiveTypes(qpid_interop_test.qit_common.QitTestTypeMap):
                  str(UUID('00010203-0405-0607-0809-0a0b0c0d0e0f')),
                  str(uuid4())],
         'binary': [bytes(),
-                   bytes(12345),
+                   bytes([1, 2, 3, 4, 5]),
                    b'Hello, world',
-                   b'\\x01\\x02\\x03\\x04\\x05abcde\\x80\\x81\\xfe\\xff',
-                   b'The quick brown fox jumped over the lazy dog 0123456789.' * 100
+                   b'\x01\x02\x03\x04\x05abcde\x80\x81\xfe\xff',
+                   b'The quick brown fox jumped over the lazy dog 0123456789.' * 10#0
                   ],
-        # strings must be unicode to comply with AMQP spec
-        'string': [u'',
-                   u'Hello, world',
-                   u'"Hello, world"',
-                   u"Charlie's peach",
-                   u'The quick brown fox jumped over the lazy dog 0123456789.' * 100
+        'string': ['',
+                   '12345'
+                   'Hello, world',
+                   '"Hello, world"', # Embedded quotes
+                   "Charlie's peach", # Embedded apostrophe
+                   'The quick brown fox jumped over the lazy dog 0123456789.' * 100
                   ],
         'symbol': ['',
+                   '12345'
                    'myDomain.123',
                    'domain.0123456789.' * 100,
                   ],
-        'list': [[],
-                 ['ubyte:0x1', 'int:-0x2', 'float:0x40490fdb'],
-                 ['string:a', 'string:hello', 'string:world!', 'binary:\x01\x02\x03\x04\x05abcde'],
-                 ['long:0x102030405',
-                  'timestamp:0x%x' % int(time()*1000),
-                  'short:-0x8000',
-                  'uuid:%s' % str(uuid4()),
-                  'symbol:a.b.c',
-                  'null:None',
-                  'ulong:0x400921fb54442eea',
-                  #'decimal64:0x400921fb54442eea' # Decimal byte reversal issue: PROTON-1160
-                 ],
-                 [[],
-                  'null:None',
-                  ['ubyte:0x1', 'ubyte:0x2', 'ubyte:0x3'],
-                  'boolean:True',
-                  'boolean:False',
-                  {},
-                  {'string:hello': 'long:-0x1234', 'string:goodbye': 'boolean:True'}
-                 ],
-                 [[], [[], [[], [], []], []], []],
-                 ['short:0x0',
-                  'short:0x1',
-                  'short:0x2',
-                  'short:0x3',
-                  'short:0x4',
-                  'short:0x5',
-                  'short:0x6',
-                  'short:0x7',
-                  'short:0x8',
-                  'short:0x9'] * 10
-                ],
-        'map': [{}, # Enpty map
-                # Map with string keys
-                {'string:one': 'ubyte:0x1',
-                 'string:two': 'ushort:0x2'},
-                # Map with other AMQP simple types as keys
-                {'null:None': 'string:None',
-                 'string:None': 'null:None',
-                 'string:One': 'long:-0x102030405',
-                 'short:0x2': 'int:0x2',
-                 'boolean:True': 'string:True',
-                 'string:False': 'boolean:False',
-                 #['string:AAA', 'ushort:0x5951']: 'string:list value',
-                 #{'byte:-55': 'ubyte:200',
-                 # 'boolean:True': 'string:Hello, world'}: 'symbol:map.value',
-                 'string:list': ['byte:0x12', 'ushort:0x234', 'uuid:%s' % str(uuid4()), ],
-                 'string:map': {'char:A': 'int:0x1',
-                                'char:B': 'int:0x2'}
-                },
-               ],
-        # array: Each array is constructed from the test values in this map. This list contains
-        # the keys to the array value types to be included in the test. See function create_test_arrays()
-        # for the top-level function that performs the array creation.
-        #'array': ['boolean',
-        #          'ubyte',
-        #          'ushort',
-        #          'uint',
-        #          'ulong',
-        #          'byte',
-        #          'short',
-        #          'int',
-        #          'long',
-        #          'float',
-        #          'double',
-        #          'decimal32',
-        #          'decimal64',
-        #          'decimal128',
-        #          'char',
-        #          'uuid',
-        #          'binary',
-        #          'string',
-        #          'symbol',
-        #         ],
         }
 
     # This section contains tests that should be skipped because of known issues that would cause the test to fail.
@@ -296,27 +224,26 @@ class AmqpPrimitiveTypes(qpid_interop_test.qit_common.QitTestTypeMap):
                 test_array.append(val)
         return test_array
 
-    def create_test_arrays(self):
-        """ Method to synthesize the test arrays from the values used in the previous type tests """
-        test_arrays = []
-        for array_amqp_type in self.type_map['array']:
-            test_arrays.append(self.create_array(array_amqp_type, 1))
-        print(test_arrays)
-        return test_arrays
-
     def get_test_values(self, test_type):
         """
-        Overload the parent method so that arrays can be synthesized rather than read directly.
+        Overload the parent method so that binary types can be base64 encoded for use in json.
         The test_type parameter is the AMQP type in this case
         """
-        if test_type == 'array':
-            return self.create_test_arrays()
+        if test_type == 'binary':
+            # Convert all binary to base64 strings, as bytes are not JSON serializable
+            test_values = []
+            bytes_test_values = super(AmqpPrimitiveTypes, self).get_test_values(test_type)
+            for bytes_test_value in bytes_test_values:
+                test_values.append(b64encode(bytes_test_value).decode('ascii'))
+            return test_values
         return super(AmqpPrimitiveTypes, self).get_test_values(test_type)
 
 
 class AmqpTypeTestCase(qpid_interop_test.qit_common.QitTestCase):
     """Abstract base class for AMQP Type test cases"""
 
+    #pylint: disable=too-many-arguments
+    #pylint: disable=too-many-locals
     def run_test(self, sender_addr, receiver_addr, amqp_type, test_value_list, send_shim, receive_shim, timeout):
         """
         Run this test by invoking the shim send method to send the test values, followed by the shim receive method
diff --git a/src/python/qpid_interop_test/jms_hdrs_props_test.py b/src/python/qpid_interop_test/jms_hdrs_props_test.py
index ae13d5f..f9a8872 100755
--- a/src/python/qpid_interop_test/jms_hdrs_props_test.py
+++ b/src/python/qpid_interop_test/jms_hdrs_props_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Module to test JMS headers and properties on messages accross different clients
@@ -27,13 +27,15 @@ import signal
 import sys
 import unittest
 
+from base64 import b64encode
 from itertools import combinations, product
 from json import dumps
 
 import qpid_interop_test.qit_common
 from qpid_interop_test.qit_errors import InteropTestError, InteropTestTimeout
+from encodings.base64_codec import base64_encode
 
-DEFAULT_TEST_TIMEOUT = 10 # seconds
+DEFAULT_TEST_TIMEOUT = 20 # seconds
 
 
 class JmsHdrPropTypes(qpid_interop_test.qit_common.QitTestTypeMap):
@@ -176,8 +178,8 @@ class JmsHdrPropTypes(qpid_interop_test.qit_common.QitTestTypeMap):
         #    'java.lang.Byte': ['-128',
         #                       '0',
         #                       '127'],
-        #    'java.lang.Character': [u'a',
-        #                            u'Z'],
+        #    'java.lang.Character': ['a',
+        #                            'Z'],
         #    'java.lang.Double': ['0.0',
         #                         '3.141592654',
         #                         '-2.71828182846'],
@@ -208,11 +210,11 @@ class JmsHdrPropTypes(qpid_interop_test.qit_common.QitTestTypeMap):
         #                        '127',
         #                        '128',
         #                        '32767'],
-        #    'java.lang.String': [u'',
-        #                         u'Hello, world',
-        #                         u'"Hello, world"',
-        #                         u"Charlie's \"peach\"",
-        #                         u'Charlie\'s "peach"']
+        #    'java.lang.String': ['',
+        #                         'Hello, world',
+        #                         '"Hello, world"',
+        #                         "Charlie's \"peach\"",
+        #                         'Charlie\'s "peach"']
         #    },
         }
 
@@ -222,6 +224,7 @@ class JmsHdrPropTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 
     client_skip = {}
 
+    #pylint: disable=too-many-branches
     def get_types(self, args):
         if 'include_hdr' in args and args.include_hdr is not None:
             new_hdrs_map = {}
@@ -267,10 +270,12 @@ class JmsHdrPropTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 
         return self
 
-
 class JmsMessageHdrsPropsTestCase(qpid_interop_test.qit_common.QitTestCase):
     """Abstract base class for JMS message headers and properties tests"""
 
+    #pylint: disable=too-many-arguments
+    #pylint: disable=too-many-locals
+    #pylint: disable=too-many-branches
     def run_test(self, sender_addr, receiver_addr, queue_name_fragment, jms_message_type, test_values, msg_hdrs,
                  msg_props, send_shim, receive_shim, timeout):
         """
@@ -401,6 +406,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
         test_case_class_d = self._generate_part_d(timeout)
         self.test_suite.addTest(unittest.makeSuite(test_case_class_d))
 
+    #pylint: disable=too-many-locals
     def _generate_part_a(self, timeout):
         """
         Class factory function which creates new subclasses to JmsMessageTypeTestCase. Creates a test case class for
@@ -411,6 +417,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
             """Print the class name"""
             return self.__class__.__name__
 
+        #pylint: disable=too-many-arguments
         def add_test_method(cls, queue_name_fragment, hdrs, props, send_shim, receive_shim, timeout):
             """Function which creates a new test method in class cls"""
 
@@ -443,11 +450,13 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
         new_class = type(class_name, (JmsMessageHdrsPropsTestCase,), class_dict)
 
         for send_shim, receive_shim in product(self.shim_map.values(), repeat=2):
-            for msg_header in self.types.headers_map.iterkeys():
-                for header_type, header_val_list in self.types.headers_map[msg_header].iteritems():
+            for msg_header in self.types.headers_map.keys():
+                for header_type, header_val_list in iter(self.types.headers_map[msg_header].items()):
                     header_val_cnt = 0
                     for header_val in header_val_list:
                         header_val_cnt += 1
+                        if header_type == 'bytes':
+                            header_val = b64encode(header_val).decode('utf-8')
                         method_subname = '%s.%s-%02d' % (msg_header, header_type, header_val_cnt)
                         add_test_method(new_class,
                                         method_subname,
@@ -469,6 +478,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
             """Print the class name"""
             return self.__class__.__name__
 
+        #pylint: disable=too-many-arguments
         def add_test_method(cls, queue_name_fragment, hdrs, props, send_shim, receive_shim, timeout):
             """Function which creates a new test method in class cls"""
 
@@ -500,9 +510,10 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
                       'test_values': self.types.get_test_values(jms_message_type)}
         new_class = type(class_name, (JmsMessageHdrsPropsTestCase,), class_dict)
 
+        #pylint: disable=too-many-nested-blocks
         for send_shim, receive_shim in product(self.shim_map.values(), repeat=2):
             for jms_hdrs_combo_index in range(0, len(self.types.headers_map.keys())+1):
-                for jms_hdrs_combo in combinations(self.types.headers_map.iterkeys(), jms_hdrs_combo_index):
+                for jms_hdrs_combo in combinations(self.types.headers_map.keys(), jms_hdrs_combo_index):
                     jms_hdr_list = []
                     for jms_header in jms_hdrs_combo:
                         data_type_list = []
@@ -519,6 +530,11 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
                                 method_subname += '%s:%s' % combo_item
                                 header_type_map = self.types.headers_map[combo_item[0]]
                                 header_val_list = header_type_map[combo_item[1]]
+                                if combo_item[1] == 'bytes':
+                                    encoded_list = []
+                                    for header_val in header_val_list:
+                                        encoded_list.append(b64encode(header_val).decode('utf-8'))
+                                    header_val_list = encoded_list
                                 header_map[combo_item[0]] = {combo_item[1]: header_val_list[0]}
                             add_test_method(new_class,
                                             method_subname,
@@ -540,6 +556,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
             """Print the class name"""
             return self.__class__.__name__
 
+        #pylint: disable=too-many-arguments
         def add_test_method(cls, queue_name_fragment, hdrs, props, send_shim, receive_shim, timeout):
             """Function which creates a new test method in class cls"""
 
@@ -572,7 +589,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
         new_class = type(class_name, (JmsMessageHdrsPropsTestCase,), class_dict)
 
         for send_shim, receive_shim in product(self.shim_map.values(), repeat=2):
-            for prop_type, prop_val_list in self.types.properties_map.iteritems():
+            for prop_type, prop_val_list in iter(self.types.properties_map.items()):
                 prop_val_cnt = 0
                 for prop_val in prop_val_list:
                     prop_val_cnt += 1
@@ -597,6 +614,7 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
             """Print the class name"""
             return self.__class__.__name__
 
+        #pylint: disable=too-many-arguments
         def add_test_method(cls, queue_name_fragment, hdrs, props, send_shim, receive_shim, timeout):
             """Function which creates a new test method in class cls"""
 
@@ -629,14 +647,14 @@ class JmsHdrsPropsTest(qpid_interop_test.qit_common.QitJmsTest):
         new_class = type(class_name, (JmsMessageHdrsPropsTestCase,), class_dict)
 
         all_hdrs = {}
-        for msg_header in self.types.headers_map.iterkeys():
+        for msg_header in self.types.headers_map.keys():
             header_type_dict = self.types.headers_map[msg_header]
-            header_type, header_val_list = header_type_dict.iteritems().next()
+            header_type, header_val_list = next(iter(header_type_dict.items()))
             header_val = header_val_list[0]
             all_hdrs[msg_header] = {header_type: header_val}
 
         all_props = {}
-        for prop_type, prop_val_list in self.types.properties_map.iteritems():
+        for prop_type, prop_val_list in iter(self.types.properties_map.items()):
             prop_val_cnt = 0
             for prop_val in prop_val_list:
                 prop_val_cnt += 1
diff --git a/src/python/qpid_interop_test/jms_messages_test.py b/src/python/qpid_interop_test/jms_messages_test.py
index dcee572..033632c 100755
--- a/src/python/qpid_interop_test/jms_messages_test.py
+++ b/src/python/qpid_interop_test/jms_messages_test.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Module to test JMS message types across different clients
@@ -27,13 +27,14 @@ import signal
 import sys
 import unittest
 
+from base64 import b64encode
 from itertools import product
 from json import dumps
 
 import qpid_interop_test.qit_common
 from qpid_interop_test.qit_errors import InteropTestError, InteropTestTimeout
 
-DEFAULT_TEST_TIMEOUT = 10 # seconds
+DEFAULT_TEST_TIMEOUT = 20 # seconds
 
 
 class JmsMessageTypes(qpid_interop_test.qit_common.QitTestTypeMap):
@@ -109,7 +110,7 @@ class JmsMessageTypes(qpid_interop_test.qit_common.QitTestTypeMap):
         'bytes': [b'',
                   b'12345',
                   b'Hello, world',
-                  b'\\x01\\x02\\x03\\x04\\x05abcde\\x80\\x81\\xfe\\xff',
+                  b'\x01\x02\x03\x04\x05abcde\x80\x81\xfe\xff',
                   b'The quick brown fox jumped over the lazy dog 0123456789.' #* 100],
                  ],
         'char': [b'a',
@@ -144,8 +145,8 @@ class JmsMessageTypes(qpid_interop_test.qit_common.QitTestTypeMap):
         #    'java.lang.Byte': ['-128',
         #                       '0',
         #                       '127'],
-        #    'java.lang.Character': [u'a',
-        #                            u'Z'],
+        #    'java.lang.Character': [a',
+        #                            Z'],
         #    'java.lang.Double': ['0.0',
         #                         '3.141592654',
         #                         '-2.71828182846'],
@@ -176,11 +177,11 @@ class JmsMessageTypes(qpid_interop_test.qit_common.QitTestTypeMap):
         #                        '127',
         #                        '128',
         #                        '32767'],
-        #    'java.lang.String': [u'',
-        #                         u'Hello, world',
-        #                         u'"Hello, world"',
-        #                         u"Charlie's \"peach\"",
-        #                         u'Charlie\'s "peach"']
+        #    'java.lang.String': [',
+        #                         Hello, world',
+        #                         "Hello, world"',
+        #                         "Charlie's \"peach\"",
+        #                         Charlie\'s "peach"']
         #    },
         }
 
@@ -190,10 +191,29 @@ class JmsMessageTypes(qpid_interop_test.qit_common.QitTestTypeMap):
 
     client_skip = {}
 
+    def get_test_values(self, test_type):
+        """
+        Overload the parent method so that binary types can be base64 encoded for use in json.
+        The test_type parameter is the JMS message type in this case
+        """
+        type_map = super(JmsMessageTypes, self).get_test_values(test_type)
+        for key in type_map:
+            if key in ['bytes', 'char']:
+                new_vals = []
+                for val in type_map[key]:
+                    if isinstance(val, bytes):
+                        new_vals.append(b64encode(val).decode('utf-8'))
+                    else:
+                        new_vals.append(val)
+                type_map[key] = new_vals
+        return type_map
+
 
 class JmsMessageTypeTestCase(qpid_interop_test.qit_common.QitTestCase):
     """Abstract base class for JMS message type tests"""
 
+    #pylint: disable=too-many-arguments
+    #pylint: disable=too-many-locals
     def run_test(self, sender_addr, receiver_addr, jms_message_type, test_values, send_shim, receive_shim, timeout):
         """
         Run this test by invoking the shim send method to send the test values, followed by the shim receive method
diff --git a/src/python/qpid_interop_test/qit_broker_props.py b/src/python/qpid_interop_test/qit_broker_props.py
old mode 100644
new mode 100755
index 1553744..f983c8c
--- a/src/python/qpid_interop_test/qit_broker_props.py
+++ b/src/python/qpid_interop_test/qit_broker_props.py
@@ -1,3 +1,4 @@
+#!/usr/bin/env python3
 """
 Module containing a small client which connects to the broker and
 gets the broker connection properties so as to identify the broker.
@@ -34,7 +35,7 @@ class Client(proton.handlers.MessagingHandler):
     def __init__(self, url, max_num_retries):
         super(Client, self).__init__()
         self.url = url
-        self.max_num_retries = max_num_retries;
+        self.max_num_retries = max_num_retries
         self.num_retries = 0
         self.remote_properties = None
 
@@ -55,10 +56,10 @@ class Client(proton.handlers.MessagingHandler):
 
     def on_transport_error(self, event):
         self.num_retries += 1
-        if (self.num_retries == 1):
+        if self.num_retries == 1:
             sys.stdout.write('WARNING: broker not found at %s, retrying *' % self.url)
             sys.stdout.flush()
-        elif (self.num_retries <= self.max_num_retries):
+        elif self.num_retries <= self.max_num_retries:
             sys.stdout.write(' *')
             sys.stdout.flush()
         else:
@@ -70,3 +71,16 @@ def get_broker_properties(broker_url):
     msg_handler = Client(broker_url, 25)
     proton.reactor.Container(msg_handler).run()
     return msg_handler.get_connection_properties()
+
+
+#--- Main program start ---
+
+if __name__ == '__main__':
+    if (len(sys.argv)) != 2:
+        print('Incorrect number of arguments')
+        print('Usage: %s <broker-url>'%sys.argv[0])
+        sys.exit(1)
+    try:
+        print(get_broker_properties(sys.argv[1]))
+    except KeyboardInterrupt:
+        print()
diff --git a/src/python/qpid_interop_test/qit_common.py b/src/python/qpid_interop_test/qit_common.py
index 675bcd0..88dcad4 100644
--- a/src/python/qpid_interop_test/qit_common.py
+++ b/src/python/qpid_interop_test/qit_common.py
@@ -44,7 +44,7 @@ QIT_TEST_SHIM_HOME = path.join(QIT_INSTALL_PREFIX, 'libexec', 'qpid_interop_test
 QPID_JMS_SHIM_VER = '0.3.0-SNAPSHOT'
 
 
-class QitTestTypeMap(object):
+class QitTestTypeMap:
     """
     Class which contains all the described types and the test values to be used in testing against those types.
     """
@@ -165,7 +165,7 @@ class QitTestTypeMap(object):
         return res
 
 
-class QitCommonTestOptions(object):
+class QitCommonTestOptions:
     """
     Class controlling common command-line arguments used to control tests.
     """
@@ -246,12 +246,13 @@ class QitTestCase(unittest.TestCase):
 #        test(result)
 
 
-class QitTest(object):
+#pylint: disable=too-many-instance-attributes
+class QitTest:
     """
     Top-level test class with test entry-point
     """
 
-    class TestTime(object):
+    class TestTime:
         """Class for measuring elapsed time of a test"""
         def __init__(self):
             self.start_time = time.time()
@@ -398,11 +399,11 @@ class QitTest(object):
         if connection_props is None:
             print('WARNING: Unable to get %s connection properties - unknown broker' % broker_role)
             return None
-        broker_name = connection_props[symbol(u'product')] if symbol(u'product') in connection_props \
+        broker_name = connection_props[symbol('product')] if symbol('product') in connection_props \
                       else '<product not found>'
-        broker_version = connection_props[symbol(u'version')] if symbol(u'version') in connection_props \
+        broker_version = connection_props[symbol('version')] if symbol('version') in connection_props \
                          else '<version not found>'
-        broker_platform = connection_props[symbol(u'platform')] if symbol(u'platform') in connection_props \
+        broker_platform = connection_props[symbol('platform')] if symbol('platform') in connection_props \
                           else '<platform not found>'
         print('%s broker: %s v.%s on %s' % (broker_role.title(), broker_name, broker_version, broker_platform))
         return (broker_name, broker_version, broker_platform)
diff --git a/src/python/qpid_interop_test/qit_errors.py b/src/python/qpid_interop_test/qit_errors.py
index 8f03ba1..b07ae93 100644
--- a/src/python/qpid_interop_test/qit_errors.py
+++ b/src/python/qpid_interop_test/qit_errors.py
@@ -25,10 +25,8 @@ class InteropTestError(Exception):
     """
     Generic simple error class for use in interop tests
     """
-    pass
 
 class InteropTestTimeout(InteropTestError):
     """
     Test timeout error
     """
-    pass
diff --git a/src/python/qpid_interop_test/qit_jms_types.py b/src/python/qpid_interop_test/qit_jms_types.py
index 32745da..4db17d7 100644
--- a/src/python/qpid_interop_test/qit_jms_types.py
+++ b/src/python/qpid_interop_test/qit_jms_types.py
@@ -23,7 +23,7 @@ Common JMS types and definitions as implemented by QpidJMS
 
 from proton import byte, symbol
 
-QPID_JMS_TYPE_ANNOTATION_NAME = symbol(u'x-opt-jms-msg-type')
+QPID_JMS_TYPE_ANNOTATION_NAME = symbol('x-opt-jms-msg-type')
 
 QPID_JMS_TYPE_ANNOTATIONS = {
     'JMS_MESSAGE_TYPE': byte(0),
diff --git a/src/python/qpid_interop_test/qit_shim.py b/src/python/qpid_interop_test/qit_shim.py
index 52f5674..53b31bc 100644
--- a/src/python/qpid_interop_test/qit_shim.py
+++ b/src/python/qpid_interop_test/qit_shim.py
@@ -51,26 +51,28 @@ class ShimProcess(subprocess.Popen):
         try:
             timer.start()
             (stdoutdata, stderrdata) = self.communicate()
+            stdoutstr =  stdoutdata.decode('ascii')
+            stderrstr = stderrdata.decode('ascii')
             if self.killed_flag:
                 raise InteropTestTimeout('%s: Timeout after %d seconds' % (self.proc_name, timeout))
             if self.returncode != 0:
-                return 'Return code %d\nstderr=%s\nstdout=%s' % (self.returncode, stderrdata, stdoutdata)
-            if stderrdata: # length > 0
+                return 'Return code %d\nstderr=%s\nstdout=%s' % (self.returncode, stderrstr, stdoutstr)
+            if stderrstr: # length > 0
                 # Workaround for Amqp.NetLite which on some OSs produces a spurious error message on stderr
                 # which should be ignored:
                 # Workaround for deprecation warning on stderr:
-                if not stderrdata.startswith('Got a bad hardware address length for an AF_PACKET') and \
-                not "[DEP0005]" in stderrdata:
-                    return 'stderr: %s\nstdout: %s' % (stderrdata, stdoutdata)
-            if not stdoutdata: # zero length
+                if not stderrstr.startswith('Got a bad hardware address length for an AF_PACKET') and \
+                "[DEP0005]" not in stderrstr:
+                    return 'stderr: %s\nstdout: %s' % (stderrstr, stdoutstr)
+            if not stdoutstr: # zero length
                 return None
-            type_value_list = stdoutdata.split('\n')[0:-1] # remove trailing '\n', split by only remaining '\n'
+            type_value_list = stdoutstr.split('\n')[0:-1] # remove trailing '\n', split by only remaining '\n'
             if len(type_value_list) == 2:
                 try:
                     return (type_value_list[0], json.loads(type_value_list[1])) # Return tuple
                 except ValueError:
-                    return stdoutdata # ERROR: return single string
-            return stdoutdata # ERROR: return single string
+                    return stdoutstr # ERROR: return single string
+            return stdoutstr # ERROR: return single string
         except (KeyboardInterrupt) as err:
             self.send_signal(signal.SIGINT)
             raise err
@@ -79,6 +81,7 @@ class ShimProcess(subprocess.Popen):
 
     def _kill(self, timeout):
         """Method called when timer expires"""
+        del timeout # unused
         self.kill()
         self.killed_flag = True
 
@@ -95,7 +98,7 @@ class Receiver(ShimProcess):
         #print('\n>>>RCVR>>> %s python3_flag=%s' % (params, python3_flag))
         super(Receiver, self).__init__(params, python3_flag, proc_name)
 
-class Shim(object):
+class Shim:
     """Abstract shim class, parent of all shims."""
     NAME = ''
     JMS_CLIENT = False # Enables certain JMS-specific message checks
diff --git a/src/python/qpid_interop_test/qit_xunit_log.py b/src/python/qpid_interop_test/qit_xunit_log.py
index 8ce67ba..c512fd3 100644
--- a/src/python/qpid_interop_test/qit_xunit_log.py
+++ b/src/python/qpid_interop_test/qit_xunit_log.py
@@ -21,7 +21,6 @@ Module providing xUnit logging functionality
 # under the License.
 #
 
-import os
 import os.path
 import sys
 import time
@@ -32,8 +31,10 @@ from qpid_interop_test.qit_errors import InteropTestError
 
 DEFUALT_XUNIT_LOG_DIR = os.path.join(os.getcwd(), 'xunit_logs')
 
-class Xunit(object):
+#pylint: disable= too-many-instance-attributes
+class Xunit:
     """Class that provides test reporting in xUnit format"""
+    #pylint: disable=too-many-arguments
     def __init__(self, test_name, test_args, test_suite, test_result, test_duration, broker_connection_props):
         self.test_name = test_name
         self.test_args = test_args
diff --git a/src/python/qpid_interop_test/run_all.py b/src/python/qpid_interop_test/run_all.py
old mode 100644
new mode 100755
index 56e4ffe..e371ac2
--- a/src/python/qpid_interop_test/run_all.py
+++ b/src/python/qpid_interop_test/run_all.py
@@ -1,4 +1,4 @@
-#!/usr/bin/env python
+#!/usr/bin/env python3
 
 """
 Script to run all available tests


---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@qpid.apache.org
For additional commands, e-mail: commits-help@qpid.apache.org