@@ -279,23 +279,9 @@ def context_matches_condition(
279279 context_value = get_context_value (context , condition_property )
280280
281281 if condition_operator == constants .IN :
282- if isinstance (segment_value := condition ["value" ], list ):
283- in_values = segment_value
284- else :
285- try :
286- in_values = json .loads (segment_value )
287- # Only accept JSON lists.
288- # Ideally, we should use something like pydantic.TypeAdapter[list[str]],
289- # but we aim to ditch the pydantic dependency in the future.
290- if not isinstance (in_values , list ):
291- raise ValueError
292- except ValueError :
293- in_values = segment_value .split ("," )
294- in_values = [str (value ) for value in in_values ]
282+ in_values = _get_in_values (condition ["value" ])
295283 # Guard against comparing boolean values to numeric strings.
296- if isinstance (context_value , int ) and not (
297- context_value is True or context_value is False
298- ):
284+ if type (context_value ) is int :
299285 context_value = str (context_value )
300286 return context_value in in_values
301287
@@ -348,6 +334,30 @@ def _matches_context_value(
348334 return False
349335
350336
337+ @lru_cache (maxsize = 1024 )
338+ def _parse_in_values_str (segment_value : str ) -> frozenset [str ]:
339+ """
340+ Parse a string-form IN condition value into a frozenset of strings.
341+ A bracketed value is tried as JSON first (with CSV fallback on parse
342+ error); anything else is split on commas directly.
343+ """
344+ if segment_value .startswith ("[" ):
345+ try :
346+ parsed : list [typing .Any ] = json .loads (segment_value )
347+ except ValueError :
348+ return frozenset (segment_value .split ("," ))
349+ return frozenset (v if type (v ) is str else str (v ) for v in parsed )
350+ return frozenset (segment_value .split ("," ))
351+
352+
353+ def _get_in_values (
354+ segment_value : typing .Union [str , list [typing .Any ]],
355+ ) -> frozenset [str ]:
356+ if isinstance (segment_value , list ):
357+ return frozenset (v if type (v ) is str else str (v ) for v in segment_value )
358+ return _parse_in_values_str (segment_value )
359+
360+
351361def _evaluate_not_contains (
352362 segment_value : typing .Optional [str ],
353363 context_value : ContextValue ,
0 commit comments