2017-04-07 31 views
0

我刚开始使用Checker Framework,并且存在一个问题,该问题完全可以在此框架作者的示例项目之一上重现。该项目可以在这里找到: https://github.com/typetools/checker-framework/tree/master/docs/examples/GradleExamples如何在检查器框架中显示完整的编译错误消息信息使用行号等

当我从root身份运行此命令:

>gradle compileJava 

我收到此编译输出:

 public static /*@Nullable*/ Object nullable = null; 
               ^

    required: @Initialized @NonNull Object 

     list.add(null); // error on this line 
       ^

    required: @Initialized @NonNull String 
2 errors 
:compileJava FAILED 

正如你可以看到,没有任何信息在那里发生错误,如类名,代码中的行号等。 我在他们的官方手册中找不到任何有关可以适当更改输出格式的编译器参数的信息。我要的错误信息是这样的:

~\GradleExample.java:33 error: ';' expected 

UPDATE:

我上实现3台这种行为:

    • 操作系统:Microsoft Windows 7 64位旗舰版SP1 [版本6.1.7601];
    • Java:1.8.0_73;
    • Gradle:2.14。
    • 操作系统:Microsoft Windows 10的x64 Pro的[版本10.0.14393]
    • Java:1.8.0_121;
    • Gradle:3.4.1。
    • 操作系统:Microsoft Windows 7 64位旗舰版SP1 [版本6.1.7601]
    • Java:1.8.0_121;
    • Gradle:3.4.1。

缺少行号和类名与摇篮运行时,只有经历。我也尝试从Maven和命令行运行Javac来运行检查器,并且它运行得非常完美。
使用Gradle i配置Checker Framework遵循手动步骤。有3个步骤:

  1. 下载框架;
  2. 将其解压缩以创建检查器框架目录;
  3. 将Gradle配置为在类路径中包含Checker Framework。

据我所知,当通过依赖关系管理提供所需的Checker Framework的罐子时,Gradle会自动执行步骤1和步骤2。不过我想这两个选项:

  1. 依赖管理:
    我只是下载示例项目,并从GradleJava7Example项目的根 执行“gradle这个compileJava”。
  2. 在gradle这个build文件手工编写的路径:
allprojects { 

     tasks.withType(JavaCompile).all { JavaCompile compile -> 

      compile.options.compilerArgs = [ 
      '-processor', 'org.checkerframework.checker.nullness.NullnessChecker', 
      '-processorpath', "C:\\checker-framework-2.1.10\\checker\\dist\\checker.jar", 
      "-Xbootclasspath/p:C:\\checker-framework-2.1.10\\checker\\dist\\jdk8.jar", 
      '-classpath', 'C:\\checker-framework-2.1.10\\checker\\dist\\checker.jar;C:\\checker-framework-2.1.10\\checker\\dist\\javac.jar' 
      ] 
     } 
    } 
+0

我无法重现您的问题。当我尝试这个例子时,输出包含了行号。你能提供更多细节吗?什么操作系统,什么版本的Java,什么版本的gradle,你使用GradleJava7Example还是GradleJava8Example,你使用Checker Framework发行版还是从GitHub等中克隆它?请给出一个完整的配方来重现问题,最好从安装Checker框架开始。然后其他人可以帮助你。 – mernst

回答

0

我已经找到了解决办法。以后我会解释,但现在如果有人有同样的问题,该行添加到您JavaCompile任务配置:

所有的
allprojects { 
    tasks.withType(JavaCompile).all { JavaCompile compile -> 

     System.setProperty("line.separator", "\n") // <<<<<< add this line 

     compile.options.compilerArgs = [ 
      '-processor', 'org.checkerframework.checker.nullness.NullnessChecker', 
      '-processorpath', "${configurations.checkerFramework.asPath}", 
      "-Xbootclasspath/p:${configurations.checkerFrameworkAnnotatedJDK.asPath}" 
     ] 
    } 
} 

首先我必须说,这个问题是不是在检查框架在所有。我设法重现了与没有Checker Framework的问题中提到的相同的行为。我创建了一个小的自定义注释处理器。这里是代码:

@SupportedSourceVersion(value = SourceVersion.RELEASE_8) 
@SupportedAnnotationTypes(value = {"*"}) 
public class MyProcessor extends AbstractProcessor{ 

    @Override 
    public boolean process(Set<? extends TypeElement> annotations, RoundEnvironment roundEnv) { 
     String sepr = System.getProperty("line.separator"); 

     processingEnv.getMessager().printMessage(Diagnostic.Kind.ERROR, "[error code] " + sepr + " catched!!!"); 

     return true; 
    } 

} 

正如你所看到的,它所做的一切就是马上打印一条消息。请注意,我使用java.lang.System类提供的行分隔符来拆分消息。当我注册了这个处理器,并试图运行“gradle这个compileJava”的gradle从项目它产生的输出如下:

:compileJava 

    catched!!! 

1 error 
:compileJava FAILED 

属性“line.separator”针对Windows操作系统返回CR + LF:“\ r \ n” 。我不知道为什么Messager.printMessage(Diagnostic.Kind kind, CharSequence msg)有这种行为,因为当我键入System.err.print("[error code] " + sepr + " catched!!!")而不是,一切工作正常(也注意到,这个问题只发生在我使用Gradle,如果我手动运行所有参数的javac或使用Maven everyting罚款)。
我发现如果我使用简单的“\ n”符号代替系统分隔符提供的编译器错误消息显示正确。 现在我选择此解决方案作为解决方法。

相关问题