gradle: can you apply plugin from command line - eclipse

I downloaded an open source gradle-built project and ran gradle eclipse but apply plugin: 'eclipse' was not in build.gradle so it failed. I edited the file and added the line then successfully ran gradle eclipse. I found this a bit clunky inasmuch as I'd prefer to be able to run gradle eclipse with some flag for instance so that I don't need to change the source at all. Is there an alternative to my action?

My approach to this problem is to write custom gradle scripts in ~/.gradle/init.d/ such as this one:
allprojects {
project.apply plugin: 'maven'
buildscript {
repositories {
mavenLocal()
}
}
repositories {
mavenLocal()
}
}
(this one is to ensure I can leverage mavenLocal repository in every gradle project, but you can do the same and apply eclipse plugin)
This scripts are executed in every gradle build (in alphabetical order, so using a convention similar to Linux init.d in naming can help, e.g. 00-eclipse.gradle) and can enrich your build.
I favor this approach for things which would be user-specific and don't deserve to be in everyone's build script (eclipse/idea/mavenLocal fit that category, and I also apply gradle-tools-plugin for easier debugging through command line.
Note that like Ben mentioned, I usually recommend against using the eclipse/idea project generation plugins, but prefer the IDE gradle integration, but that's another story.

Related

Do dependencies need to be added through both the Eclipse GUI and the Gradle configuration files?

Two Gradle Git projects need to be created, within the same repository, using the Eclipse IDE. Project A depends upon a third-party library (a JAR, source code, Javadoc and natives) and project B depends upon project A.
Without Gradle, both projects would be created and Git would be enabled with Project Explorer > [Project Name] > Team > Share Project. Then, dependencies would be added via Project Explorer > [Project Name] > Build Path > Configure Build Path, followed by Projects > Add and Libraries > Add External JARs (which would also allow the specification of the locations of related source code, Javadoc and natives). This would enable automatic code completion of Project A from Project B as well as source code and Javadoc integration, within Eclipse.
With Gradle, should the settings.gradle or build.gradle files be manually edited, without adding dependencies through the Eclipse GUI, or must both be used simultaneously? Additionally,how does this effect which hidden files should be indexed by Git (.project, .classpath, .settings, .gradle)?
How is this setup through Eclipse and Gradle?
When you use a build-tool like Gradle (or maven), it is kind of assumed that the build-tool is in charge of configuring stuff like project dependencies and classpaths.
This kind of conflicts with the Eclipse UI which is kind of built to allow you to manage classpath / dependencies via its own ui.
But the Eclipse UI only controls what eclipse uses as the classpath when the Eclipse JDT compiler compiles your code... inside Eclipse.
So if you change things that way, then Gradle will not know about these dependencies and the build won't work.
Yep, this is definitely confusing :-)
The proper thing to do is manage your dependencies and project configuration entirely through gradle. So that means editing the build.gradle and settings.gradle.
The tools (BuildShip or STS Gradle Tools) provide a 'bridge' to try and configure Eclipse projects in conformance with your build.
E.g they may offer a 'Update Project' or 'Refresh Dependencies' command in project context menu.
Even if you don't use Gradle tooling, this kind of holds true. You then would use Gradle's 'ecplise' plugin and run a command like
gradle cleanEclipse eclipse
To generate the eclipse project config from the build config. Then import the project into Eclipse as configured by gradle. Also in this case, it would be a bad idea to use Eclipse UI to make changes to the buildpath since ultimately it has the same issue, changes you make to those generated files may make things compile inside Eclipse, but Gradle doesn't know you changed anything. And the next time you run gradle cleanEclipse eclipse your changes are also blown away.
As to your specific questions:
should the settings.gradle or build.gradle files be manually edited ...
Yes.
... without adding dependencies through the Eclipse GUI ...
Yes.
... or must both be used simultaneously?
No, only configure things in gradle. Then 'synch it up' to eclipse with some tool (BuildShip / STS Gradle / gradle cleanEclipse eclipse)
How does this effect which hidden files should be indexed by Git (.project, .classpath, .settings, .gradle)?
General rule of thumb. Only index the stuff that defines gradle's behaviour (there may be some exceptions, but in general try to minimize them only violate this rule if you have a good reason).
So specifically don't put in git these 'eclipse metadata'
.settings
.project
.classpath
Do put in git: the gradle wrapper and its properties file.
Gradle also has a .gradle folder. It belongs to gradle, not eclipse, buts is caches and things which are 'transient'. You don't want those in git either.

Gradle Eclipse Plugin only half-working

I am trying to achieve the following between Eclipse and Gradle:
Allow Gradle to handle 100% of my local build logic; only use Eclipse as an IDE for syntax highlighting, refactoring, etc. Every time I wish to build my app I want to drop into a command line and run a Gradle build invocation from there.
I want the dependencies closure of my build.gradle file to be the sole location for configuring 3rd party dependencies; every time I make a change to this closure (adding/removing a dependency/JAR), I want Eclipse to automagically "see" this change and adjust my project's classpath accordingly
I installed the Gradle-Eclipse Integration plugin and then I followed this tutorial for configuring it correctly.
First I ran:
gradle clean build
And then I added:
apply plugin: 'eclipse'
To my build.gradle, and then ran:
gradle eclipse
I saw a lot of output, the tail end of which is:
gradle eclipse
:myapp:eclipseClasspath
Download http://repo1.maven.org/maven2/org/apache/commons/commons-lang3/3.3.2/commons-lang3-3.3.2-sources.jar
Download http://repo1.maven.org/maven2/org/sonatype/sisu/inject/cglib/2.2.1-v20090111/cglib-2.2.1-v20090111-sources.jar
Download http://repo1.maven.org/maven2/asm/asm/3.1/asm-3.1-sources.jar
Download http://repo1.maven.org/maven2/com/google/inject/guice/3.0/guice-3.0-sources.jar
Download http://repo1.maven.org/maven2/org/codehaus/groovy/groovy-all/2.3.7/groovy-all-2.3.7-sources.jar
Download http://repo1.maven.org/maven2/aopalliance/aopalliance/1.0/aopalliance-1.0-sources.jar
Download http://repo1.maven.org/maven2/javax/inject/javax.inject/1/javax.inject-1-sources.jar
:myapp:eclipseJdt
:myapp:eclipseProject
:myapp:eclipse
I then opened my .classpath file and see that its been correctly updated with all the transitive dependencies defined in my dependencies closure back inside build.gradle.
However, there is not visual indication inside Eclipse that anything is wired correctly. With Ivy or Maven, you usally get something like a Ivy Repository Manager or Maven Dependency Library that automatically changes anytime you modify ivy.xml or pom.xml.
Most importantly, this just doesn't seem to be working! As you see above, Apache Commons Lang 3 is a dependency, but when I try to add org.apache.commons.lang3.exception.ExceptionUtils to a Groovy source file, Eclipse can't find it. I have already tried restarting Eclipse to see if that shook any bugs out.
Am I just not using this plugin correctly, or does it just not work? Using Groovy/Grails Tool Suite 3.6.0.RELEASE here, which is based on Eclipse Luna 4.4.

Gradle IDE (Eclipse) Documentation

I am learning Gradle and have found my way around the normal use case. But now I have to step into integration with Eclipse (specifically STS) and need to learn more about how "Gradle projects" are imported into Eclipse (without having to generate the .project files using the inverse - Eclipse plugin for Gradle). By just attempting it I discovered that it did import my projects. However, projects written in Scala (some are pure Java, some Scala, some mixed) were not recognized and applied as Scala projects. In fact, Eclipse attempted to compile ".scala" files as if they were ".java" somehow and obviously failed miserably.
Tried Googling around to find more documentation on Eclipse integration but this appears to be significantly obscured by the "eclipse plugin" for Gradle in search results. Can someone, please, point me at documentation, if available, or provide at least some guidance with respect to my problem above...
Thanks!
I'm not sure what you mean by:
without having to generate the .project files using the inverse - Eclipse plugin for Gradle
Does this mean that you don't want to apply the Eclipse plugin in your Gradle project? Can I ask why? My experience of it has been very positive.
Here's what I've done in such cases:
apply the Eclipse plugin in my Gradle project (apply plugin: 'eclipse')
run the 'eclipse' Gradle task (gradle eclipse)
in Eclipse, do File>Import...>Existing projects into workspace and navigate to the Gradle project directory (or the root directory of a multi-project structure); (don't check Copy projects into workspace)
If the Gradle project also applies the Java plugin, you'll get a .project file that declares a javanature and refers to the javabuilder, and a .classpath file will also be generated. If not, you'll just get a vanilla .project file. The Gradle documentation makes it sound very much as if a similar thing applies in the case of the Scala plugin: http://www.gradle.org/docs/current/userguide/scala_plugin.html#N12EC0. Does this not work for you?

Gradle eclipse classpath - Switching between SNAPSHOT and project dependency

We have a multiple modules in our Java project and each module publishes SNAPSHOT jar files to Nexus repository. All the sub-modules are directly dependent on the SNAPSHOT jar files.
During development, we want to depend on the Eclipse project rather than SNAPSHOT jars. So we introduced a flag which switches between the dependencies as shown below.
if(System.properties.'setupProject'){
compile project(':Core')
compile project(':Module1')
compile project(':Module2')
}else{
compile 'com.test:core:0.1-SNAPSHOT'
compile 'com.test:module1:0.1-SNAPSHOT'
compile 'com.test:module2:0.1-SNAPSHOT'
}
Executing the following command generates the .classpath file as expected.
gradle eclipse -DsetupProject=true
Is there a better way to do this? Can we use Gradle configurations to achieve the same?
I could not find good examples for the same.
At the moment this is the way to go. You might tweak this even more and instead of using a System property to mark a project as available you can check if the project folder is available (project is checked out)
cheers,
René

Global Plugins in Gradle

I am using Gradle as a build tool for my Scala projects. I am also using Eclipse for development, so I always use the apply plugin: 'eclipse' in my build files.
Is there also a way to define the apply plugin globally? SBT already has such a feature. The reason why I want this, is that other developers who’re using my project probably don’t use Eclipse but another IDE and they would have to change the build script for their needs. If there were a global configuration file, one could put personal configurations in there and it wouldn’t conflict other ones.
You can put this into ~/.gradle/init.gradle:
rootProject.allprojects {
apply plugin: "eclipse"
}
The drawback of this approach is that it makes the build less reproducible. People now need to add something to their init.gradle to make (some aspect of) the build work. Therefore, I would recommend to apply the Eclipse plugin in the main build script; it won't hurt people who don't use it.
for the accepted answer, I also got the error message "The root project is not yet available for build".
I am using gradle 7.6 and I was trying to use the Gradle Test Logger Plugin
Here's the ~/.gradle/init.gradle that worked for me:
initscript {
repositories {
gradlePluginPortal()
}
dependencies {
classpath 'com.adarshr:gradle-test-logger-plugin:3.2.0'
}
}
allprojects {
apply plugin: com.adarshr.gradle.testlogger.TestLoggerPlugin
}
There are multiple things to be aware of when configuring a 3rd party plugin globally:
you need to add the plugin as a dependency to make it available
you need to reference the plugin by its implementation class rather than its ID
you must not use quotes around the implementation class
The last two points are described in the Gradle Forums question
Cannot apply plugin by id in init.gradle script.
How to Find the Implementation Class
If you wonder what the implementation class is for your plugin, here's how I found it for the Gradle Test Logger Plugin:
Open the project on github
Look at it's build.gradle file
Look for the section gradlePlugin {
Take the value from implementationClass
for example: https://github.com/radarsh/gradle-test-logger-plugin/blob/29af9282761f003f51d49aa804cc72e35b16c33b/build.gradle#L61
Remember to not copy the quotes :)
You could create a build.gradle in buildSrc which implements your custom logic. Just don't check it into version control. To apply it to multiple projects you could create a central buildSrc directory and create symbolic links in the projects that you want to apply it to.