@toptal/davinci-monorepo 8.1.4-alpha-CRT-5891-create-coverage-command-23386c1d.2 → 8.1.4-alpha-CRT-5891-create-coverage-command-c72932eb.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bin/davinci-monorepo.js +1 -1
- package/package.json +5 -3
- package/src/commands/codeowners/core/codeowners/codeowners.js +0 -3
- package/src/commands/coverage-command/config.js +3 -0
- package/src/commands/{generate-team-coverage.js → coverage-command/generate-team-coverage.js} +37 -39
- package/src/commands/{group-coverage-by-codeowners.js → coverage-command/group-coverage-by-codeowners.js} +40 -30
- package/src/commands/coverage-command/services/sanitize-team-name/sanitize-team-name.js +1 -0
- package/src/index.js +1 -1
- package/src/commands/{coverage.js → coverage-command/index.js} +1 -1
package/bin/davinci-monorepo.js
CHANGED
|
@@ -7,7 +7,7 @@ import { createGraphGenerateCommand } from '../src/commands/graph-generate.js'
|
|
|
7
7
|
import metricsCommand from '../src/commands/metrics.js'
|
|
8
8
|
// eslint-disable-next-line no-restricted-syntax
|
|
9
9
|
import codeownersCommand from '../src/commands/codeowners/index.js'
|
|
10
|
-
import { coverageCommand } from '../src/commands/coverage.js'
|
|
10
|
+
import { coverageCommand } from '../src/commands/coverage-command/index.js'
|
|
11
11
|
|
|
12
12
|
cliEngine.loadCommands(
|
|
13
13
|
[
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@toptal/davinci-monorepo",
|
|
3
|
-
"version": "8.1.4-alpha-CRT-5891-create-coverage-command-
|
|
3
|
+
"version": "8.1.4-alpha-CRT-5891-create-coverage-command-c72932eb.4+c72932eb",
|
|
4
4
|
"description": "Monorepo utility tools",
|
|
5
5
|
"publishConfig": {
|
|
6
6
|
"access": "public"
|
|
@@ -35,13 +35,15 @@
|
|
|
35
35
|
"dependencies": {
|
|
36
36
|
"@nodelib/fs.walk": "^1.2.6",
|
|
37
37
|
"@oclif/core": "^1.16.1",
|
|
38
|
-
"@toptal/davinci-cli-shared": "2.3.1-alpha-CRT-5891-create-coverage-command-
|
|
38
|
+
"@toptal/davinci-cli-shared": "2.3.1-alpha-CRT-5891-create-coverage-command-c72932eb.36+c72932eb",
|
|
39
39
|
"chalk": "^4.1.2",
|
|
40
40
|
"codeowners": "5.1.1",
|
|
41
|
+
"commander": "^10.0.0",
|
|
41
42
|
"dependency-cruiser": "^12.5.0",
|
|
42
43
|
"ervy": "^1.0.7",
|
|
43
44
|
"execa": "^5.1.1",
|
|
44
45
|
"find-up": "5.0.0",
|
|
46
|
+
"find-yarn-workspace-root": "^2.0.0",
|
|
45
47
|
"glob": "^8.0.3",
|
|
46
48
|
"ignore": "^5.2.0",
|
|
47
49
|
"is-directory": "^0.3.1",
|
|
@@ -53,5 +55,5 @@
|
|
|
53
55
|
"devDependencies": {
|
|
54
56
|
"@jest/globals": "^29.4.2"
|
|
55
57
|
},
|
|
56
|
-
"gitHead": "
|
|
58
|
+
"gitHead": "c72932ebed3392a4ffb196fb2e6a21b9c5e8c3f1"
|
|
57
59
|
}
|
|
@@ -62,9 +62,6 @@ Codeowners.prototype.getOwner =
|
|
|
62
62
|
* @param {string} filePath
|
|
63
63
|
*/
|
|
64
64
|
function getOwner(filePath) {
|
|
65
|
-
console.log({ filePath })
|
|
66
|
-
console.log({ entries: this.ownerEntries })
|
|
67
|
-
|
|
68
65
|
for (const entry of this.ownerEntries) {
|
|
69
66
|
if (entry.match(filePath)) {
|
|
70
67
|
return entry.usernames
|
package/src/commands/{generate-team-coverage.js → coverage-command/generate-team-coverage.js}
RENAMED
|
@@ -1,24 +1,28 @@
|
|
|
1
1
|
import path from 'path'
|
|
2
|
-
import * as url from 'url'
|
|
3
2
|
import execa from 'execa'
|
|
4
3
|
import fs from 'fs'
|
|
5
4
|
import { print } from '@toptal/davinci-cli-shared'
|
|
5
|
+
import getWorkspaceRoot from 'find-yarn-workspace-root'
|
|
6
6
|
|
|
7
|
-
|
|
7
|
+
// eslint-disable-next-line no-restricted-syntax
|
|
8
|
+
import Codeowners from '../codeowners/core/codeowners/codeowners.js'
|
|
9
|
+
import { sanitizeTeamName } from './services/sanitize-team-name/sanitize-team-name.js'
|
|
10
|
+
import {
|
|
11
|
+
CYPRESS_COVERAGE_PATH,
|
|
12
|
+
JEST_COVERAGE_PATH,
|
|
13
|
+
TEAMS_COVERAGE_PATH,
|
|
14
|
+
} from './config.js'
|
|
8
15
|
|
|
9
|
-
const
|
|
10
|
-
const rootProjectPath = path.join(__dirname, '../../')
|
|
11
|
-
|
|
12
|
-
const sanitizeTeamName = team => team.replace('/', '-').replace('@', '')
|
|
16
|
+
const workspaceRoot = getWorkspaceRoot()
|
|
13
17
|
|
|
14
18
|
const sanitizeNycPercentage = percentage =>
|
|
15
19
|
percentage === 'Unknown' ? 0 : percentage
|
|
16
20
|
|
|
17
21
|
// eslint-disable-next-line max-statements
|
|
18
22
|
const generateTeamCoverage = async options => {
|
|
19
|
-
print.header('
|
|
23
|
+
print.header('Generating team coverage')
|
|
20
24
|
|
|
21
|
-
const codeowners = new Codeowners(
|
|
25
|
+
const codeowners = new Codeowners(workspaceRoot)
|
|
22
26
|
|
|
23
27
|
const ownerEntries = codeowners.ownerEntries
|
|
24
28
|
const uniqueTeams = ownerEntries
|
|
@@ -26,43 +30,40 @@ const generateTeamCoverage = async options => {
|
|
|
26
30
|
// eslint-disable-next-line id-length
|
|
27
31
|
.filter((v, i, a) => a.indexOf(v) === i)
|
|
28
32
|
|
|
29
|
-
|
|
30
|
-
console.log('Teams:', uniqueTeams)
|
|
33
|
+
print.grey('Teams: ', uniqueTeams)
|
|
31
34
|
|
|
32
35
|
const teams = uniqueTeams
|
|
33
36
|
|
|
34
|
-
await execa.command(`rm -rf
|
|
35
|
-
await execa.command(`mkdir
|
|
37
|
+
await execa.command(`rm -rf ${TEAMS_COVERAGE_PATH}`)
|
|
38
|
+
await execa.command(`mkdir ${TEAMS_COVERAGE_PATH}`)
|
|
36
39
|
|
|
37
40
|
for await (const team of teams) {
|
|
38
41
|
const sanitizedTeam = sanitizeTeamName(team)
|
|
42
|
+
const sanitizedTeamPath = path.join(TEAMS_COVERAGE_PATH, sanitizedTeam)
|
|
39
43
|
|
|
40
|
-
await execa.command(`mkdir
|
|
41
|
-
await execa.command(`mkdir
|
|
42
|
-
await execa.command(`mkdir
|
|
44
|
+
await execa.command(`mkdir ${sanitizedTeamPath}`)
|
|
45
|
+
await execa.command(`mkdir ${sanitizedTeamPath}/jest`)
|
|
46
|
+
await execa.command(`mkdir ${sanitizedTeamPath}/cypress`)
|
|
43
47
|
}
|
|
44
48
|
|
|
45
49
|
for await (const team of teams) {
|
|
46
|
-
|
|
47
|
-
console.log('Team coverage:', team)
|
|
50
|
+
print.gray('Team coverage: ', team)
|
|
48
51
|
|
|
49
52
|
const sanitizedTeam = sanitizeTeamName(team)
|
|
53
|
+
const sanitizedTeamPath = path.join(TEAMS_COVERAGE_PATH, sanitizedTeam)
|
|
50
54
|
|
|
51
55
|
await execa.command(
|
|
52
|
-
`cp
|
|
56
|
+
`cp ${JEST_COVERAGE_PATH}/coverage-final-${sanitizedTeam}.json ${sanitizedTeamPath}/jest/coverage-final.json`
|
|
53
57
|
)
|
|
54
|
-
|
|
55
|
-
// TODO add nyc as deps?
|
|
56
58
|
await execa.command(
|
|
57
|
-
`yarn nyc report --temp-dir
|
|
59
|
+
`yarn nyc report --temp-dir ${sanitizedTeamPath}/jest --reporter json-summary --reporter html --report-dir ${sanitizedTeamPath}/jest`
|
|
58
60
|
)
|
|
59
61
|
|
|
60
62
|
await execa.command(
|
|
61
|
-
`cp
|
|
63
|
+
`cp ${CYPRESS_COVERAGE_PATH}/coverage-final-${sanitizedTeam}.json ${sanitizedTeamPath}/cypress/coverage-final.json`
|
|
62
64
|
)
|
|
63
|
-
|
|
64
65
|
await execa.command(
|
|
65
|
-
`yarn nyc report --temp-dir
|
|
66
|
+
`yarn nyc report --temp-dir ${sanitizedTeamPath}/cypress --reporter json-summary --reporter html --report-dir ${sanitizedTeamPath}/cypress`
|
|
66
67
|
)
|
|
67
68
|
}
|
|
68
69
|
|
|
@@ -71,6 +72,8 @@ const generateTeamCoverage = async options => {
|
|
|
71
72
|
|
|
72
73
|
for await (const team of teams) {
|
|
73
74
|
const sanitizedTeam = sanitizeTeamName(team)
|
|
75
|
+
const sanitizedTeamPath = path.join(TEAMS_COVERAGE_PATH, sanitizedTeam)
|
|
76
|
+
|
|
74
77
|
const result = {
|
|
75
78
|
created_at,
|
|
76
79
|
team,
|
|
@@ -78,10 +81,7 @@ const generateTeamCoverage = async options => {
|
|
|
78
81
|
}
|
|
79
82
|
|
|
80
83
|
const jestCoverageSummary = JSON.parse(
|
|
81
|
-
fs.readFileSync(
|
|
82
|
-
`coverage/teams/${sanitizedTeam}/jest/coverage-summary.json`,
|
|
83
|
-
'utf8'
|
|
84
|
-
)
|
|
84
|
+
fs.readFileSync(`${sanitizedTeamPath}/jest/coverage-summary.json`, 'utf8')
|
|
85
85
|
)
|
|
86
86
|
|
|
87
87
|
result.jest_lines_coverage = sanitizeNycPercentage(
|
|
@@ -99,7 +99,7 @@ const generateTeamCoverage = async options => {
|
|
|
99
99
|
|
|
100
100
|
const cypressCoverageSummary = JSON.parse(
|
|
101
101
|
fs.readFileSync(
|
|
102
|
-
|
|
102
|
+
`${sanitizedTeamPath}/cypress/coverage-summary.json`,
|
|
103
103
|
'utf8'
|
|
104
104
|
)
|
|
105
105
|
)
|
|
@@ -120,21 +120,19 @@ const generateTeamCoverage = async options => {
|
|
|
120
120
|
results.push(result)
|
|
121
121
|
}
|
|
122
122
|
|
|
123
|
-
fs.writeFileSync(
|
|
124
|
-
'team-tests-coverage-results.json',
|
|
125
|
-
JSON.stringify(results, null, 2)
|
|
126
|
-
)
|
|
123
|
+
fs.writeFileSync(options.outputFileName, JSON.stringify(results, null, 2))
|
|
127
124
|
}
|
|
128
125
|
|
|
129
|
-
export const generateTeamCoverageCommand = program =>
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
return program
|
|
126
|
+
export const generateTeamCoverageCommand = program =>
|
|
127
|
+
program
|
|
133
128
|
.command('generate-team-coverage')
|
|
134
129
|
.description('TODO: generate-team-coverage')
|
|
135
130
|
.requiredOption(
|
|
136
131
|
'-r, --repository <repository_name>',
|
|
137
132
|
'specify repository name'
|
|
138
133
|
)
|
|
139
|
-
.
|
|
140
|
-
|
|
134
|
+
.requiredOption(
|
|
135
|
+
'-o, --output-file-name <output_file_name>',
|
|
136
|
+
'specify output file name'
|
|
137
|
+
)
|
|
138
|
+
.action(generateTeamCoverage)
|
|
@@ -1,17 +1,20 @@
|
|
|
1
1
|
import path from 'path'
|
|
2
2
|
import fs from 'fs'
|
|
3
|
-
import * as url from 'url'
|
|
4
3
|
import { print } from '@toptal/davinci-cli-shared'
|
|
4
|
+
import getWorkspaceRoot from 'find-yarn-workspace-root'
|
|
5
5
|
|
|
6
|
-
|
|
6
|
+
// eslint-disable-next-line no-restricted-syntax
|
|
7
|
+
import Codeowners from '../codeowners/core/codeowners/codeowners.js'
|
|
8
|
+
import { CYPRESS_COVERAGE_PATH, JEST_COVERAGE_PATH } from './config.js'
|
|
9
|
+
import { sanitizeTeamName } from './services/sanitize-team-name/sanitize-team-name.js'
|
|
7
10
|
|
|
8
|
-
const
|
|
9
|
-
const rootProjectPath = path.join(__dirname, '../../')
|
|
11
|
+
const workspaceRoot = getWorkspaceRoot()
|
|
10
12
|
|
|
11
13
|
const readJestCoverageReport = () => {
|
|
12
14
|
const jestCoverageReportPath = path.join(
|
|
13
|
-
|
|
14
|
-
|
|
15
|
+
workspaceRoot,
|
|
16
|
+
JEST_COVERAGE_PATH,
|
|
17
|
+
'coverage-final-jest.json'
|
|
15
18
|
)
|
|
16
19
|
|
|
17
20
|
const data = fs.readFileSync(jestCoverageReportPath, 'utf8')
|
|
@@ -21,8 +24,9 @@ const readJestCoverageReport = () => {
|
|
|
21
24
|
|
|
22
25
|
const readCypressCoverageReport = () => {
|
|
23
26
|
const cypressCoverageReportPath = path.join(
|
|
24
|
-
|
|
25
|
-
|
|
27
|
+
workspaceRoot,
|
|
28
|
+
CYPRESS_COVERAGE_PATH,
|
|
29
|
+
'coverage-final-cypress.json'
|
|
26
30
|
)
|
|
27
31
|
|
|
28
32
|
const data = fs.readFileSync(cypressCoverageReportPath, 'utf8')
|
|
@@ -30,16 +34,19 @@ const readCypressCoverageReport = () => {
|
|
|
30
34
|
return JSON.parse(data)
|
|
31
35
|
}
|
|
32
36
|
|
|
33
|
-
const
|
|
34
|
-
|
|
35
|
-
|
|
37
|
+
const splitReportIntoTeams = ({
|
|
38
|
+
reportObj,
|
|
39
|
+
teams,
|
|
40
|
+
codeowners,
|
|
41
|
+
coveragePath,
|
|
42
|
+
}) => {
|
|
36
43
|
const teamsReport = {}
|
|
37
44
|
|
|
38
45
|
Object.entries(reportObj).forEach(([reportPathKey, report]) => {
|
|
39
46
|
const file = report.path
|
|
40
|
-
const
|
|
47
|
+
const relativeWorkspacePath = path.relative(workspaceRoot, file)
|
|
41
48
|
|
|
42
|
-
const owners = codeowners.getOwner(
|
|
49
|
+
const owners = codeowners.getOwner(relativeWorkspacePath)
|
|
43
50
|
|
|
44
51
|
owners.forEach(owner => {
|
|
45
52
|
teamsReport[owner] = {
|
|
@@ -54,8 +61,9 @@ const splitReportIntoTeams = (reportObj, teams, codeowners, coveragePath) => {
|
|
|
54
61
|
const sanitizedTeamPath = sanitizeTeamName(team)
|
|
55
62
|
|
|
56
63
|
const reportPath = path.join(
|
|
57
|
-
|
|
58
|
-
|
|
64
|
+
workspaceRoot,
|
|
65
|
+
coveragePath,
|
|
66
|
+
`coverage-final-${sanitizedTeamPath}.json`
|
|
59
67
|
)
|
|
60
68
|
|
|
61
69
|
fs.writeFileSync(reportPath, JSON.stringify(teamReport, null, 2))
|
|
@@ -69,34 +77,36 @@ const getAllTeams = codeowners => {
|
|
|
69
77
|
// eslint-disable-next-line id-length
|
|
70
78
|
.filter((v, i, a) => a.indexOf(v) === i)
|
|
71
79
|
|
|
72
|
-
|
|
73
|
-
console.log('Teams:', uniqueTeams)
|
|
80
|
+
print.gray('Teams: ', uniqueTeams)
|
|
74
81
|
|
|
75
82
|
return uniqueTeams
|
|
76
83
|
}
|
|
77
84
|
|
|
78
85
|
const groupCoverageByCodeowners = async () => {
|
|
79
|
-
print.header('
|
|
86
|
+
print.header('Grouping coverage by codeowners')
|
|
80
87
|
|
|
81
88
|
const jestReport = readJestCoverageReport()
|
|
82
89
|
const cypressReport = readCypressCoverageReport()
|
|
83
90
|
|
|
84
|
-
const codeowners = new Codeowners(
|
|
91
|
+
const codeowners = new Codeowners(workspaceRoot)
|
|
85
92
|
const teams = getAllTeams(codeowners)
|
|
86
93
|
|
|
87
|
-
splitReportIntoTeams(
|
|
88
|
-
|
|
94
|
+
splitReportIntoTeams({
|
|
95
|
+
report: jestReport,
|
|
96
|
+
teams,
|
|
97
|
+
codeowners,
|
|
98
|
+
coveragePath: JEST_COVERAGE_PATH,
|
|
99
|
+
})
|
|
100
|
+
splitReportIntoTeams({
|
|
101
|
+
report: cypressReport,
|
|
102
|
+
teams,
|
|
103
|
+
codeowners,
|
|
104
|
+
coveragePath: CYPRESS_COVERAGE_PATH,
|
|
105
|
+
})
|
|
89
106
|
}
|
|
90
107
|
|
|
91
|
-
export const groupCoverageByCodeownersCommand = program =>
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
return program
|
|
108
|
+
export const groupCoverageByCodeownersCommand = program =>
|
|
109
|
+
program
|
|
95
110
|
.command('group-coverage-by-codeowners')
|
|
96
111
|
.description('TODO: group-coverage-by-codeowners')
|
|
97
|
-
.requiredOption(
|
|
98
|
-
'-r, --repository <repository_name>',
|
|
99
|
-
'specify repository name'
|
|
100
|
-
)
|
|
101
112
|
.action(groupCoverageByCodeowners)
|
|
102
|
-
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const sanitizeTeamName = team => team.replace('/', '-').replace('@', '')
|
package/src/index.js
CHANGED
|
@@ -2,7 +2,7 @@ import detectCircularityCommandCreator from './commands/detect-circularity.js'
|
|
|
2
2
|
import metricsCommandCreator from './commands/metrics.js'
|
|
3
3
|
import { createGraphGenerateCommand } from './commands/graph-generate.js'
|
|
4
4
|
import codeownersCommand from './commands/codeowners/index.js'
|
|
5
|
-
import { coverageCommand } from './commands/coverage.js'
|
|
5
|
+
import { coverageCommand } from './commands/coverage-command/index.js'
|
|
6
6
|
import checkIfMonorepo from './utils/check-if-monorepo.js'
|
|
7
7
|
import getPackages from './utils/get-packages.js'
|
|
8
8
|
|
|
@@ -4,8 +4,8 @@ import { groupCoverageByCodeownersCommand } from './group-coverage-by-codeowners
|
|
|
4
4
|
export const coverageCommand = program => {
|
|
5
5
|
const coverage = program.createCommand('coverage').description('TODO ..')
|
|
6
6
|
|
|
7
|
-
generateTeamCoverageCommand(coverage)
|
|
8
7
|
groupCoverageByCodeownersCommand(coverage)
|
|
8
|
+
generateTeamCoverageCommand(coverage)
|
|
9
9
|
|
|
10
10
|
return coverage
|
|
11
11
|
}
|