android studio中配置代码检查-CheckStyle

本文介绍如何使用CheckStyle插件自动化检查Java代码规范,包括配置方法、常见问题及解决策略。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

为了规范编码,使用到了CheckStyle

CheckStyle的主要功能就是实时检测,代码的规范(Code Style)是否符合我们规定的一个模板,如代码和括号之间没有空格, 类中导入的包没有使用等,当发现这些不符合这些规范时,它就报一个警告或者错误等提示,导致编译不通过。

CheckStyle检验的主要内容

  1. Javadoc注释
  2. 命名约定
  3. 标题
  4. Import语句
  5. 体积大小
  6. 空白
  7. 修饰符
  8. 代码问题
  9. 类设计
  10. 混合检查(包活一些有用的比如非必须的System.out和printstackTrace)

那么,怎么使用代码检测呢?

checkstyle帮助开发者实现常用JAVA代码规范的自动化检查。它的功能比较丰富,相对配置起来比较复杂,你需要根据自己的需求配置你想检查的东西,比如Annotations,Block Checks,Class Design,Coding,Duplicate Code,Headers,Imports,Javadoc Comments,Metrics,Miscellaneous,Modifiers,Naming Conventions,Regexp,Size Violations,Whitespace。

在Android开发中,也需要我们去定义,Android Studio继承了IDEA的可拓展特性,它也拥有CheckStyle的插件,在Android项目中,使用的Gradle配置。

一、自定义checkstyle插件的check.gradle

/*
 * 检查代码规范
 */

apply plugin: 'checkstyle'

//设置CheckStyle版本
checkstyle {
    ignoreFailures = false
    showViolations true
    toolVersion '8.0'
}

//设置配置文件
task checkstyle(type: Checkstyle) {
    description 'Check code standard'
    group 'verification'

    configFile file("${project.rootDir}/buildConfig/checkstyle.xml")
    source 'src'
    include '**/*.java'
    exclude '**/gen/**'
    exclude '**/test/**'
    exclude '**/androidTest/**'

    classpath = files()
}

// 每次编绎时都进行checkstyle检测
project.afterEvaluate {
    preBuild.dependsOn 'checkstyle'
}

 

二、设置配置文件checkstyle.xml,定义我们想要校验的内容

<?xml version="1.0" encoding="UTF-8"?><!DOCTYPE module PUBLIC
    "-//Puppy Crawl//DTD Check Configuration 1.3//EN"
    "http://checkstyle.sourceforge.net/dtds/configuration_1_3.dtd">

<module name="Checker">
    <!-- 更多配置情况参见: http://blog.youkuaiyun.com/yang1982_0907/article/details/18086693 -->

    <property name="charset" value="UTF-8" />
    <property name="severity" value="error" />

    <!-- Checks for Size Violations.  -->
    <!-- 检查文件的长度(行) default max=2500 -->
    <module name="FileLength">
        <property name="max" value="3000" />
        <property name="severity" value="warning" />
    </module>

    <!-- 检查源码中没有制表符('\t') -->
    <module name="FileTabCharacter">
        <property name="eachLine" value="true" />
    </module>

    <module name="TreeWalker">
        <module name="SuppressWarningsHolder" />
        <!--空格检测-->
        <module name="WhitespaceAround">
            <property name="allowEmptyConstructors" value="true" />
            <property name="allowEmptyMethods" value="true" />
            <property name="allowEmptyTypes" value="true" />
            <property name="allowEmptyLoops" value="true" />
            <message key="ws.notFollowed"
                value="WhitespaceAround: ''{0}'' is not followed by whitespace." />
            <message key="ws.notPreceded"
                value="WhitespaceAround: ''{0}'' is not preceded with whitespace." />
        </module>

        <module name="GenericWhitespace">
            <message key="ws.followed"
                value="GenericWhitespace ''{0}'' is followed by whitespace." />
            <message key="ws.preceded"
                value="GenericWhitespace ''{0}'' is preceded with whitespace." />
            <message key="ws.illegalFollow"
                value="GenericWhitespace ''{0}'' should followed by whitespace." />
            <message key="ws.notPreceded"
                value="GenericWhitespace ''{0}'' is not preceded with whitespace." />
        </module>

        <!-- Checks for imports    -->
        <!-- 必须导入类的完整路径,即不能使用*导入所需的类 -->
        <module name="AvoidStarImport" />

        <!-- 检查是否从非法的包中导入了类 illegalPkgs: 定义非法的包名称-->
        <module name="IllegalImport" /> <!-- defaults to sun.* packages -->

        <!-- 检查是否导入了不必显示导入的类-->
        <module name="RedundantImport" />

        <!-- 检查是否导入的包没有使用-->
        <module name="UnusedImports" />

        <!-- 检查代码块的左花括号的放置位置 -->
        <module name="LeftCurly">
            <property name="option" value="eol" />
        </module>

        <!--检查代码块周围是否有大括号,可以检查do、else、if、for、while等关键字所控制的代码块-->
        <module name="NeedBraces">
            <property name="tokens"
                value="LITERAL_DO, LITERAL_ELSE, LITERAL_FOR, LITERAL_WHILE" /> <!-- LITERAL_IF 不检测-->
            <property name="allowSingleLineStatement" value="true" />
        </module>

        <!--检查else、try、catch标记的代码块的右花括号的放置位置-->
        <module name="RightCurly">
            <property name="id" value="RightCurlySame" />
            <property name="tokens"
                value="LITERAL_TRY, LITERAL_CATCH, LITERAL_FINALLY, LITERAL_IF, LITERAL_ELSE, LITERAL_DO" />
        </module>

        <module name="RightCurly">
            <property name="id" value="RightCurlyAlone" />
            <property name="option" value="alone" />
            <property name="tokens"
                value="CLASS_DEF, METHOD_DEF, CTOR_DEF, LITERAL_FOR, LITERAL_WHILE, STATIC_INIT, INSTANCE_INIT" />
        </module>

        <!-- 检查在重写了equals方法后是否重写了hashCode方法 -->
        <module name="EqualsHashCode" />

        <!--检查是否有不合法的实例化操作,是否使用工厂方法更好-->
        <module name="IllegalInstantiation">
            <property name="classes" value="java.lang.Boolean" />
        </module>

        <!--检查Java代码的缩进是否正确-->
        <module name="Indentation">
            <property name="arrayInitIndent" value="8" />
        </module>

        <module name="SimplifyBooleanExpression" />

        <module name="SimplifyBooleanReturn" />

        <!--检查每个变量是否使用一行一条语句进行声明-->
        <!--<module name="MultipleVariableDeclarations" />-->

        <!--检查数组定义的风格,默认java风格-->
        <module name="ArrayTypeStyle" />

        <!--检查long类型的常量在定义时是否由大写的“L”开头-->
        <module name="UpperEll" />

        <!--检查switch中case后是否加入了跳出语句,例如:return、break、throw、continue -->
        <module name="FallThrough" />

        <!-- Checks the number of parameters of a method or constructor. max default 7个. -->
        <module name="ParameterNumber">
            <property name="max" value="19" />
        </module>

        <!-- 每行字符数 -->
        <module name="LineLength">
            <property name="max" value="250" />
        </module>

        <!-- Checks for long methods and constructors. max default 150行. max=300 设置长度300 -->
        <module name="MethodLength">
            <property name="max" value="200" />
        </module>

        <!-- ModifierOrder 检查修饰符的顺序,默认是 public,protected,private,abstract,static,final,transient,volatile,synchronized,native -->
        <module name="ModifierOrder" />

        <!-- 检查是否有多余的修饰符,例如:接口中的方法不必使用public、abstract修饰  -->
        <!--<module name="RedundantModifier">-->
        <!--</module>-->

        <!--- 字符串比较必须使用 equals() -->
        <module name="StringLiteralEquality" />

        <!--限制try代码块的嵌套层数(默认值为1)-->
        <module name="NestedTryDepth">
            <property name="max" value="2" />
        </module>

        <!-- 返回个数 -->
        <module name="ReturnCount">
            <property name="max" value="15" />
            <property name="maxForVoid" value="15" />
            <property name="format" value="^$" />
        </module>

    </module>

</module>

三、在项目中引入check.gradle即可。我将其引入到app的build.gradle中

//代码检查checkstyle
apply from: '../buildConfig/check.gradle'

编译

然后,根据错误提示,找到对应的错误,修复即可。

代码检测的使用就这样了。

 

》》》有可能会遇到的问题

一、Unexpected character 0xfeff in identifier

Caused by: F:\project\work\AppFleet_Android\app\src\main\java\com\fleet\statistics\StatisticsUtil.java:1:1: Unexpected character 0xfeff in identifier
	at com.puppycrawl.tools.checkstyle.grammars.GeneratedJavaLexer.nextToken(GeneratedJavaLexer.java:405)
	at antlr.TokenStreamHiddenTokenFilter.consume(TokenStreamHiddenTokenFilter.java:38)
	at antlr.TokenStreamHiddenTokenFilter.consumeFirst(TokenStreamHiddenTokenFilter.java:42)
	at antlr.TokenStreamHiddenTokenFilter.nextToken(TokenStreamHiddenTokenFilter.java:122)
	at antlr.TokenBuffer.fill(TokenBuffer.java:69)
	at antlr.TokenBuffer.LA(TokenBuffer.java:80)
	at antlr.LLkParser.LA(LLkParser.java:52)
	at com.puppycrawl.tools.checkstyle.grammars.GeneratedJavaRecognizer.compilationUnit(GeneratedJavaRecognizer.java:158)
	at com.puppycrawl.tools.checkstyle.TreeWalker.parse(TreeWalker.java:446)
	at com.puppycrawl.tools.checkstyle.TreeWalker.processFiltered(TreeWalker.java:179)
	... 67 more

这是因为出错的Java文件编码和CheckStyle设置的编码不同。CheckStyle里设置的编码是UTF-8。

而Java文件的编码可以通过编辑器Notepad++打开查看,如下

将Java文件的编码改为UTF-8编码即可,不要带BOM。

 

二、member def modifier

 

就这个类,一直编译不通过,我仔细检查了,没有其他问题啊,但是报的错表示这个类的所有代码都有问题,那我想会不会是代码编码问题,看了一下,都是UTF-8,没问题。既然编码没问题,那会不会是格式的问题。仔细一看,果真,就是格式化的问题。用Ctrl + Shift +F 格式化一下就好了。

 

编码过程中,多使用格式化。

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值