GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Passed
Push — master ( 25ec51...117080 )
by
unknown
07:44
created

derBuilder.WithDurationSeconds   A

Complexity

Conditions 1

Size

Total Lines 3
Code Lines 3

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 3
nop 1
dl 0
loc 3
rs 10
c 0
b 0
f 0
1
package providers
2
3
import (
4
	"encoding/json"
5
	"errors"
6
	"fmt"
7
	"net/http"
8
	"net/url"
9
	"os"
10
	"strconv"
11
	"strings"
12
	"time"
13
14
	httputil "github.com/aliyun/credentials-go/credentials/internal/http"
15
	"github.com/aliyun/credentials-go/credentials/internal/utils"
16
)
17
18
type assumedRoleUser struct {
19
}
20
21
type credentials struct {
22
	SecurityToken   *string `json:"SecurityToken"`
23
	Expiration      *string `json:"Expiration"`
24
	AccessKeySecret *string `json:"AccessKeySecret"`
25
	AccessKeyId     *string `json:"AccessKeyId"`
26
}
27
28
type assumeRoleResponse struct {
29
	RequestID       *string          `json:"RequestId"`
30
	AssumedRoleUser *assumedRoleUser `json:"AssumedRoleUser"`
31
	Credentials     *credentials     `json:"Credentials"`
32
}
33
34
type sessionCredentials struct {
35
	AccessKeyId     string
36
	AccessKeySecret string
37
	SecurityToken   string
38
	Expiration      string
39
}
40
41
type HttpOptions struct {
42
	Proxy string
43
	// Connection timeout, in milliseconds.
44
	ConnectTimeout int
45
	// Read timeout, in milliseconds.
46
	ReadTimeout int
47
}
48
49
type RAMRoleARNCredentialsProvider struct {
50
	// for previous credentials
51
	accessKeyId         string
52
	accessKeySecret     string
53
	securityToken       string
54
	credentialsProvider CredentialsProvider
55
56
	roleArn         string
57
	roleSessionName string
58
	durationSeconds int
59
	policy          string
60
	externalId      string
61
	// for sts endpoint
62
	stsRegionId string
63
	enableVpc   bool
64
	stsEndpoint string
65
	// for http options
66
	httpOptions *HttpOptions
67
	// inner
68
	expirationTimestamp int64
69
	lastUpdateTimestamp int64
70
	sessionCredentials  *sessionCredentials
71
}
72
73
type RAMRoleARNCredentialsProviderBuilder struct {
74
	provider *RAMRoleARNCredentialsProvider
75
}
76
77
func NewRAMRoleARNCredentialsProviderBuilder() *RAMRoleARNCredentialsProviderBuilder {
78
	return &RAMRoleARNCredentialsProviderBuilder{
79
		provider: &RAMRoleARNCredentialsProvider{},
80
	}
81
}
82
83
func (builder *RAMRoleARNCredentialsProviderBuilder) WithAccessKeyId(accessKeyId string) *RAMRoleARNCredentialsProviderBuilder {
84
	builder.provider.accessKeyId = accessKeyId
85
	return builder
86
}
87
88
func (builder *RAMRoleARNCredentialsProviderBuilder) WithAccessKeySecret(accessKeySecret string) *RAMRoleARNCredentialsProviderBuilder {
89
	builder.provider.accessKeySecret = accessKeySecret
90
	return builder
91
}
92
93
func (builder *RAMRoleARNCredentialsProviderBuilder) WithSecurityToken(securityToken string) *RAMRoleARNCredentialsProviderBuilder {
94
	builder.provider.securityToken = securityToken
95
	return builder
96
}
97
98
func (builder *RAMRoleARNCredentialsProviderBuilder) WithCredentialsProvider(credentialsProvider CredentialsProvider) *RAMRoleARNCredentialsProviderBuilder {
99
	builder.provider.credentialsProvider = credentialsProvider
100
	return builder
101
}
102
103
func (builder *RAMRoleARNCredentialsProviderBuilder) WithRoleArn(roleArn string) *RAMRoleARNCredentialsProviderBuilder {
104
	builder.provider.roleArn = roleArn
105
	return builder
106
}
107
108
func (builder *RAMRoleARNCredentialsProviderBuilder) WithStsRegionId(regionId string) *RAMRoleARNCredentialsProviderBuilder {
109
	builder.provider.stsRegionId = regionId
110
	return builder
111
}
112
113
func (builder *RAMRoleARNCredentialsProviderBuilder) WithEnableVpc(enableVpc bool) *RAMRoleARNCredentialsProviderBuilder {
114
	builder.provider.enableVpc = enableVpc
115
	return builder
116
}
117
118
func (builder *RAMRoleARNCredentialsProviderBuilder) WithStsEndpoint(endpoint string) *RAMRoleARNCredentialsProviderBuilder {
119
	builder.provider.stsEndpoint = endpoint
120
	return builder
121
}
122
123
func (builder *RAMRoleARNCredentialsProviderBuilder) WithRoleSessionName(roleSessionName string) *RAMRoleARNCredentialsProviderBuilder {
124
	builder.provider.roleSessionName = roleSessionName
125
	return builder
126
}
127
128
func (builder *RAMRoleARNCredentialsProviderBuilder) WithPolicy(policy string) *RAMRoleARNCredentialsProviderBuilder {
129
	builder.provider.policy = policy
130
	return builder
131
}
132
133
func (builder *RAMRoleARNCredentialsProviderBuilder) WithExternalId(externalId string) *RAMRoleARNCredentialsProviderBuilder {
134
	builder.provider.externalId = externalId
135
	return builder
136
}
137
138
func (builder *RAMRoleARNCredentialsProviderBuilder) WithDurationSeconds(durationSeconds int) *RAMRoleARNCredentialsProviderBuilder {
139
	builder.provider.durationSeconds = durationSeconds
140
	return builder
141
}
142
143
func (builder *RAMRoleARNCredentialsProviderBuilder) WithHttpOptions(httpOptions *HttpOptions) *RAMRoleARNCredentialsProviderBuilder {
144
	builder.provider.httpOptions = httpOptions
145
	return builder
146
}
147
148
func (builder *RAMRoleARNCredentialsProviderBuilder) Build() (provider *RAMRoleARNCredentialsProvider, err error) {
149
	if builder.provider.credentialsProvider == nil {
150
		if builder.provider.accessKeyId != "" && builder.provider.accessKeySecret != "" && builder.provider.securityToken != "" {
151
			builder.provider.credentialsProvider, err = NewStaticSTSCredentialsProviderBuilder().
152
				WithAccessKeyId(builder.provider.accessKeyId).
153
				WithAccessKeySecret(builder.provider.accessKeySecret).
154
				WithSecurityToken(builder.provider.securityToken).
155
				Build()
156
			if err != nil {
157
				return
158
			}
159
		} else if builder.provider.accessKeyId != "" && builder.provider.accessKeySecret != "" {
160
			builder.provider.credentialsProvider, err = NewStaticAKCredentialsProviderBuilder().
161
				WithAccessKeyId(builder.provider.accessKeyId).
162
				WithAccessKeySecret(builder.provider.accessKeySecret).
163
				Build()
164
			if err != nil {
165
				return
166
			}
167
		} else {
168
			err = errors.New("must specify a previous credentials provider to assume role")
169
			return
170
		}
171
	}
172
173
	if builder.provider.roleArn == "" {
174
		if roleArn := os.Getenv("ALIBABA_CLOUD_ROLE_ARN"); roleArn != "" {
175
			builder.provider.roleArn = roleArn
176
		} else {
177
			err = errors.New("the RoleArn is empty")
178
			return
179
		}
180
	}
181
182
	if builder.provider.roleSessionName == "" {
183
		if roleSessionName := os.Getenv("ALIBABA_CLOUD_ROLE_SESSION_NAME"); roleSessionName != "" {
184
			builder.provider.roleSessionName = roleSessionName
185
		} else {
186
			builder.provider.roleSessionName = "credentials-go-" + strconv.FormatInt(time.Now().UnixNano()/1000, 10)
187
		}
188
	}
189
190
	// duration seconds
191
	if builder.provider.durationSeconds == 0 {
192
		// default to 3600
193
		builder.provider.durationSeconds = 3600
194
	}
195
196
	if builder.provider.durationSeconds < 900 {
197
		err = errors.New("session duration should be in the range of 900s - max session duration")
198
		return
199
	}
200
201
	// sts endpoint
202
	if builder.provider.stsEndpoint == "" {
203
		if !builder.provider.enableVpc {
204
			builder.provider.enableVpc = strings.ToLower(os.Getenv("ALIBABA_CLOUD_VPC_ENDPOINT_ENABLED")) == "true"
205
		}
206
		prefix := "sts"
207
		if builder.provider.enableVpc {
208
			prefix = "sts-vpc"
209
		}
210
		if builder.provider.stsRegionId != "" {
211
			builder.provider.stsEndpoint = fmt.Sprintf("%s.%s.aliyuncs.com", prefix, builder.provider.stsRegionId)
212
		} else if region := os.Getenv("ALIBABA_CLOUD_STS_REGION"); region != "" {
213
			builder.provider.stsEndpoint = fmt.Sprintf("%s.%s.aliyuncs.com", prefix, region)
214
		} else {
215
			builder.provider.stsEndpoint = "sts.aliyuncs.com"
216
		}
217
	}
218
219
	provider = builder.provider
220
	return
221
}
222
223
func (provider *RAMRoleARNCredentialsProvider) getCredentials(cc *Credentials) (session *sessionCredentials, err error) {
224
	method := "POST"
225
	req := &httputil.Request{
226
		Method:   method,
227
		Protocol: "https",
228
		Host:     provider.stsEndpoint,
229
		Headers:  map[string]string{},
230
	}
231
232
	queries := make(map[string]string)
233
	queries["Version"] = "2015-04-01"
234
	queries["Action"] = "AssumeRole"
235
	queries["Format"] = "JSON"
236
	queries["Timestamp"] = utils.GetTimeInFormatISO8601()
237
	queries["SignatureMethod"] = "HMAC-SHA1"
238
	queries["SignatureVersion"] = "1.0"
239
	queries["SignatureNonce"] = utils.GetNonce()
240
	queries["AccessKeyId"] = cc.AccessKeyId
241
242
	if cc.SecurityToken != "" {
243
		queries["SecurityToken"] = cc.SecurityToken
244
	}
245
246
	bodyForm := make(map[string]string)
247
	bodyForm["RoleArn"] = provider.roleArn
248
	if provider.policy != "" {
249
		bodyForm["Policy"] = provider.policy
250
	}
251
	if provider.externalId != "" {
252
		bodyForm["ExternalId"] = provider.externalId
253
	}
254
	bodyForm["RoleSessionName"] = provider.roleSessionName
255
	bodyForm["DurationSeconds"] = strconv.Itoa(provider.durationSeconds)
256
	req.Form = bodyForm
257
258
	// caculate signature
259
	signParams := make(map[string]string)
260
	for key, value := range queries {
261
		signParams[key] = value
262
	}
263
	for key, value := range bodyForm {
264
		signParams[key] = value
265
	}
266
267
	stringToSign := utils.GetURLFormedMap(signParams)
268
	stringToSign = strings.Replace(stringToSign, "+", "%20", -1)
269
	stringToSign = strings.Replace(stringToSign, "*", "%2A", -1)
270
	stringToSign = strings.Replace(stringToSign, "%7E", "~", -1)
271
	stringToSign = url.QueryEscape(stringToSign)
272
	stringToSign = method + "&%2F&" + stringToSign
273
	secret := cc.AccessKeySecret + "&"
274
	queries["Signature"] = utils.ShaHmac1(stringToSign, secret)
275
276
	req.Queries = queries
277
278
	// set headers
279
	req.Headers["Accept-Encoding"] = "identity"
280
	req.Headers["Content-Type"] = "application/x-www-form-urlencoded"
281
	req.Headers["x-acs-credentials-provider"] = cc.ProviderName
282
283
	connectTimeout := 5 * time.Second
284
	readTimeout := 10 * time.Second
285
286
	if provider.httpOptions != nil && provider.httpOptions.ConnectTimeout > 0 {
287
		connectTimeout = time.Duration(provider.httpOptions.ConnectTimeout) * time.Millisecond
288
	}
289
	if provider.httpOptions != nil && provider.httpOptions.ReadTimeout > 0 {
290
		readTimeout = time.Duration(provider.httpOptions.ReadTimeout) * time.Millisecond
291
	}
292
	if provider.httpOptions != nil && provider.httpOptions.Proxy != "" {
293
		req.Proxy = provider.httpOptions.Proxy
294
	}
295
	req.ConnectTimeout = connectTimeout
296
	req.ReadTimeout = readTimeout
297
298
	res, err := httpDo(req)
299
	if err != nil {
300
		return
301
	}
302
303
	if res.StatusCode != http.StatusOK {
304
		err = errors.New("refresh session token failed: " + string(res.Body))
305
		return
306
	}
307
	var data assumeRoleResponse
308
	err = json.Unmarshal(res.Body, &data)
309
	if err != nil {
310
		err = fmt.Errorf("refresh RoleArn sts token err, json.Unmarshal fail: %s", err.Error())
311
		return
312
	}
313
	if data.Credentials == nil {
314
		err = fmt.Errorf("refresh RoleArn sts token err, fail to get credentials")
315
		return
316
	}
317
318
	if data.Credentials.AccessKeyId == nil || data.Credentials.AccessKeySecret == nil || data.Credentials.SecurityToken == nil {
319
		err = fmt.Errorf("refresh RoleArn sts token err, fail to get credentials")
320
		return
321
	}
322
323
	session = &sessionCredentials{
324
		AccessKeyId:     *data.Credentials.AccessKeyId,
325
		AccessKeySecret: *data.Credentials.AccessKeySecret,
326
		SecurityToken:   *data.Credentials.SecurityToken,
327
		Expiration:      *data.Credentials.Expiration,
328
	}
329
	return
330
}
331
332
func (provider *RAMRoleARNCredentialsProvider) needUpdateCredential() (result bool) {
333
	if provider.expirationTimestamp == 0 {
334
		return true
335
	}
336
337
	return provider.expirationTimestamp-time.Now().Unix() <= 180
338
}
339
340
func (provider *RAMRoleARNCredentialsProvider) GetCredentials() (cc *Credentials, err error) {
341
	if provider.sessionCredentials == nil || provider.needUpdateCredential() {
342
		// 获取前置凭证
343
		previousCredentials, err1 := provider.credentialsProvider.GetCredentials()
344
		if err1 != nil {
345
			return nil, err1
346
		}
347
		sessionCredentials, err2 := provider.getCredentials(previousCredentials)
348
		if err2 != nil {
349
			return nil, err2
350
		}
351
352
		expirationTime, err := time.Parse("2006-01-02T15:04:05Z", sessionCredentials.Expiration)
353
		if err != nil {
354
			return nil, err
355
		}
356
357
		provider.expirationTimestamp = expirationTime.Unix()
358
		provider.lastUpdateTimestamp = time.Now().Unix()
359
		provider.sessionCredentials = sessionCredentials
360
	}
361
362
	cc = &Credentials{
363
		AccessKeyId:     provider.sessionCredentials.AccessKeyId,
364
		AccessKeySecret: provider.sessionCredentials.AccessKeySecret,
365
		SecurityToken:   provider.sessionCredentials.SecurityToken,
366
		ProviderName:    fmt.Sprintf("%s/%s", provider.GetProviderName(), provider.credentialsProvider.GetProviderName()),
367
	}
368
	return
369
}
370
371
func (provider *RAMRoleARNCredentialsProvider) GetProviderName() string {
372
	return "ram_role_arn"
373
}
374