Add interface(trait?) without modifying a class


#1

it often happens that someone need to add a function on a type.

Kotlin extension are the way to go to solve this problem in general.

But sometimes, you want to add same functionality on different type you don’t have control onto, then pass them in another function that use thos functionality, ex:

// class I cannot modify
class ComingFromADependency1
class ComingFromADependency2

//my code
class MyType
trait MyTypeAble{
   fun toMyType: MyType
}

impl MyTypeAble for ComingFromADependency1{
  fun toMyType = ...
}

impl MyTypeAble for ComingFromADependency2{
  fun toMyType = ...
}

fun target(x: myTypeAble) {
//  ...
  x.toMyType()
//...
}

This is a feature I love in rust. this is were I pick the word “trait”. Rust has a security forcing you to implement trait either in class package or in interface package (this avoid weird thing as you probably can imagine…).

now the problem is… java interroperability : I don’t see a resonable way to expose trait & use them in java… But maybe it is still possible. Maybe a solution would be not to allow to expose traits (trait would not be public then, confined in module).

But still because kotlin tends to be multiplatform, maybe it would be great to look beyond java interrop… But this is another topic.

what do you guys think about it ?


#2

Use a function type instead of a trait as the parameter to target:

fun target(x: () -> MyType) {
// ...
     x()
// ...
}

#3

Ok adding the function call…
target(aComingFromADependency1)
Or
target(aComingFromADependency2)


#4

Pass the body of the following function:

impl MyTypeAble for ComingFromADependency1{
  fun toMyType = ...
}

As a lambda:

// The dots here are what originally is supposed to be at the dots above.
target { … }

#5

I believe this KEEP issue is what you’re looking for: https://github.com/Kotlin/KEEP/pull/87


#6

I also believe this is the KEEP OP is looking for, was going to share it until I saw someone else already did!


#7

Thx, that is close to what I’m trying to do.