orchestr7 / ktoml

Kotlin Multiplatform parser and compile-time serializer/deserializer for TOML format (Native, JS, JVM) based on KxS
https://akuleshov7.github.io/ktoml
MIT License
454 stars 24 forks source link

Support Arrays of Tables #88

Open NfNitLoop opened 2 years ago

NfNitLoop commented 2 years ago

I see this is already called out as a feature that's not yet implemented in the README:

❌ Array of Tables

I just wanted to make a ticket for it so folks can vote for it, and so I can get notified when it's implemented. (It's currently a blocker for my use case.)


My use case is this:

I want to support multiple configuration environments in one file. Like:

[[environments]]
name = "foo"
# …

[[environments]]
name = "bar"
# …

But that currently gives an error:

Not able to parse the key: [[environments]] as it contains invalid symbols. In case you would like to use special symbols - use quotes as it is required by TOML standard: "My key ~ with special % symbols"


Alternatively, I also tried a "Map of Tables" approach like this, but that didn't work either:

[environments.foo]
# …

[environments.bar]
# …

Error:

Invalid number of key-value arguments provided in the input for deserialization. Missing the required field <0> from class in the input

orchestr7 commented 2 years ago

@NfNitLoop Thank you for this issue, I will pin it. I actually planned to start from it right now :)

orchestr7 commented 2 years ago

A link for the SPEC: https://toml.io/en/v1.0.0#inline-table

What should we pay attention on: 1) nested array of tables (may be later) 2) If the parent of a table or array of tables is an array element, that element must already have been defined before the child can be defined (not sure if this is really needed):

# INVALID TOML DOC
[fruit.physical]  # subtable, but to which parent element should it belong?
color = "red"
shape = "round"

[[fruit]]  # parser must throw an error upon discovering that "fruit" is
           # an array rather than a table
name = "apple"

3) Attempting to append to a statically defined array, even if that array is empty, must produce an error at parse time:

# INVALID TOML DOC
fruits = []

[[fruits]] # Not allowed

4) Attempting to define a normal table with the same name as an already established array must produce an error at parse time. Attempting to redefine a normal table as an array must likewise produce a parse-time error.

orchestr7 commented 2 years ago

Difficult part here is to understand how to represent such structure in a tree.

I suppose that we need to do the following: 1) If the trimmed string starts with ''Parse [[ ]] and put it to some ArrayTableNode that will contain children TableNode 2) each time we will append a TableNode to such array

orchestr7 commented 2 years ago

Finally added the support for parsing of arrays of tables: https://github.com/akuleshov7/ktoml/pull/104 Next step is to make the decoding

bishiboosh commented 2 years ago

@akuleshov7 so what's still missing for array of tables to work ?

orchestr7 commented 2 years ago

@akuleshov7 so what's still missing for array of tables to work ?

decoding process. I have added parsing, added tree structures, only decoding is missing now

Wavesonics commented 1 year ago

@akuleshov7 any progress on decoding these? Just ran into this in my project

sschuberth commented 1 year ago

I'm interested in parsing cargo.lock files, see e.g. this. Am I correct to assume that this issue would need to get resolved for that first?

orchestr7 commented 1 year ago

I'm interested in parsing cargo.lock files, see e.g. this. Am I correct to assume that this issue would need to get resolved for that first?

Oh, I missed that question, sorry. Yes, this is a blocker and we will take it as the highest priority. As I didn't know that Cargo has arrays of tables. Will take it into 0.6.0 release, as previously we thought that multiline arrays/strings and streaming had more priority and were focused on that.

This one is a very long story and I hope to finish it in the nearest months.

sschuberth commented 1 year ago

Will take it into 0.6.0 release

Thanks for prioritizing this!

kubeliv commented 1 year ago

I am also patiently waiting for this feature! 🙂

severinsch commented 1 year ago

This is also a blocker for my use case, can you provide a rough timeline on when we can expect the new release? :pray:

orchestr7 commented 1 year ago

This is also a blocker for my use case, can you provide a rough timeline on when we can expect the new release? 🙏

ktoml is community project, driven only by several people, so probably there are some time difficulties in supporting it. But you can also contribute and collaborate if it is a hard stopper for you, we will appreciate it 🙏

My personal estimation was to make it last month, but still did not get a chance for it. I will be on vacation next week, so probably I will give it a try…

orchestr7 commented 9 months ago

related issues: https://github.com/akuleshov7/ktoml/issues/259 https://github.com/akuleshov7/ktoml/issues/254 https://github.com/akuleshov7/ktoml/issues/231

mgroth0 commented 7 months ago

For anyone who needs this, I think a temporary workaround is to use TomlJ to convert the toml to json and then decode as json. Theoretically this should be very simple to swap for ktoml once it is ready.