diff --git a/arkouda/message.py b/arkouda/message.py index d771a6d74b..c230331b73 100644 --- a/arkouda/message.py +++ b/arkouda/message.py @@ -115,11 +115,21 @@ def _build_list_param(key: str, val: list) -> ParameterObject: ------- ParameterObject """ - dtypes = set([p.dtype if hasattr(p, "dtype") else type(p).__name__ for p in val]) + from arkouda.pdarrayclass import pdarray + from arkouda.strings import Strings + + # want the object type. If pdarray the content dtypes can vary + dtypes = set([type(p).__name__ for p in val]) if len(dtypes) > 1: t_str = ", ".join(dtypes) raise TypeError(f"List values must be of the same type. Found {t_str}") - return ParameterObject(key, ObjectType.LIST, dtypes.pop(), json.dumps(val)) + t = dtypes.pop() + if any(x == t for x in [pdarray.__name__, Strings.__name__]): + return ParameterObject(key, ObjectType.LIST, t, json.dumps([x.name for x in val])) + else: + # need all values to be str for chapel to read list properly + v = val if t == str.__name__ else [str(x) for x in val] + return ParameterObject(key, ObjectType.LIST, t, json.dumps(v)) @staticmethod @typechecked diff --git a/tests/message_test.py b/tests/message_test.py index 05a547e0b9..8e2a3e53f6 100644 --- a/tests/message_test.py +++ b/tests/message_test.py @@ -1,7 +1,11 @@ import json import unittest +from base_test import ArkoudaTest + +from arkouda.client import _json_args_to_str from arkouda.message import MessageFormat, MessageType, ReplyMessage, RequestMessage +from arkouda.pdarraycreation import arange, array class MessageTest(unittest.TestCase): @@ -98,3 +102,62 @@ def testReplyMessage(self): with self.assertRaises(ValueError): ReplyMessage.fromdict({"msg": "normal result", "msgType": "NORMAL"}) + + +class JSONArgs(ArkoudaTest): + def testJSONArgs(self): + # test single value args + size, args = _json_args_to_str({"arg1": "Test", "arg2": 5}) + self.assertEqual(size, 2) + self.assertListEqual( + [ + '{"key": "arg1", "objType": "VALUE", "dtype": "str", "val": "Test"}', + '{"key": "arg2", "objType": "VALUE", "dtype": "int", "val": "5"}', + ], + json.loads(args), + ) + + # test list arg of numerics + size, args = _json_args_to_str({"list1": [3, 2, 4]}) + self.assertEqual(size, 1) + self.assertListEqual( + [ + '{"key": "list1", "objType": "LIST", "dtype": "int", "val": "[\\"3\\", \\"2\\", \\"4\\"]"}' + ], + json.loads(args), + ) + + # test list of str + size, args = _json_args_to_str({"list1": ["a", "b", "c"], "list2": ["d", "e", "f"]}) + self.assertEqual(size, 2) + self.assertListEqual( + [ + '{"key": "list1", "objType": "LIST", "dtype": "str", "val": "[\\"a\\", \\"b\\", \\"c\\"]"}', + '{"key": "list2", "objType": "LIST", "dtype": "str", "val": "[\\"d\\", \\"e\\", \\"f\\"]"}', + ], + json.loads(args), + ) + + # test list of pdarray + pd1 = arange(3) + pd2 = arange(4) + size, args = _json_args_to_str({"pd1": pd1, "pd2": pd2}) + self.assertEqual(size, 2) + for a in json.loads(args): + p = json.loads(a) + self.assertRegex(p["key"], "^pd(1|2)$") + self.assertEqual(p["objType"], "PDARRAY") + self.assertEqual(p["dtype"], "int64") + self.assertRegex(p["val"], "^id_\\w{7}_\\d$") + + # test list of Strings + str1 = array(["abc", "def"]) + str2 = array(["Test", "Test2"]) + size, args = _json_args_to_str({"str1": str1, "str2": str2}) + self.assertEqual(size, 2) + for a in json.loads(args): + p = json.loads(a) + self.assertRegex(p["key"], "^str(1|2)$") + self.assertEqual(p["objType"], "SEGSTRING") + self.assertEqual(p["dtype"], "str") + self.assertRegex(p["val"], "^id_\\w{7}_\\d$")