BenWoodworth / knbt

Kotlin NBT library for kotlinx.serialization
GNU Lesser General Public License v3.0
79 stars 3 forks source link

[FEATURE] A JsonPath-like DSL for reading specific properties from an NBT source #6

Closed RaphaelTarita closed 3 years ago

RaphaelTarita commented 3 years ago

It'd be cool to have a DSL that allows you to access specifc properties of an arbitrary NBT source without needing a model class. Similar to how KotlinNBT does it or how I plan to do it in my version.

The DSL definitions for KotlinNBT can be found here. An example of this DSL would be:

val fibonacci: IntArray = nbt["testCompound"].asTagCompound["fibonacciWithoutZero"].asIntArray
val message: String = nbt["testList"].asTagList[0].asTagCompound["firstString"].asString
val timestamp: Long = nbt["timestamp"].asLong

The DSL definitions for KXSmine can be found here. An example of this DSL would be:

val fibonacci = root.compound("testCompound").intarray("fibonacciWithoutZero").data
val message = root.list("testList").compoundAt(0).string("firstString").data
val timestamp = root.long("timestamp").data

The main benefit from such a DSL would be the ability to type-safely access just specific properties without having to write a whole model class for the NBT source you're parsing.

BenWoodworth commented 3 years ago

Good idea! I'm closely following kotlinx.serialization's conventions, so copying the approach used with JSON should work.

So based on that, what do you think about adding a bunch of .nbt* properties that cast to the specific tag type?

And for primitives do you think there should also/instead be .byte, .int, .string, etc. properties to return the value directly? I'm not sure there's a good use case for tag.nbtByte if we already have tag.byte.

BenWoodworth commented 3 years ago

If you want to make a PR (to the 0.6 branch), adding these extension properties to NbtTag.kt would be a good start. Otherwise I'll get to this when I have the time

Primitives (returns Byte, etc.): byte, short, int, long, float, double, string Tags (returns Nbt*): nbtByteArray, nbtIntArray, nbtLongArray, nbtList, nbtCompound

RaphaelTarita commented 3 years ago

Sounds good! I'll get to that when I have time, so I guess whoever's faster gets to do it 😅

BenWoodworth commented 3 years ago

Added it in this commit :)

I decided to make all the properties .nbt* for NbtTag types, instead of having .byte, etc. properties for Kotlin types