Spring Boot: Restarting App using Dev Tools with IntelliJ IDEA

Spring Boot provides spring-boot-devtools module that allows the app to “smartly” restart whenever the files on the classpath have changed.

Because the rarely changed classes (ex: 3rd party JARs) are separated out into a different classloader from the app’s actively developed classes’ classloader, it allows Spring Boot to quickly restart the app compared to “cold start”.

DEPENDENCY

First, add the following dependency:-

<dependency>
	<groupId>org.springframework.boot</groupId>
	<artifactId>spring-boot-devtools</artifactId>
	<scope>runtime</scope>
</dependency>

CONFIGURING INTELLIJ IDEA

In IntelliJ IDEA:-

  • Click SHIFT twice to bring up the “Search History” dialog.
  • Select “Actions” tab.
  • Type “Registry” in the search box.
  • Select “Registry…”.

In the “Registry” dialog:-

  • Find “compiler.automake.allow.when.app.running” key.
  • Check the checkbox.
  • Close the dialog.

In IntelliJ IDEA “Preferences” dialog:-

  • Go to “Build, Execution, Deployment” » “Compiler”.
  • Check “Build project automatically”.
  • Close the dialog.

Finally, instead of running Maven goals to run the Spring Boot app, select the Application class (annotated with @SpringBootApplication) and run it from IntelliJ IDEA.

Anytime the app’s class files have changed, IntelliJ IDEA will compile the app, which will then trigger Spring Boot Dev Tools to restart the app.

IntelliJ IDEA: Configuring Default Project Settings

PROBLEM

When creating or checking out a project for the first time in IntelliJ IDEA, we may need to reconfigure the project settings. My biggest pain is IntelliJ IDEA will always use the wrong Maven version when I check out the project from the source control.

SOLUTION

The good news is there is a way to set up default project settings in IntelliJ IDEA.

In the Welcome dialog, select Configure -> Project Defaults.

From here, we can create all the default project settings, such as JDK version, Maven version, code style formatter and so on.

IntelliJ IDEA 14.1: Better equals(), hashCode() and toString()

PROBLEM

Let’s assume we want to create the default equals(), hashCode() and toString() with the following bean:-

public final class Person {
    private final String name;
    private final Collection<Car> cars;

    public Person(final String name, final Collection<Car> cars) {
        this.name = name;
        this.cars = cars;
    }

    public String getName() {
        return name;
    }

    public Collection<Car> getCars() {
        return cars;
    }
}

Most IDEs, including older version of IntelliJ, have code generation features that would create something similar to this:-

public final class Person {
    ...

    @Override
    public boolean equals(final Object o) {
        if (this == o) {
            return true;
        }
        if (o == null || getClass() != o.getClass()) {
            return false;
        }

        final Person person = (Person) o;

        if (name != null ? !name.equals(person.name) : person.name != null) {
            return false;
        }
        return !(cars != null ? !cars.equals(person.cars) : person.cars != null);
    }

    @Override
    public int hashCode() {
        int result = name != null ? name.hashCode() : 0;
        result = 31 * result + (cars != null ? cars.hashCode() : 0);
        return result;
    }

    @Override
    public String toString() {
        return "Person{" +
               "name='" + name + '\'' +
               ", cars=" + cars +
               '}';
    }
}

While it works, the generated code is usually crazy horrendous.

SOLUTION

With IntelliJ 14.x, it allows us to select templates from several proven libraries.

To generate equals() and hashCode(), select equals() and hashCode() option from the Generate pop-up dialog:-

There are several templates to choose from:-

Here’s an example of equals() and hashCode() using Guava and getter methods:-

public final class Person {
    ...

    @Override
    public boolean equals(final Object o) {
        if (this == o) {
            return true;
        }
        if (o == null || getClass() != o.getClass()) {
            return false;
        }
        final Person person = (Person) o;
        return Objects.equal(getName(), person.getName()) &&
               Objects.equal(getCars(), person.getCars());
    }

    @Override
    public int hashCode() {
        return Objects.hashCode(getName(), getCars());
    }
}

To generate toString(), select toString() option from the Generate pop-up dialog:-

Again, there are several templates to choose from:-

Here’s an example of toString() using Guava:-

public final class Person {
    ...

    @Override
    public String toString() {
        return Objects.toStringHelper(this)
                .add("name", name)
                .add("cars", cars)
                .toString();
    }
}

IntelliJ IDEA: Generating Immutable Classes and Fields

PROBLEM

By default, IntelliJ IDEA generates mutable classes and fields.

One of the steps to achieve immutability is to make all classes and fields to be final.

SOLUTION

Making Fields Final

Go to Preferences... -> Code Style -> Java -> Code Generation tab

Under Final Modifier, check both Make generated local variables final and Make generated parameters final.

Making Classes Final

Go to Preferences... -> File and Code Templates -> Templates tab

Select Class and add final.

IntelliJ : Karma Integration

Overview

Although we can run karma start karma.conf.js on the command line to start Karma test runner, JetBrains provides a great Karma-IntelliJ integration to run and display the JavaScript test results within IntelliJ.

Prerequisites

Install Karma Plugin in IntelliJ

The first step is to install the Karma plugin created by JetBrains.

Create Karma “Run” Configuration

From the drop down list on top right of IntelliJ, select Edit Configurations….

In Run/Debug Configuration dialog, select + and then select Karma.

Enter a name, in this example, we call it Karma.

Use the drop down list to select a configuration file called karma.conf.js.

The Node interpreter and Karma package should already be defined, otherwise, use the drop down lists to select the right values.

On top right of IntelliJ, select the green Play button to run Karma test runner.

IntelliJ should now run Karma and display the familiar green/red bar based on the JavaScript test results.

There are few things we can configure here:-

  • Button 1 – When selected, IntelliJ will automatically rerun all the tests whenever we change the production or test JavaScript files.
  • Button 2 – When unselected, all passed tests are displayed.
  • Button 3 – When selected, all tests are expanded.