handle default args

This commit is contained in:
Khaleel Al-Adhami 2025-01-23 13:09:47 -08:00
parent d3b12a84fa
commit 0d746bf762
4 changed files with 35 additions and 19 deletions

View File

@ -1219,9 +1219,20 @@ class FunctionVar(
args = tuple(map(LiteralVar.create, args))
self._pre_check(*args)
return_type = self._return_type(*args)
if arg_len == len(args) and isinstance(
self, (ArgsFunctionOperation, ArgsFunctionOperationBuilder)
):
if isinstance(self, (ArgsFunctionOperation, ArgsFunctionOperationBuilder)):
default_args = self._default_args()
max_allowed_arguments = (
arg_len if arg_len is not None else len(args) + len(default_args)
)
provided_argument_count = len(args)
# we skip default args which we provided
default_args_provided = len(default_args) - (
max_allowed_arguments - provided_argument_count
)
full_args = args + tuple(default_args[default_args_provided:])
if self._raw_js_function is not None:
return VarOperationCall.create(
FunctionStringVar.create(
@ -1229,13 +1240,13 @@ class FunctionVar(
_var_type=self._var_type,
_var_data=self._get_all_var_data(),
),
*args,
*full_args,
_var_type=return_type,
).guess_type()
if self._original_var_operation is not None:
return ExpressionCall.create(
self._original_var_operation,
*args,
*full_args,
_var_data=self._get_all_var_data(),
_var_type=return_type,
).guess_type()
@ -1316,6 +1327,20 @@ class FunctionVar(
)
return 0
def _default_args(self) -> list[Any]:
"""Get the default arguments of the function.
Returns:
The default arguments of the function.
"""
if isinstance(self, (ArgsFunctionOperation, ArgsFunctionOperationBuilder)):
return [
arg.default
for arg in self._default_values
if not isinstance(arg, inspect.Parameter.empty)
]
return []
def _return_type(self, *args: Var | Any) -> GenericType:
"""Override the type of the function call with the given arguments.

View File

@ -21,10 +21,7 @@ def cond_state(request):
def test_f_string_cond_interpolation():
# make sure backticks inside interpolation don't get escaped
var = LiteralVar.create(f"x {cond(True, 'a', 'b')}")
assert (
str(var)
== '("x "+(true ? "a" : "b"))'
)
assert str(var) == '("x "+(true ? "a" : "b"))'
@pytest.mark.parametrize(

View File

@ -148,7 +148,7 @@ def test_create_map_fn_var_subclass(cls, fn_body, fn_args, explicit_return, expe
(
"code",
{},
r"""(({node, inline, className, children, ...props}) => { const match = (className || '').match(/language-(?<lang>.*)/); const _language = match ? match[1] : ''; if (_language) { (async () => { try { const module = await import(`react-syntax-highlighter/dist/cjs/languages/prism/${_language}`); SyntaxHighlighter.registerLanguage(_language, module.default); } catch (error) { console.error(`Error importing language module for ${_language}:`, error); } })(); } ; return inline ? ( <RadixThemesCode {...props}>{children}</RadixThemesCode> ) : ( <SyntaxHighlighter children={((Array.isArray(children)) ? (((...args) => (((_array, _sep = "") => Array.prototype.join.apply(_array,[_sep]))(children, ...args)))("\n")) : children)} css={({ ["marginTop"] : "1em", ["marginBottom"] : "1em" })} customStyle={({ ["marginTop"] : "1em", ["marginBottom"] : "1em" })} language={_language} style={((resolvedColorMode === "light") ? oneLight : oneDark)} wrapLongLines={true} {...props}/> ); })"""
r"""(({node, inline, className, children, ...props}) => { const match = (className || '').match(/language-(?<lang>.*)/); const _language = match ? match[1] : ''; if (_language) { (async () => { try { const module = await import(`react-syntax-highlighter/dist/cjs/languages/prism/${_language}`); SyntaxHighlighter.registerLanguage(_language, module.default); } catch (error) { console.error(`Error importing language module for ${_language}:`, error); } })(); } ; return inline ? ( <RadixThemesCode {...props}>{children}</RadixThemesCode> ) : ( <SyntaxHighlighter children={((Array.isArray(children)) ? (((...args) => (((_array, _sep = "") => Array.prototype.join.apply(_array,[_sep]))(children, ...args)))("\n")) : children)} css={({ ["marginTop"] : "1em", ["marginBottom"] : "1em" })} customStyle={({ ["marginTop"] : "1em", ["marginBottom"] : "1em" })} language={_language} style={((resolvedColorMode === "light") ? oneLight : oneDark)} wrapLongLines={true} {...props}/> ); })""",
),
(
"code",
@ -157,7 +157,7 @@ def test_create_map_fn_var_subclass(cls, fn_body, fn_args, explicit_return, expe
value, **props
)
},
r"""(({node, inline, className, children, ...props}) => { const match = (className || '').match(/language-(?<lang>.*)/); const _language = match ? match[1] : ''; ; return inline ? ( <RadixThemesCode {...props}>{children}</RadixThemesCode> ) : ( <RadixThemesBox css={({ ["pre"] : ({ ["margin"] : "0", ["padding"] : "24px", ["background"] : "transparent", ["overflow-x"] : "auto", ["border-radius"] : "6px" }) })} {...props}><ShikiCode code={((Array.isArray(children)) ? (((...args) => (((_array, _sep = "") => Array.prototype.join.apply(_array,[_sep]))(children, ...args)))("\n")) : children)} decorations={[]} language={_language} theme={((resolvedColorMode === "light") ? "one-light" : "one-dark-pro")} transformers={[]}/></RadixThemesBox> ); })"""
r"""(({node, inline, className, children, ...props}) => { const match = (className || '').match(/language-(?<lang>.*)/); const _language = match ? match[1] : ''; ; return inline ? ( <RadixThemesCode {...props}>{children}</RadixThemesCode> ) : ( <RadixThemesBox css={({ ["pre"] : ({ ["margin"] : "0", ["padding"] : "24px", ["background"] : "transparent", ["overflow-x"] : "auto", ["border-radius"] : "6px" }) })} {...props}><ShikiCode code={((Array.isArray(children)) ? (((...args) => (((_array, _sep = "") => Array.prototype.join.apply(_array,[_sep]))(children, ...args)))("\n")) : children)} decorations={[]} language={_language} theme={((resolvedColorMode === "light") ? "one-light" : "one-dark-pro")} transformers={[]}/></RadixThemesBox> ); })""",
),
(
"h1",

View File

@ -1194,14 +1194,8 @@ def test_array_operations():
str(array_var.reverse())
== "(((...args) => (((_array) => _array.slice().reverse())([1, 2, 3, 4, 5], ...args)))())"
)
assert (
str(ArrayVar.range(10))
== "(((_e1, _e2 = null, _step = 1) => [...range(_e1, _e2, _step)])(10))"
)
assert (
str(ArrayVar.range(1, 10))
== "(((_e1, _e2 = null, _step = 1) => [...range(_e1, _e2, _step)])(1, 10))"
)
assert str(ArrayVar.range(10)) == "[...range(10, null, 1)]"
assert str(ArrayVar.range(1, 10)) == "[...range(1, 10, 1)]"
assert str(ArrayVar.range(1, 10, 2)) == "[...range(1, 10, 2)]"
assert str(ArrayVar.range(1, 10, -1)) == "[...range(1, 10, -1)]"