From 12e378a86365a43b94a97467bfb605ef01916ba8 Mon Sep 17 00:00:00 2001 From: Fredrik Bagge Carlson Date: Thu, 5 Sep 2024 08:33:04 +0200 Subject: [PATCH 1/4] Respect positional arguments in `@mtkmodel` Fixes #3018 --- src/systems/model_parsing.jl | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/src/systems/model_parsing.jl b/src/systems/model_parsing.jl index f7466235f5..d346aff703 100644 --- a/src/systems/model_parsing.jl +++ b/src/systems/model_parsing.jl @@ -952,8 +952,23 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing) for i in start:lastindex(b.args) arg = b.args[i] arg isa LineNumberNode && continue + @show arg MLStyle.@match arg begin - x::Symbol || Expr(:kw, x) => begin + x::Symbol => begin + varname, _varname = _rename(a, x) + b.args[i] = :($_varname) + push!(varexpr.args, :((if $varname !== nothing + $_varname = $varname + elseif @isdefined $x + # Allow users to define a var in `structural_parameters` and set + # that as positional arg of subcomponents; it is useful for cases + # where it needs to be passed to multiple subcomponents. + $_varname = $x + end))) + push!(kwargs, Expr(:kw, varname, nothing)) + # dict[:kwargs][varname] = nothing + end + Expr(:kw, x) => begin varname, _varname = _rename(a, x) b.args[i] = Expr(:kw, x, _varname) push!(varexpr.args, :((if $varname !== nothing From 7c21c63093e4855f10f071fd1ec15296bd05661f Mon Sep 17 00:00:00 2001 From: Fredrik Bagge Carlson Date: Thu, 5 Sep 2024 08:35:24 +0200 Subject: [PATCH 2/4] Update model_parsing.jl --- src/systems/model_parsing.jl | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/systems/model_parsing.jl b/src/systems/model_parsing.jl index d346aff703..ea56e92bb6 100644 --- a/src/systems/model_parsing.jl +++ b/src/systems/model_parsing.jl @@ -952,9 +952,8 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing) for i in start:lastindex(b.args) arg = b.args[i] arg isa LineNumberNode && continue - @show arg MLStyle.@match arg begin - x::Symbol => begin + x::Symbol => begin # handle positional args varname, _varname = _rename(a, x) b.args[i] = :($_varname) push!(varexpr.args, :((if $varname !== nothing @@ -968,7 +967,7 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing) push!(kwargs, Expr(:kw, varname, nothing)) # dict[:kwargs][varname] = nothing end - Expr(:kw, x) => begin + Expr(:kw, x) => begin # handle keyword args varname, _varname = _rename(a, x) b.args[i] = Expr(:kw, x, _varname) push!(varexpr.args, :((if $varname !== nothing From f9875564f9c38ecdcc0430030e07da1f346a791e Mon Sep 17 00:00:00 2001 From: Fredrik Bagge Carlson Date: Thu, 5 Sep 2024 08:52:00 +0200 Subject: [PATCH 3/4] Update model_parsing.jl --- src/systems/model_parsing.jl | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/src/systems/model_parsing.jl b/src/systems/model_parsing.jl index ea56e92bb6..4dd1ab34ee 100644 --- a/src/systems/model_parsing.jl +++ b/src/systems/model_parsing.jl @@ -945,17 +945,19 @@ end ### Parsing Components: -function component_args!(a, b, varexpr, kwargs; index_name = nothing) +function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = false ) + # keywords indicates if whether or not the keyword arg delimiter ; has been seen # Whenever `b` is a function call, skip the first arg aka the function name. # Whenever it is a kwargs list, include it. start = b.head == :call ? 2 : 1 + for i in start:lastindex(b.args) arg = b.args[i] arg isa LineNumberNode && continue MLStyle.@match arg begin - x::Symbol => begin # handle positional args + Expr(:kw, x) || (x::Symbol && if keywords end) => begin # handle keyword args varname, _varname = _rename(a, x) - b.args[i] = :($_varname) + b.args[i] = Expr(:kw, x, _varname) push!(varexpr.args, :((if $varname !== nothing $_varname = $varname elseif @isdefined $x @@ -967,9 +969,9 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing) push!(kwargs, Expr(:kw, varname, nothing)) # dict[:kwargs][varname] = nothing end - Expr(:kw, x) => begin # handle keyword args + x::Symbol && if !keywords end => begin # handle positional args varname, _varname = _rename(a, x) - b.args[i] = Expr(:kw, x, _varname) + b.args[i] = :($_varname) push!(varexpr.args, :((if $varname !== nothing $_varname = $varname elseif @isdefined $x @@ -982,7 +984,8 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing) # dict[:kwargs][varname] = nothing end Expr(:parameters, x...) => begin - component_args!(a, arg, varexpr, kwargs) + + component_args!(a, arg, varexpr, kwargs; keywords = true) end Expr(:kw, x, y) => begin varname, _varname = _rename(a, x) From f6de2c07f2fd06d92854fec36f9ba705d43472d6 Mon Sep 17 00:00:00 2001 From: Fredrik Bagge Carlson Date: Thu, 5 Sep 2024 09:13:21 +0200 Subject: [PATCH 4/4] Apply suggestions from code review Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> --- src/systems/model_parsing.jl | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/src/systems/model_parsing.jl b/src/systems/model_parsing.jl index 4dd1ab34ee..e282f9def7 100644 --- a/src/systems/model_parsing.jl +++ b/src/systems/model_parsing.jl @@ -945,7 +945,7 @@ end ### Parsing Components: -function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = false ) +function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = false) # keywords indicates if whether or not the keyword arg delimiter ; has been seen # Whenever `b` is a function call, skip the first arg aka the function name. # Whenever it is a kwargs list, include it. @@ -955,7 +955,8 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = arg = b.args[i] arg isa LineNumberNode && continue MLStyle.@match arg begin - Expr(:kw, x) || (x::Symbol && if keywords end) => begin # handle keyword args + Expr(:kw, x) || (x::Symbol && if keywords + end) => begin # handle keyword args varname, _varname = _rename(a, x) b.args[i] = Expr(:kw, x, _varname) push!(varexpr.args, :((if $varname !== nothing @@ -969,7 +970,8 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = push!(kwargs, Expr(:kw, varname, nothing)) # dict[:kwargs][varname] = nothing end - x::Symbol && if !keywords end => begin # handle positional args + x::Symbol && if !keywords + end => begin # handle positional args varname, _varname = _rename(a, x) b.args[i] = :($_varname) push!(varexpr.args, :((if $varname !== nothing @@ -984,7 +986,6 @@ function component_args!(a, b, varexpr, kwargs; index_name = nothing, keywords = # dict[:kwargs][varname] = nothing end Expr(:parameters, x...) => begin - component_args!(a, arg, varexpr, kwargs; keywords = true) end Expr(:kw, x, y) => begin