Integration of jQAssistant into a Spring Boot project which is built using Apache Maven.

Note
This tutorial has been written for jQAssistant 1.8.0

1. Prerequisites

  • Spring Boot project based on Maven as created by https://start.spring.io/ using the required dependencies (e.g. Web, JPA and H2).

  • For rendering PlantUML diagrams Graphviz needs to be installed and available via the system path.

2. Overview

jQAssistant comes with a plugin for Spring based applications that provides rules for enforcing best practices, e.g.

  • allowed dependencies between Controllers, Services and Repositories

  • correct usage of transactional methods

  • enforcing constructor injection instead of field injection.

  • …​

Detected violations will be printed as warnings at the end of the build or might even break it if required.

The steps in this tutorial illustrate:

3. jQAssistant Maven Plugin

jQAssistant runs as part of the build process and therefore needs to be integrated as Maven plugin. This is done by adding the following setup to the build/plugins section of the file pom.xml:

pom.xml
<plugin>
    <groupId>com.buschmais.jqassistant</groupId>
    <artifactId>jqassistant-maven-plugin</artifactId>
    <version>1.8.0</version>
    <executions>
        <execution>
            <id>default-cli</id>
            <goals>
                <goal>scan</goal>
                <goal>analyze</goal>
            </goals>
            <configuration>
                <groups>
                    <group>spring-boot:Strict</group>
                    <!--
                    <group>spring-boot:Default</group>
                    -->
                    <group>Default</group>
                </groups>
                <warnOnSeverity>MINOR</warnOnSeverity>
                <failOnSeverity>BLOCKER</failOnSeverity> <!-- default: MAJOR -->
                <rule>
                    <defaultConceptSeverity>INFO</defaultConceptSeverity>
                </rule>
            </configuration>
        </execution>
    </executions>
</plugin>

The configuration above…​

  • activates the goals scan and analyze during a build

  • defines the rule group spring-boot:Strict to be executed during analysis (alternatively spring-boot:Default, for Default see Project Specific Rules And Reports)

  • sets severity thresholds for printing warnings and breaking the build to MINOR (concepts) and BLOCKER (constraints)

  • sets the default severity for concepts that cannot be applied to INFO

The Maven build can be triggered as usual on the command line:

mvn clean install
Note
The default severity of concepts is MINOR and therefore the default setup of jQAssistant would issue a warning for each concept that could not be applied (e.g. if there are no @Configuration annotated beans present in the code). For this reason this configuration sets the default concept severity to INFO.

4. Pre-Defined Rules

The setup above activates the pre-defined group spring-boot:Strict that provides recommended constraints for the structure and architecture of the project.

Executing the goal effective-rules on the command line using

mvn jqassistant:effective-rules

prints a summary of the activated rules including their descriptions:

[INFO] Groups [7]
[INFO]   "spring-boot:Default"
[INFO]   "spring-boot:Strict"
[INFO]   "spring-component:Default"
[INFO]   "spring-component:Strict"
[INFO]   "spring-injection:Default"
[INFO]   "spring-injection:Strict"
[INFO]   "spring-transaction:Default"
[INFO] Constraints [15]
[INFO]   "spring-boot:AllTypesInApplicationPackage" - All types of of a Spring Boot application must be located in the same package or a sub-package of
            the application class.

[INFO]   "spring-component:ControllerMustOnlyDependOnServicesRepositoriesOrComponents" - A Spring controller can only have dependencies to other Spring components that are services or
            repositories.
...
Tip
There is also a pre-defined group activating a smaller and less strict set of rules. For using it just replace spring-boot:Strict with spring-boot:Default in your pom.xml (see above). For a detailed description of available concepts and constraints refer to the plugin documentation.

5. Project Specific Rules And Reports

The concepts defined by the Spring plugin are also a good base for project specific rules. Such rules must be located in the directory /jqassistant and can be written either in XML or Asciidoc files.

The latter is recommended for writing executable documentation and used in this example. Therefore the directory contains the files index.adoc, package.adoc and maven.adoc.

index.adoc defines a group Default which just includes all groups matching the pattern *:Default:

jqassistant/index.adoc
[[Default]]
[role=group,includesGroups="*:Default"]
== Architecture and Design Guidelines

This section describes architecture and design principles of the application.

package.adoc contains a matching group package:Default which itself includes all constraints matching package:*:

jqassistant/package.adoc
[[package:Default]]
[role=group,includesConstraints="package:*"]
=== Package Structure

To improve maintainability in the long term the following rules for structuring the application into packages must be applied.

[[package:ServicePackage]]
[source,cypher,role=constraint,requiresConcepts="spring-component:Service"]
.Spring Services must be located in packages named `service`.
----
MATCH
  (package:Package)-[:CONTAINS]->(service:Spring:Service)
WHERE
  package.name <> "service"
RETURN
  service as ServicesInInvalidPackage
----
Tip
Using wildcard for including groups, concepts or constraints allows easily adding new rules.

The example constraint package:ServicePackage ensures that Spring services (i.e. classes annotated with @Service) are located in packages named service.

In a similar way maven.adoc defines a group maven:Default but it includes all concepts matching maven:*:

jqassistant/maven.adoc
[[maven:Default]]
[role=group,includesConcepts="maven:*"]
=== Maven Project

[[maven:ProjectArtifactDependencies]]
[source,cypher,role=concept,reportType="plantuml-component-diagram"]
.Report about project artifacts and their direct dependencies
----
MATCH
  (:Maven:Project)-[:CREATES]->(artifact:Artifact)
OPTIONAL MATCH
  (artifact)-[dependsOn:DEPENDS_ON]->(dependency:Artifact)
RETURN
  *
----

The concept maven:ProjectArtifactDependencies defines the report type plantuml-component-diagram. This will render the rule result (i.e. nodes and relations returned by the Cypher query) to the desired diagram type.

Finally the group Default must be activated in the configuration section of the jQAssistant Maven Plugin.

The project can be built and verified by running the following command:

mvn clean install

After the execution the HTML documentation including the rule results is available in the folder target/jqassistant/report/asciidoc.

6. Resources