SpringCloud实战(十二)-自动化质量检测工具(SonarQube)

本文是SpringCloud实战(十二)-自动化代码检测工具(SonarQube),若要关注前文,请点击传送门:

SpringCloud实战(十一)-更优的分布式配置解决方案(Apollo)

前文我们介绍了携程的Apollo配置中心。在我们的日常开发中,程序有BUG是一件很让人苦恼的事情,开发过程中定位BUG和解决问题都会占据我们很多的时间,市面上已经提供了一些代码检测工具来帮助我们完成这些事情,就我用过的有阿里巴巴编码规范扫描、SonarQube,这两者的区别是前者是基于SonarQube进行的封装(也许大家都以为是阿里自研的代码检测工具,其实不然),后者提供了更加强大和完善的代码监测Dashboard,这对于现在的微服务模块开发起到了关键作用,他可以将所有微服务模块进行统一监测,所以基于上面这两点,我选择SonarQube作为工程质量监测工具。

一、SonarQube简介

SonarQube 是一个用于代码质量管理的开源平台,用于管理源代码的质量。 通过插件形式,可以支持包括 java, C#, C/C++, PL/SQL, Cobol, JavaScrip, Groovy 等等二十几种编程语言的代码质量管理与检测。Sonar可以从以下七个维度检测代码质量,而作为开发人员至少需要处理前5种代码质量问题,通过sonar可以找出循环,展示包与包、类与类之间的相互依赖关系,可以检测自定义的架构规则 通过sonar可以管理第三方的jar包,可以利用LCOM4检测单个任务规则的应用情况, 检测耦合,对于开发人员提高代码质量,了解自己在编码过程中犯过的错误,让自己的代码更具有可读性和维护性有很大的帮助。

SonarQube应用部署示意图:

二、准备工作

在本专栏的eureka-server工程基础上进行改造,可以不集成docker相关的东西,不过maven、jdk1.8是要有的。

三、SonarQube部署

首先我们需要去官网下载Sonar相关的安装包,这里SonarQube选择目前稳定版本sonarqube-6.7.7,Scanner选择sonar-scanner-cli-3.3.0.1492-linux,系统选择Linux的。

SonarQube安装包下载

SonarQube Scanner安装包下载

将安装包上传到服务器,如图所示:

解压重命名,执行以下命令

$ unzip sonarqube-6.7.7.zip
$ unzip sonar-scanner-cli-3.3.0.1492-linux.zip
$ mv ./sonarqube-6.7.7 ./sonarqube
$ mv ./sonar-scanner-cli-3.3.0.1492-linux ./sonar-scanner

配置并追加Sonar环境变量

    $ vim /etc/profile
#sonar
export SONAR_HOME=/home/sonarqube
export SONAR_SCANNER_HOME=/home/sonar-scanner
export PATH=$PATH:$SONAR_HOME/bin:$SONAR_SCANNER_HOME/bin

修改完成后,如图所示:

让环境变量生效

    $ source /etc/profile

之后我们需要修改SonarQube配置文件

    $ vim /home/sonarqube/conf/sonar.properties

 主要修改以下几个地方

# User credentials.
# Permissions to create tables, indices and triggers must be granted to JDBC user.
# The schema must be created first.
sonar.jdbc.username=root
sonar.jdbc.password=aidclouddb@123!@#

#----- MySQL 5.6 or greater
# Only InnoDB storage engine is supported (not myISAM).
# Only the bundled driver is supported. It can not be changed.
sonar.jdbc.url=jdbc:mysql://192.168.3.203:3306/sonar?useUnicode=true&characterEncoding=utf8&rewriteBatchedStatements=true&useConfigs=maxPerformance&useSSL=false

# Binding IP address. For servers with more than one IP address, this property specifies which
# address will be used for listening on the specified ports.
# By default, ports will be used on all IP addresses associated with the server.
sonar.web.host=192.168.3.202

# Web context. When set, it must start with forward slash (for example /sonarqube).
# The default value is root context (empty value).
#sonar.web.context=
# TCP port for incoming HTTP connections. Default value is 9000.
sonar.web.port=9000

配置文件修改完成后,如图所示:

然后修改sonar-scanner的配置文件(虽然现阶段不配置也可以,不过后面集成Jenkins是需要配置的)

    $ vim /home/sonar-scanner/conf/sonar-scanner.properties

修改配置文件的以下内容

#----- Default SonarQube server
sonar.host.url=http://192.168.3.202:9000

#----- Default source code encoding
sonar.sourceEncoding=UTF-8

配置文件修改完成后,如图所示:

sonar-scanner.properties修改完之后倒是不需要重启什么东西。

我们在mysql中新建数据库sonar,如图所示:

  

我们需要通过sonar用户来启动命令,所以这里我们来新建sonar用户和用户组

$ groupadd sonar
$ useradd -g sonar sonar

然后我们将sonarqube的文件夹及下面的所有子文件的用户和用户组都改为sonar

    $ chown -R sonar:sonar /home/sonarqube

切换到sonar用户,启动SonarQube,执行以下命令

$ su sonar
$ /home/sonarqube/bin/linux-x86-64/sonar.sh start
$ /home/sonarqube/bin/linux-x86-64/sonar.sh status

 验证是否启动成功

  

访问 http://192.168.3.202:9000/,如图所示:

到此SonarQube部署成功。

四、代码质量检测 

Sonar提供了两种检测方式,一种是通过Idea插件检测、一种是通过本地上传Jar包到Sonar检测,我们一般是这两种方式结合使用,下面来逐一讲解。

1、Idea插件检测

这种方式很方便,可以在开发过程中就发现BUG,首先我们去Idea的setting中找到Plugins,在MarketPlace中搜索sonar,如图所示:

安装第一个,点击install,安装完成后重启Idea,重启完之后我们就可以看到Sonar插件就已经装好了,如图所示:

 Sonar插件就会实时监测我们的代码质量了。

2、上传Jar包到Sonar检测

这种方式是通过maven命令来实现的,首先需要配置maven的setting文件,添加sonar相关配置,setting配置如下

<?xml version="1.0" encoding="UTF-8"?>

<!--
Licensed to the Apache Software Foundation (ASF) under one
or more contributor license agreements.  See the NOTICE file
distributed with this work for additional information
regarding copyright ownership.  The ASF licenses this file
to you under the Apache License, Version 2.0 (the
"License"); you may not use this file except in compliance
with the License.  You may obtain a copy of the License at

    http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing,
software distributed under the License is distributed on an
"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
KIND, either express or implied.  See the License for the
specific language governing permissions and limitations
under the License.
-->

<!--
 | This is the configuration file for Maven. It can be specified at two levels:
 |
 |  1. User Level. This settings.xml file provides configuration for a single user,
 |                 and is normally provided in ${user.home}/.m2/settings.xml.
 |
 |                 NOTE: This location can be overridden with the CLI option:
 |
 |                 -s /path/to/user/settings.xml
 |
 |  2. Global Level. This settings.xml file provides configuration for all Maven
 |                 users on a machine (assuming they're all using the same Maven
 |                 installation). It's normally provided in
 |                 ${maven.conf}/settings.xml.
 |
 |                 NOTE: This location can be overridden with the CLI option:
 |
 |                 -gs /path/to/global/settings.xml
 |
 | The sections in this sample file are intended to give you a running start at
 | getting the most out of your Maven installation. Where appropriate, the default
 | values (values used when the setting is not specified) are provided.
 |
 |-->
<settings xmlns="http://maven.apache.org/SETTINGS/1.0.0"
          xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
          xsi:schemaLocation="http://maven.apache.org/SETTINGS/1.0.0 http://maven.apache.org/xsd/settings-1.0.0.xsd">
  <!-- localRepository
   | The path to the local repository maven will use to store artifacts.
   |
   | Default: ${user.home}/.m2/repository
  <localRepository>/path/to/local/repo</localRepository>
  -->
<localRepository>C:\Users\Lenovo\.m2\repo\</localRepository>

  <!-- interactiveMode
   | This will determine whether maven prompts you when it needs input. If set to false,
   | maven will use a sensible default value, perhaps based on some other setting, for
   | the parameter in question.
   |
   | Default: true
  <interactiveMode>true</interactiveMode>
  -->

  <!-- offline
   | Determines whether maven should attempt to connect to the network when executing a build.
   | This will have an effect on artifact downloads, artifact deployment, and others.
   |
   | Default: false
  <offline>false</offline>
  -->

  <!-- pluginGroups
   | This is a list of additional group identifiers that will be searched when resolving plugins by their prefix, i.e.
   | when invoking a command line like "mvn prefix:goal". Maven will automatically add the group identifiers
   | "org.apache.maven.plugins" and "org.codehaus.mojo" if these are not already contained in the list.
   |-->
  <pluginGroups>
    <!-- pluginGroup
     | Specifies a further group identifier to use for plugin lookup.
    <pluginGroup>com.your.plugins</pluginGroup>
    -->
  </pluginGroups>

  <!-- proxies
   | This is a list of proxies which can be used on this machine to connect to the network.
   | Unless otherwise specified (by system property or command-line switch), the first proxy
   | specification in this list marked as active will be used.
   |-->
  <proxies>
    <!-- proxy
     | Specification for one proxy, to be used in connecting to the network.
     |
    <proxy>
      <id>optional</id>
      <active>true</active>
      <protocol>http</protocol>
      <username>proxyuser</username>
      <password>proxypass</password>
      <host>proxy.host.net</host>
      <port>80</port>
      <nonProxyHosts>local.net|some.host.com</nonProxyHosts>
    </proxy>
    -->
  </proxies>

  <!-- servers
   | This is a list of authentication profiles, keyed by the server-id used within the system.
   | Authentication profiles can be used whenever maven must make a connection to a remote server.
   |-->
  <servers>
    <!-- server
     | Specifies the authentication information to use when connecting to a particular server, identified by
     | a unique name within the system (referred to by the 'id' attribute below).
     |
     | NOTE: You should either specify username/password OR privateKey/passphrase, since these pairings are
     |       used together.
     |
    <server>
      <id>deploymentRepo</id>
      <username>repouser</username>
      <password>repopwd</password>
    </server>
    -->

    <!-- Another sample, using keys to authenticate.
    <server>
      <id>siteServer</id>
      <privateKey>/path/to/private/key</privateKey>
      <passphrase>optional; leave empty if not used.</passphrase>
    </server>
    -->
	<server>
      <id>nexus-snapshots</id>
      <username>admin</username>
      <password>admin123</password>
    </server>
    <server>
      <id>nexus-releases</id>
      <username>admin</username>
      <password>admin123</password>
    </server>
	<server>
        <id>192.168.3.202:8088</id>
        <username>admin</username>
        <password>admin123</password>
    </server>
  </servers>

  <!-- mirrors
   | This is a list of mirrors to be used in downloading artifacts from remote repositories.
   |
   | It works like this: a POM may declare a repository to use in resolving certain artifacts.
   | However, this repository may have problems with heavy traffic at times, so people have mirrored
   | it to several places.
   |
   | That repository definition will have a unique id, so we can create a mirror reference for that
   | repository, to be used as an alternate download site. The mirror site will be the preferred
   | server for that repository.
   |-->
  <mirrors>
    <!-- mirror
     | Specifies a repository mirror site to use instead of a given repository. The repository that
     | this mirror serves has an ID that matches the mirrorOf element of this mirror. IDs are used
     | for inheritance and direct lookup purposes, and must be unique across the set of mirrors.
     |
    <mirror>
      <id>mirrorId</id>
      <mirrorOf>repositoryId</mirrorOf>
      <name>Human Readable Name for this Mirror.</name>
      <url>http://my.repository.com/repo/path</url>
    </mirror>
     -->
  </mirrors>

  <!-- profiles
   | This is a list of profiles which can be activated in a variety of ways, and which can modify
   | the build process. Profiles provided in the settings.xml are intended to provide local machine-
   | specific paths and repository locations which allow the build to work in the local environment.
   |
   | For example, if you have an integration testing plugin - like cactus - that needs to know where
   | your Tomcat instance is installed, you can provide a variable here such that the variable is
   | dereferenced during the build process to configure the cactus plugin.
   |
   | As noted above, profiles can be activated in a variety of ways. One way - the activeProfiles
   | section of this document (settings.xml) - will be discussed later. Another way essentially
   | relies on the detection of a system property, either matching a particular value for the property,
   | or merely testing its existence. Profiles can also be activated by JDK version prefix, where a
   | value of '1.4' might activate a profile when the build is executed on a JDK version of '1.4.2_07'.
   | Finally, the list of active profiles can be specified directly from the command line.
   |
   | NOTE: For profiles defined in the settings.xml, you are restricted to specifying only artifact
   |       repositories, plugin repositories, and free-form properties to be used as configuration
   |       variables for plugins in the POM.
   |
   |-->
  <profiles>
    <!-- profile
     | Specifies a set of introductions to the build process, to be activated using one or more of the
     | mechanisms described above. For inheritance purposes, and to activate profiles via <activatedProfiles/>
     | or the command line, profiles have to have an ID that is unique.
     |
     | An encouraged best practice for profile identification is to use a consistent naming convention
     | for profiles, such as 'env-dev', 'env-test', 'env-production', 'user-jdcasey', 'user-brett', etc.
     | This will make it more intuitive to understand what the set of introduced profiles is attempting
     | to accomplish, particularly when you only have a list of profile id's for debug.
     |
     | This profile example uses the JDK version to trigger activation, and provides a JDK-specific repo.
    <profile>
      <id>jdk-1.4</id>

      <activation>
        <jdk>1.4</jdk>
      </activation>

      <repositories>
        <repository>
          <id>jdk14</id>
          <name>Repository for JDK 1.4 builds</name>
          <url>http://www.myhost.com/maven/jdk14</url>
          <layout>default</layout>
          <snapshotPolicy>always</snapshotPolicy>
        </repository>
      </repositories>
    </profile>
    -->

    <!--
     | Here is another profile, activated by the system property 'target-env' with a value of 'dev',
     | which provides a specific path to the Tomcat instance. To use this, your plugin configuration
     | might hypothetically look like:
     |
     | ...
     | <plugin>
     |   <groupId>org.myco.myplugins</groupId>
     |   <artifactId>myplugin</artifactId>
     |
     |   <configuration>
     |     <tomcatLocation>${tomcatPath}</tomcatLocation>
     |   </configuration>
     | </plugin>
     | ...
     |
     | NOTE: If you just wanted to inject this configuration whenever someone set 'target-env' to
     |       anything, you could just leave off the <value/> inside the activation-property.
     |
    <profile>
      <id>env-dev</id>

      <activation>
        <property>
          <name>target-env</name>
          <value>dev</value>
        </property>
      </activation>

      <properties>
        <tomcatPath>/path/to/tomcat/instance</tomcatPath>
      </properties>
    </profile>
    -->
      <profile>
        <id>sonar</id>
        <activation>
          <activeByDefault>true</activeByDefault>
        </activation>
        <properties>
		  <sonar.jdbc.url>
            jdbc:mysql://192.168.3.203:3306/sonar
          </sonar.jdbc.url>
          <sonar.jdbc.driver>com.mysql.jdbc.Driver</sonar.jdbc.driver>
          <sonar.jdbc.username>root</sonar.jdbc.username>
          <sonar.jdbc.password>aidclouddb@123!@#</sonar.jdbc.password>
          <sonar.host.url>http://192.168.3.202:9000</sonar.host.url>
        </properties>
      </profile>
		<profile>
		  <id>nexus-releases</id>
		  <repositories>
			<repository>
			  <id>central</id>
			  <url>http://192.168.3.202:8083/repository/maven-public/</url>
			  <releases>
				  <enabled>true</enabled>
				  <updatePolicy>always</updatePolicy>
				<checksumPolicy>warn</checksumPolicy>
			  </releases>
			  <snapshots><enabled>true</enabled></snapshots>
			</repository>
		  </repositories>
		 <pluginRepositories>
			<pluginRepository>
			  <id>central</id>
			  <url>http://192.168.3.202:8083/repository/maven-public/</url>
			  <releases>
				  <enabled>true</enabled>
				  <updatePolicy>always</updatePolicy>
				<checksumPolicy>warn</checksumPolicy>
				</releases>
			  <snapshots><enabled>true</enabled></snapshots>
			</pluginRepository>
		  </pluginRepositories>
		</profile>
  </profiles>

  <!-- activeProfiles
   | List of profiles that are active for all builds.
   |
  <activeProfiles>
    <activeProfile>alwaysActiveProfile</activeProfile>
    <activeProfile>anotherAlwaysActiveProfile</activeProfile>
  </activeProfiles>
  -->
</settings>

上面增加的只有一个地方,如图所示:

然后在Idea中执行mvn命令

    $ clean install sonar:sonar

 执行完之后访问 http://192.168.3.202:9000,如图所示:

这个项目就被分析出来了,从最近一次分析的时间可以看出是刚刚我上传的项目。

五、Jenkins自动化质量检测

Jenkins自动化质量检测的前提是在本专栏自动化部署与持续集成搭建完成的基础上进行的。

1、安装Sonar插件

进入Jenkins系统管理 -> 插件管理,我们需要安装Jenkins的Sonar插件,插件名叫做SonarQube Scanner,如图所示:

这里我已经装好了,没安装的去可选插件搜一下安装就行了。

2、系统设置

进入Jenkins系统管理 -> 系统设置,找到配置SonarQube servers那块,如图所示:

这里的Server URL是SonarQube所在服务器的地址,Server authentication token需要去SonarQube上面生成一下,我们登录SonarQube,找到我的账号 -> 安全 -> 生成令牌,如图所示:

将这个生成的令牌复制到Jenkins刚刚的Server authentication token上面就可以了。

3、全局工具配置

进入Jenkins系统管理 -> 全局工具配置,找到配置SonarQube Scanner那块,如图所示:

 这里的SONAR_RUNNER_HOME指的是服务器上sonar-scanner根目录所在路径,这里和环境变量中的sonar-scanner配置一致就可以了。

4、项目配置

最后我们要对Jenkins中的每个项目单独进行配置,找到我们之前的eureka-server项目,点击配置,如图所示:

 然后找到Pre Steps这一块,设置Sonar的环境变量

sonar.projectKey=eureka-server
sonar.projectName=eureka-server
sonar.projectVersion=1.0
sonar.sourceEncoding=UTF-8
sonar.language=java
sonar.login=admin
sonar.password=admin
sonar.sources=./src
sonar.java.binaries=./target/classes

修改完成后,如图所示:

配置完这一块点击保存,然后我们就可以去构建这个项目,构建成功之后我们就可以去SonarQube上看到最新的代码质量分析了,如图所示:

 到此Jenkins自动化质量检测配置完成。

发布了352 篇原创文章 · 获赞 390 · 访问量 37万+

猜你喜欢

转载自blog.csdn.net/qq_19734597/article/details/90487473
今日推荐