Skip to content

Commit e9cfaf5

Browse files
authored
Merge pull request #227 from codecov/fix-token-from-yaml
feat: Allow for token from yaml
2 parents 3e1beda + a2e5f4f commit e9cfaf5

File tree

10 files changed

+208
-26
lines changed

10 files changed

+208
-26
lines changed

npm-shrinkwrap.json

Lines changed: 66 additions & 13 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@
2828
"homepage": "https://github.com/codecov/uploader#readme",
2929
"dependencies": {
3030
"glob": "7.1.7",
31+
"js-yaml": "4.1.0",
3132
"line-reader": "0.4.0",
3233
"superagent": "6.1.0",
3334
"typescript": "4.3.5",

src/helpers/files.js

Lines changed: 8 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
// @ts-check
22
const childProcess = require('child_process')
33
const fs = require('fs')
4-
const path = require('path').posix
54
const glob = require('glob')
5+
const path = require('path').posix
6+
67
const { log } = require('./logger')
78

89
/**
@@ -337,16 +338,16 @@ function removeFile(projectRoot, filePath) {
337338
}
338339

339340
module.exports = {
340-
readCoverageFile,
341-
getFileListing,
341+
coverageFilePatterns,
342+
endEnvironmentMarker,
342343
endFileMarker,
343344
endNetworkMarker,
344-
endEnvironmentMarker,
345-
fileHeader,
346345
fetchGitRoot,
347-
parseGitIgnore,
346+
fileHeader,
348347
getCoverageFiles,
349-
coverageFilePatterns,
348+
getFileListing,
350349
getFilePath,
350+
parseGitIgnore,
351+
readCoverageFile,
351352
removeFile,
352353
}

src/helpers/token.js

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
const fs = require('fs')
2+
const path = require('path')
3+
const yaml = require('js-yaml')
4+
5+
const { log } = require('./logger')
6+
const validateHelpers = require('./validate')
7+
8+
function getToken(inputs, projectRoot) {
9+
const { args, envs } = inputs
10+
const options = [
11+
[args.token, 'arguments'],
12+
[envs.CODECOV_TOKEN, 'environment variables'],
13+
[getTokenFromYaml(projectRoot), 'Codecov yaml config'],
14+
]
15+
16+
for (const option of options) {
17+
if (option[0] && validateHelpers.validateToken(option[0])) {
18+
log(`-> Token set by ${option[1]}`)
19+
return option[0]
20+
}
21+
}
22+
23+
return ''
24+
}
25+
26+
function getTokenFromYaml(projectRoot) {
27+
const dirNames = [
28+
'',
29+
'.github',
30+
'dev',
31+
]
32+
33+
const yamlNames = [
34+
'.codecov.yaml',
35+
'.codecov.yml',
36+
'codecov.yaml',
37+
'codecov.yml',
38+
]
39+
40+
for (const dir of dirNames) {
41+
for (const name of yamlNames) {
42+
const filePath = path.join(projectRoot, dir, name);
43+
44+
try {
45+
if (fs.existsSync(filePath)) {
46+
const fileContents = fs.readFileSync(filePath, {
47+
encoding: 'utf-8',
48+
});
49+
const yamlConfig = yaml.load(fileContents);
50+
if (
51+
yamlConfig['codecov_token'] &&
52+
validateHelpers.validateToken(yamlConfig['codecov_token'])
53+
) {
54+
return yamlConfig['codecov_token']
55+
}
56+
}
57+
} catch(err) {
58+
log(`Error searching for upload token in ${filePath}: ${err}`, { level: 'debug' })
59+
}
60+
}
61+
}
62+
return ''
63+
}
64+
65+
66+
module.exports = {
67+
getToken,
68+
getTokenFromYaml,
69+
}

src/index.js

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ const zlib = require('zlib')
33
const { version } = require('../package.json')
44
const fileHelpers = require('./helpers/files')
55
const validateHelpers = require('./helpers/validate')
6+
const tokenHelpers = require('./helpers/token')
67
const webHelpers = require('./helpers/web')
78
const { log } = require('./helpers/logger')
89
const providers = require('./ci_providers')
@@ -71,7 +72,6 @@ async function main(args) {
7172
? args.url
7273
: 'https://codecov.io'
7374

74-
const token = validateHelpers.getToken(args)
7575
log(generateHeader(getVersion()))
7676

7777
// == Step 2: detect if we are in a git repo
@@ -84,7 +84,10 @@ async function main(args) {
8484

8585
log(`=> Project root located at: ${projectRoot}`)
8686

87-
// == Step 3: get network
87+
// == Step 3: sanitize and set token
88+
const token = await tokenHelpers.getToken(inputs, projectRoot)
89+
90+
// == Step 4: get network
8891
let uploadFile = ''
8992

9093
if (!args.feature || args.feature.split(',').includes('network') === false) {
@@ -101,7 +104,7 @@ async function main(args) {
101104
.concat(fileHelpers.endNetworkMarker())
102105
}
103106

104-
// == Step 4: select coverage files (search or specify)
107+
// == Step 5: select coverage files (search or specify)
105108

106109
// Look for files
107110
let coverageFilePaths = []
@@ -136,7 +139,7 @@ async function main(args) {
136139
}
137140
log('End of network processing', { level: 'debug', args })
138141

139-
// == Step 5: generate upload file
142+
// == Step 6: generate upload file
140143
// TODO: capture envs
141144

142145
// Get coverage report contents
@@ -181,7 +184,7 @@ async function main(args) {
181184

182185
const gzippedFile = zlib.gzipSync(uploadFile)
183186

184-
// == Step 6: determine CI provider
187+
// == Step 7: determine CI provider
185188

186189
// Determine CI provider
187190
let serviceParams
@@ -197,7 +200,7 @@ async function main(args) {
197200
throw new Error('Unable to detect service, please specify manually.')
198201
}
199202

200-
// == Step 7: either upload or dry-run
203+
// == Step 8: either upload or dry-run
201204

202205
const query = webHelpers.generateQuery(
203206
webHelpers.populateBuildParams(inputs, serviceParams),

test/fixtures/yaml/.codecov.yaml

Whitespace-only changes.

test/fixtures/yaml/.codecov.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
codecov_token: invalid token

test/fixtures/yaml/codecov.yaml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
codecov_token: faketoken

test/fixtures/yaml/codecov.yml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
codecov_token: anotherfaketoken

test/helpers/token.test.js

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
const path = require('path')
2+
3+
const fileHelpers = require('../../src/helpers/files')
4+
const tokenHelpers = require('../../src/helpers/token')
5+
6+
describe('Get tokens', () => {
7+
const fixturesDir = path.join(fileHelpers.fetchGitRoot(), 'test/fixtures/yaml')
8+
console.log(fixturesDir)
9+
describe('From yaml', () => {
10+
it('Returns empty with no yaml file', () => {
11+
expect(tokenHelpers.getTokenFromYaml('.')).toBe('')
12+
})
13+
14+
it('Returns the correct token from file', () => {
15+
expect(tokenHelpers.getTokenFromYaml(fixturesDir)).toBe('faketoken')
16+
})
17+
})
18+
19+
describe('From right source', () => {
20+
it('Returns from args', () => {
21+
const inputs = {
22+
args: { token: 'argtoken' },
23+
envs: { CODECOV_TOKEN: 'envtoken' }
24+
}
25+
expect(tokenHelpers.getToken(inputs, fixturesDir)).toBe('argtoken')
26+
})
27+
28+
it('Returns from env', () => {
29+
const inputs = {
30+
args: {},
31+
envs: { CODECOV_TOKEN: 'envtoken' }
32+
}
33+
expect(tokenHelpers.getToken(inputs, fixturesDir)).toBe('envtoken')
34+
})
35+
36+
it('Returns from env', () => {
37+
const inputs = {
38+
args: {},
39+
envs: {}
40+
}
41+
expect(tokenHelpers.getToken(inputs, fixturesDir)).toBe('faketoken')
42+
})
43+
44+
it('Returns from no source', () => {
45+
const inputs = {
46+
args: {},
47+
envs: {}
48+
}
49+
expect(tokenHelpers.getToken(inputs, '.')).toBe('')
50+
})
51+
})
52+
})

0 commit comments

Comments
 (0)