From f96cc3bd740ffbd9301dd310bfad328852ca144d Mon Sep 17 00:00:00 2001 From: Itamar Goldman Date: Mon, 28 Aug 2023 13:10:56 +0300 Subject: [PATCH 1/4] Update json.py --- qiskit_ibm_provider/utils/json.py | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/qiskit_ibm_provider/utils/json.py b/qiskit_ibm_provider/utils/json.py index 7853e1550..7512589fc 100644 --- a/qiskit_ibm_provider/utils/json.py +++ b/qiskit_ibm_provider/utils/json.py @@ -203,8 +203,9 @@ def default(self, obj: Any) -> Any: # pylint: disable=arguments-differ return {"__type__": "ndarray", "__value__": obj.tolist()} value = _serialize_and_encode(obj, np.save, allow_pickle=False) return {"__type__": "ndarray", "__value__": value} - if isinstance(obj, np.int64): - return {"__type__": "int", "__value__": int(obj)} + if isinstance(obj, np.number): + # Maybe we should encode the numpy data type here for better accuracy. + return {"__type__": type(obj.item()).__name__, "__value__": obj.item()} if isinstance(obj, set): return {"__type__": "set", "__value__": list(obj)} if isinstance(obj, Result): @@ -294,7 +295,12 @@ def object_hook(self, obj: Any) -> Any: if obj_type == "set": return set(obj_val) if obj_type == "QuantumCircuit": - return _decode_and_deserialize(obj_val, load)[0] + return _decode_and_deserialize( + data=obj_val, + deserializer=lambda buff: load( + buff, metadata_deserializer=RuntimeDecoder + ), + )[0] # type: ignore[no-untyped-call] if obj_type == "Parameter": return _decode_and_deserialize(obj_val, _read_parameter, False) if obj_type == "ParameterExpression": From b614a8ce299545d81e88253f4f649000ede965ce Mon Sep 17 00:00:00 2001 From: Itamar Goldman Date: Mon, 28 Aug 2023 13:52:58 +0300 Subject: [PATCH 2/4] Update json.py --- qiskit_ibm_provider/utils/json.py | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/qiskit_ibm_provider/utils/json.py b/qiskit_ibm_provider/utils/json.py index 7512589fc..380d9b000 100644 --- a/qiskit_ibm_provider/utils/json.py +++ b/qiskit_ibm_provider/utils/json.py @@ -300,7 +300,9 @@ def object_hook(self, obj: Any) -> Any: deserializer=lambda buff: load( buff, metadata_deserializer=RuntimeDecoder ), - )[0] # type: ignore[no-untyped-call] + )[ + 0 + ] # type: ignore[no-untyped-call] if obj_type == "Parameter": return _decode_and_deserialize(obj_val, _read_parameter, False) if obj_type == "ParameterExpression": From 50790c804d7fc689c4d6d5825b21246534e69fdc Mon Sep 17 00:00:00 2001 From: Itamar Goldman Date: Thu, 31 Aug 2023 14:17:07 +0300 Subject: [PATCH 3/4] Added test for metadata serialization --- test/unit/test_serialization.py | 19 ++++++++++++++++--- 1 file changed, 16 insertions(+), 3 deletions(-) diff --git a/test/unit/test_serialization.py b/test/unit/test_serialization.py index d3b5cefc7..b1700a484 100644 --- a/test/unit/test_serialization.py +++ b/test/unit/test_serialization.py @@ -14,6 +14,9 @@ import json import numpy as np + +from ddt import data, ddt + from qiskit import assemble from qiskit import QuantumCircuit, QuantumRegister, ClassicalRegister from qiskit.circuit import Parameter @@ -23,6 +26,7 @@ from ..ibm_test_case import IBMTestCase +@ddt class TestSerialization(IBMTestCase): """Test data serialization.""" @@ -67,11 +71,20 @@ def test_encode_replace(self): IBMJsonEncoder().encode(test_dir), ) - def test_circuit_metadata(self): + @data( + np.arange(0, 10, 1), + np.arange(0.0, 10.0, 1), + np.int32(1), + np.int64(2), + np.float64(3.1), + complex(1, 1), + np.complex64(complex(1, 3)), + "TEST", + ) + def test_circuit_metadata(self, metadata_test): """Test serializing circuit metadata.""" - circ = QuantumCircuit(1) - circ.metadata = {"test": np.arange(0, 10)} + circ.metadata = {"test": metadata_test} payload = {"circuits": [circ]} self.assertTrue(json.dumps(payload, cls=RuntimeEncoder)) From 85f78de20c4211b0d93b4b21a4a1322668a1c64d Mon Sep 17 00:00:00 2001 From: Itamar Goldman Date: Thu, 31 Aug 2023 14:59:19 +0300 Subject: [PATCH 4/4] added release notes --- ...g-fix-metadata-numpy-number-support-7613af6c44b99107.yaml | 5 +++++ 1 file changed, 5 insertions(+) create mode 100644 releasenotes/notes/bug-fix-metadata-numpy-number-support-7613af6c44b99107.yaml diff --git a/releasenotes/notes/bug-fix-metadata-numpy-number-support-7613af6c44b99107.yaml b/releasenotes/notes/bug-fix-metadata-numpy-number-support-7613af6c44b99107.yaml new file mode 100644 index 000000000..25f711b55 --- /dev/null +++ b/releasenotes/notes/bug-fix-metadata-numpy-number-support-7613af6c44b99107.yaml @@ -0,0 +1,5 @@ +--- +fixes: + - | + Fixed an issue where circuit metadata was not being serialized correctly + for numpy numbers. In addition, added `RuntimeDecoder` as metadata deserializer.