一文搞定SonarQube接入C#(.NET)代码质量分析

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
简介: 一文搞定SonarQube接入C#(.NET)代码质量分析

1. 前言


     C#语言接入Sonar代码静态扫描相较于Java、Python来说,相对麻烦一些。Sonar检测C#代码时需要预先编译,而且C#代码必须用MSbuid进行编译,如果需要使用SonarQube对C#进行代码质量分析,则需要下载Sonar-Scanner-MSBuild和MSBuild,其中要求MSBuild在V14.0以上。


2. Sonar-Scanner for MSBuild安装与配置


1、下载SonarQube Scanner for MSBuild,它是C# Framework的Sonar分析插件。

下载地址:


https://github.com/SonarSource/sonar-scanner-msbuild/releases/download/4.3.1.1372/sonar-scanner-msbuild-4.3.1.1372-net46.zip


2、下载并解压之后,设置SonarQube Scanner for MSBuild的环境变量。


例如我的解压路径是:C:\Users\Administrator\Downloads\sonar-scanner-msbuild-4.3.1.1372-net466,则把该路径添加到Path下。

SonarQube Scanner for MSBuild解压目录如下图所示:

微信图片_20220523184844.png

3、修改SonarQube.Analysis.xml文件,要修改的地方只是关于SonarQube服务器的一些配置,如服务器URL、USER、PASSWORD等,详细配置修改如下:

<?xml version="1.0" encoding="utf-8" ?>
<!--
  This file defines properties which would be understood by the SonarQube Scanner for MSBuild, if not overridden (see below)
  By default the SonarScanner.MSBuild.exe picks-up a file named SonarQube.Analysis.xml in the folder it
  is located (if it exists). It is possible to use another properties file by using the /s:filePath.xml flag
  The overriding strategy of property values is the following:
  - A project-specific property defined in the MSBuild *.*proj file (corresponding to a SonarQube module) can override:
  - A property defined in the command line (/d:propertyName=value) has which can override:
  - A property defined in the SonarQube.Analysis.xml configuration file [this file] which can override:
  - A property defined in the SonarQube User Interface at project level which can override:
  - A property defined in the SonarQube User Interface at global level which can't override anything.
  Note that the following properties cannot be set through an MSBuild project file or an SonarQube.Analysis.xml file:
  sonar.projectName, sonar.projectKey, sonar.projectVersion
  The following flags need to be used to set their value: /n:[SonarQube Project Name] /k:[SonarQube Project Key] /v:[SonarQube Project Version]
-->
<SonarQubeAnalysisProperties  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns="http://www.sonarsource.com/msbuild/integration/2015/1">
  <Property Name="sonar.host.url">http://sonar_ip:sonar_port</Property>
  <Property Name="sonar.login">login_username</Property>
  <Property Name="sonar.password">login_password</Property>
  <!-- Required only for versions of SonarQube prior to 5.2 -->
  <Property Name="sonar.jdbc.url">jdbc:mysql://db_ip:db_port/sonar?useUnicode=true;characterEncoding=utf8;rewriteBatchedStatements=true;useConfigs=maxPerformance;useSSL=false</Property>
  <Property Name="sonar.jdbc.username">jdbc.username</Property>
  <Property Name="sonar.jdbc.password">jdbc.password</Property>
</SonarQubeAnalysisProperties>

3. MSBuild安装与配置


    Visual Studio IDE在编译*.sln解决方案时默认是调用msbuild.exe来实现的。如果你的机器上没有装有Visual Studio,那么也可以单独使用MSBuild来编译.sln(工程解决方案)或.csproj(项目)。MSBuild可以直接通过.NETFramework来安装获得。


msbuild.exe的路径一般如下:

X86: C:\Program Files (x86)\MSBuild\14.0\Bin\MSBuild.exe
X64: C:\Program Files (x86)\MSBuild\14.0\Bin\amd64\MSBuild.exe

msbuild.exe 目录如下所示:

微信图片_20220523185129.png


将MSBuild.exe添加到Path环境变量,便于后面在命令行中调用MSBuild。


msbuild常用编译命令:

MSBuild MyApp.sln /t:Rebuild /p:Configuration=Release
MSBuild MyApp.csproj /t:Clean /p:Configuration=Debug;/p:Platform=x86;TargetFrameworkVersion=v3.5
编译为 Release 代码 -p:configuration="release"
清理项目 -t:clean
重新编译 -t:rebuild
编译项目 -t:build 默认可以忽略这个参数
发布 -t:Publish
注意:这里的 -t 和 /t 作用是相同的。

4. Sonar+命令行分析C#代码


1、打开CMD,切换到指定的项目根目录,必须和.sln或者.csproj同级目录。例如以\hcloud\Common\KDY.WebApi.Core项目为例,如下图所示。

微信图片_20220523185230.png

2、使用MSBuild方式进行Sonar Scanner扫描代码前期准备文件生成,CMD命令下运行:


SonarScanner.MSBuild.exe begin /k:"hcloud.Common.KDY.WebApi.Core" /n:"hcloud.Common.KDY.WebApi.Core" /v:"1.0"

命令执行结果如下:

微信图片_20220523185255.png


参数说明:

  • /key(简写k):对应projectKey即项目的唯一代码,如两套源代码使用同一个projectKey那扫描的结果将混在一起,所以一个项目需要有一个单独的projectKey
  • /name(简写n):对应projectName即项目的名称,为项目的一个显示的名称,建立使用完整的项目名称
  • /version(简写v):对应projectVersion即项目的版本,项目在不同的时期版本也是不一样的,如果方便,可以在sonarQube的服务器中查看到不同的版本代码其中问题的变化


执行上述命令后,在项目目录下,生成.sonarqube目录。


3、通过MSBuild命令编译项目,在CMD命令行下执行:

MSBuild.exe /t:Rebuild   (默认为Debug模式)
或者
MSBuild.exe /t:Rebuild /p:Configuration=Release  (指定编译模式)
或者
MSBuild.exe D:\hcloud\Common\Common.sln /t:Rebuild  (指定具体的.sln解决方案)

编译项目运行结果如下所示:

微信图片_20220523185355.png


0个错误,则代表MSBuild编译成功,编译成功后,在当前目录下会生成一个obj目录。(编译成功后默认生成Debug产物),SonarQube分析C#项目工程时,前提需要MSBuild能预编译成功,如果存在错误,则无法成功完成后续Sonar分析动作。

4、分析C#扫描结果,将分析报告上传给SonarQube,CMD命令下运行:


SonarScanner.MSBuild.exe end

执行结果如下图所示:

微信图片_20220523185426.png


温馨提示:

1、如果运行出现错误请检查sonar server的log,路径为Snoar\sonarqube-6.7\logs下的sonar.log,web.log和access.log。

2、如果遇到需要检测比较大的项目,可能上传的mysql数据量会很大,会超出默认的mysql上传的最大值,此时需要设置mysql的max_allowed_packet。


5、查看Sonar分析扫描后的结果,访问http://10.0.0.147:9000/dashboard?id=hcloud.Common.KDY.WebApi.Core,分析结果如下图所示:

微信图片_20220523185456.png


5. Jenkins+Sonar+MSBuild分析C#代码


1、编译.NET(C#)应用程序可通过微软提供的MSBuild工具,先安装插件MSBuild,在Jenkins中搜索并安装MSBuild插件,如下图所示。

微信图片_20220523185523.png


2、插件安装完毕后,进入系统管理->全局工具配置(Global Tool Configuration)找到MSBuild配置选项,如下图所示。

微信图片_20220523185545.png


3、配置SonarScanner for MSBuild,如下图所示。

微信图片_20220523185613.png

4、由于示例中的Jenkins服务是部署在Linux系统中,故此处可添加一台Windows主机(10.0.0.148)作为C#项目编译运行环境,在Windows从节点配置中,添加并配置相应工具,如下图所示。

微信图片_20220523185639.png

5、新建并配置JOB,添加JOB运行节点(编译C#工程项目的运行机),如下图所示。

微信图片_20220523185716.png

6、配置源码管理及其它所需配置(较为简单,此处省略)后,添加并配置构建选项,如下图所示。

微信图片_20220523185741.png

7、JOB构建运行结果如下图所示。

微信图片_20220523185802.png

8、JOB构建成功后,Sonar代码分析报告如下图所示。

微信图片_20220523185831.png


6. 常见问题


1、解决SonarQube检测C#执行成功,但不能获取检测结果的问题,现象如下图所示。微信图片_20220523185900.png


由图中可以看到文件扫描成功了,但是却没有任何文件被发现,所有的指标数据皆为0。


解决方案

将Sonar插件中的C#插件改为5.9的版本即可。修改方式将plugin目录下原本的C#插件删除掉,将5.9版本的插件放入进来。重启SonarQube后问题即可解决。(备注示例中的SonarQube版本为6.7.5)


plugin目录替换后如下图所示:

微信图片_20220523185936.png


2. Jenkins +MSBuild+Sonar构建编译Job时提示Running the Scanner for MSBuild under Local System or Network Service account is not supported. Please, use a local or domain user account instead.

现象如下图所示:

微信图片_20220523190006.png

解决方法:

登录从节点10.0.0.148(windows主机),右击我的电脑选择管理然后从管理界面里面找到服务或者在cmd界面输入services.msc打开服务管理界面,从服务管理界面找到jenkins slave服务,右键点击属性,在弹出的对话框中切换到登陆标签,默认登录方式为本地系统帐号,此处我们选择此账户。然后输入账户和密码点击确定,完成以上操作以后重新启动jenkins slave服务然后再重新执行即可。


修改方式如下图所示:

微信图片_20220523190040.png


3、Jenkins单独构建没问题,Sonar静态检查代码单独执行也没问题,但是Jenkins+Sonar集成时出现未经授权问题,现象如下图所示。

微信图片_20220523190106.png

解决方案:

原因是由于Jenkins上已经通过admin生成了Token来进行连接认证,需要注释掉SonarQube.Analysis.xml里面的sonar.login和sonar.password,删除或者注释后,再重新执行即可。

修改如下图所示(下图采用注释来解决该问题的)

微信图片_20220523190132.png

相关实践学习
基于CentOS快速搭建LAMP环境
本教程介绍如何搭建LAMP环境,其中LAMP分别代表Linux、Apache、MySQL和PHP。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助 &nbsp; &nbsp; 相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
目录
相关文章
|
13天前
|
算法 C# 数据库
【干货】一份10万字免费的C#/.NET/.NET Core面试宝典
C#/.NET/.NET Core相关技术常见面试题汇总,不仅仅为了面试而学习,更多的是查漏补缺、扩充知识面和大家共同学习进步。该知识库主要由自己平时学习实践总结、网上优秀文章资料收集(这一部分会标注来源)和社区小伙伴提供三部分组成。该份基础面试宝典完全免费,发布两年来收获了广大.NET小伙伴的好评,我会持续更新和改进,欢迎关注我的公众号【追逐时光者】第一时间获取最新更新的面试题内容。
|
13天前
|
数据可视化 网络协议 C#
C#/.NET/.NET Core优秀项目和框架2024年3月简报
公众号每月定期推广和分享的C#/.NET/.NET Core优秀项目和框架(每周至少会推荐两个优秀的项目和框架当然节假日除外),公众号推文中有项目和框架的介绍、功能特点、使用方式以及部分功能截图等(打不开或者打开GitHub很慢的同学可以优先查看公众号推文,文末一定会附带项目和框架源码地址)。注意:排名不分先后,都是十分优秀的开源项目和框架,每周定期更新分享(欢迎关注公众号:追逐时光者,第一时间获取每周精选分享资讯🔔)。
|
13天前
|
安全 数据安全/隐私保护 开发者
三款.NET 代码混淆工具比较分析:ConfuserEx、Obfuscar 和 Ipa Guard
三款.NET 代码混淆工具比较分析:ConfuserEx、Obfuscar 和 Ipa Guard
|
13天前
|
SQL 数据库 C#
C# .NET面试系列十一:数据库SQL查询(附建表语句)
#### 第1题 用一条 SQL 语句 查询出每门课都大于80 分的学生姓名 建表语句: ```sql create table tableA ( name varchar(10), kecheng varchar(10), fenshu int(11) ) DEFAULT CHARSET = 'utf8'; ``` 插入数据 ```sql insert into tableA values ('张三', '语文', 81); insert into tableA values ('张三', '数学', 75); insert into tableA values ('李四',
82 2
C# .NET面试系列十一:数据库SQL查询(附建表语句)
|
13天前
|
开发框架 算法 搜索推荐
C# .NET面试系列九:常见的算法
#### 1. 求质数 ```c# // 判断一个数是否为质数的方法 public static bool IsPrime(int number) { if (number < 2) { return false; } for (int i = 2; i <= Math.Sqrt(number); i++) { if (number % i == 0) { return false; } } return true; } class Progr
69 1
|
13天前
|
开发框架 .NET 中间件
C#/.NET快速上手学习资料集(让现在的自己不再迷茫)
C#/.NET快速上手学习资料集(让现在的自己不再迷茫)
|
1天前
|
编译器 C#
C#.Net筑基-类型系统②常见类型 --record是什么类型?
`record`在C#中是一种创建简单、只读数据结构的方式,常用于轻量级数据传输。它本质上是类(默认)或结构体的快捷形式,包含自动生成的属性、`Equals`、`ToString`、解构赋值等方法。记录类型可以继承其他record或接口,但不继承普通类。支持使用`with`语句创建副本。例如,`public record User(string Name, int Age)`会被编译为包含属性、相等比较和`ToString()`等方法的类。记录类型提供了解构赋值和自定义实现,如密封的`sealed`记录,防止子类重写。
|
1天前
|
存储 安全 Unix
C#.Net筑基-类型系统②常见类型--日期和时间的故事
在System命名空间中,有几种表示日期时间的不可变结构体(Struct):DateTime、DateTimeOffset、TimeSpan、DateOnly和TimeOnly。DateTime包含当前本地或UTC时间,以及最小和最大值;DateTimeOffset增加了时区偏移信息,适合跨时区操作。UTC是世界标准时间,而格林尼治标准时间(GMT)不稳定,已被更精确的UTC取代。DateTimeOffset和DateTime提供了转换为UTC和本地时间的方法,以及各种解析和格式化函数。
|
1天前
|
安全 API C#
C#.Net筑基-类型系统②常见类型--枚举Enum
枚举(enum)是C#中的一种值类型,用于创建一组命名的整数常量。它们基于整数类型(如int、byte等),默认为int。枚举成员可指定值,未指定则从0开始自动递增。默认值为0。枚举可以与整数类型互相转换,并可通过`[Flags]`特性表示位域,支持位操作,用于多选场景。`System.Enum`类提供了如`HasFlag`、`GetName`等方法进行枚举操作。
|
1天前
|
存储 C#
C#.Net筑基-类型系统②常见类型--结构体类型Struct
本文介绍了C#中的结构体(struct)是一种用户自定义的值类型,适用于定义简单数据结构。结构体可以有构造函数,能定义字段、属性和方法,但不能有终结器或继承其他类。它们在栈上分配,参数传递为值传递,但在类成员或包含引用类型字段时例外。文章还提到了`readonly struct`和`ref struct`,前者要求所有字段为只读,后者强制结构体存储在栈上,适用于高性能场景,如Span和ReadOnlySpan。