Spring Java Format

repository·main·Indexed 21 days ago

https://github.com/spring-io/spring-javaformat

A set of plugins to enforce a consistent 'Spring' coding style across Java projects. It includes a source formatter for whitespace and wrapping, a Checkstyle plugin for rule enforcement, and a Javadoc doclet. The project provides official plugins for Maven, Gradle, Eclipse, IntelliJ IDEA, and Visual Studio Code.

Tokens
5.6K
Snippets
17
Records
25
Agent score
75%

What's inside spring-javaformat

  1. Overview of Spring Java Format Project Structure

    main

    The project is composed of 6 main top-level projects:

    1. spring-javaformat: The core formatter project.
    2. spring-javaformat-eclipse: The Eclipse plugin.
    3. spring-javaformat-gradle: The Gradle plugin.
    4. spring-javaformat-intellij: The IntelliJ IDEA plugin.
    5. spring-javaformat-maven: The Maven plugin.
    6. spring-javaformat-vscode: The Visual Studio Code extension.

    Core Formatter Sub-projects

    Under spring-javaformat, the following key modules exist:

    • spring-javaformat-formatter: The main formatter code.
    • spring-javaformat-formatter-shaded: A shaded version of the formatter with all dependencies included.
    • spring-javaformat-formatter-eclipse-runtime: A minimal Eclipse runtime JAR (built with Proguard) used when running the formatter outside of Eclipse.
    • spring-javaformat-formatter-eclipse-jdk8 / spring-javaformat-formatter-eclipse-jdk17: Repackaged and adapted Eclipse JDK formatters.
    • spring-javaformat-checkstyle: The Checkstyle plugin.
  2. Build Spring Java Format from source

    main

    To build the project from the root directory, you must have JDK 17 installed. Use the Maven wrapper (./mvnw) to perform a clean install.

    If you encounter memory issues during the build, increase the available heap size by setting the MAVEN_OPTS environment variable to -Xmx512m.

    $ ./mvnw clean install
  3. Configure Checkstyle for Maven

    main

    To enforce Spring Checkstyle conventions in Maven, add the maven-checkstyle-plugin with dependencies on both checkstyle and spring-javaformat-checkstyle:

    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-checkstyle-plugin</artifactId>
        <version>3.1.1</version>
        <dependencies>
            <dependency>
                <groupId>com.puppycrawl.tools</groupId>
                <artifactId>checkstyle</artifactId>
                <version>{checkstyle-version}</version>
            </dependency>
            <dependency>
                <groupId>io.spring.javaformat</groupId>
                <artifactId>spring-javaformat-checkstyle</artifactId>
                <version>{release-version}</version>
            </dependency>
        </dependencies>
        <executions>
            <execution>
                <id>checkstyle-validation</id>
                <phase>validate</phase>
                <inherited>true</inherited>
                <configuration>
                    <configLocation>io/spring/javaformat/checkstyle/checkstyle.xml</configLocation>
                    <includeTestSourceDirectory>true</includeTestSourceDirectory>
                </configuration>
                <goals>
                    <goal>check</goal>
                </goals>
            </execution>
        </executions>
    </plugin>
  4. Import Spring Java Format into IntelliJ IDEA

    main

    Import the project as a Maven project.

    Note on Module Dependencies: Because the modules spring-javaformat-formatter-eclipse and spring-javaformat-formatter-eclipse-runtime perform repackaging (shading and binary manipulation), IntelliJ IDEA cannot resolve all classes via standard module dependencies. You must manually add these modules as JAR dependencies instead of module dependencies.

    Steps to set up JAR dependencies:

    1. Add a JAR-based project library:
      • Go to Project Settings -> Libraries.
      • Click +, select Java, and specify the JAR file.
      • You can use the JAR from the target directory (e.g., <PROJECT>/spring-javaformat/spring-javaformat-formatter-eclipse-runtime/target/spring-javaformat-formatter-eclipse-runtime-0.0.28-SNAPSHOT.jar) or from your local Maven repository.
    2. Add library dependencies to modules:
      • Go to Project Settings -> Modules.
      • Select the module that depends on the repackaging modules.
      • Click + and select 2 Library.
      • Choose the libraries added in the previous step.
      • Move the added libraries higher than the module dependencies (or remove the module dependencies).
  5. Configure Checkstyle for Gradle

    main

    To enforce Checkstyle conventions in Gradle, apply both the io.spring.javaformat plugin and the standard checkstyle plugin:

    plugins {
        id "io.spring.javaformat" version "{release-version}"
        id "checkstyle"
    }
    
    checkstyle {
        toolVersion = "{checkstyle-version}"
    }
    
    springJavaFormat {
        checkstyle {
            applyDefaultConfig()
        }
    }

    Customization Options

    • Apply Default Spring Config: Use springJavaFormat.checkstyle.applyDefaultConfig() to use the built-in Spring checks.
    • Provide Custom XML: Alternatively, provide your own checkstyle.xml that configures the io.spring.javaformat.checkstyle.SpringChecks module.
    • Disable Dependency Injection: If you want to use Spring Java Format but do NOT want it to automatically configure dependencies for the Checkstyle plugin, set:
      springJavaFormat {
          checkstyle {
              configureDependencies = false
          }
      }
  6. Develop the IntelliJ IDEA Plugin

    main

    To develop the spring-javaformat-intellij-idea-plugin module, follow these steps:

    1. Download IntelliJ IDEA Images

    • Open pom.xml in spring-javaformat-intellij-idea/spring-javaformat-intellij-idea-runtime.
    • Check intellij.binary and intellij.source properties to identify the required version.
    • Download the binary from the URL in intellij.binary (use .dmg instead of .tar.gz for OSX).
    • Install the image and download/unzip the source files from the GitHub location specified in intellij.source.

    2. Setup SDK

    • In IntelliJ, go to Project Structure -> Platform Settings -> SDKs.
    • Click + and select Add Intellij Platform Plugin SDK....
    • Specify the installed IntelliJ image (e.g., /applications/IntelliJ IDEA CE on OSX).
    • In the Sourcepath field on the right, click + and specify the unzipped IntelliJ source directory.
    • Specify a Sandbox Home directory.

    3. Convert to Plugin Module

    By default, the module is recognized as a Java module. You must convert it to a plugin module:

    • Open spring-javaformat-intellij-idea-plugin.iml in spring-javaformat-intellij-idea/spring-javaformat-intellij-idea-plugin.
    • Change type="JAVA_MODULE" to type="PLUGIN_MODULE".
    <module org.jetbrains.idea.maven.project.MavenProjectsManager.isMavenModule="true" type="PLUGIN_MODULE" version="4">
    • Verify the icon in Project Structure -> Modules has changed to a plugin icon.
    • Under Plugin Deployment, set the Path to META-INF/plugin.xml to: <PROJECT>spring-javaformat/spring-javaformat-intellij-idea/spring-javaformat-intellij-idea-plugin/src/main/resources.
  7. Develop the Visual Studio Code Extension

    main

    The spring-javaformat-vscode-extension consists of a Java formatter and a TypeScript extension.

    • TypeScript Development: Open the extension folder directly in VS Code.
    • Building: Maven delegates to npm run package to generate the extension.
    • Formatting: Code is formatted with Prettier. To reformat, run:
      npx prettier --write .
    • Testing: Since the extension requires UI elements, tests do not run during the regular build. To run tests, use the Extension Tests command from within VS Code.
    npx prettier --write .
  8. Configure Spring Java Format for Gradle

    main

    To use Spring Java Format in Gradle, first ensure mavenCentral() is in your pluginManagement repositories in settings.gradle:

    pluginManagement {
        repositories {
            gradlePluginPortal()
            mavenCentral()
        }
    }

    Then apply the plugin in build.gradle:

    plugins {
        id "io.spring.javaformat" version "{release-version}"
    }

    Available Tasks

    • format: Applies formatting to source files.
    • checkFormat: Validates that code matches the style. This task is automatically executed when running the standard Gradle check task.

    Excluding Packages from Formatting

    To exclude specific packages (e.g., generated sources) from the checkFormat task:

    tasks.withType(io.spring.javaformat.gradle.tasks.CheckFormat) {
        exclude "package/to/exclude"
    }
  9. Use Javadoc Offline Links Doclet

    main

    The io.spring.javaformat:spring-javaformat-doclet module allows -linkoffline locations to be expanded against source directories. This is useful for linking against *-javadoc.jar files.

    Usage Pattern

    1. Extract package-list and element-list files from Javadoc jars (e.g., using maven-dependency-plugin with the unpack goal).
    2. Configure the maven-javadoc-plugin to use io.spring.javaformat.doclet.OfflineLinksDoclet.
    3. Use -offlinelinks-source with the @name@ placeholder to expand locations.

    Example configuration:

    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-javadoc-plugin</artifactId>
        <configuration>
            <doclet>io.spring.javaformat.doclet.OfflineLinksDoclet</doclet>
            <docletArtifact>
                <groupId>io.spring.javaformat</groupId>
                <artifactId>spring-javaformat-doclet</artifactId>
                <version>{release-version}</version>
            </docletArtifact>
            <additionalOptions>
                <additionalOption>-offlinelinks-source ${project.build.directory}/javadoc-dependencies/@name@-javadoc-jar</additionalOption>
                <additionalOption>-linkoffline https://docs.spring.io/spring/docs/${spring.version}/javadoc-api/ spring-beans,spring-core</additionalOption>
            </additionalOptions>
        </configuration>
    </plugin>

    Key Features

    • Expansion: The @name@ element in -offlinelinks-source is replaced with each location name provided in -linkoffline.
    • Validation: Unlike the standard Javadoc doclet, this doclet checks that {@link ...} references are valid. It will fail if links cannot be found.
    • Ignoring Packages: Use the -offlinelinks-ignore-packages option to ignore specific packages that do not have links.
    <plugin>
        <groupId>org.apache.maven.plugins</groupId>
        <artifactId>maven-javadoc-plugin</artifactId>
        <configuration>
            <doclet>io.spring.javaformat.doclet.OfflineLinksDoclet</doclet>
            <docletArtifact>
                <groupId>io.spring.javaformat</groupId>
                <artifactId>spring-javaformat-doclet</artifactId>
                <version>{release-version}</version>
            </docletArtifact>
            <additionalOptions>
                <additionalOption>-offlinelinks-source ${project.build.directory}/javadoc-dependencies/@name@-javadoc-jar</additionalOption>
                <additionalOption>-linkoffline https://docs.spring.io/spring/docs/${spring.version}/javadoc-api/ spring-beans,spring-core,spring-context,spring-test,spring-web,spring-webflux,spring-webmvc</additionalOption>
                <additionalOption>-linkoffline https://javadoc.io/doc/com.fasterxml.jackson.core/jackson-databind/${jackson.version} jackson-databind</additionalOption>
            </additionalOptions>
        </configuration>
    </plugin>
  10. Develop the Gradle Plugin

    main

    The spring-javaformat-gradle-plugin module is a Gradle plugin and requires Gradle-related classes. To enable development, convert this module into a Gradle project:

    1. Locate the build.gradle file in the spring-javaformat-gradle-plugin module.
    2. Right-click the file in the project pane.
    3. Select Import Gradle Project.
  11. Configure Spring Java Format for Maven

    main

    To use Spring Java Format in a Maven project, you need to add the spring-javaformat-maven-plugin to your build plugins and register the io.spring.javaformat plugin group in your ~/.m2/settings.xml to enable shorthand goal execution.

    Source Formatting

    Add the plugin to your pom.xml:

    <build>
        <plugins>
            <plugin>
                <groupId>io.spring.javaformat</groupId>
                <artifactId>spring-javaformat-maven-plugin</artifactId>
                <version>{release-version}</version>
            </plugin>
        </plugins>
    </build>

    Register the plugin group in ~/.m2/settings.xml:

    <pluginGroups>
        <pluginGroup>io.spring.javaformat</pluginGroup>
    </pluginGroups>

    Run ./mvnw spring-javaformat:apply to reformat your code.

    Enforcing Style via Validation

    To ensure all code matches the required style during the build, bind the validate goal to the validate phase:

    <plugin>
        <groupId>io.spring.javaformat</groupId>
        <artifactId>spring-javaformat-maven-plugin</artifactId>
        <version>{release-version}</version>
        <executions>
            <execution>
                <phase>validate</phase>
                <inherited>true</inherited>
                <goals>
                    <goal>validate</goal>
                </goals>
            </execution>
        </executions>
    </plugin>
  12. Import Spring Java Format into Eclipse

    main

    Import the project into any Eclipse-based distribution using the M2Eclipse plugin.

    After importing, you must run the following command to apply the project's Eclipse settings:

    $ ./mvnw -Peclipse validate

    Important: After importing, you must close the spring-javaformat-formatter-eclipse and spring-javaformat-formatter-eclipse-runtime projects, as they contain rewritten packages that are not supported by the IDE.