auto-reload / hot swap plain groovy dependency in Grails multi-project build - grails

I have a Grails project that includes a separate Gradle project containing utility Java/Groovy classes that are shared among many projects. I am using a multi-project build so that I can develop both projects simultaneously.
The utility classes in the included project are not being hot-swapped / hot-reloaded / auto-reloaded / spring-loaded (I guess there are a lot of synonyms for this concept). This means that every time I make a change in one of the utility classes from the included project, I have to restart the Grails application.
Does anyone know how to make the subproject use the hot-swapping feature that Grails uses? It looks from this comment that Grails does this using Spring Boot's spring-loaded feature: https://github.com/spring-projects/spring-boot/issues/43#issuecomment-24723710
I have even tried setting up the subproject as suggested in this tutorial on using the spring-loaded feature: http://mrhaki.blogspot.com/2015/09/spring-sweets-reload-classes-spring.html. But when I run gradle -t classes, I end up with this output:
Continuous build is an incubating feature.
:compileJava UP-TO-DATE
:compileGroovy FAILED
FAILURE: Build failed with an exception.
* What went wrong:
java.lang.UnsupportedOperationException (no error message)
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.
BUILD FAILED
Total time: 1.832 secs
Waiting for changes to input files of tasks... (ctrl-d then enter to exit)
The build fails, but the process is still running. So I tried starting the Grails app and checking if the utility classes were being hot-swapped, but they weren't. I hope there is a solution that doesn't require starting a separate process with gradle -t classes before starting the Grails app, but either way, if anyone has any ideas, I'd love to hear them.

Related

intellij grails unable to resolve external library at groovy compile time

I'm writing a simple etrade programmatic trading program that needs to authenticate with etrade oauth. I'm using IntelliJ Ultimate with Grails 3.1.9.
I added a folder full of jars to Project Settings->Libraries and Project Settings->Modules->main project (accessible by pressing "command ;") and selected "export." The classes resolve fine in the groovy editor in my controller class but they don't resolve at groovy compile time. Why is that?
~/IdeaProjects/<project name>/grails-app/controllers/etradescripter/ETradeUserController.groovy: 8: unable to resolve class com.etrade.etws.sdk.client.ClientRequest
# line 8, column 1.
import com.etrade.etws.sdk.client.ClientRequest;
Grails use the Gradle build system, which is comparable (superior IMHO) to maven.
It is completely external to the IDE itself and not dependend to any IDE.
It is a very powerfull external build tool which has it's own tooling, dependency management,
library cache and logs.
The libraries and SDK you declare in Intellij project structure settings are for IntelliJ internal support (intellisense, code assist, decompiling etc) not for building and/or debugging
The gradle tooling support for your project (found in File/Settings/Gradle) can be:
a gradlew declaration in the project : the project will use it's own
build system version downloaded from the specifications in
gradle/wrapper/gradle-wrapper.properties file with the accompanying
gradle-wrapper.jar downloader - this is the recommended way to go if you are not comfortable with the system to avoid
problems but disk consuming and not the fastest build. There will be a gradle binary distribution download for the first build
a Gradle version bundled with Intellij (2.13 for the last IntelliJ version I think)
one you can declare in the project settings (ie your own Gradle installation root, you have to install it before and set the right
environment variables to make it work) for the last one it can be a
"daemon" version which speeds up thing notably but is very cpu and
memory expensive for a large project (be prepared for 100% cpu and
memory hogs for a large project whatever computer you have).
The main file for build where you declare the build and debug dependencies is "Build.gradle" file at the root of your project.
Dependencies are declared with lines (Groovy syntax, gradle is a groovy tool) like:
dependencies {
assets "com.craigburke.angular:angular-template-asset-pipeline:2.2.6"
assets "com.craigburke.angular:angular-annotate-asset-pipeline:2.4.0"
assets "com.craigburke:js-closure-wrap-asset-pipeline:1.2.0"
compile "org.springframework.boot:spring-boot-starter-logging"
compile "org.springframework.boot:spring-boot-autoconfigure"
etc...
This is where you have to add your own dependencies, not in IntelliJ SDK/lib settings.
This is comparable to the maven system with a different syntax (groovy).
For jars comming from an external repo or local dependencies, you should see lines that you can copy/paste and modify.
If not look at gradle docs
especially 23.3 and 23.4, how to declare you dependencies.
There can be other gradle files in gradle directory and/or subprojects directory. It depend on your project.
To build your project, you can open the Gradle tool window in IntelliJ (View/Tool Windows/Gradle), select the build task (Task/build/build), double click on it and it will launch the build.
This will change the run/debug configuration in the IntelliJ IDE so you can build it again with the IDE toolbar by clicking on the Run button
Note: the run button runs the currently selected gradle task, not the application, this is a bit confusing at the beginning
To run or debug you app, you select the appropriate task, in case of Grails task, application/bootrun and double click on it.
This will launch your application (after a build if needed), and if it is a web app, you can browse you application in your browser.
When you run the Run task (not the build task) you can also click on 'Debug' icon to debug your application
If you select another task and click debug, you will have a socket exception because IntelliJ thinks you are launching a jvm and tries to connect to it for debugging.
(they are lots of predefined task in Gradle : assembling jars, building docs etc... and the Run task may be specific to a project
Generally Build tasks are under the build category and run task under the application category)

Generating WAR using Gradle wrapper in a Grails application

Is it possible to generate a WAR using the Gradle wrapper (ie. gradlew) that comes with a Grails application?
As far as I can tell, after listing all the available tasks, it doesn't seem like it's possible. If not, I wonder why it isn't.
Side note, using it to publish to Artifactory, which is cool IMO.
Update #1
me#workstation ~/ghi
$ ./gradlew help --task assemble
:help
Detailed task information for assemble
Path
:assemble
Type
Task (org.gradle.api.Task)
Description
Assembles the outputs of this project.
Group
build
BUILD SUCCESSFUL
Total time: 6.345 secs
Update #2
I tried the following command: gradlew -Dgrails.env=xxx war
META-INF\grails.build.info shows grails.env=xxx.
Seems like that would work.
The command you're looking for is
./gradlew assemble
and your war will be in build/libs/

Intellij IDEA 14 Errors with grails run-app

I upgraded to IDEA 14 (from 13) and when I attempt to run my grails 2.2.0 application, I am getting the following error:
FAILURE: Build failed with an exception.
* Where:
Build file '/Users/gdboling/Projects/GenRocket/web/build.gradle' line: 92
* What went wrong:
A problem occurred evaluating root project 'web'.
> No such property: environment for class: org.gradle.api.internal.project.DefaultProject_Decorated
It would seem that IDEA is attempting to use my build.gradle as part of the grails build process. IDEA 13 didn't do this. I use the build.gradle for some other non-grails related tasks for the project.
If I remove the build.gradle file all together, I get this error:
FAILURE: Build failed with an exception.
* What went wrong:
Task 'grails-run-app' not found in root project 'web'.
* Try:
Run gradle tasks to get a list of available tasks. Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.
I do see the Grails View in the IDE but when I try and do a Make, it is telling me to re-import the gradle project. So it would seem that IntelliJ think this is a gradle project. How I can tell it that is is just a grails project?
To confirm my suspicions, I've opened a grails project that did not contain a build.gradle and it works just fine.
I had faced similar issue when unknowingly kept on hit next next in hurry. So, you probably mistakenly created a gradle project as shown in screenshot.
And when you recreated the project created it as "Create project from existing source" which idea well knows as grails-app (default for idea).
See if you can reproduce the error by re-importing the project using import project form external module.

Can't launch libgdx ios/robovm build in IPhone simulator with gradle

I'm trying to get a basic Hello World libgdx application running on the IPhone Simulator using gradle. I am new to gradle and robovm.
First I should note that I am able to successfully build and run tis example app https://github.com/jtakakura/robovm-sample-ios-app with the command:
./gradlew build launchIPhoneSimulator
Just as a small diversion, I am curious to know why
./gradlew launchIPhoneSimulator
fails. Apparently 'build' needs to be explicit.
wintermute:robovm-sample-ios-app matt$ ./gradlew launchIPhoneSimulator
:launchIPhoneSimulator
Classpath entry /Users/matt/code/robovm-sample-ios-app/build/classes/main does not exist
:launchIPhoneSimulator FAILED
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':launchIPhoneSimulator'.
> Main class org.robovm.sample.ios.RoboVMSampleIOSApp not found
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.
BUILD FAILED
Total time: 7.115 secs
I would have thought that the launchIPhoneSimulator task would depend on the build task and that calling lanuchIPhoneSimulator would implicitly invoke build. Is this a mistake in the gradle-robovm-plugin (https://github.com/jtakakura/gradle-robovm-plugin) or is there something I am missing about gradle?
Ok, sorry back to my main question:
I generated a libgdx project using the command line tool supplied by Gdx-setup (https://github.com/libgdx/libgdx/tree/master/extensions/gdx-setup) with the arguments:
--dir /Users/matt/code/test --name test --package com.foo.bar --mainClass FooTest
I threw the generated project up on github so you can clone it with less hassle:
git clone https://github.com/mattwalters/libgdx-test libgdx-test
Then I'll run
./gradlew build
to build all the sub projects. But I am unable to get the ios build running on the simulator via
./gradlew launchIPhoneSimulator
I get a similar error to the one above:
wintermute:test matt$ ./gradlew ios:launchIPhoneSimulator
:ios:launchIPhoneSimulator
Classpath entry /Users/matt/code/test/ios/build/classes/main does not exist
:ios:launchIPhoneSimulator FAILED
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':ios:launchIPhoneSimulator'.
> Main class com.foo.bar.IOSLauncher not found
* Try:
Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output.
BUILD FAILED
Total time: 12.759 secs
I double checked that there is no typo between the actual name of the main class and the mainClass declared to gradle. And there is indeed no classes directory in ios/build, but I am not sure why.
Can anyone help shed some light on this for me? Thanks very much in advance.
Update 2014-01-24: At least one other user has verified that it now works, so please make sure you try again if you are still having problems.
Update 2014-01-23: I've recently checked in some bugfixes to the libgdx gradle support which has been merged into the daily builds. Assuming you use the daylies they should appear within 24 hours. At my end the new bugfixes makes "./gradlew ios:assemble launchIPhoneSimulator" work out of the box after creating a new project with the GdxSetup class.
Original response below:
First, make sure you use at least version 0.0.2 of the gradle-robovm-plugin. Secondly, try to build the sample project using the plugin from here:
https://github.com/jtakakura/robovm-sample-ios-app
The author of the plugin was kind enough to make this based on my request. I've tested the plugin with the example and it works without a hitch. It was discussed and resolved in a closed issue here:
https://github.com/jtakakura/gradle-robovm-plugin/issues/3
It's also worth noting that on recent libgdx builds, the command line tool for generating libgdx application templates already uses the plugin so you should be ready to go without the need to download and/or muck with the stuff yourself (short of getting libdx and running the command line util for generating a template project).
If you already have a project that you need to adapt, look carefully at the build.gradle file in the robovm-sample-ios-app example from the author of the example. It shows you what is needed to get a robovm build going.
Try to check is roboVMVersion and robovm-gradle-plugin in your main build.gradle points to latest robovm/plugin versions. If no - try to use latest. This helps me several times.

Sonar using Sonar Runner on Jenkins Job fails to access classes

Im trying to run a sonar analysis on a Jenkins Job. Im using ant so im using Sonar Runner and sonar.properties in the projects. Im configuring the the binaries to
sonar.binaries=build/ant/classes
After a successfull build Sonar starts and is running a while. But i get a lot of warnings during bytecode analysis.
Im getting WARN XX - Class 'XX' is not accessible through the ClassLoader.
for every class...
I dont really know why classes are all there?
These are warnings issued by Findbugs, which requires access to source, compile binaries and 3rd party libraries.
To resolve these warnings you need to include an additional sonar.libraries property, populated with the 3rd party jars your code depends upon (See Analaysis Parameters documentation)
I actually had the same problem, but that was because of an issue with the maven caches.
I had run mvn clean install in the directory on my local machine, but was running sonar on the directory on a virtual box. This resulted in classes not being found.

Resources