OCLint的使用与集成

OCLint的使用与集成

1,通过Homebrew安装

使用命令行

brew tap oclint/formulae
brew install oclint

2,下载安装包安装

1,进入OCLint在Github的地址,选择release,选择最新版本的安装包
2,解压下载文件。将文件存放到一个合适的位置。(比如我选择将这些需要的源代码存放到 Document 目录下)
3,在终端编辑当前环境的配置文件,将 bin 目录添加到 PATH 下,编辑 .bashrc 或
vim .bash_profile
OCLint_PATH=/Users/zjh48/Documents/oclint/build/oclint-release export PATH=$OCLint_PATH/bin:$PATH
或者
vim .zshrc
export PATH="/Users/gyenno/Documents/oclint-22.02/bin:$PATH"

4,将配置文件 source 一下。
source .bash_profile
或者
source .zshrc

5,验证是否安装成功。在终端输入
oclint --version

6,安装xcpretty,需要使用OCLint对日志信息进行分析运行命令,安装xcpretty,使用xcpretty命令分析日志信息。xcpretty是用来格式化xcodebuild输出的工具,使用ruby开发。安装:
gem install xcpretty

3,使用

cd到项目根目录,使用以下命令行

xcodebuild -scheme ZJHAnalyzeDemo -workspace ZJHAnalyzeDemo.xcworkspace clean && xcodebuild -scheme ZJHAnalyzeDemo -workspace ZJHAnalyzeDemo.xcworkspace -configuration Debug | xcpretty -r json-compilation-database -o compile_commands.json

oclint-json-compilation-database -e Pods -- -report-type html -o oclintReport.html

注明:某个文件夹进行分析
oclint-json-compilation-database -i 需要静态分析的文件夹或文件 -- -report-type html -o oclintReport.html 其他的参数

3,报错问题

1,报错:oclint: error: one compiler command contains multiple jobs

1,将 Project 和 Targets 中 Building Settings 下的 COMPILER_INDEX_STORE_ENABLE 设置为 NO

2,在 podfile 中 target ‘xx’ do 前面添加下面的脚本

post_install do |installer|
    installer.pods_project.targets.each do |target|
        target.build_configurations.each do |config|
            config.build_settings['COMPILER_INDEX_STORE_ENABLE'] = "NO"
        end
    end
end

2,报错:oclint: error: violations exceed threshold

看到报错信息是默认的警告数量超过限制,则 lint 失败。事实上 lint 后可以跟参数,所以我们修改脚本如下:
oclint-json-compilation-database -e Pods -- -report-type html -o oclintReport.html -rc LONG_LINE=9999 -max-priority-1=9999 -max-priority-2=9999 -max-priority-3=9999

4,OCLint的规则

1,可以通过 -e 参数忽略指定的文件,比如忽略Pods文件夹:
oclint-json-compilation-database -e Pods -- -o=report.html

2,通过-rc改变检查规则的默认值
比如有一条默认规则:long line [size|P3] Line with 137 characters exceeds limit of 100 ,这表示一个方法里的代码行数不能超过100,可以通过-rc改变默认100行的限制比如改成200行
oclint-json-compilation-database -- -rc=LONG_LINE=200 -o=report.html

3,通过 -disable-rule可以禁止某一规则,比如禁止LongLine长方法检查:
oclint-json-compilation-database -disable-rule=LongLine

4,命令的组合使用,组合的命令使用空格隔开,例如 -e Pods -rc=LONG_LINE=200
oclint-json-compilation-database -e Pods -rc=LONG_LINE=200-- -o=report.html

5,如果需要更改的规则比较多,可以通过.oclint 文件配置规则(暂未找到该文件在哪个地方)
在这里插入图片描述

6,忽略Pods以及第三方文件夹

oclint-json-compilation-database -e Pods -e GyennoMedical/ThirdLibrary -- -report-type html -o oclintReport.html -rc LONG_LINE=9999 -max-priority-1=9999 -max-priority-2=9999 -max-priority-3=9999

7,通过该脚本可以分模块进行检测,例如检测HomeModule

xcodebuild -scheme GyennoMedical -workspace GyennoMedical.xcworkspace clean && xcodebuild -scheme GyennoMedical -workspace GyennoMedical.xcworkspace -configuration Debug | xcpretty -r json-compilation-database -o compile_commands.json && oclint-json-compilation-database -i GyennoMedical/HomeModule -- -report-type  html -o oclintReport.html

5,Xcode脚本使用

1、创建Aggregate项目

OClint 可以和 Xcode IDE 结合,把错误直接在 IDE 中显示出来。首先,我们在项目中创建一个新的 target,然后选择 Aggregate 作为模板。在项目的 TARGETS 下面,点击下方的 “+” ,选择 cross-platform 下面的 Aggregate。输入自定义名字,这里命名为 ZJHLint。注意我们可以建立多个 target,然后分别关注代码分析的多个方面。
在这里插入图片描述

2,添加 Run Script 脚本

选择对应的 TARGET -> ZJHLint。然后在 Build Phases 选项卡中选择 Add Run Script。
在这里插入图片描述

关于脚本的编写我们仍然选择最简单的方式,即 xcodebuild + xcpretty + oclint-json-compilation-database 的方式来做 oclint。脚本如下:

$ cd ${SRCROOT}
$ xcodebuild -scheme ZJHAnalyzeDemo -workspace ZJHAnalyzeDemo.xcworkspace clean && xcodebuild -scheme ZJHAnalyzeDemo -workspace ZJHAnalyzeDemo.xcworkspace -configuration Debug | xcpretty -r json-compilation-database -o compile_commands.json && oclint-json-compilation-database -e Pods -- -report-type Xcode

xcode中持续集成可使用脚本

export LC_CTYPE=en_US.UTF-8
cd ${SRCROOT}
xcodebuild -scheme GyennoMedical -workspace GyennoMedical.xcworkspace clean && xcodebuild -scheme GyennoMedical -workspace GyennoMedical.xcworkspace -configuration Debug | xcpretty -r json-compilation-database -o compile_commands.json && oclint-json-compilation-database -i GyennoMedical/HomeModule -- -report-type xcode

如oclint路径设置使用的是.zshrc,则使用以下命令集成到xcode中

source ~/.zshrc
cd ${PROJECT_DIR}
xcodebuild -scheme VideoTest -workspace VideoTest.xcworkspace clean
xcodebuild -scheme VideoTest -workspace VideoTest.xcworkspace -configuration Debug | xcpretty -r json-compilation-database -o compile_commands.json
oclint-json-compilation-database -e Pods -- -report-type xcode

3,运行Aggregate项目

然后我们就可以开始执行分析了,因为这里我们选择的 report-type 是 xcode,这时 oclint 发现的错误会直接在 IDE 中标示出来,方便我们对代码进行改进。当然这只是一种参考,不一定要采纳 oclint 给的提示。(我这边在Xcode运行脚本时,识别不出 xcpretty 指令,搜索了好久,还是没找到原因,这里先用了别人的截图)
在这里插入图片描述

6,OCLint自定义规则

1,首先在文件夹oclint-scripts,,使用./make执行脚本;(该过程可能需要翻墙才能完成)

2,在文件夹oclint-scripts执行./scaffoldRule GTETestRule -t ASTVisitor,创建自定义规则的文件;

3,在oclint的根目录创建文件夹oclint-xcoderules,执行完该命令后,会在oclint-rules/rules自动生成文件夹custom,其内有文件GTETestRule.cpp以及CMakeLists.txt;

4,cd到文件夹oclint-xcoderules,创建create-xcode-rules.sh;

5,脚本文件中输入内容如下:

#! /bin/sh -e

cmake -G Xcode -D CMAKE_CXX_COMPILER=../build/llvm-install/bin/clang++  -D CMAKE_C_COMPILER=../build/llvm-install/bin/clang -D OCLINT_BUILD_DIR=../build/oclint-core -D OCLINT_SOURCE_DIR=../oclint-core -D OCLINT_METRICS_SOURCE_DIR=../oclint-metrics -D OCLINT_METRICS_BUILD_DIR=../build/oclint-metrics -D LLVM_ROOT=../build/llvm-install/ ../oclint-rules

6,使用./create-xcode-rules.sh执行脚本;

7,执行完上述脚本后,会在oclint-xcoderules文件夹生成一个OCLINT_RULES工程,如下图:
在这里插入图片描述

8,打开工程可以看到所有的rule文件,所有规则都在里面,自定义的规则一般在最底部;
在这里插入图片描述

9,在工程顶部选择我们修改过的scheme,使用command+b编译;
在这里插入图片描述

10,编译完成后在Products文件可以看到我们要的dylib文件;
在这里插入图片描述

11,选中该文件右键,Show in Finder,可以看到dylib文件,将该文件复制到文件夹oclint/build/oclint-release/lib/oclint/rules则可以使用该规则了。

7,安装过程问题记录

1,执行完脚本sh create-xcode-rules.sh以后,在工程哪个地方可以查看创建的rule

2,如何更新dylib

8,默认规则整理

规则文件作用备注修改后的限制(需讨论)优先级
LongMethodRule单个方法的行数限制,默认为50行
LongLineRule单行的字数限制,默认100字符
OCLintAbstractRule未知未测试出来
BitwiseOperatorInConditionalRule条件判断语句中含有位操作符会提示举例if (a & b)
BrokenNullCheckRule无效检查的规则未测试出来
BrokenOddnessCheckRule违反奇偶校验规则未测试出来
CollapsibleIfStatementsRule可折叠的if语句规则,if语句可以折叠却未折叠使用时触发举例if (str > 1) { if (str < 10) { }}
ConstantConditionalOperatorRule条件运算符一直为真或者一直为假时触发
ConstantIfExpressionRule作用类似同上,具体未知
DeadCodeRule有永远无法被执行的代码时会触发比如return后面的无效代码
DoubleNegativeRule有使用双重否定的代码时触发未测试出来
ForLoopShouldBeWhileLoopRule有可以简化的for循环时触发,即可修改为while循环的代码未测试出来
GotoStatementRule未知未测试出来
JumbledIncrementerRule多重循环嵌套时递增错误时触发例如;for (int i = 0; i < a; i++) {for (int j = 0; j < a; i++) { // references both ‘i’ and ‘j’ }}
MisplacedNullCheckRule向空指针发送消息时会触发未测试出来
MultipleUnaryOperatorRule多个一元运算符会触发例如int b = -(+(!(~1)))
ReturnFromFinallyBlockRule抛出异常时在finally使用return触发
ThrowExceptionFromFinallyBlockRule在finally抛出异常时会触发未测试出来
ObjCVerifyIsEqualHashRule重写isEqual方法但没重写hash方法时会触发
ObjCVerifyMustCallSuperRule使用__attribute__((annotate(“oclint:enforce[base method]”)))修饰方法时,子类调用该方法但未实现super的时候会触发
ObjCVerifySubclassMustImplementRule未知未测试出来
ObjCVerifyProhibitedCallRule使用__attribute__((annotate(“oclint:enforce[prohibited method]”)))修饰方法时,任何地方调用该方法都会触发
ObjCVerifyProtectedMethodRule使用__attribute__((annotate(“oclint:enforce[protected method]”)))修饰方法时,除了其本身和其子类的其他地方调用该方法都会触发,代表该方法只能其内部调用
AvoidBranchingStatementAsLastInLoopRulefor循环最后一句使用break会触发
BaseClassDestructorShouldBeVirtualOrProtectedRule未知未测试出来
DefaultLabelNotLastInSwitchStatementRule在switch语句中,如果default不是写在最后则会触发
DestructorOfVirtualClassRule未知未测试出来
InvertedLogicRule使用一些难以理解的逆向判断会触发
MissingBreakInSwitchStatementRuleswitch语句中缺少break会触发
NonCaseLabelInSwitchStatementRule未知未测试出来
ObjCAssignIvarOutsideAccessorsRule未知未测试出来
ParameterReassignmentRule在方法中将方法的参数重新赋值时会触发
PreferEarlyExitRule方法中可以使用判断提前return却没有使用时会触发
SwitchStatementsShouldHaveDefaultRuleswitch语句没有default时会提示这种情况系统也有警告
CoveredSwitchStatementsDontNeedDefaultRule当switch语句涵盖了所有情况时不需要default,否则会触发
TooFewBranchesInSwitchStatementRule当判断较少时,使用switch而不使用if会触发
CudaBranchDivergenceRule未知未测试出来
AvoidDefaultArgumentsOnVirtualMethodsRule未知未测试出来
AvoidPrivateStaticMembersRule未知未测试出来
EmptyCatchStatementRule未知未测试出来
EmptyDoWhileStatementRuledo/while语句中未实现内容时会触发
EmptyElseBlockRuleif语句中的else未实现内容时会触发
EmptyFinallyStatementRulecry/catch/finally语句中,finally中没有任何东西时会触发
EmptyForStatementRulefor循环语句中没有任何有用的代码时会触发
EmptyIfStatementRuleif语句中没有任何有用的代码时会触发
EmptySwitchStatementRuleswitch语句中没有任何有用的代码时会触发
EmptyTryStatementRuletry语句中没有任何有用的代码时会触发
EmptyWhileStatementRulewhile语句中没有任何有用的代码时会触发
ObjCBoxedExpressionsRule未知未测试出来
ObjCContainerLiteralsRule不可变数组字典等集合类,创建时建议直接赋值,无需使用arrayWithObjects等方法,否则会触发
ObjCNSNumberLiteralsRule创建NSNumber类型常量时建议直接使用@(),无需使用numberWithInt等方法,否则会触发
ObjCObjectSubscriptingRule获取数组、字典等类型中的数据时,建议使用[],无需使用objectForKey和objectAtIndex,否则会触发
LongVariableNameRule变量名过长时会提示,默认20字符
ShortVariableNameRule变量名过短时会提示,默认3字符
RedundantConditionalOperatorRule赋值表达式使用多余的判断时会触发bool b1 = a > b ? true : false;应当使用bool b1 = a > b;
RedundantIfStatementRuleif判断语句使用多余的判断时会触发
RedundantLocalVariableRule当一个变量刚声明就被return时,应该直接return声明该变量表达式右侧的值,否则会触发
RedundantNilCheckRule多余的nil判断会被触发
UnnecessaryElseStatementRuleif语句中被return的话,则无需写else语句,否则会触发
UnnecessaryNullCheckForCXXDeallocRule未知未测试出来
UselessParenthesesRule检测一些无用的括号例如return (0),应直接使用return 0
CyclomaticComplexityRule检测方法中的if、for、switch等语句是否超过10,超过则会触发
LongClassRule检测一个类中代码行数是否超过1000行,超过则会触发
LongLineRule检测一行代码行数是否超过100字符,超过则会触发
LongMethodRule检测一个方法中代码行数是否超过50行,超过则会触发
NcssMethodCountRule检测一个方法中有效行数是否超过30行(不算空行、括号等)
NestedBlockDepthRule检测方法中的{}嵌套层数,默认5层
NPathComplexityRule未知未测试出来
TooManyFieldsRule未知未测试出来
TooManyMethodsRule方法过多时会触发
TooManyParametersRule方法参数过多时会触发,默认10个参数
UnusedLocalVariableRule定义了未使用的变量会触发
UnusedMethodParameterRule定义了未使用的方法参数会触发
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值