I have a Java class that holds generic information on databse entities (i.e. their id).
@Data
public class DbEntity {
protected final String id;
public DbEntity(String id) {
this.id = id;
}
}
We use Lombok @Data
to generate getters, toString
, equals
...
In Java I would simply extend this class and add @Data
once again.
@Data
class JavaSubClass extends DbEntity {
public JavaSubClass(String id) {
super(id);
}
}
In a newer service we use Kotlin but would like to reuse standard classes such as DbEntity
.
My first approach was to simply declare a data class such as
data class SubClass1(val id: String, val name: String) : DbEntity(id)
Accidental override: The following declarations have the same JVM signature (getId()Ljava/lang/String;):
fun <get-id>(): String defined in com.demo.SubClass1
fun getId(): String! defined in com.demo.SubClass1
After some reading I found several solutions, all of which I'm not super happy with.
- Don't use data classes. This works but leaves me with the task of implementing
equals
etc.
class SubClass4(id: String, val name: String) : DbEntity(id)
- Duplicate the field. This works but we end up with two fields that could go out of sync.
data class SubClass3(val subId: String, val name: String) : DbEntity(subId)
- Assign a different name to the getter. This fundamentally also duplicates the field, but hides the getter.
data class SubClass2(@get:JvmName("getId_") val id: String, val name: String) : DbEntity(id)
As I said, I'm not happy with any of the solution presented above. Having an abstract super class or an interface instead would certainly be more appropriate. However the Entity class resides in a library that primarily Java projects depend on. I'm hesitant to change it just because of a new Kotlin dependnecy.
Did anyone encounter similar issues and has advice on how to solve them?