1+ import json
12import re
23from typing import Any , Callable , Dict , List , Optional , Tuple , Union
34
@@ -26,7 +27,7 @@ class InputFilter:
2627 "__global_validators" ,
2728 "__data" ,
2829 "__validated_data" ,
29- "__error_message " ,
30+ "__errors " ,
3031 )
3132
3233 def __init__ (self , methods : Optional [List [str ]] = None ) -> None :
@@ -37,7 +38,7 @@ def __init__(self, methods: Optional[List[str]] = None) -> None:
3738 self .__global_validators : List [BaseValidator ] = []
3839 self .__data : Dict [str , Any ] = {}
3940 self .__validated_data : Dict [str , Any ] = {}
40- self .__error_message : str = ""
41+ self .__errors : Dict [ str , str ] = {}
4142
4243 @final
4344 def add (
@@ -269,10 +270,10 @@ def clear(self) -> None:
269270 self .__global_validators .clear ()
270271 self .__data .clear ()
271272 self .__validated_data .clear ()
272- self .__error_message = ""
273+ self .__errors . clear ()
273274
274275 @final
275- def getErrorMessage (self ) -> str :
276+ def getErrorMessage (self , field_name : str ) -> str :
276277 """
277278 Retrieves and returns a predefined error message.
278279
@@ -286,7 +287,23 @@ def getErrorMessage(self) -> str:
286287 Returns:
287288 str: A string representing the predefined error message.
288289 """
289- return self .__error_message
290+ return self .__errors .get (field_name )
291+
292+ @final
293+ def getErrorMessages (self ) -> Dict [str , str ]:
294+ """
295+ Retrieves all error messages associated with the fields in the
296+ input filter.
297+
298+ This method aggregates and returns a dictionary of error messages
299+ where the keys represent field names, and the values are their
300+ respective error messages.
301+
302+ Returns:
303+ Dict[str, str]: A dictionary containing field names as keys and
304+ their corresponding error messages as values.
305+ """
306+ return self .__errors
290307
291308 @final
292309 def getValue (self , name : str ) -> Any :
@@ -516,8 +533,8 @@ def isValid(self) -> bool:
516533 try :
517534 self .validateData (self .__data )
518535
519- except ( ValidationError , Exception ) as e :
520- self .__error_message = str ( e )
536+ except ValidationError as e :
537+ self .__errors = e . args [ 0 ]
521538 return False
522539
523540 return True
@@ -549,6 +566,7 @@ def validateData(
549566 """
550567 validated_data = self .__validated_data
551568 data = data or self .__data
569+ errors = {}
552570
553571 for field_name , field_info in self .__fields .items ():
554572 value = data .get (field_name )
@@ -562,30 +580,38 @@ def validateData(
562580 external_api = field_info .external_api
563581 copy = field_info .copy
564582
565- if copy :
566- value = validated_data .get (copy )
567-
568- if external_api :
569- value = self .__callExternalApi (
570- external_api , fallback , validated_data
571- )
583+ try :
584+ if copy :
585+ value = validated_data .get (copy )
572586
573- value = self .__applyFilters (filters , value )
587+ if external_api :
588+ value = self .__callExternalApi (
589+ external_api , fallback , validated_data
590+ )
574591
575- value = self .__validateField (validators , fallback , value ) or value
592+ value = self .__applyFilters (filters , value )
593+ value = (
594+ self .__validateField (validators , fallback , value ) or value
595+ )
596+ value = self .__applySteps (steps , fallback , value ) or value
597+ value = self .__checkForRequired (
598+ field_name , required , default , fallback , value
599+ )
576600
577- value = self . __applySteps ( steps , fallback , value ) or value
601+ validated_data [ field_name ] = value
578602
579- value = self .__checkForRequired (
580- field_name , required , default , fallback , value
581- )
603+ except ValidationError as e :
604+ errors [field_name ] = str (e )
582605
583- validated_data [field_name ] = value
606+ try :
607+ self .__checkConditions (validated_data )
608+ except ValidationError as e :
609+ errors ["_condition" ] = str (e )
584610
585- self .__checkConditions (validated_data )
611+ if errors :
612+ raise ValidationError (errors )
586613
587614 self .__validated_data = validated_data
588-
589615 return validated_data
590616
591617 @classmethod
@@ -626,7 +652,11 @@ def wrapper(
626652 g .validated_data = input_filter .validateData ()
627653
628654 except ValidationError as e :
629- return Response (status = 400 , response = str (e ))
655+ return Response (
656+ status = 400 ,
657+ response = json .dumps (e .args [0 ]),
658+ mimetype = "application/json" ,
659+ )
630660
631661 return f (* args , ** kwargs )
632662
@@ -724,8 +754,14 @@ def __callExternalApi(
724754 Raised if the external API call does not succeed and no
725755 fallback value is provided.
726756 """
757+ import logging
758+
727759 import requests
728760
761+ logger = logging .getLogger (__name__ )
762+
763+ data_key = config .data_key
764+
729765 requestData = {
730766 "headers" : {},
731767 "params" : {},
@@ -753,25 +789,22 @@ def __callExternalApi(
753789 response = requests .request (** requestData )
754790
755791 if response .status_code != 200 :
756- raise ValidationError (
757- f"External API call failed with "
758- f"status code { response .status_code } "
792+ logger . error (
793+ f"External_api request inside of InputFilter "
794+ f"failed: { response .text } "
759795 )
796+ raise
760797
761798 result = response .json ()
762799
763- data_key = config .data_key
764800 if data_key :
765801 return result .get (data_key )
766802
767803 return result
768- except Exception as e :
804+ except Exception :
769805 if fallback is None :
770- self .__error_message = str (e )
771-
772806 raise ValidationError (
773- f"External API call failed for field "
774- f"'{ config .data_key } '."
807+ f"External API call failed for field " f"'{ data_key } '."
775808 )
776809
777810 return fallback
@@ -829,7 +862,9 @@ def __checkForRequired(
829862
830863 raise ValidationError (f"Field '{ field_name } ' is required." )
831864
832- def __checkConditions (self , validated_data : dict ) -> None :
865+ def __checkConditions (self , validated_data : Dict [ str , Any ] ) -> None :
833866 for condition in self .__conditions :
834867 if not condition .check (validated_data ):
835- raise ValidationError (f"Condition '{ condition } ' not met." )
868+ raise ValidationError (
869+ f"Condition '{ condition .__class__ .__name__ } ' not met."
870+ )
0 commit comments