can i somehow override setters of `var`s in a data...
# announcements
n
can i somehow override setters of `var`s in a data class so i can sanity-check the data coming in ?
m
Have you tried using custom setters? Does it compile? If it does, then write a test around it, and see if it works.
This is the approach many of us have taken to answer our questions, and learn more about the inner workings of Kotlin.
n
so as far as i can tell its not possible to make it part of the data class constructor with custom setter and adding it to the body might work but will then not be int the autogenerated toString function
m
Not surprised.
data class
is fairly restricted, and seems to be intended for simple POJO's. It allows mutable properties, but is best suited to immutable. I suspect if you require a
var
, then you use a regular class. Alternatively, use an immutable data class, and a helper method that leverages
copy
and has the pre-checks. Obviously not as efficient as a regular setter, but if your app isn't super performance constrained, it's an alternative approach.
m
data classes aren't meant to contain any checking on the input since it's construction is done via the constructor. You can't really check an entire constructor other than generating errors. A data class should just hold data, and that's it. If you add a sanity check to a variable, you should also test it in it's constructor.
Copy code
fun main(){
    val test1 = Class(-1)
    println(test1)

    val test2 = Class(1)!!
    println(test2)

    test2.test = 3
    println(test2)

    test2.test = -1
    println(test2)
}

data class Class private constructor(
    private var _test: Int
){
    var test: Int
        set(value) {if(value >= 0) _test = value}
        get() = _test

    companion object{
        operator fun invoke(test: Int) = test.takeIf { it >= 0 }?.let { Class(it) }
    }
}
This is already kind of hacky:
Copy code
null
Class(_test=1)
Class(_test=3)
Class(_test=3)
n
now add sealed classes and inheritance to that and you have the mess i found myself in..
m
what is the required behaviour whenever your sanity check fails?
n
i would call error(), that is fine by me
m
what about just writing your own annotation class that handles the java generated setter?
n
i have no clue how, if you can show me any example..