-
Notifications
You must be signed in to change notification settings - Fork 72
#15 better support for compiler plugins #27
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
#15 better support for compiler plugins #27
Conversation
|
Looks nice. Arrow-meta was announced to the public at lambda world conf this Friday, so it's good if we have more ergonomic support for compiler plugins soon when more people will write their own. Is this ready to be merged or more like a WIP? I will do a closer review tomorrow. The stupid CI failed again but I think it's unrelated to these changes. |
|
Hi, i heard about arrow-meta and i'm excited to try it out :) This is ready to be merged, i wanted to add this feature, before i will add the support of the JSCompiler |
| var pluginClasspaths: List<File> = emptyList() | ||
|
|
||
| /** | ||
| * Compiler plugins that should be added the compilation |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
typo
| if(annotationProcessors.isEmpty()) { | ||
| log("No services were given. Not running kapt steps.") | ||
| return ExitCode.OK | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why was this removed?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I removed this because it was not possible to execute the compiler plugins without also adding an annotation processor.
The problem was that the pluginClasspaths were set after this check.
I restored this and made changes. Inside stubsAndApt, only the annotation processors are added to threadLocalParameters. Then inside compileKotlin, only the compiler plugins are set, so the processors aren't getting executed twice.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't this change the behaviour so that additional compiler plugins are only registered in the compileKotlin step? The current behaviour of #23. Is that additional plugins are executed in both steps. I don't know which way is actually right though,
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe you are right, we could also do it this way:
if(annotationProcessors.isEmpty() && compilerPlugins.isEmpty()) {
log("No services were given. Not running kapt steps.")
return ExitCode.OK
}I remove the changes in stubsAndApt and compileKotlin and just add the additional check for the compilerPlugins. Then the behaviour stays the same and it's possible to add compilerPlugins without also adding annotation processors.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it would be best to always add compiler plugins in the stubsAndApt step but cancel it if there are no annotation processors, like we did previously.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure if i understand it correctly, in stubsAndApt we'll add the compiler plugins and cancel if there is no annotation processor. And then in compileKotlin we'll add the plugins again?
Otherwise i can't see how it's possible to add a compiler plugin without also having to add a annotation processor.
src/test/kotlin/com/tschuchort/compiletesting/CompilerPluginsTest.kt
Outdated
Show resolved
Hide resolved
|
|
||
| override fun registerProjectComponents(project: MockProject, configuration: CompilerConfiguration) { | ||
| val parameters = threadLocalParameters.get() | ||
| KaptComponentRegistrar(parameters.processors,parameters.kaptOptions).registerProjectComponents(project,configuration) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I read a few days ago in the Kotlin slack that the order of registering compiler plugins matters. Right now we are registering Kapt first. Could there be a problem here? For example if a compiler plugin like arrow-meta introduces some new syntax/type checking that isn't legal in vanilla Kotlin the respective plugin would have to be run before Kapt or Kapt wouldn't know how to deal with that. Any thoughts on this @raulraja?
|
Unless I'm missing this is fine because meta does not rely on java stubs,
it's interleaved with the compiler. But you may want to offer kapt
registration as opt in and let them specify which plugin they want to run
supporting a predefined set of known plugins like kapt, serialization, meta
etc.
…On Sat, Oct 26, 2019, 3:52 PM Thilo Schuchort ***@***.***> wrote:
***@***.**** commented on this pull request.
------------------------------
In src/main/kotlin/com/tschuchort/compiletesting/MainComponentRegistrar.kt
<#27 (comment)>
:
> + * limitations under the License.
+ */
+
+package com.tschuchort.compiletesting
+
+import org.jetbrains.kotlin.base.kapt3.KaptOptions
+import org.jetbrains.kotlin.com.intellij.mock.MockProject
+import org.jetbrains.kotlin.compiler.plugin.ComponentRegistrar
+import org.jetbrains.kotlin.config.CompilerConfiguration
+import org.jetbrains.kotlin.kapt3.base.incremental.IncrementalProcessor
+
+internal class MainComponentRegistrar : ComponentRegistrar {
+
+ override fun registerProjectComponents(project: MockProject, configuration: CompilerConfiguration) {
+ val parameters = threadLocalParameters.get()
+ KaptComponentRegistrar(parameters.processors,parameters.kaptOptions).registerProjectComponents(project,configuration)
I read a few days ago in the Kotlin slack that the order of registering
compiler plugins matters. Right now we are registering Kapt first. Could
there be a problem here? For example if a compiler plugin like arrow-meta
introduces some new syntax/type checking that isn't legal in vanilla Kotlin
the respective plugin would have to be run before Kapt or Kapt wouldn't
know how to deal with that. Any thoughts on this @raulraja
<https://github.com/raulraja>?
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
<#27?email_source=notifications&email_token=AADPQXDSIWXGBBN5ZQC7T63QQRDTNA5CNFSM4JCVVQ7KYY3PNVWWK3TUL52HS4DFWFIHK3DMKJSXC5LFON2FEZLWNFSXPKTDN5WW2ZLOORPWSZGOCJKH27Q#pullrequestreview-307527038>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AADPQXBKC5VCSRXP4ART2HTQQRDTNANCNFSM4JCVVQ7A>
.
|
|
@raulraja That's not really what I meant. Let's assume you have some plugin that replaces every method named |
|
Yes, I see what you mean now, sorry I misunderstood. Yes, in that case
order matters.
…On Sun, Oct 27, 2019, 3:15 PM Thilo Schuchort ***@***.***> wrote:
@raulraja <https://github.com/raulraja> That's not really what I meant.
Let's assume you have some plugin that replaces every method named foo
with a method bar. If the Kapt plugin is registered first, I assume that
apt will see a foo method in the stub files. If Kapt is registered last,
then I assume apt will see a bar method in the stub files. This could be
problematic.
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
<#27?email_source=notifications&email_token=AADPQXHEHLFPZBVNYNUEMHLQQWIANA5CNFSM4JCVVQ7KYY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGOECK7LXY#issuecomment-546698719>,
or unsubscribe
<https://github.com/notifications/unsubscribe-auth/AADPQXHJAPC3GSGWGAVZO7LQQWIANANCNFSM4JCVVQ7A>
.
|
|
|
||
| /** | ||
| * Here the list of compiler plugins is set | ||
| * | ||
| * To avoid that the annotation processors are executed twice, | ||
| * the list is set to empty | ||
| */ | ||
| MainComponentRegistrar.threadLocalParameters.set( | ||
| MainComponentRegistrar.Parameters( | ||
| listOf(), | ||
| KaptOptions.Builder(), | ||
| compilerPlugins | ||
| ) | ||
| ) | ||
|
|
||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why did you remove this again? I think we always need to add the compiler plugins to the compileKotlin step, even if they already ran in the stubsAndApt step.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hi @tschuchortdev , i removed it because i wanted to change a less as possible, because i couldn't guarantee that it would break any behaviour of any other compiler plugins that runs in any of the compiler phases. All i can say is, that i could test my MpApt Plugin with these changes and it didn't break any of the existing tests and Kapt was also working. I don't know much about when which compiler phase is running, because my plugin is only running in one phase.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Are you creating new source files with your plugin or simply adding to the AST?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
My plugin just detects the annotations, it doesn't provide code generation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think we still need to run the plugins in the compileKotlin step then, because all the changes done to the AST during stubsAndApt will be discarded, so a compiler plugin that changes the AST would have no effect.
But I think we also need to run the plugins in the stubsAndApt step as well, before kapt plugin is run.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I also think that we should add it to both. I could restore my deleted version.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Sounds good 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I restored it, and changed the check in stubsAndApt to "annotationProcessors.isEmpty()" again, because without, all added plugins were executed in both phases. In the future we need an option where you can set in which phases you want to execute the plugins, but for now i would keep it that way. If you think otherwise, just add " && compilerPlugins.isEmpty()" to the if statement again.
|
@Foso Can you check what the correct behaviour is when KApt interacts with compiler plugins? If you just modify your MpApt plugin to add some dummy method to all classes and then run it together with a regular annotation processor, you should be able to see the method (or not) in the AP and we can be sure. I'm not so familiar with compiler plugins unfortunately or I would do it myself. If not, I say we just register first-party plugins before KApt in the |
…ile-testing into tschuchortdev#15-betterSupportForCompilerPlugins � Conflicts: � src/test/kotlin/com/tschuchort/compiletesting/KotlinCompilationTests.kt
…ion - add plugins in compileKotlin
…ion - add plugins in compileKotlin
tschuchortdev
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The arrow-meta people will be happy to have this. I will merge it manually.
This PR will added the option to add a list of ComponentRegistrars to the compiler.