from test_pil_builder_utils import TestParser, Expr
def test_pil_builder_constant():
with TestParser():
@TestParser.test
def const_binop_left():
var_x = 2 + Expr.int(0)
Expr.str(var_x)
@TestParser.test
def const_binop_right():
var_x = Expr.int(0) + 3
Expr.str(var_x)
@TestParser.test
def const_binop_both():
var_x = 2 + 3
Expr.str(var_x)
@TestParser.test
def const_unary_neg():
var_x = -1
Expr.str(var_x)
@TestParser.test
def const_unary_not():
var_x = not False
Expr.str(var_x)
@TestParser.test
def const_if_true():
if 1:
Expr.str(0)
else:
Expr.str(1)
@TestParser.test
def const_if_false():
if 0:
Expr.str(0)
else:
Expr.str(1)
@TestParser.test
def const_for_iter():
for var_x in (0, 1, 2):
Expr.str(var_x)
@TestParser.test
def const_while_test():
while 1:
Expr.str(0)
break
@TestParser.test
def const_call_pos_arg():
def func(x):
Expr.str(x)
func(42)
@TestParser.test
def const_call_kw_arg():
def func(x):
Expr.str(x)
func(x=42)
@TestParser.test
def const_in_tuple():
var_t = (0, Expr.int(1), 2)
Expr.str(var_t[0])
Expr.str(var_t[1])
Expr.str(var_t[2])
@TestParser.test
def const_in_list():
var_l = [0, Expr.int(1), 2]
Expr.str(var_l[0])
Expr.str(var_l[1])
Expr.str(var_l[2])
@TestParser.test
def const_dict_key():
var_d = {0: Expr.int(1)}
Expr.str(var_d[0])
@TestParser.test
def const_dict_value():
var_d = {Expr.int(0): 99}
Expr.str(var_d[0])
@TestParser.test
def const_dict_both():
var_d = {0: 99}
Expr.str(var_d[0])
@TestParser.test
def const_in_set():
var_s = {0, Expr.int(1)}
Expr.str(0 in var_s)
@TestParser.test
def const_subscript_index():
var_obj = Expr(0)
var_obj[0] = Expr.int(1)
var_x = var_obj[0]
Expr.str(var_x)
@TestParser.test
def const_slice_bounds():
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[1:3]
Expr.str(var_s[0])
@TestParser.test
def const_annotation_no_value():
var_x: int
@TestParser.test
def const_annotation_with_value():
var_x: int = Expr.int(0)
Expr.str(var_x)
def test_pil_builder_joined_str():
with TestParser():
@TestParser.test
def fstr_single_expr():
var_x = f"{Expr.str(0)}"
@TestParser.test
def fstr_prefix_and_expr():
var_x = f"prefix_{Expr.str(0)}"
@TestParser.test
def fstr_expr_and_suffix():
var_x = f"{Expr.str(0)}_suffix"
@TestParser.test
def fstr_prefix_expr_suffix():
var_x = f"prefix_{Expr.str(0)}_suffix"
@TestParser.test
def fstr_two_exprs():
var_x = f"{Expr.str(0)}{Expr.str(1)}"
@TestParser.test
def fstr_expr_sep_expr():
var_x = f"{Expr.str(0)}_{Expr.str(1)}"
@TestParser.test
def fstr_conversion_s():
var_x = f"{Expr.int(0)!s}"
@TestParser.test
def fstr_conversion_r():
var_x = f"{Expr.int(0)!r}"
@TestParser.test
def fstr_conversion_a():
var_x = f"{Expr.int(0)!a}"
@TestParser.test
def fstr_format_spec_const():
var_x = f"{Expr.str(0):>10}"
@TestParser.test
def fstr_format_spec_expr():
var_fmt = '>10'
var_x = f"{Expr.str(0):{var_fmt}}"
@TestParser.test
def fstr_conversion_and_format_spec():
var_x = f"{Expr.int(0)!r:>10}"
@TestParser.test
def fstr_nested_call_expr():
var_x = f"{Expr.str(Expr.int(0))}"
def test_pil_builder_dict():
with TestParser():
@TestParser.test
def dict_empty():
var_d = {}
@TestParser.test
def dict_const_key_call_value():
var_d = {0: Expr.int(1)}
@TestParser.test
def dict_call_key_call_value():
var_d = {Expr.int(0): Expr.int(1)}
@TestParser.test
def dict_multiple_pairs():
var_d = {Expr.int(0): Expr.int(1), Expr.int(2): Expr.int(3)}
@TestParser.test
def dict_three_pairs():
var_d = {Expr.int(0): Expr.int(1), Expr.int(2): Expr.int(3), Expr.int(4): Expr.int(5)}
@TestParser.test
def dict_spread_only():
var_other = {0: Expr.int(0)}
var_d = {**var_other}
@TestParser.test
def dict_normal_then_spread():
var_other = {2: Expr.int(2)}
var_d = {Expr.int(0): Expr.int(1), **var_other}
@TestParser.test
def dict_spread_in_middle():
var_other = {1: Expr.int(2)}
var_d = {Expr.int(0): Expr.int(0), **var_other, Expr.int(3): Expr.int(4)}
@TestParser.test
def dict_multiple_spreads():
var_a = {0: Expr.int(0)}
var_b = {1: Expr.int(1)}
var_d = {**var_a, **var_b}
@TestParser.test
def dict_spread_from_func_call():
def make():
return {Expr.int(0): Expr.int(1)}
var_d = {**make()}
@TestParser.test
def dict_normal_then_spread_from_call():
def make():
return {Expr.int(2): Expr.int(3)}
var_d = {Expr.int(0): Expr.int(1), **make()}
@TestParser.test
def dict_spread_from_call_then_normal():
def make():
return {Expr.int(0): Expr.int(1)}
var_d = {**make(), Expr.int(2): Expr.int(3)}
@TestParser.test
def dict_multiple_spreads_from_calls():
def make_a():
return {Expr.int(0): Expr.int(1)}
def make_b():
return {Expr.int(2): Expr.int(3)}
var_d = {**make_a(), **make_b()}
@TestParser.test
def dict_nested_value():
var_d = {Expr.int(0): {Expr.int(1): Expr.int(2)}}
def test_pil_builder_set():
with TestParser():
@TestParser.test
def set_single_const():
var_s = {0}
@TestParser.test
def set_single_call():
var_s = {Expr.int(0)}
@TestParser.test
def set_multiple_calls():
var_s = {Expr.int(0), Expr.int(1), Expr.int(2)}
@TestParser.test
def set_spread_only():
var_other = [Expr.int(0), Expr.int(1)]
var_s = {*var_other}
@TestParser.test
def set_spread_from_func_call():
def make():
return [Expr.int(0), Expr.int(1)]
var_s = {*make()}
@TestParser.test
def set_normal_then_spread():
def make():
return [Expr.int(2), Expr.int(3)]
var_s = {Expr.int(0), Expr.int(1), *make()}
@TestParser.test
def set_spread_then_normal():
def make():
return [Expr.int(0), Expr.int(1)]
var_s = {*make(), Expr.int(2), Expr.int(3)}
@TestParser.test
def set_spread_in_middle():
def make():
return [Expr.int(1), Expr.int(2)]
var_s = {Expr.int(0), *make(), Expr.int(3)}
@TestParser.test
def set_multiple_spreads_from_calls():
def make_a():
return [Expr.int(0), Expr.int(1)]
def make_b():
return [Expr.int(2), Expr.int(3)]
var_s = {*make_a(), *make_b()}
def test_pil_builder_list():
with TestParser():
@TestParser.test
def list_empty():
var_l = []
@TestParser.test
def list_single_const():
var_l = [0]
@TestParser.test
def list_single_call():
var_l = [Expr.int(0)]
@TestParser.test
def list_multiple_calls():
var_l = [Expr.int(0), Expr.int(1), Expr.int(2)]
@TestParser.test
def list_starred_only():
var_other = [Expr.int(0), Expr.int(1)]
var_l = [*var_other]
@TestParser.test
def list_starred_from_call():
def make():
return [Expr.int(0), Expr.int(1)]
var_l = [*make()]
@TestParser.test
def list_normal_then_starred():
def make():
return [Expr.int(2), Expr.int(3)]
var_l = [Expr.int(0), Expr.int(1), *make()]
@TestParser.test
def list_starred_then_normal():
def make():
return [Expr.int(0), Expr.int(1)]
var_l = [*make(), Expr.int(2), Expr.int(3)]
@TestParser.test
def list_starred_in_middle():
def make():
return [Expr.int(1), Expr.int(2)]
var_l = [Expr.int(0), *make(), Expr.int(3)]
@TestParser.test
def list_multiple_starred_from_calls():
def make_a():
return [Expr.int(0), Expr.int(1)]
def make_b():
return [Expr.int(2), Expr.int(3)]
var_l = [*make_a(), *make_b()]
@TestParser.test
def list_nested():
var_l = [Expr.int(0), [Expr.int(1), Expr.int(2)]]
def test_pil_builder_tuple():
with TestParser():
@TestParser.test
def tuple_single_const():
var_t = (0,)
@TestParser.test
def tuple_single_call():
var_t = (Expr.int(0),)
@TestParser.test
def tuple_multiple_calls():
var_t = (Expr.int(0), Expr.int(1), Expr.int(2))
@TestParser.test
def tuple_starred_only():
var_other = [Expr.int(0), Expr.int(1)]
var_t = (*var_other,)
@TestParser.test
def tuple_starred_from_call():
def make():
return [Expr.int(0), Expr.int(1)]
var_t = (*make(),)
@TestParser.test
def tuple_normal_then_starred():
def make():
return [Expr.int(2), Expr.int(3)]
var_t = (Expr.int(0), Expr.int(1), *make())
@TestParser.test
def tuple_starred_then_normal():
def make():
return [Expr.int(0), Expr.int(1)]
var_t = (*make(), Expr.int(2), Expr.int(3))
@TestParser.test
def tuple_starred_in_middle():
def make():
return [Expr.int(1), Expr.int(2)]
var_t = (Expr.int(0), *make(), Expr.int(3))
@TestParser.test
def tuple_multiple_starred_from_calls():
def make_a():
return [Expr.int(0), Expr.int(1)]
def make_b():
return [Expr.int(2), Expr.int(3)]
var_t = (*make_a(), *make_b())
@TestParser.test
def tuple_nested():
var_t = (Expr.int(0), (Expr.int(1), Expr.int(2)))
def test_pil_builder_attribute():
with TestParser():
@TestParser.test
def attr_binop_left():
var_obj = Expr(0)
var_obj.val = Expr.int(2)
var_x = var_obj.val + Expr.int(1)
Expr.str(var_x)
@TestParser.test
def attr_binop_right():
var_obj = Expr(0)
var_obj.val = Expr.int(3)
var_x = Expr.int(1) + var_obj.val
Expr.str(var_x)
@TestParser.test
def attr_binop_both():
var_a = Expr(0)
var_a.val = Expr.int(2)
var_b = Expr(1)
var_b.val = Expr.int(3)
var_x = var_a.val + var_b.val
Expr.str(var_x)
@TestParser.test
def attr_unary_neg():
var_obj = Expr(0)
var_obj.val = Expr.int(5)
var_x = -var_obj.val
Expr.str(var_x)
@TestParser.test
def attr_unary_not():
var_obj = Expr(0)
var_obj.val = Expr.true(0)
var_x = not var_obj.val
Expr.str(var_x)
@TestParser.test
def attr_if_true():
var_obj = Expr(0)
var_obj.val = Expr.true(0)
if var_obj.val:
Expr.str(1)
else:
Expr.str(2)
@TestParser.test
def attr_if_false():
var_obj = Expr(0)
var_obj.val = Expr.false(0)
if var_obj.val:
Expr.str(1)
else:
Expr.str(2)
@TestParser.test
def attr_for_iter():
var_obj = Expr(0)
var_obj.val = [Expr.int(0), Expr.int(1), Expr.int(2)]
for var_x in var_obj.val:
Expr.str(var_x)
@TestParser.test
def attr_while_test():
var_obj = Expr(0)
var_obj.val = Expr.true(0)
while var_obj.val:
Expr.str(1)
var_obj.val = False
@TestParser.test
def attr_call_pos_arg():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
Expr.str(var_obj.val)
@TestParser.test
def attr_call_kw_arg():
def func(x):
Expr.str(x)
var_obj = Expr(0)
var_obj.val = Expr.int(1)
func(x=var_obj.val)
@TestParser.test
def attr_in_tuple():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
var_t = (var_obj.val, Expr.int(2))
Expr.str(var_t[0])
Expr.str(var_t[1])
@TestParser.test
def attr_in_list():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
var_l = [var_obj.val, Expr.int(2)]
Expr.str(var_l[0])
Expr.str(var_l[1])
@TestParser.test
def attr_dict_key():
var_obj = Expr(0)
var_obj.val = Expr.int(0)
var_d = {var_obj.val: Expr.int(1)}
Expr.str(var_d[0])
@TestParser.test
def attr_dict_value():
var_obj = Expr(0)
var_obj.val = Expr.int(99)
var_d = {Expr.int(0): var_obj.val}
Expr.str(var_d[0])
@TestParser.test
def attr_in_set():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
var_s = {var_obj.val, Expr.int(2)}
Expr.str(1 in var_s)
@TestParser.test
def attr_subscript_index():
var_obj = Expr(0)
var_obj.val = Expr.int(0)
var_arr = Expr(1)
var_arr[0] = Expr.int(99)
var_x = var_arr[var_obj.val]
Expr.str(var_x)
@TestParser.test
def attr_slice_lower():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
var_l = [Expr.int(0), Expr.int(1), Expr.int(2)]
var_s = var_l[var_obj.val:3]
Expr.str(var_s[0])
@TestParser.test
def attr_slice_upper():
var_obj = Expr(0)
var_obj.val = Expr.int(2)
var_l = [Expr.int(0), Expr.int(1), Expr.int(2)]
var_s = var_l[0:var_obj.val]
Expr.str(var_s[0])
@TestParser.test
def attr_slice_both():
var_lo = Expr(0)
var_lo.val = Expr.int(1)
var_hi = Expr(1)
var_hi.val = Expr.int(3)
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[var_lo.val:var_hi.val]
Expr.str(var_s[0])
@TestParser.test
def attr_annotation_no_value():
var_x: Expr.ContextManager
@TestParser.test
def attr_annotation_with_value():
var_x: Expr.ContextManager = Expr.int(0)
Expr.str(var_x)
def test_pil_builder_subscript():
with TestParser():
@TestParser.test
def subscript_binop_left():
var_l = [Expr.int(2), Expr.int(3)]
var_x = var_l[0] + Expr.int(1)
Expr.str(var_x)
@TestParser.test
def subscript_binop_right():
var_l = [Expr.int(3), Expr.int(4)]
var_x = Expr.int(1) + var_l[0]
Expr.str(var_x)
@TestParser.test
def subscript_binop_both():
var_l = [Expr.int(2), Expr.int(3)]
var_x = var_l[0] + var_l[1]
Expr.str(var_x)
@TestParser.test
def subscript_unary_neg():
var_l = [Expr.int(5)]
var_x = -var_l[0]
Expr.str(var_x)
@TestParser.test
def subscript_unary_not():
var_l = [Expr.true(0)]
var_x = not var_l[0]
Expr.str(var_x)
@TestParser.test
def subscript_if_true():
var_l = [Expr.true(0)]
if var_l[0]:
Expr.str(1)
else:
Expr.str(2)
@TestParser.test
def subscript_if_false():
var_l = [Expr.false(0)]
if var_l[0]:
Expr.str(1)
else:
Expr.str(2)
@TestParser.test
def subscript_for_iter():
var_l = [[Expr.int(0), Expr.int(1), Expr.int(2)]]
for var_x in var_l[0]:
Expr.str(var_x)
@TestParser.test
def subscript_while_test():
var_l = [True]
while var_l[0]:
Expr.str(0)
var_l[0] = False
@TestParser.test
def subscript_call_pos_arg():
var_l = [Expr.int(0)]
Expr.str(var_l[0])
@TestParser.test
def subscript_call_kw_arg():
def func(x):
Expr.str(x)
var_l = [Expr.int(0)]
func(x=var_l[0])
@TestParser.test
def subscript_in_tuple():
var_l = [Expr.int(1), Expr.int(2)]
var_t = (var_l[0], var_l[1])
Expr.str(var_t[0])
Expr.str(var_t[1])
@TestParser.test
def subscript_in_list():
var_l = [Expr.int(1), Expr.int(2)]
var_r = [var_l[0], var_l[1]]
Expr.str(var_r[0])
Expr.str(var_r[1])
@TestParser.test
def subscript_dict_key():
var_keys = [Expr.int(0)]
var_d = {var_keys[0]: Expr.int(99)}
Expr.str(var_d[0])
@TestParser.test
def subscript_dict_value():
var_vals = [Expr.int(99)]
var_d = {Expr.int(0): var_vals[0]}
Expr.str(var_d[0])
@TestParser.test
def subscript_in_set():
var_l = [Expr.int(1), Expr.int(2)]
var_s = {var_l[0], var_l[1]}
Expr.str(1 in var_s)
@TestParser.test
def subscript_as_index():
var_idx = [Expr.int(0)]
var_arr = Expr(0)
var_arr[0] = Expr.int(99)
var_x = var_arr[var_idx[0]]
Expr.str(var_x)
@TestParser.test
def subscript_annotation_no_value():
var_x: list[int]
@TestParser.test
def subscript_annotation_with_value():
var_x: list[int] = [Expr.int(0)]
Expr.str(var_x[0])
@TestParser.test
def slice_index_attr():
var_obj = Expr(0)
var_obj.val = Expr.int(1)
var_arr = Expr(1)
var_arr[1] = Expr.int(99)
var_x = var_arr[var_obj.val]
Expr.str(var_x)
@TestParser.test
def slice_index_call():
def idx():
return Expr.int(0)
var_arr = Expr(0)
var_arr[0] = Expr.int(99)
var_x = var_arr[idx()]
Expr.str(var_x)
@TestParser.test
def slice_index_binop():
var_arr = Expr(0)
var_arr[2] = Expr.int(99)
var_x = var_arr[Expr.int(1) + Expr.int(1)]
Expr.str(var_x)
@TestParser.test
def slice_index_unary():
var_arr = Expr(0)
var_arr[-1] = Expr.int(99)
var_x = var_arr[-Expr.int(1)]
Expr.str(var_x)
@TestParser.test
def slice_index_subscript():
var_idxs = [Expr.int(0)]
var_arr = Expr(0)
var_arr[0] = Expr.int(99)
var_x = var_arr[var_idxs[0]]
Expr.str(var_x)
@TestParser.test
def slice_index_dict():
var_d = {0: Expr.int(1)}
var_arr = Expr(0)
var_arr[1] = Expr.int(99)
var_x = var_arr[var_d[0]]
Expr.str(var_x)
@TestParser.test
def slice_index_set():
var_s = {0}
var_arr = Expr(0)
var_arr[True] = Expr.int(99)
var_x = var_arr[0 in var_s]
Expr.str(var_x)
@TestParser.test
def slice_index_named_expr():
var_arr = Expr(0)
var_arr[0] = Expr.int(99)
var_x = var_arr[(var_k := Expr.int(0))]
Expr.str(var_x)
Expr.str(var_k)
@TestParser.test
def slice_range_attr_bounds():
var_lo = Expr(0)
var_lo.val = Expr.int(1)
var_hi = Expr(1)
var_hi.val = Expr.int(3)
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[var_lo.val:var_hi.val]
Expr.str(var_s[0])
@TestParser.test
def slice_range_call_bounds():
def lo():
return Expr.int(1)
def hi():
return Expr.int(3)
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[lo():hi()]
Expr.str(var_s[0])
@TestParser.test
def slice_range_binop_bounds():
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[Expr.int(0) + 1: Expr.int(1) + 2]
Expr.str(var_s[0])
@TestParser.test
def slice_range_subscript_bounds():
var_bounds = [Expr.int(1), Expr.int(3)]
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[var_bounds[0]:var_bounds[1]]
Expr.str(var_s[0])
@TestParser.test
def slice_range_dict_bounds():
var_d = {'lo': Expr.int(1), 'hi': Expr.int(3)}
var_l = [Expr.int(0), Expr.int(1), Expr.int(2), Expr.int(3)]
var_s = var_l[var_d['lo']:var_d['hi']]
Expr.str(var_s[0])