@@ -65,37 +65,51 @@ def __post_init__(self):
6565 if isinstance (self .type , typing ._GenericAlias ):
6666 # means that could be a list, tuple or dict
6767 origin = self .type .__origin__
68-
69- if origin is list :
70- # because avro can have only one type, we take the first one
71- items_type = self .type .__args__ [0 ]
72-
73- if items_type in PYTHON_PRIMITIVE_TYPES :
74- self .items_type = PYTHON_TYPE_TO_AVRO [items_type ]
75- else :
76- # means is a custom type
77- self .items_type = schema_generator .SchemaGenerator (
78- items_type ).avro_schema_to_python ()
79- elif origin is dict :
80- # because avro can have only one type, we take the first one
81- values_type = self .type .__args__ [1 ]
82-
83- if values_type in PYTHON_PRIMITIVE_TYPES :
84- self .values_type = PYTHON_TYPE_TO_AVRO [values_type ]
85- else :
86- self .values_type = schema_generator .SchemaGenerator (
87- values_type ).avro_schema_to_python ()
88-
89- elif origin is tuple :
90- self .symbols = list (self .default )
91- else :
92- # we do not accept any other typing._GenericAlias like a set
93- # we should raise an exception
94- raise ValueError (
95- f"Invalid Type for field { self .name } . Accepted types are list, tuple or dict" )
68+ processor = self .get_processor (origin )
69+ processor ()
9670
9771 self .type = origin
9872
73+ def get_processor (self , origin ):
74+ if origin is list :
75+ return self ._process_list_type
76+ elif origin is dict :
77+ return self ._process_dict_type
78+ elif origin is tuple :
79+ return self ._process_tuple_type
80+ else :
81+ # we do not accept any other typing._GenericAlias like a set
82+ # we should raise an exception
83+ raise ValueError (
84+ f"Invalid Type for field { self .name } . Accepted types are list, tuple or dict" )
85+
86+ def _process_list_type (self ):
87+ # because avro can have only one type, we take the first one
88+ items_type = self .type .__args__ [0 ]
89+
90+ if items_type in PYTHON_PRIMITIVE_TYPES :
91+ self .items_type = PYTHON_TYPE_TO_AVRO [items_type ]
92+ elif isinstance (items_type , typing ._GenericAlias ):
93+ # Checking for a self reference. Maybe is a typing.ForwardRef
94+ self .items_type = self ._process_self_reference_type (items_type )
95+ else :
96+ # means is a custom type
97+ self .items_type = schema_generator .SchemaGenerator (
98+ items_type ).avro_schema_to_python ()
99+
100+ def _process_dict_type (self ):
101+ # because avro can have only one type, we take the first one
102+ values_type = self .type .__args__ [1 ]
103+
104+ if values_type in PYTHON_PRIMITIVE_TYPES :
105+ self .values_type = PYTHON_TYPE_TO_AVRO [values_type ]
106+ else :
107+ self .values_type = schema_generator .SchemaGenerator (
108+ values_type ).avro_schema_to_python ()
109+
110+ def _process_tuple_type (self ):
111+ self .symbols = list (self .default )
112+
99113 @staticmethod
100114 def get_singular_name (name ):
101115 singular = p .singular_noun (name )
0 commit comments