用于 Typescript 的 Sonarqube 上未显示代码覆盖率

Posted

技术标签:

【中文标题】用于 Typescript 的 Sonarqube 上未显示代码覆盖率【英文标题】:Code coverage is not showing on Sonarqube for Typescript 【发布时间】:2021-06-10 12:49:56 【问题描述】:

我正在为我的 Nestjs 项目使用 Sonarqube 分析。当我开玩笑地运行单元测试时,它们都通过了,代码覆盖率约为 80%。在 Sonarqube 上,它仍然显示为 0%。

我的sonar-project.properties文件如下

sonar.projectKey=<project-key>
sonar.projectName=
sonar.sources=src
sonar.tests=src
sonar.inclusions=**
sonar.test.inclusions=src/**/*.spec.ts
sonar.testExecutionReportPaths=test-report.xml
sonar.exclusions=node_modules 

我的jest.json如下


"moduleFileExtensions": [
      "ts",
      "tsx",
      "js",
      "json"
  ],
  "transform": 
      "^.+\\.tsx?$": "ts-jest"
  ,
  "testRegex": "/src/.*\\.(test|spec).(ts|tsx|js)$",
  "collectCoverageFrom" : ["src/**/*.js,jsx,tsx,ts", "!**/node_modules/**", "!**/vendor/**"],
  "coverageReporters": ["json", "lcov"]

我的 package.json 的相关部分

  "devDependencies": 
"@nestjs/cli": "^7.5.4",
"@nestjs/schematics": "^7.2.7",
"@nestjs/testing": "^7.6.11",
"@types/jest": "^26.0.20",
"@types/node": "^14.14.25",
"@types/supertest": "^2.0.10",
"@typescript-eslint/eslint-plugin": "^4.14.2",
"@typescript-eslint/parser": "^4.14.2",
"eslint": "^7.19.0",
"eslint-config-prettier": "^7.2.0",
"eslint-plugin-prettier": "^3.1.4",
"jest": "^26.6.3",
"jest-sonar-reporter": "^2.0.0",
"prettier": "^2.2.1",
"serverless": "^2.23.0",
"supertest": "^6.1.3",
"ts-jest": "^26.5.0",
"ts-loader": "^8.0.15",
"ts-node": "^9.1.1",
"tsconfig-paths": "^3.9.0",
"typescript": "^4.1.3"
  ,
  "jest": 
"testResultsProcessor": "jest-sonar-reporter",
"moduleFileExtensions": [
  "js",
  "json",
  "ts"
],
"rootDir": "src",
"testRegex": ".*\\.spec\\.ts$",
"transform": 
  "^.+\\.(t|j)s$": "ts-jest"
,
"collectCoverageFrom": [
  "**/*.(t|j)s"
],
"coverageDirectory": "../coverage",
"testEnvironment": "node"

我的源代码及其各自的单元测试位于同一位置。测试文件的扩展名为 .spec.ts

在本地运行测试时,所有测试都通过,并且在本地 repo 上生成 test-report.xml。我们还在运行声纳扫描仪之前在 Jenkins 上运行单元测试。

Sonarqube 代码覆盖率对我们来说是一个重要指标,没有它,管道就不会进一步移动。这里有什么提示吗?

Sonarqube 企业版版本 7.9.5(内部版本 38598)

【问题讨论】:

【参考方案1】:

您是否尝试过像这样指定 lcov.info 文件的路径: sonar.javascript.lcov.reportPaths=coverage/lcov.info

这些参数记录在here:

【讨论】:

【参考方案2】:

我无法确定,但您的症状与我在 SonarTS 插件中发现错误时所看到的相符。我们使用的是较旧版本的 SonarQube (7.9.2)。你还没说你用的是什么版本。

我从一些随机实验中发现,如果“lcov.info”文件中的文件路径与符号链接交叉,SonarTS 插件将无法打开该文件,从而发现该文件的覆盖率为零。如果 lcov.info 文件中的单个文件跨过符号链接,则很可能所有文件都会跨过。

我通过编写一个处理 lcov.info 文件的脚本来解决此问题,将所有文件路径替换为它们的“绝对”文件路径,遵循符号链接。

我们的 Jenkins 共享库中的代码如下所示:

shterse "cat coverage/lcov.info | " +
   "while IFS= read -r line; do if [[ \"\$line\" == \"SF:\"* ]]; then line=\"SF:\$(realpath \"\$line#SF:\")\"; fi; echo \"\$line\"; done > /tmp/lcov.info"
sh "mv /tmp/lcov.info coverage/lcov.info"

“shterse”在哪里:

// This will turn off verbose output.
def shterse(cmd) 
    sh('#!/bin/sh -e\n' + cmd)

【讨论】:

感谢您的回答。不幸的是,在我们的管道中,这不是我的选择。我们不控制 Jenkins Master,只有某些 groovy 脚本被批准。我现在用版本更新了问题。

以上是关于用于 Typescript 的 Sonarqube 上未显示代码覆盖率的主要内容,如果未能解决你的问题,请参考以下文章

SonarQube 未检测到 Angular-TypeScript 规则违规

如何为基于 Typescript 的 AngularJS 项目配置 SonarQube?

Docker 容器中的 TypeScript SonarQube 扫描

SonarQube:找不到打字稿模块

手把手使用SonarQube分析改善项目代码质量

SonarQube:扫描过程忽略 lcov.info