Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

TOML: fix converted tabular data printing #41009

Merged
merged 1 commit into from
May 30, 2021
Merged

TOML: fix converted tabular data printing #41009

merged 1 commit into from
May 30, 2021

Conversation

aviatesk
Copy link
Member

@aviatesk aviatesk commented May 30, 2021

Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
Dict or Arrays. Rather it leads to runtime error because we don't
pass over the same by keyword argument through recursive calls and it
may not be assigned:

julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
foo = ERROR: UndefKeywordError: keyword argument by not assigned
Stacktrace:
 [1] printvalue(f::var"#3#4", io::Base.TTY, value::Dict{Symbol, Int64}; sorted::Bool)
   @ TOML.Internals.Printer ~/julia/julia2/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:46
 [2] #invokelatest#2
   @ ./essentials.jl:728 [inlined]
 [3] #printvalue#2
   @ ~/julia/julia2/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:44 [inlined]
 [4] _print(f::var"#3#4", io::Base.TTY, a::Dict{Symbol, MyStruct}, ks::Vector{String}; indent::Int64, first_block::Bool, sorted::Bool, by::Function)
   @ TOML.Internals.Printer ~/julia/julia2/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88
 [5] #print#14
   @ ~/julia/julia2/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:129 [inlined]
 [6] print(f::var"#3#4", a::Dict{Symbol, MyStruct}; sorted::Bool, by::Function)
   @ TOML.Internals.Printer ~/julia/julia2/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:130
 [7] top-level scope
   @ REPL[4]:1
Originally reported by the following JET analysis:
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo

With this PR, everything should work:

After

julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1

Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
`Dict` or `Array`s. Rather it leads to runtime error because we don't
pass over the same `by` keyword  argument through recursive calls and it
may not be assigned:
```julia
julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
ERROR: MethodError: no method matching print(::var"#38#39", ::Dict{Symbol, MyStruct}; softed=true)
You may have intended to import Base.print
Closest candidates are:
  print(::Union{Nothing, Function}, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:130 got unsupported keyword argument "softed"
  print(::Union{Nothing, Function}, ::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:129 got unsupported keyword argument "softed"
  print(::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:131 got unsupported keyword argument "softed"
Stacktrace:
 [1] kwerr(::NamedTuple{(:softed,), Tuple{Bool}}, ::Function, ::Function, ::Dict{Symbol, MyStruct})
   @ Base ./error.jl:163
 [2] top-level scope
   @ none:1
```

<details><summary>Originally reported by JET:</summary>
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo
</details>

With this PR, everything should work:
> After
```julia
julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1
```
@aviatesk aviatesk requested a review from KristofferC May 30, 2021 08:07
@aviatesk aviatesk merged commit 311ff56 into master May 30, 2021
@aviatesk aviatesk deleted the avi/toml branch May 30, 2021 10:40
shirodkara pushed a commit to shirodkara/julia that referenced this pull request Jun 9, 2021
Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
`Dict` or `Array`s. Rather it leads to runtime error because we don't
pass over the same `by` keyword  argument through recursive calls and it
may not be assigned:
```julia
julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
ERROR: MethodError: no method matching print(::var"JuliaLang#38#39", ::Dict{Symbol, MyStruct}; softed=true)
You may have intended to import Base.print
Closest candidates are:
  print(::Union{Nothing, Function}, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:130 got unsupported keyword argument "softed"
  print(::Union{Nothing, Function}, ::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:129 got unsupported keyword argument "softed"
  print(::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:131 got unsupported keyword argument "softed"
Stacktrace:
 [1] kwerr(::NamedTuple{(:softed,), Tuple{Bool}}, ::Function, ::Function, ::Dict{Symbol, MyStruct})
   @ Base ./error.jl:163
 [2] top-level scope
   @ none:1
```

<details><summary>Originally reported by JET:</summary>
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(JuliaLang#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo
</details>

With this PR, everything should work:
> After
```julia
julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1
```
@KristofferC KristofferC added the backport 1.6 Change should be backported to release-1.6 label Jun 10, 2021
KristofferC pushed a commit that referenced this pull request Jun 10, 2021
Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
`Dict` or `Array`s. Rather it leads to runtime error because we don't
pass over the same `by` keyword  argument through recursive calls and it
may not be assigned:
```julia
julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
ERROR: MethodError: no method matching print(::var"#38#39", ::Dict{Symbol, MyStruct}; softed=true)
You may have intended to import Base.print
Closest candidates are:
  print(::Union{Nothing, Function}, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:130 got unsupported keyword argument "softed"
  print(::Union{Nothing, Function}, ::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:129 got unsupported keyword argument "softed"
  print(::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:131 got unsupported keyword argument "softed"
Stacktrace:
 [1] kwerr(::NamedTuple{(:softed,), Tuple{Bool}}, ::Function, ::Function, ::Dict{Symbol, MyStruct})
   @ Base ./error.jl:163
 [2] top-level scope
   @ none:1
```

<details><summary>Originally reported by JET:</summary>
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo
</details>

With this PR, everything should work:
> After
```julia
julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1
```

(cherry picked from commit 311ff56)
johanmon pushed a commit to johanmon/julia that referenced this pull request Jul 5, 2021
Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
`Dict` or `Array`s. Rather it leads to runtime error because we don't
pass over the same `by` keyword  argument through recursive calls and it
may not be assigned:
```julia
julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
ERROR: MethodError: no method matching print(::var"JuliaLang#38#39", ::Dict{Symbol, MyStruct}; softed=true)
You may have intended to import Base.print
Closest candidates are:
  print(::Union{Nothing, Function}, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:130 got unsupported keyword argument "softed"
  print(::Union{Nothing, Function}, ::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:129 got unsupported keyword argument "softed"
  print(::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:131 got unsupported keyword argument "softed"
Stacktrace:
 [1] kwerr(::NamedTuple{(:softed,), Tuple{Bool}}, ::Function, ::Function, ::Dict{Symbol, MyStruct})
   @ Base ./error.jl:163
 [2] top-level scope
   @ none:1
```

<details><summary>Originally reported by JET:</summary>
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(JuliaLang#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo
</details>

With this PR, everything should work:
> After
```julia
julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1
```
@KristofferC KristofferC mentioned this pull request Jul 12, 2021
75 tasks
@KristofferC KristofferC removed the backport 1.6 Change should be backported to release-1.6 label Jul 12, 2021
staticfloat pushed a commit that referenced this pull request Dec 23, 2022
Previously the printing pass for converted data only works for
non-tabular data (like simple number literals), and it doesn't work for
`Dict` or `Array`s. Rather it leads to runtime error because we don't
pass over the same `by` keyword  argument through recursive calls and it
may not be assigned:
```julia
julia> struct MyStruct
           a::Int
       end

julia> data = Dict(:foo => MyStruct(1))
Dict{Symbol, MyStruct} with 1 entry:
  :foo => MyStruct(1)

julia> TOML.print(data; softed=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
ERROR: MethodError: no method matching print(::var"#38#39", ::Dict{Symbol, MyStruct}; softed=true)
You may have intended to import Base.print
Closest candidates are:
  print(::Union{Nothing, Function}, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:130 got unsupported keyword argument "softed"
  print(::Union{Nothing, Function}, ::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:129 got unsupported keyword argument "softed"
  print(::IO, ::AbstractDict; sorted, by) at /Users/aviatesk/julia/julia/stdlib/TOML/src/print.jl:131 got unsupported keyword argument "softed"
Stacktrace:
 [1] kwerr(::NamedTuple{(:softed,), Tuple{Bool}}, ::Function, ::Function, ::Dict{Symbol, MyStruct})
   @ Base ./error.jl:163
 [2] top-level scope
   @ none:1
```

<details><summary>Originally reported by JET:</summary>
julia> using JET, Pkg

julia> @report_call Pkg.project()
═════ 3 possible errors found ═════
┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/API.jl:103 Pkg.API.EnvCache()
│┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:285 #self#(Pkg.Types.nothing)
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:288 Pkg.Types.read_project(project_file)
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:138 Pkg.Types.sprint(Pkg.Types.showerror, e)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ toml_parser.jl:326 Base.TOML.point_to_line(Base.getproperty(err, :str), pos, pos, io)
│││││││ for 1 of union split cases, no matching method found for call signatures (Tuple{typeof(Base.TOML.point_to_line), Nothing, Int64, Int64, IOBuffer})): Base.TOML.point_to_line(Base.getproperty(err::Base.TOML.ParserError, :str::Symbol)::Union{Nothing, String}, pos::Int64, pos::Int64, io::IOBuffer)
││││││└──────────────────────
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:142 Pkg.Types.Project(raw)
││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/project.jl:124 Base.setproperty!(project, :targets, Pkg.Types.read_project_targets(Pkg.Types.get(raw, "targets", Pkg.Types.nothing), project))
│││││┌ @ Base.jl:35 Base.convert(Base.fieldtype(Base.typeof(x), f), v)
││││││┌ @ abstractdict.jl:523 _(x)
│││││││┌ @ dict.jl:104 Base.setindex!(h, v, k)
││││││││┌ @ dict.jl:382 Base.convert(_, v0)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/LinearAlgebra/src/factorization.jl:58 _(f)
││││││││││ no matching method found for call signature (Tuple{Type{Vector{String}}, LinearAlgebra.Factorization}): _::Type{Vector{String}}(f::LinearAlgebra.Factorization)
│││││││││└─────────────────────────────────────────────────────────────────────────────────────────────────
││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:305 Pkg.Types.write_env_usage(manifest_file, "manifest_usage.toml")
│││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:436 Pkg.Types.sprint(#35)
││││┌ @ strings/io.jl:106 Base.#sprint#412(Core.tuple(Base.nothing, 0, #self#, f), args...)
│││││┌ @ strings/io.jl:112 f(Core.tuple(s), args...)
││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/Pkg/src/Types.jl:437 TOML.print(io, Pkg.Types.Dict(Pkg.Types.=>(Core.getfield(#self#, :source_file), Base.vect(Pkg.Types.Dict(Pkg.Types.=>("time", Pkg.Types.now()))))))
│││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 TOML.Internals.Printer.#print#16(false, TOML.Internals.Printer.identity, #self#, io, a)
││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:131 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted, :by))(Core.tuple(sorted, by)), TOML.Internals.Printer._print, TOML.Internals.Printer.nothing, io, a)
│││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 TOML.Internals.Printer.#_print#11(indent, first_block, sorted, by, _3, f, io, a, ks)
│││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:88 Core.kwfunc(TOML.Internals.Printer.printvalue)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer.printvalue, f, io, value)
││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:25 TOML.Internals.Printer.#printvalue#1(sorted, _3, f, io, value)
│││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:29 Core.kwfunc(TOML.Internals.Printer._print)(Core.apply_type(Core.NamedTuple, (:sorted,))(Core.tuple(sorted)), TOML.Internals.Printer._print, f, io, x)
││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 #s848(_2, _3, f, io, a, Base.getindex(TOML.Internals.Printer.String))
│││││││││││││││┌ @ /Users/aviatesk/julia/julia/usr/share/julia/stdlib/v1.7/TOML/src/print.jl:76 Core.throw(Core.UndefKeywordError(:by))
││││││││││││││││ UndefKeywordError: keyword argument by not assigned
│││││││││││││││└────────────────────────────────────────────────────────────────────────────────
Pkg.API.ProjectInfo
</details>

With this PR, everything should work:
> After
```julia
julia> TOML.print(data; sorted=true) do x
           x isa MyStruct && return Dict(:bar => x.a)
       end
[foo]
bar = 1
```

(cherry picked from commit 311ff56)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants