-->

How to suppress Java warnings for specific directo

2019-01-10 05:25发布

问题:

I'm using a parser generator that creates somewhat ugly code. As a result my Eclipse project has several dozen warnings emanating from generated source files. I know I can use the @SuppressWarning annotation to suppress particular warnings in particular elements, but any annotations I add by hand will be lost when the parser generator runs again. Is there a way to configure Eclipse to suppress warnings for a particular file or directory?

回答1:

Starting with version 3.8 M6, Eclipse (to be exact: the JDT) has built-in functionality for this. It is configurable through a project's build path: Project properties > Java Build Path > Compiler > Source

Announced here: Eclipse 3.8 and 4.2 M6 - New and Noteworthy, called Selectively ignore errors/warnings from source folders. That's also where the screenshot is from. This is the new feature developed on the previously linked Bug 220928.



回答2:

There is a ticket for this, Bug 220928, that has since been completed for Eclipse 3.8. Please see this answer for details.

If you're stuck with Eclipse 3.7 or lower: The user "Marc" commenting on that ticket created (or at least links to) a plugin called 'warningcleaner' in comment 35. I'm using that with a lot of success while waiting for this feature to be integrated into Eclipse.

It's really quite simple:

  1. Install plugin.
  2. Right-click project and select "Add/remove generated code nature".
  3. Open the project settings (right-click and select "properties").
  4. Open the tab 'Warning Cleaner'.
  5. Select the source folders you want to ignore the warnings from.



回答3:

I solved this by using the maven regexp replace plugin - it does not solve the cause, but heals the pain:

<plugin>
  <groupId>com.google.code.maven-replacer-plugin</groupId>
  <artifactId>maven-replacer-plugin</artifactId>
  <version>1.3.2</version>
  <executions>
<execution>
  <phase>prepare-package</phase>
  <goals>
    <goal>replace</goal>
  </goals>
</execution>
  </executions>
  <configuration>
<includes>
  <include>target/generated-sources/antlr/**/*.java</include>
</includes>

<regex>true</regex>
<regexFlags>
  <regexFlag>MULTILINE</regexFlag>
</regexFlags>

<replacements>
  <replacement>
    <token>^public class</token>
    <value>@SuppressWarnings("all") public class</value>
  </replacement>
</replacements>
  </configuration>
</plugin>

Note that I did not manage to get the ** notation to work, so you might have to specify path exactly.

See comment below for an improvement on how not to generate duplicate @SupressWarnings



回答4:

I think the best you can do is enable project specific settings for displaying warnings.

Window -> Preferences -> Java -> Compiler -> Errors/Warnings

On the top of the form is a link for configuring project specific settings.



回答5:

User @Jorn hinted at Ant code to do this. Here's what I have

<echo>Adding @SuppressWarnings("all") to ANTLR generated parser/lexer *.java</echo>
<echo> in ${project.build.directory}/generated-sources/antlr/</echo>
<replace dir="${project.build.directory}/generated-sources/antlr/" 
         summary="true" 
         includes="**/*.java" 
         token="public class" 
         value='@SuppressWarnings("all") public class' />

Note that Ant's <replace> does text replacement, not regular expression replacement, so it cannot use the ^ meta-character in the token to match beginning of line as the maven regexp replace plugin does.

I'm doing this at the same time that I run Antlr from maven-antrun-plugin in my Maven pom, because the ANTLR maven plugin did not play well with the Cobertura maven plugin.

(I realize this is not an answer to the original question, but I can't format Ant code in a comment/reply to another answer, only in an answer)



回答6:

I don't think Eclipse inherently provides a way to do this at the directory level (but I'm not sure).

You could have the generated files go into a separate Java project, and control warnings for that specific project.

I generally prefer to place automatically-generated code in a separate project anyway.



回答7:

You can only suppress warnings at the project level. However, you can configure your problems tab to suppress warnings from files or packages. Go into the Configure Contents menu and work with the "On working set:" scope.



回答8:

I'm doing this to a few ANTLR grammars, which generate a Java parser using Ant. The Ant build script adds the @SuppressWarnings("all") to one Java file, and @Override to a few methods in another. I can look up how it's done exactly, if you're interested.



回答9:

This small python script "patches" the M2E-generated .classpath files and adds the required XML tag to all source folders starting with target/generated-sources. You can just run it from you project's root folder. Obviously you need to re-run it when the Eclipse project information is re-generated from M2E. And all at your own risk, obviously ;-)

#!/usr/bin/env python
from xml.dom.minidom import parse
import glob
import os

print('Reading .classpath files...')
for root, dirs, files in os.walk('.'):
    for name in files:
        if (name == '.classpath'):
            classpathFile = os.path.join(root, name)
            print('Patching file:' + classpathFile)
            classpathDOM = parse(classpathFile)
            classPathEntries = classpathDOM.getElementsByTagName('classpathentry')
            for classPathEntry in classPathEntries:
                if classPathEntry.attributes["path"].value.startswith('target/generated-sources'):
                    # ensure that the <attributes> tag exists
                    attributesNode = None;
                    for attributes in classPathEntry.childNodes:
                            if (attributes.nodeName == 'attributes'):
                                attributesNode = attributes

                    if (attributesNode == None):
                        attributesNode = classpathDOM.createElement('attributes')
                        classPathEntry.appendChild(attributesNode)

                    # search if the 'ignore_optional_problems' entry exists
                    hasBeenSet = 0
                    for node in attributesNode.childNodes:
                        if (node.nodeName == 'attribute' and node.getAttribute('name') == 'ignore_optional_problems'):
                            # it exists, make sure its value is true
                            node.setAttribute('value','true')
                            #print(node.getAttribute('name'))
                            hasBeenSet = 1

                    if (not(hasBeenSet)):
                        # it does not exist, add it
                        x = classpathDOM.createElement("attribute")
                        x.setAttribute('name','ignore_optional_problems')
                        x.setAttribute('value','true')
                        attributesNode.appendChild(x)

            try:
                f = open(classpathFile, "w") 
                classpathDOM.writexml(f)
                print('Writing file:' + classpathFile)
            finally:
                f.close()
print('Done.')


回答10:

In the case of ANTLR 2, it is possible to suppress warnings in generated code by appenidng @SuppressWarnings before the class declaration in the grammar file, e.g.

{@SuppressWarnings("all")} class MyBaseParser extends Parser;


回答11:

This can be done by excluding certain directories from the build path (The following example is given using Eclipse 3.5)

[1] Bring up the Java Build Path

  • Click on the projectin Package Explorer
  • Right click, properties
  • Select Java Build Path

[2] Add directories to exclude

  • The Source tab should contain details of the project source folders
  • Expand the source folder and locate the 'Excluded:' property
  • Select 'Excluded:' and click Edit
  • Add folders into the Exclusion patterns using the Add/Add Multiple options
  • Click Finish, then ok for Eclipse to rebuild.


回答12:

It's been a while since I have released the warning-cleaner plugin, and now that I am using Eclipse 3.8, I have no need for it anymore. However, for those who still need this plugin, I have released it on github with the update site on bintray. If you are still using Eclipse 3.7 or before, this could be useful. Check this site for installation details.