screwdriver-api 6.0.8 → 6.0.10
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/config/custom-environment-variables.yaml +7 -0
- package/config/default.yaml +24 -1
- package/lib/server.js +2 -2
- package/package.json +1 -1
- package/plugins/auth/index.js +10 -3
- package/plugins/auth/login.js +21 -6
- package/plugins/auth/token.js +6 -4
- package/plugins/builds/token.js +1 -0
- package/plugins/pipelines/caches/request.js +1 -1
|
@@ -31,9 +31,16 @@ auth:
|
|
|
31
31
|
whitelist:
|
|
32
32
|
__name: SECRET_WHITELIST
|
|
33
33
|
__format: json
|
|
34
|
+
allowList:
|
|
35
|
+
__name: SECRET_ALLOW_LIST
|
|
36
|
+
__format: json
|
|
34
37
|
admins:
|
|
35
38
|
__name: SECRET_ADMINS
|
|
36
39
|
__format: json
|
|
40
|
+
sdAdmins:
|
|
41
|
+
__name: SECRET_SD_ADMINS
|
|
42
|
+
__format: json
|
|
43
|
+
authCheckById: AUTH_CHECK_BY_ID
|
|
37
44
|
# Default session timeout (in minutes)
|
|
38
45
|
sessionTimeout: SESSION_TIMEOUT
|
|
39
46
|
# Oauth redirect uri, configure this if your app is not running at root under the host
|
package/config/default.yaml
CHANGED
|
@@ -32,10 +32,33 @@ auth:
|
|
|
32
32
|
https: false
|
|
33
33
|
# A flag to set if you want guests to browse your pipelines
|
|
34
34
|
allowGuestAccess: false
|
|
35
|
-
#
|
|
35
|
+
# Deprecated. Instead, use allowList which is more secure.
|
|
36
|
+
# List of users able to authenticate against the system
|
|
36
37
|
# if empty, it allows everyone
|
|
38
|
+
# Values should follow '{scmDisplayName:scmUsername}' format
|
|
39
|
+
# Ex: ['github:john', 'bitbucket:john']
|
|
37
40
|
whitelist: []
|
|
41
|
+
# list of users able to authenticate against the system
|
|
42
|
+
# if empty, it allows everyone
|
|
43
|
+
# Values should follow '{scmDisplayName:scmUsername:scmUserId}' format
|
|
44
|
+
# Ex: ['github:john:12345', 'bitbucket:john:{98fsa1ba-0b91-4e3c-95ee-55899e933b0}']
|
|
45
|
+
allowList: []
|
|
46
|
+
# Deprecated. Instead, use sdAdmins which is more secure.
|
|
47
|
+
# List of users who should be given screwdriver admin privileges
|
|
48
|
+
# Values should follow '{scmDisplayName:scmUsername}' format
|
|
49
|
+
# Ex: ['github:john', 'bitbucket:john']
|
|
38
50
|
admins: []
|
|
51
|
+
# List of users who should be given screwdriver admin privileges
|
|
52
|
+
# Values should follow '{scmDisplayName:scmUsername:scmUserId}' format
|
|
53
|
+
# Ex: ['github:john:12345', 'bitbucket:john:{98fsa1ba-0b91-4e3c-95ee-55899e933b0}']
|
|
54
|
+
sdAdmins: []
|
|
55
|
+
# When set to true
|
|
56
|
+
# - grant admin privileges to the users listed in 'sdAdmins'
|
|
57
|
+
# - only authenticate the users listed in 'allowList'
|
|
58
|
+
# When set to false, performs
|
|
59
|
+
# - grant admin privileges to the users listed in 'admins'
|
|
60
|
+
# - only authenticate the users listed in 'whitelist'
|
|
61
|
+
authCheckById: true
|
|
39
62
|
# Default session timeout (in minutes)
|
|
40
63
|
sessionTimeout: 120
|
|
41
64
|
# SameSite Cookie Option
|
package/lib/server.js
CHANGED
|
@@ -201,7 +201,7 @@ module.exports = async config => {
|
|
|
201
201
|
server.app.buildFactory.apiUri = server.info.uri;
|
|
202
202
|
server.app.buildFactory.tokenGen = (buildId, metadata, scmContext, expiresIn, scope = ['temporal']) =>
|
|
203
203
|
server.plugins.auth.generateToken(
|
|
204
|
-
server.plugins.auth.generateProfile(buildId, scmContext, scope, metadata),
|
|
204
|
+
server.plugins.auth.generateProfile(buildId, null, scmContext, scope, metadata),
|
|
205
205
|
expiresIn
|
|
206
206
|
);
|
|
207
207
|
server.app.buildFactory.executor.tokenGen = server.app.buildFactory.tokenGen;
|
|
@@ -209,7 +209,7 @@ module.exports = async config => {
|
|
|
209
209
|
server.app.jobFactory.apiUri = server.info.uri;
|
|
210
210
|
server.app.jobFactory.tokenGen = (username, metadata, scmContext, scope = ['user']) =>
|
|
211
211
|
server.plugins.auth.generateToken(
|
|
212
|
-
server.plugins.auth.generateProfile(username, scmContext, scope, metadata)
|
|
212
|
+
server.plugins.auth.generateProfile(username, null, scmContext, scope, metadata)
|
|
213
213
|
);
|
|
214
214
|
server.app.jobFactory.executor.userTokenGen = server.app.jobFactory.tokenGen;
|
|
215
215
|
|
package/package.json
CHANGED
package/plugins/auth/index.js
CHANGED
|
@@ -60,8 +60,11 @@ const AUTH_PLUGIN_SCHEMA = joi.object().keys({
|
|
|
60
60
|
jwtPrivateKey: joi.string().required(),
|
|
61
61
|
jwtPublicKey: joi.string().required(),
|
|
62
62
|
jwtQueueServicePublicKey: joi.string().required(),
|
|
63
|
+
authCheckById: JOI_BOOLEAN.default(true),
|
|
63
64
|
whitelist: joi.array().default([]),
|
|
65
|
+
allowList: joi.array().default([]),
|
|
64
66
|
admins: joi.array().default([]),
|
|
67
|
+
sdAdmins: joi.array().default([]),
|
|
65
68
|
bell: joi.object().required(),
|
|
66
69
|
scm: joi.object().required(),
|
|
67
70
|
sessionTimeout: joi.number().integer().positive().default(120),
|
|
@@ -95,12 +98,13 @@ const authPlugin = {
|
|
|
95
98
|
* Generates a profile for storage in cookie and jwt
|
|
96
99
|
* @method generateProfile
|
|
97
100
|
* @param {String} username Username of the person
|
|
101
|
+
* @param {String} scmUserId User ID in the SCM
|
|
98
102
|
* @param {String} scmContext Scm to which the person logged in belongs
|
|
99
103
|
* @param {Array} scope Scope for this profile (usually build or user)
|
|
100
104
|
* @param {Object} metadata Additonal information to tag along with the login
|
|
101
105
|
* @return {Object} The profile to be stored in jwt and/or cookie
|
|
102
106
|
*/
|
|
103
|
-
server.expose('generateProfile', (username, scmContext, scope, metadata) => {
|
|
107
|
+
server.expose('generateProfile', (username, scmUserId, scmContext, scope, metadata) => {
|
|
104
108
|
const profile = { username, scmContext, scope, ...(metadata || {}) };
|
|
105
109
|
|
|
106
110
|
if (pluginOptions.jwtEnvironment) {
|
|
@@ -110,10 +114,13 @@ const authPlugin = {
|
|
|
110
114
|
if (scmContext) {
|
|
111
115
|
const { scm } = pluginOptions;
|
|
112
116
|
const scmDisplayName = scm.getDisplayName({ scmContext });
|
|
113
|
-
const userDisplayName =
|
|
117
|
+
const userDisplayName = pluginOptions.authCheckById
|
|
118
|
+
? `${scmDisplayName}:${username}:${scmUserId}`
|
|
119
|
+
: `${scmDisplayName}:${username}`;
|
|
120
|
+
const admins = pluginOptions.authCheckById ? pluginOptions.sdAdmins : pluginOptions.admins;
|
|
114
121
|
|
|
115
122
|
// Check admin
|
|
116
|
-
if (
|
|
123
|
+
if (admins.length > 0 && admins.includes(userDisplayName)) {
|
|
117
124
|
profile.scope.push('admin');
|
|
118
125
|
}
|
|
119
126
|
}
|
package/plugins/auth/login.js
CHANGED
|
@@ -32,7 +32,13 @@ function addGuestRoute(config) {
|
|
|
32
32
|
}
|
|
33
33
|
|
|
34
34
|
const username = `guest/${uuidv4()}`;
|
|
35
|
-
const profile = request.server.plugins.auth.generateProfile(
|
|
35
|
+
const profile = request.server.plugins.auth.generateProfile(
|
|
36
|
+
username,
|
|
37
|
+
null,
|
|
38
|
+
null,
|
|
39
|
+
['user', 'guest'],
|
|
40
|
+
{}
|
|
41
|
+
);
|
|
36
42
|
|
|
37
43
|
// Log that the user has authenticated
|
|
38
44
|
request.log(['auth'], `${username} has logged in`);
|
|
@@ -81,14 +87,23 @@ function addOAuthRoutes(config) {
|
|
|
81
87
|
const { userFactory } = request.server.app;
|
|
82
88
|
const { collectionFactory } = request.server.app;
|
|
83
89
|
const accessToken = request.auth.credentials.token;
|
|
84
|
-
const { username } = request.auth.credentials.profile;
|
|
85
|
-
|
|
86
|
-
const profile = request.server.plugins.auth.generateProfile(
|
|
90
|
+
const { username, id: scmUserId } = request.auth.credentials.profile;
|
|
91
|
+
|
|
92
|
+
const profile = request.server.plugins.auth.generateProfile(
|
|
93
|
+
username,
|
|
94
|
+
scmUserId,
|
|
95
|
+
scmContext,
|
|
96
|
+
['user'],
|
|
97
|
+
{}
|
|
98
|
+
);
|
|
87
99
|
const scmDisplayName = await userFactory.scm.getDisplayName({ scmContext });
|
|
88
|
-
const userDisplayName =
|
|
100
|
+
const userDisplayName = config.authCheckById
|
|
101
|
+
? `${scmDisplayName}:${username}:${scmUserId}`
|
|
102
|
+
: `${scmDisplayName}:${username}`;
|
|
103
|
+
const allowList = config.authCheckById ? config.allowList : config.whitelist;
|
|
89
104
|
|
|
90
105
|
// Check whitelist
|
|
91
|
-
if (
|
|
106
|
+
if (allowList.length > 0 && !allowList.includes(userDisplayName)) {
|
|
92
107
|
return boom.forbidden(`User ${userDisplayName} is not allowed access`);
|
|
93
108
|
}
|
|
94
109
|
|
package/plugins/auth/token.js
CHANGED
|
@@ -39,10 +39,12 @@ module.exports = () => ({
|
|
|
39
39
|
const job = await jobFactory.get(build.jobId);
|
|
40
40
|
const pipeline = pipelineFactory.get(job.pipelineId);
|
|
41
41
|
|
|
42
|
-
profile = request.server.plugins.auth.generateProfile(
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
42
|
+
profile = request.server.plugins.auth.generateProfile(
|
|
43
|
+
request.params.buildId,
|
|
44
|
+
null,
|
|
45
|
+
pipeline.scmContext,
|
|
46
|
+
['build', 'impersonated']
|
|
47
|
+
);
|
|
46
48
|
profile.token = request.server.plugins.auth.generateToken(profile);
|
|
47
49
|
|
|
48
50
|
request.cookieAuth.set(profile);
|
package/plugins/builds/token.js
CHANGED
|
@@ -36,7 +36,7 @@ async function invoke(request) {
|
|
|
36
36
|
const { username, scmContext } = auth.credentials;
|
|
37
37
|
|
|
38
38
|
const token = request.server.plugins.auth.generateToken(
|
|
39
|
-
request.server.plugins.auth.generateProfile(username, scmContext, ['sdapi'], { pipelineId })
|
|
39
|
+
request.server.plugins.auth.generateProfile(username, null, scmContext, ['sdapi'], { pipelineId })
|
|
40
40
|
);
|
|
41
41
|
|
|
42
42
|
const options = {
|