Accessing information about the running environmen...
# compiler
n
Accessing information about the running environment from inside Kotlin compiler plugin I have a Kotlin compiler plugin and to make it as easy as possible for users to submit issues with relevant information, I would like to print out the environment information together with the error. So, I would like to programmatically (from inside a running compiler plugin) find out about the currently running environment: What is the version of the currently running plugin? I think I can find out the answer via
Class.getPackage().implementationVersion
, using some class of the compiler plugin. What is the version of a third-party library on the compilation classpath that my plugin depends on? The library might not be present. I cannot use the previous approach as classes for the 3rd party library are not loaded to the classpath of my plugin. Is there something in the compiler API that I can use to read resources on the compilation classpath? What is the version of Kotlin (compiler) that is currently running? This might have the same answer as the first question (as the API is loaded on the classpath), using some class of the compiler API?
d
There is no such information in the compiler, but most likely it is at the Gradle level
n
Well,
MANIFEST.MF
file inside the JAR file contains entry
Implementation-Version
(returned by the
Class.getPackage().implementationVersion
as I mentioned above). This method works for JAR files that have been loaded by Java class loader (plugin JAR and probably also kotlin-stdlib JAR). However, the 3rd party library is on the compilation classpath not on the compiler plugin classpath — thus my question: is there a way to access the compilation classpath? To load a resource from it? I can load classes with
IrPluginContext.referenceClass()
method but can I also load resources? Most likely there is a way, I just do not know it.
d
The compilation classpath is listed inside the
compilerConfiguration.contentRoots
(at least for JVM). You can access
CompilerConfiguration
instance from the current compilation inside the
CompilerPluginRegistrar.registerExtensions
n
So, if I would like to know the version of a library, I would have to: 1. iterate over all content roots 2. for each JAR file in that list, open the JAR in-memory (it is a ZIP file) and: a. check if the JAR contains a well-known class from the 3rd party library b. if it does, get the MANIFEST.MF file from that JAR and read the
Implementation-Version
. I was hoping for something simpler (as Kotlin compiler already has access to all those JAR files) but I see no reason why it would not work. UPDATE: I now checked the library in question (kotlin-logging) and it does not seem to contain
Implementation-Version
in the MANIFEST.MF file. So, the new logic is actually a bit simpler: 1. iterate over all content roots 2. for each JAR file in that list, check if the file name has a well-known prefix. If it does, get the version from the file name. It seems a bit fragile (relying on file name patterns which depend heavily on the internals of the build system) but it might work just fine in practice.
d
I was hoping for something simpler (as Kotlin compiler already has access to all those JAR files)
The compiler processes them exactly from
configuration.contentRoots
It seems a bit fragile (relying on file name patterns which depend heavily on the internals of the build system)
That's why I suggested to do it on the build system level. It has a concept of the version out of box
n
How can I get access to the same content roots on Kotlin 2.1.10 and 2.0.21?
CLIConfigurationKeys.kt
is lacking that extension function.
d
compilerConfiguration.getList(CLIConfigurationKeys.CONTENT_ROOTS)
👍 1