33

I'm trying to use Lombok in combination with AspectJ and Maven. So, what's the problem? When I use the AspectJ Maven Plugin (www.mojohaus.org/aspectj-maven-plugin/), it takes the sources and compiles them and ignores changes made by Lombok. I followed this tutorial and came up with this code and AspectJ works, but Lombok dies with this message:

[WARNING] You aren't using a compiler supported by lombok, so lombok will not work and has been disabled.
Your processor is: org.aspectj.org.eclipse.jdt.internal.compiler.apt.dispatch.BatchProcessingEnvImpl
Lombok supports: sun/apple javac 1.6, ECJ

So, does anyone know how to get Lombok in combination with AspectJ working?

Dharman
  • 30,962
  • 25
  • 85
  • 135
NyxCode
  • 584
  • 1
  • 4
  • 13

7 Answers7

26

Use ajc to process classes.

<plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>aspectj-maven-plugin</artifactId>
            <version>1.11</version>

            <configuration>
                <complianceLevel>8</complianceLevel>
                <source>8</source>
                <target>8</target>
                <showWeaveInfo>true</showWeaveInfo>
                <verbose>true</verbose>
                <Xlint>ignore</Xlint>
                <encoding>UTF-8</encoding>


                <!-- IMPORTANT-->
                <excludes>
                    <exclude>**/*.java</exclude>
                </excludes>
                <forceAjcCompile>true</forceAjcCompile>
                <sources/>
                <!-- IMPORTANT-->


                <aspectLibraries>
                    <aspectLibrary>
                        <groupId>you.own.aspect.libary</groupId>
                        <artifactId>your-library</artifactId>
                    </aspectLibrary>
                </aspectLibraries>

            </configuration>
            <executions>
                <execution>
                    <id>default-compile</id>
                    <phase>process-classes</phase>
                    <goals>
                        <!-- use this goal to weave all your main classes -->
                        <goal>compile</goal>
                    </goals>
                    <configuration>
                        <weaveDirectories>
                            <weaveDirectory>${project.build.directory}/classes</weaveDirectory>
                        </weaveDirectories>
                    </configuration>
                </execution>
                <execution>
                    <id>default-testCompile</id>
                    <phase>process-test-classes</phase>
                    <goals>
                        <!-- use this goal to weave all your test classes -->
                        <goal>test-compile</goal>
                    </goals>
                    <configuration>
                        <weaveDirectories>
                            <weaveDirectory>${project.build.directory}/test-classes</weaveDirectory>
                        </weaveDirectories>
                    </configuration>
                </execution>
            </executions>
        </plugin>
SoilChang
  • 281
  • 3
  • 4
  • I am using IntelliJ. Actually, I need to switch to javac to make this work via IntelliJ. But it works! – Jay Cui Dec 31 '18 at 21:23
  • @JayCui I don't think you are weaving if you switch back to `javac` – Ghilteras Feb 26 '19 at 21:19
  • 6
    @Ghilteras I actually found another solution for this without switching to javac. Assume you are using Intellij as well. Go to File > Project Structure > Modules >AspectJ, check the option: Post-compile weave mode. It should work properly. – Jay Cui Feb 27 '19 at 07:36
  • @Ghilteras Actually it works with javac and maven build. Did tests on it. But I think the Post-compile weave mode is better. – Jay Cui Feb 27 '19 at 07:37
  • @JayCui I think it still works because you weave at runtime, but some Aspects require you to weave at compile time (like https://github.com/spring-projects/spring-retry). I should probably test what happens with that and Post-compile – Ghilteras Mar 12 '19 at 19:53
  • 1
    For anybody coming here later, this seems to be the correct solution. Just see the part "" and execution configs. If you are having problems only in test compilation it is because you have to make a separate configuration for test-compile because otherwise aspectj will compile your test codes instead of maven-compiler and lombok will not work with those. – berserk81 Sep 30 '19 at 20:43
  • @berserk81 for this to work I have to additionally disable the default execution of aspectj-maven-plugin which normally kicks in during compile phase, as follows: ` default none ` – Olivier Gérardin May 27 '20 at 12:59
  • 6
    Most people know `${project.build.directory}` is `target`, but you can use `${project.build.outputDirectory}` and `${project.build.testOutputDirectory}` for `target/classes` and `target/test-classes` :) – Captain Man Jun 12 '20 at 18:59
  • For the aspect library, how does this work? I'm just adding this plugin to a submodule POM that has the aspect defined in it.. do I set the aspect-library to my own project somehow? Or should I move the aspects somewhere else and reference as a lib? Thanks for any clarification.. – TheJeff Nov 17 '20 at 20:45
  • I'm getting AJC compiler errors:error no sources specified. Any reason for this error? – Lakmal Jan 17 '21 at 06:35
  • @Lakmal because this answer is wrong, it's specifically excluding all sources from compile time weaving which means, for example your aspects in your source code aren't being processed. – CodeMonkey May 28 '21 at 21:42
4

Use delombok to generate normal source code. And then proceed as you would if Lombok were not being used.

Store your Lombok-annotated code in main/src/lombok (for example) and then have the delombok plugin convert these annotations into normal code and into the directory /delomboked (for example).

Alok P
  • 994
  • 1
  • 9
  • 18
3

I tried various solutions, finally specifying the javac compiler option like the below one worked enter image description here

ernitingoel
  • 621
  • 2
  • 9
  • 24
  • I don't think you are actually weaving if you switch back to `javac` – Ghilteras Feb 26 '19 at 21:19
  • 2
    @Ghilteras I actually found another solution for this without switching to javac. Assume you are using Intellij as well. Go to File > Project Structure > Modules >AspectJ, check the option: Post-compile weave mode. It should work properly. – Jay Cui Feb 27 '19 at 07:36
0

This works for me with command line mvn clean install, but in Eclipse IDE, the problem is not solved, eg. log is not correctly recognized for @Slf4j.

<plugin>
            <groupId>org.codehaus.mojo</groupId>
            <artifactId>aspectj-maven-plugin</artifactId>
            <version>1.10</version>
            <configuration>
                <verbose>true</verbose>
                <showWeaveInfo>true</showWeaveInfo>
                <source>1.7</source>
                <target>1.7</target>
                <complianceLevel>1.7</complianceLevel>
                <!-- <encoding>UTF-8</encoding> -->
                <verbose>false</verbose>
                <Xlint>ignore</Xlint>
                <outxml>true</outxml>
                <forceAjcCompile>true</forceAjcCompile>
                <reweavable>false</reweavable>
                <aspectLibraries>
                    <aspectLibrary> 
                        <groupId>com.aspectj.library.yours</groupId>
                        <artifactId>your-library</artifactId>
                    </aspectLibrary>
                </aspectLibraries>
                <!-- this is important: start-->
                <sources/>
                <weaveDirectories>
                    <weaveDirectory>${project.build.directory}/classes</weaveDirectory>
                </weaveDirectories>
                <!-- this is important: end-->
            </configuration>
            <executions>
                <execution>
                    <!-- The right phase is very important! Compile and weave aspects after all classes compiled by javac -->
                    <phase>process-classes</phase>
                    <goals>
                        <goal>compile</goal>
                    </goals>
                </execution>
            </executions>
            <dependencies>
                <dependency>
                    <groupId>org.aspectj</groupId>
                    <artifactId>aspectjweaver</artifactId>
                    <version>1.8.9</version>
                </dependency>
                <dependency>
                    <groupId>org.aspectj</groupId>
                    <artifactId>aspectjtools</artifactId>
                    <version>1.8.9</version>
                </dependency>
            </dependencies>
        </plugin>
Miroslav Glamuzina
  • 4,472
  • 2
  • 19
  • 33
Ivan
  • 9
  • 3
0

I had a configuration/excludes/exclude section with the spring-boot-maven-plugin where the "aspectjweaver" dependency had been declared. The exclude section had "org.projectlombok" in it, and looks like that's why none of my lombok annotations were being processed while building using "mvn clean install"

I initially had this:

<plugin>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-maven-plugin</artifactId>
    <dependencies>
        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>${aspectj.version}</version>
        </dependency>
    </dependencies>
    <configuration>
        <excludes> <!------- THIS IS WHERE my problem started by exluding lombok -->
            <exclude>
                <groupId>org.projectlombok</groupId>
                <artifactId>lombok</artifactId>
            </exclude>
        </excludes>
    </configuration>
</plugin>

When I removed the excludes part, then the build started taking the lombok annotations and worked. This is my section now:

<plugin>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-maven-plugin</artifactId>
    <dependencies>
        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <version>${aspectj.version}</version>
        </dependency>
    </dependencies>
</plugin>
0

SpringBoot AND Java: 16

At this moment (19-11-2022) aspectJ plugin not support 17

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>2.7.5</version>
        <relativePath/>
   </parent>
   
   ...
   YOUR GROUP, ARTIFACT NAME, VERSION ETC HERE
   ...

   <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
        <dependency>
            <groupId>org.aspectj</groupId>
            <artifactId>aspectjweaver</artifactId>
            <scope>compile</scope>
        </dependency>
      
        <dependency>
            <groupId>org.projectlombok</groupId>
            <artifactId>lombok</artifactId>
            <version>1.18.24</version>
        </dependency>

        <dependency>
            <groupId>kkl.lib.dev.tools</groupId>
            <artifactId>lib-dev-tools</artifactId>
            <version>1.0-SNAPSHOT</version>
        </dependency>

    </dependencies>

    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
                <configuration>
                    <excludes>
                        <exclude>
                            <groupId>org.projectlombok</groupId>
                            <artifactId>lombok</artifactId>
                        </exclude>
                    </excludes>
                </configuration>
            </plugin>

            <plugin>
                <groupId>org.codehaus.mojo</groupId>
                <artifactId>aspectj-maven-plugin</artifactId>
                <version>1.14.0</version>
                <configuration>
                    <showWeaveInfo/>
                    <sources/>
                    <weaveDirectories>
                        <weaveDirectory>${project.build.directory}/classes</weaveDirectory>
                    </weaveDirectories>
                    <forceAjcCompile>true</forceAjcCompile>
                    <source>16</source>
                    <target>16</target>
                    <proc>none</proc>
                    <complianceLevel>16</complianceLevel>
                </configuration>
                <executions>
                    <execution>
                        <phase>process-classes</phase>
                        <goals>
                            <goal>compile</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>
        </plugins>
        
    </build>

Krzysztof
  • 1,861
  • 4
  • 22
  • 33
0

After reseach and testing all day, here is my success build.

Main idea is using javac to compile code first (compliance with lombok) and after that use aspectj only for weaving class.

<build>
        <extensions>
            <extension>
                <groupId>kr.motd.maven</groupId>
                <artifactId>os-maven-plugin</artifactId>
                <version>1.6.1</version>
            </extension>
        </extensions>
        <plugins>
            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-antrun-plugin</artifactId>
                <version>1.8</version>
                <executions>
                    <execution>
                        <id>unwovenClassesFolder</id>
                        <phase>generate-resources</phase>
                        <configuration>
                            <tasks>
                                <delete dir="${project.build.directory}/unwoven-classes"/>
                                <mkdir dir="${project.build.directory}/unwoven-classes"/>
                            </tasks>
                        </configuration>
                        <goals>
                            <goal>run</goal>
                        </goals>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-compiler-plugin</artifactId>
                <version>3.1</version>
                <executions>
                    <execution>
                        <!-- Modifying output directory of default compile because non-weaved classes must be stored
                             in separate folder to not confuse ajc by reweaving already woven classes (which leads to
                             to ajc error message like "bad weaverState.Kind: -115") -->
                        <id>default-compile</id>
                        <configuration>
                            <source>16</source>
                            <target>16</target>
                            <outputDirectory>${project.build.directory}/unwoven-classes</outputDirectory>
                        </configuration>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <groupId>org.codehaus.mojo</groupId>
                <artifactId>aspectj-maven-plugin</artifactId>
                <version>1.14.0</version>

                <dependencies>
                    <dependency>
                        <groupId>org.aspectj</groupId>
                        <artifactId>aspectjtools</artifactId>
                        <version>${aspectj.version}</version>
                    </dependency>
                </dependencies>

                <configuration>
                    <showWeaveInfo>true</showWeaveInfo>
                    <verbose>true</verbose>
                    <Xlint>ignore</Xlint>
                    <encoding>UTF-8</encoding>
                    <weaveDirectories>
                        <weaveDirectory>${project.build.directory}/unwoven-classes</weaveDirectory>
                    </weaveDirectories>
                    <!-- IMPORTANT-->
                    <excludes>
                        <exclude>**/*.java</exclude>
                    </excludes>
                    <forceAjcCompile>true</forceAjcCompile>
                    <sources/>
                    <!-- IMPORTANT-->
                    <complianceLevel>16</complianceLevel>
                    <source>16</source>
                    <target>16</target>
                </configuration>
                <executions>
                    <execution>
                        <!-- Compile and weave aspects after all classes compiled by javac -->
                        <phase>process-classes</phase>
                        <goals>
                            <goal>compile</goal>
                        </goals>
                        <configuration>
                            <complianceLevel>16</complianceLevel>
                        </configuration>
                    </execution>
                </executions>
            </plugin>

            <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-surefire-plugin</artifactId>
                <version>2.22.2</version>
            </plugin>
        </plugins>
    </build>
MashiMaro
  • 39
  • 7