Backward compatibility problem with UAST

Answered

Encapsulation does not work in inline function, so such code is dangerous:

inline fun <reified T : UElement> PsiElement?.toUElementOfType(): T? =
this?.let { UastFacade.convertElementWithParent(this, T::class.java) as T? } 

This code is from 192, and in 191 it was

inline fun <reified T : UElement> PsiElement?.toUElementOfType(): T? =
this?.let { ServiceManager.getService(project, UastContext::class.java).convertElementWithParent(this, T::class.java) as T? }

So if I use the function, and compile the plugin with 192 api and run it with IDEA 2019.1, I get the ClassDefNotFound exception, as it does not have UastFacade.

You could write the function in such way:

inline fun <reified T : UElement> PsiElement?.toUElementOfType(): T? = toUElement(T::class.java)

and it would be safe, as `toUElement` encapsulates the behavior.

1 comment
Comment actions Permalink
Official comment

Good catch! thank you for notice! It is a known issue that Kotlin inline functions could bring binary incompatibility into usage site. I've updated the code but it seems that currently there is no way to update all released IDEA-s, sorry for that.

PS. Maybe it has more sense to write such requests to Youtrack.

 

Please sign in to leave a comment.