https://kotlinlang.org logo
Title
f

Federico Tomassetti

05/26/2023, 12:49 PM
My goal would be to build a plugin to make certain classes observable while making them simpler to define. so I would transform a class like this:
data class A(p1: Int) : Node()
into
class A(p1: Int) : ObservableNode() {

  init {
      println("initializing p1 at $p1") // instead of print we will notify observers
  }
  var p1 : Int = p1
    get() {
      print("reading p1") // instead of print we will notify observers
      return field
    }
    set(value: Int) {
      println("setting p1 to $value (currently at $field)") // instead of print we will notify observers
      field = value
    }

  override fun equals(other: Any?): Boolean {
    if (this === other) return true
    if (other !is A) return false

    return p1 == other.p1
  }

  override fun hashCode(): Int {
    return p1
  }
}
I can find the ClassDeclaration and check if it extends Node, but it is unclear to me how to modify it. I tried removing the irClass in the declarations of IrFile and replace it with a copy but that cause errors
j

Javier

05/26/2023, 2:00 PM
would p1 be available to the consumer so they can reference it? if so, maybe it should be done with the frontend?
f

Federico Tomassetti

05/26/2023, 2:02 PM
p1 should be available both in the original code and in the modified code, so that code using the A class would not really need to change. However I would like to change its definition by adding the getter and setter (where I would sneak in methods to notify observers)
To do that in the frontend, should I use a different extension?
j

Javier

05/26/2023, 2:04 PM
For frontend yes
if you modify it on backend you couldn't see that green on the IDE I think, as
val number: Int = a.p1
, that
p1
wouldn't exist for the IDE as it will exist later.
f

Federico Tomassetti

05/26/2023, 2:07 PM
sorry, I realize I was missing a
val
in the original data class which would be:
data class A(val p1: Int) : Node()
So I think the
val p1
would be present also in the original code (even if with a different definition)
t

Tóth István Zoltán

05/27/2023, 3:10 AM
To do that transformation you would want to replace the initializer of the variable. That is an IrExpression which you could transform into another IrExpression that contains the prints. You can use an
IrElementTransformerVoidWithContext
for that and the
visitAnonymousInitializerNew
and
visitPropertyNew
functions in particular. I added an example below that is a transformer. It shows how a transformation is done and actually contains calls to printf in a form of trace functions. It is in-development and is a somewhat broken at the moment but you can see examples there. https://github.com/spxbhuhb/rui/blob/7468ca0db6d345298247e80367883f53f0158e8a/rui-[…]/simplexion/rui/kotlin/plugin/ir/air2ir/StateAccessTransform.kt
f

ftomassetti

05/27/2023, 10:18 AM
REMOVED BECAUSE OF COMMENT BY @Oliver.O
o

Oliver.O

05/27/2023, 11:24 AM
Could you please avoid copying messages to the channel and keep channel posts short? Especially long code excerpts and stack traces make it hard for readers on mobile devices to skip postings there.
f

ftomassetti

05/27/2023, 11:27 AM
Ok, I removed it. Thank you for providing feedback. Is there another place where one should ask for help regarding the compiler plugin?
j

Javier

05/27/2023, 11:28 AM
you can comment here, he was referring to avoid long code outside the thread
f

ftomassetti

05/27/2023, 11:29 AM
ok, so I can post code or stack traces but only within a thread, correct?
o

Oliver.O

05/27/2023, 11:30 AM
Just do short posts in the channel for new topics, then answer in the respective thread. Just do not tick the box „also send to channel „.
f

ftomassetti

05/27/2023, 11:30 AM
Understood, I will do that in the future. Thank you