Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Exclude methods annotated with @lombok.Generated #513

Merged
merged 1 commit into from
Apr 3, 2017
Merged

Conversation

marchof
Copy link
Member

@marchof marchof commented Apr 3, 2017

This is a follow-up for #495 to migrate @t1 's work to the new filtering APIs.

@marchof marchof self-assigned this Apr 3, 2017
marchof added a commit that referenced this pull request Apr 3, 2017
Based in initial contribution by Rüdiger zu Dohna.
@Godin Godin added this to the 0.7.10 milestone Apr 3, 2017
* http://www.eclipse.org/legal/epl-v10.html
*
* Contributors:
* Rüdiger zu Dohna - initial API and implementation
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof even if initial analysis wasn't done by you, all code of this PR was entirely written by you, so I believe this line should be changed - anyway there will be credits in changelog

@Test
public void testLombokGeneratedAnnotation() {
final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION,
Opcodes.ACC_SYNTHETIC, "lambda$1", "()V", null, null);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof synthetic access flag and name of lambda are unrelated to this test, so I believe that for clarity should be changed. Name can be changed for example on hashCode as one of examples of methods that Lombok generates. Can be changed for the all test cases.

}

private boolean hasLombokGeneratedAnnotation(final MethodNode methodNode) {
final List<AnnotationNode> list = methodNode.invisibleAnnotations;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof I'd prefer to name local variable invisibleAnnotations or even better runtimeInvisibleAnnotations instead of just list

@@ -28,6 +28,9 @@
<li>Exclude from a report a part of bytecode that compiler generates for a
synchronized statement
(GitHub <a href="https://github.com/jacoco/jacoco/issues/501">#501</a>).</li>
<li>Exclude methods generated by Lombok. Initial analysis and contribution by
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof I'd prefer to be more explicit here and state that

  1. they are excluded from report - to avoid confusion with exclusion from instrumentation
  2. only methods annotated with lombok.Generated are excluded - because annotation can be turned off

For consistency with previous changelog entries - we don't put dot before opening parenthesis.

So something like:

Exclude from a report methods annotated by <code>lombok.Generated</code>,
initial analysis contributed by Rüdiger zu Dohna (GitHub ...).

import org.objectweb.asm.tree.MethodNode;

/**
* Filter for methods generated by Lombok which are annotated with
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof for consistency with existing filters, I'd prefer to change on

Filters methods annotated with <code>@lombok.Generated</code>.

@Test
public void testOtherAnnotation() {
final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION,
Opcodes.ACC_SYNTHETIC, "name", "()V", null, null);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof synthetic access flag is unrelated to this test, so I'd prefer to remove it

m.visitInsn(Opcodes.RETURN);

AnnotationNode a = new AnnotationNode("Llombok/Generated;");
m.invisibleAnnotations = Arrays.asList(a);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@marchof maybe simply

m.visitAnnotation("Llombok/Generated;", false);

?

marchof added a commit that referenced this pull request Apr 3, 2017
Based on initial contribution by Rüdiger zu Dohna.
@marchof
Copy link
Member Author

marchof commented Apr 3, 2017

@Godin thx for the review! Hopefully fixed all issues.

Based on initial contribution by Rüdiger zu Dohna.
@Godin
Copy link
Member

Godin commented Apr 3, 2017

End-to-end test - example.zip

Without this change using JaCoCo 0.7.9 :

before-methods

before-source

After this change :

after-methods

after-source

@Godin Godin merged commit 7f719c8 into master Apr 3, 2017
@Godin Godin deleted the issue-513 branch April 3, 2017 15:04
@MichaelZett
Copy link

Hi, nice one. I'd like to try this out. I let lombok generate "lombok.Generated" and use the jacoco-agent with gradle. I tried the snapshot from 20170404 (-17) and it does not seem to be in there. Or do I have to configure jacoco somehow?

@marchof
Copy link
Member Author

marchof commented Apr 6, 2017

@MichaelZett I just double checked the latest snaphot (from 20170404 on) has this feature. Are you sure you're using the latest version of Lombok? The @Generated annotation has been introduced recently in version 1.16.14.

@t1
Copy link

t1 commented Apr 7, 2017

Works fine. Big thanks!

When I first looked at the code, I thought it might not work when there are other annotations next to @lombok.Generated. Something like:

    @lombok.Getter(onMethod_ = { @javax.xml.bind.annotation.XmlAttribute(name = "bar") })
    private String foo;

But it does work ;-)

Is it foreseeable when this may get released?

@MichaelZett
Copy link

@marchof yes, Lombok annotation is generated. I checked with delombok. Do I have to configure the filters to use? Does anyone has checked it with gradle (3.4.1)? Gradle uses the jacoco agent lib.

@Godin
Copy link
Member

Godin commented Apr 7, 2017

@MichaelZett here is an example with Gradle that works just perfectly - example.zip

@Godin
Copy link
Member

Godin commented Apr 7, 2017

@t1

Is it foreseeable when this may get released?

please be patient and give us some time to first finish some other filters. Thank you for your understanding.

@t1
Copy link

t1 commented Apr 8, 2017

@Godin

please be patient and give us some time to first finish some other filters.

Am I wrong to assume that this may take quite a while, as most of those filters are much harder to build than @lombok.Generated? How much work is it to build a release? I understand that also users might be annoyed by too many releases... at least I am annoyed by too many releases of Mockito ;-)... so this has to be taken into account, but I also have the need to get coverage reports that are expressive. We heavily rely on Lombok and often see coverage as low as 30% in DTO packages. We hardly look at the coverage there. If we had this fix, we would get up to maybe 90%, which already would help us greatly in seeing and then focussing on the important parts. The last 10% also would be cool, but they won't stop us from looking at the coverage.

I don't like the alternative to internally release a fork.

@BeneStem
Copy link

BeneStem commented Apr 9, 2017

@Godin @t1 We would love to have this feature released as soon as possible as well.

Thank you all for the great work. We will be patient and wait :)

For now we will be using the SNAPSHOT version. It is working great!

@Godin
Copy link
Member

Godin commented Apr 10, 2017

@t1

Am I wrong to assume that this may take quite a while, as most of those filters are much harder to build than @lombok.Generated?

Filters for synchronized statement and methods in enums are already in master - see eaef191 and e94c7af respectively. We're finalizing filters for try-with-resources statement and String in switch statement in PRs #500 and #496 respectively. From here IMO we'd better finish current work than do two releases within short timeframe. So please be a bit patient.

@MichaelZett
Copy link

@Godin Thanks for the zip. When I take this and run gradlew clean build, it produces the attached test.exec. When I look at this in intellij or sonarqube it shows still 4 missed lines. What could be the problem?
test.exec.tar.gz

@Godin
Copy link
Member

Godin commented Apr 11, 2017

@MichaelZett filtering is performed at a time of report generation (creation of html, xml, etc), not at a time of collection of execution information (creation of exec file). So that tools that read execution data directly instead of reading of xml (which is a kind of mistake on their side to rely on purely internal intermediate format, but what's done is done) and create their own report (such as SonarQube, Jenkins, etc) will need to update their dependency on JaCoCo once it will be released in order to get filtering for reports. We will notify explicitly downstream projects (in particular all mentioned above) about this when our release will be done. So once again - please be patient. Thank you for your understanding.

@Godin
Copy link
Member

Godin commented Apr 11, 2017

@MichaelZett also should be mentioned that reports produced by JaCoCo Gradle Plugin (in build/reports/jacoco/test/html/ after gradle clean test jacocoTestReport) and JaCoCo Maven Plugin (in target/site/jacoco/ after mvn clean verify) in the given examples do have filtering because they already use snapshot version of JaCoCo.

@MichaelZett
Copy link

@Godin I see, thanks. Will be waiting.

@t1
Copy link

t1 commented Apr 11, 2017

@Godin : I'll be patient... but I feel a little like a child before christmas ;-)

@tenleo
Copy link

tenleo commented Apr 14, 2017

I have successfully used the snapshot build to exclude Lombok generated code. The generated report works nicely now, thanks for this update.

Just curious though: on individual maven projects it works fine, but I have trouble generating an aggregated report for a multi-module Maven project. The reports in each module look fine, but the aggregated report is empty. Has anyone else had this issue?

Maybe its a configuration fault on my side, this is what I added to my root pom:

<plugin>

	<groupId>org.jacoco</groupId>

	<artifactId>jacoco-maven-plugin</artifactId>
	<version>0.7.10-SNAPSHOT</version>
	<configuration>
		<destFile>${project.basedir}/../target/jacoco.exec</destFile>
		<append>true</append>
	</configuration>
	<executions>
		<execution>
			<id>default-prepare-agent</id>
			<goals>
				<goal>prepare-agent</goal>
			</goals>
		</execution>
		<execution>
			<id>report-aggregate</id>
			<phase>prepare-package</phase>
			<goals>
				<goal>report-aggregate</goal>
			</goals>
		</execution>
		<execution>
			<id>default-check</id>
			<goals>
				<goal>check</goal>
			</goals>
			<configuration>
				<rules/>
			</configuration>
		</execution>
	</executions>
</plugin>

@marchof
Copy link
Member Author

marchof commented Apr 14, 2017

@tenleo Thanks for your feedback! Aggregate reports work differently. Please see documentation. You need to specify a separate module which defined the content of the report. As this is a completely different issue please use our mailing list for further questions.

@sir4ur0n
Copy link

Hi guys,

I'm curious, did anyone make it work with SonarQube?
I seem to have a clean JaCoCo report with the latest snapshot (0.7.10-SNAPSHOT) when I look at ./target/site/jacoco/index.html report.
However the report in SonarQube is completely different: different code coverage (a lot less), different values for metrics like Complexity, Lines of code, etc...

Is it just me?
I even tried with the tiny example project provided by @Godin on the 2017-04-03 (I wrote one test method covering one stupid method doing a System.out.println for the sake of having one test) and then published in my SonarQube, and the results are massively different.

I created a small github project to ease reproduction of the issue: https://github.com/Sir4ur0n/example-jacoco-lombok-sonarqube

Here's the JaCoCo report:
image
image
Here's the SonarQube report:
image

Any help or pointer on what's wrong would be greatly appreciated :(

@Godin
Copy link
Member

Godin commented Apr 21, 2017

@sir4ur0n please read carefully comments in this thread prior to yours, in particular - #513 (comment)

@sir4ur0n
Copy link

@Godin Thanks, I had completely missed this comment :'(

@charlesritchea
Copy link

charlesritchea commented Jun 30, 2017

Do we have an ETA on when 0.7.10 will be released? I couldn't find a release schedule anywhere. Asking specifically for this fix.

@Godin
Copy link
Member

Godin commented Jun 30, 2017

@novaterata please read already existing answers on such question:
https://groups.google.com/forum/#!msg/jacoco/gd8xD30TDNo/SHj-hEq1AAAJ
https://groups.google.com/forum/#!msg/jacoco/-MmsVzC6szM/Q9sPTbAeBAAJ
and in few words - no exact ETA, but as soon as it will be fully ready.
So please be patient and thank you for your understanding.

@charlesritchea
Copy link

@Godin Thank you, I didn't know where to even look

@Elena6789
Copy link

Is the filter out of lombok supported already in a released version of JaCoCo?Thanks

@charlesritchea
Copy link

charlesritchea commented Jul 3, 2017 via email

@Glamdring
Copy link

I tried using the latest snapshot, but the report generated in target/site includes the equals(..) method. Has anything changed? Are there specific configurations that one has to enable?

@Godin
Copy link
Member

Godin commented Jul 18, 2017

@Glamdring please read this thread carefully from the beginning - in particular there is full end-to-end example with all the required configuration on Lombok side in #513 (comment)

@Glamdring
Copy link

@Godin apologies for overlooking that, thanks.

@miualinionut
Copy link

Guys, I am waiting for about 4 months for this feature. Can you please give a DL when will this feature be released ?

@t1
Copy link

t1 commented Aug 1, 2017

@miualinionut: I guess it's done when it's done. That's the way open source projects work when they are driven by people spending their spare time.

@Godin: I'd rather request an intermediate release of the things that already work instead of waiting until everything is complete. Would that be possible?

@charlesritchea
Copy link

@t1 you can use the snapshot build. There is a repository you can add https://oss.sonatype.org/content/repositories/snapshots then the snapshot version should be available via maven dependencies

@MAGGGG
Copy link

MAGGGG commented Aug 2, 2017

Hello everyone ...
Same question like earlier. When 0.7.10 will be released ?
Waiting for this features:

@uzonyib
Copy link

uzonyib commented Nov 8, 2017

Hi, is there an ETA for the release of this feature?

@marchof
Copy link
Member Author

marchof commented Nov 8, 2017

@uzonyib See #513 (comment)

@jacoco jacoco locked and limited conversation to collaborators Nov 8, 2017
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
Status: Done
Development

Successfully merging this pull request may close these issues.

None yet