示例#1
0
    def test_dict_to_dataclass_deserialization_func(self):
        @dataclass
        class ExampleDataclass:
            int_field: int

        with self.subTest("Invalid deserialization"), self.assertRaises(
                DeserializationError):
            dict_to_dataclass(ExampleDataclass, {'int_field': "1"})

        with self.subTest("Using deserialization func"):
            self.assertEqual(
                ExampleDataclass(1),
                dict_to_dataclass(
                    ExampleDataclass, {'int_field': "1"},
                    deserialization_func=lambda cls, obj: int(obj)))
示例#2
0
    def test_dict_to_dataclass_basic(self):
        @dataclass
        class ExampleDataclass:
            int_field: int
            str_field: str

        self.assertEqual(
            ExampleDataclass(1, "Hello, world"),
            dict_to_dataclass(ExampleDataclass, {
                'int_field': 1,
                'str_field': "Hello, world"
            }))
    def test_dict_to_dataclass_inheritance(self):
        @dataclass
        class ExampleDataclass:
            int_field: int

        @dataclass
        class ChildDataclass(ExampleDataclass):
            str_field: str

        self.assertEqual(
            ChildDataclass(1, "Hello, world"),
            dict_to_dataclass(ChildDataclass, {
                "int_field": 1,
                "str_field": "Hello, world"
            }),
        )
    def test_dict_to_dataclass_basic(self):
        @dataclass
        class ExampleDataclass:
            int_field: int
            str_field: str
            optional_field: str = ""

        with self.subTest("Deserialize basic dict"):
            self.assertEqual(
                ExampleDataclass(1, "Hello, world", "Lorem ipsum"),
                dict_to_dataclass(
                    ExampleDataclass,
                    {
                        "int_field": 1,
                        "str_field": "Hello, world",
                        "optional_field": "Lorem ipsum",
                    },
                ),
            )

        with self.subTest("Fill in optional field"):
            self.assertEqual(
                ExampleDataclass(1, "Hello, world"),
                dict_to_dataclass(ExampleDataclass, {
                    "int_field": 1,
                    "str_field": "Hello, world"
                }),
            )

        with self.subTest("Fail missing field deserialization"
                          ), self.assertRaises(DeserializationError):
            dict_to_dataclass(ExampleDataclass, {"int_field": 1})

        with self.subTest("Fail non-dict deserialization"), self.assertRaises(
                DeserializationError):
            dict_to_dataclass(ExampleDataclass, 1)
示例#5
0
    def test_dict_to_dataclass_generics(self):
        T = TypeVar('T')

        @dataclass
        class ExampleRedundantGenericDataclass(Generic[T]):
            s: str

        @dataclass
        class ExampleGenericTypeVarDataclass(Generic[T]):
            t: T

        @dataclass
        class ExampleGenericCompoundDataclass(Generic[T]):
            t_dict: Dict[str, T]

        with self.subTest("Fail generic deserialization"):
            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleRedundantGenericDataclass, {'s': "a"})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericTypeVarDataclass, {'t': "a"})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericCompoundDataclass,
                                  {'t_dict': {}})

        with self.subTest("Deserialize bound generics"):
            self.assertEqual(
                ExampleRedundantGenericDataclass("a"),
                dict_to_dataclass(ExampleRedundantGenericDataclass[int],
                                  {'s': "a"}))

            self.assertEqual(
                ExampleGenericTypeVarDataclass("a"),
                dict_to_dataclass(ExampleGenericTypeVarDataclass[str],
                                  {'t': "a"}))
            self.assertEqual(
                ExampleGenericTypeVarDataclass(1),
                dict_to_dataclass(ExampleGenericTypeVarDataclass[int],
                                  {'t': 1}))

            self.assertEqual(
                ExampleGenericCompoundDataclass({'a': "b"}),
                dict_to_dataclass(ExampleGenericCompoundDataclass[str],
                                  {'t_dict': {
                                      'a': "b"
                                  }}))
            self.assertEqual(
                ExampleGenericCompoundDataclass({'a': 1}),
                dict_to_dataclass(ExampleGenericCompoundDataclass[int],
                                  {'t_dict': {
                                      'a': 1
                                  }}))

        with self.subTest("Deserialize indirectly bound generics"):
            self.assertEqual(
                ExampleGenericTypeVarDataclass(["a", "b"]),
                dict_to_dataclass(ExampleGenericTypeVarDataclass[List[T]][str],
                                  {'t': ["a", "b"]},
                                  deserialization_func=list_deserialization))

            self.assertEqual(
                ExampleGenericCompoundDataclass({'a': ["a", "b"]}),
                dict_to_dataclass(
                    ExampleGenericCompoundDataclass[List[T]][str],
                    {'t_dict': {
                        'a': ["a", "b"]
                    }},
                    deserialization_func=dict_deserialization(
                        value_deserialization_func=list_deserialization)))

        with self.subTest("Fail bound generic incorrect type"):
            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericTypeVarDataclass[str],
                                  {'t': 1})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericCompoundDataclass[str],
                                  {'t_dict': {
                                      'a': 1
                                  }})
    def test_dict_to_dataclass_generics(self):
        # Shadowing a non-identical TypeVar of the same name interacts strangely with postponing annotations
        # So use the one in outer scope (if it exists)
        T = globals().get("T", TypeVar("T"))

        @dataclass
        class ExampleRedundantGenericDataclass(Generic[T]):
            s: str

        @dataclass
        class ExampleGenericTypeVarDataclass(Generic[T]):
            t: T

        @dataclass
        class ExampleGenericCompoundDataclass(Generic[T]):
            t_dict: Dict[str, T]

        with self.subTest("Fail generic deserialization"):
            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleRedundantGenericDataclass, {"s": "a"})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericTypeVarDataclass, {"t": "a"})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericCompoundDataclass,
                                  {"t_dict": {}})

        with self.subTest("Deserialize bound generics"):
            self.assertEqual(
                ExampleRedundantGenericDataclass("a"),
                dict_to_dataclass(ExampleRedundantGenericDataclass[int],
                                  {"s": "a"}),
            )

            self.assertEqual(
                ExampleGenericTypeVarDataclass("a"),
                dict_to_dataclass(ExampleGenericTypeVarDataclass[str],
                                  {"t": "a"}),
            )
            self.assertEqual(
                ExampleGenericTypeVarDataclass(1),
                dict_to_dataclass(ExampleGenericTypeVarDataclass[int],
                                  {"t": 1}),
            )

            self.assertEqual(
                ExampleGenericCompoundDataclass({"a": "b"}),
                dict_to_dataclass(ExampleGenericCompoundDataclass[str],
                                  {"t_dict": {
                                      "a": "b"
                                  }}),
            )
            self.assertEqual(
                ExampleGenericCompoundDataclass({"a": 1}),
                dict_to_dataclass(ExampleGenericCompoundDataclass[int],
                                  {"t_dict": {
                                      "a": 1
                                  }}),
            )

        with self.subTest("Deserialize indirectly bound generics"):
            self.assertEqual(
                ExampleGenericTypeVarDataclass(["a", "b"]),
                dict_to_dataclass(
                    ExampleGenericTypeVarDataclass[List[T]][str],
                    {"t": ["a", "b"]},
                    deserialization_func=list_deserialization,
                ),
            )

            self.assertEqual(
                ExampleGenericCompoundDataclass({"a": ["a", "b"]}),
                dict_to_dataclass(
                    ExampleGenericCompoundDataclass[List[T]][str],
                    {"t_dict": {
                        "a": ["a", "b"]
                    }},
                    deserialization_func=dict_deserialization(
                        value_deserialization_func=list_deserialization),
                ),
            )

        with self.subTest("Fail bound generic incorrect type"):
            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericTypeVarDataclass[str],
                                  {"t": 1})

            with self.assertRaises(DeserializationError):
                dict_to_dataclass(ExampleGenericCompoundDataclass[str],
                                  {"t_dict": {
                                      "a": 1
                                  }})