How to configure a compileServer.plugin (BuilderService) using the Gradle IntelliJ plugin?

I've implemented an IntelliJ plugin and an accompanying BuilderPlugin, however I can't find any docs explaining how to combine the two in a single project using the Gradle IntelliJ plugin, which is supposed to be the preferred build environment.

A BuilderPlugin should not be configured as an IJ plugin, right?  Instead it simply needs to register itself using the standard Java services stuff in META-INF, right?  If so, how should a BuilderPlugin be configured to depend on the IJ API?  Is there a maven library with just the JPS part available?

Also the BuilderPlugin docs mention that if the BuilderPlugin module follows the proper naming convention and if the sources (and META-INF resources?) are in the right place, "‘Build’ | ‘Prepare Plugin Module for deployment’ action will automatically pack ‘jps-plugin’ part to a separate jar accordingly".  How does this work with the Gradle plugin?  Or doesn't it?

The BuilderPlugin docs are kinda vague about all this.

Thanks!

0

Hi,

For JSP part you should create a subproject (so it will be a separate jar) and use `intellij.type='JPS'` in it (so it will be compiled against jps-related jars only). 

0

I setup a subproject with `type = JPS` as you suggest, however it looks like only the jsp-builders.jar is in context -- all references to classes in jps-model.jar appear as compile errors:

0

JpsTypedElement and other classes from the screenshot are part of platform-api.jar, not jps-model.jar

0

Ah, yes.  But why is the platform-api.jar not available in a JPS project?  Surely code such as the following is commonplace:

for(JpsModuleSourceRoot jpsSourceRoot: target.getModule().getSourceRoots()) {...}
0

Sorry for digging this out again, however there hasn't been any solution and my problem is exactly the same. I'm truly puzzled about this. Did you find any solution to this? How do we link the <Whatever>-jps-plugin.jar with the main plugin? Shall it be included by being extracted or ..?

@Alexander Zolotov: where did you look up the information about type='JPS'? I cannot find it being documented anywhere. If we put this inside, not even the @NotNull annotations will work anymore.

[EDIT]

I've finally found the type='JPS' documentation: https://github.com/JetBrains/gradle-intellij-plugin

However with type='JPS' it really finds nothing in the classpath, not even JpsModule. Only the impl packages and classes are found. They're inside jps-model.jar while the interfaces are in platform-api.jar. How do we get platform-api.jar into the classpath without changing the type to something different than 'JPS'?

[EDIT]

The best comparison is probably the Erlang plugin, however it doesn't even specify the type 'JPS' for the jps-module.

0

I got a working jps-plugin by manually adding the dependencies:

in jps-plugin/build.gradle:

apply plugin: 'org.jetbrains.intellij'
intellij {
  version "IC-201.7223.91"
  plugins = ['java']
  configureDefaultDependencies = false
}
dependencies {
  compile group: 'org.jetbrains', name: 'annotations', version: '19.0.0'
  compile 'com.google.guava:guava:28.2-jre'
  testCompile group: 'junit', name: 'junit', version: '4.12'
}

afterEvaluate {
  dependencies {
    compile intellij { include('platform-api.jar') }
    compile intellij { include('util.jar') }
    compile intellij { include('jps-model.jar') }
    compile intellij { include('jdom.jar') }
    compile intellijPlugin('java') { include('jps-builders.jar') }
  }

  project.tasks.remove(project.tasks.runIde)
}


This was after some experimentation, so there might be a more optimal way of
doing this.

The last line is optional - runIde isn't a useful task in jps-plugins.

Peter

 

0

Excellent.  This looks promising.  My JPS plugin is a subproject of my primary IJ pluging, so project.tasks.remove(project.tasks.runIde) alone is gold to me.  Thanks.

0

Thanks for the investigation. It looks like this is the only way to build JPS plugin right now with gradle. Still, adding `platforma-api.jar` and its dependencies like JDOM might be risky, as there are no guarantees that it will be included in the classpath on the production, and likely at some point it won't (see https://youtrack.jetbrains.com/issue/IDEA-199271).

@Scott I'm not aware of any cases where removing a task from task graph is better than just not running it. In general, avoid running tasks you don't want to run, thus you'll have the same effect as with removing but also will get a boost to the building process as a bonus.

0

@... Because my JSP plugin is a subproject of my IDE plugin, I assume runIde is an inherited task, right? Otherwise, I'm not sure how to prevent runIde from applying to the JSP plugin without removing it with project.tasks.remove(). But I'm probably doing it wrong :/

0

@Scott, there is no inheritance in tasks. `gradle runIde` literally means "run runIde task in all nested projects even if they are not in the dependency graph". What you want to do is `gradle :runIde`, which runs a task in the root project.

https://docs.gradle.org/current/userguide/command_line_interface.html

0

 

Yes - but the natural thing to do (for a gradle beginner) is to run the 'runIde' step at top level. 

Maybe a flag in the intelij {} block to say 'don't create the runIde task' would help for where there's no need for such a task?

This would cover new jps-plugins or helper libraries.

Peter

 

0

> Yes - but the natural thing to do (for a gradle beginner) is to run the 'runIde' step at top level. 

I believe it's a gradle interface problem, I don't think plugin can solve it

> Maybe a flag in the intelij {} block to say 'don't create the runIde task' would help for where there's no need for such a task?

Tasks graph is created before the evaluation of that flag.

0

请先登录再写评论。