Commit 9855ea8c by Mitsuhiro Tanda Committed by Torkel Ödegaard

handle sts error (#7088)

parent 08bad530
...@@ -17,7 +17,6 @@ import ( ...@@ -17,7 +17,6 @@ import (
"github.com/aws/aws-sdk-go/service/cloudwatch" "github.com/aws/aws-sdk-go/service/cloudwatch"
"github.com/aws/aws-sdk-go/service/ec2" "github.com/aws/aws-sdk-go/service/ec2"
"github.com/aws/aws-sdk-go/service/sts" "github.com/aws/aws-sdk-go/service/sts"
"github.com/grafana/grafana/pkg/log"
"github.com/grafana/grafana/pkg/metrics" "github.com/grafana/grafana/pkg/metrics"
"github.com/grafana/grafana/pkg/middleware" "github.com/grafana/grafana/pkg/middleware"
m "github.com/grafana/grafana/pkg/models" m "github.com/grafana/grafana/pkg/models"
...@@ -90,7 +89,7 @@ type cache struct { ...@@ -90,7 +89,7 @@ type cache struct {
var awsCredentialCache map[string]cache = make(map[string]cache) var awsCredentialCache map[string]cache = make(map[string]cache)
var credentialCacheLock sync.RWMutex var credentialCacheLock sync.RWMutex
func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials { func getCredentials(dsInfo *datasourceInfo) (*credentials.Credentials, error) {
cacheKey := dsInfo.Profile + ":" + dsInfo.AssumeRoleArn cacheKey := dsInfo.Profile + ":" + dsInfo.AssumeRoleArn
credentialCacheLock.RLock() credentialCacheLock.RLock()
if _, ok := awsCredentialCache[cacheKey]; ok { if _, ok := awsCredentialCache[cacheKey]; ok {
...@@ -98,7 +97,7 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials { ...@@ -98,7 +97,7 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials {
(*awsCredentialCache[cacheKey].expiration).After(time.Now().UTC()) { (*awsCredentialCache[cacheKey].expiration).After(time.Now().UTC()) {
result := awsCredentialCache[cacheKey].credential result := awsCredentialCache[cacheKey].credential
credentialCacheLock.RUnlock() credentialCacheLock.RUnlock()
return result return result, nil
} }
} }
credentialCacheLock.RUnlock() credentialCacheLock.RUnlock()
...@@ -130,8 +129,7 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials { ...@@ -130,8 +129,7 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials {
svc := sts.New(session.New(stsConfig), stsConfig) svc := sts.New(session.New(stsConfig), stsConfig)
resp, err := svc.AssumeRole(params) resp, err := svc.AssumeRole(params)
if err != nil { if err != nil {
// ignore return nil, err
log.Error(3, "CloudWatch: Failed to assume role", err)
} }
if resp.Credentials != nil { if resp.Credentials != nil {
accessKeyId = *resp.Credentials.AccessKeyId accessKeyId = *resp.Credentials.AccessKeyId
...@@ -165,19 +163,28 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials { ...@@ -165,19 +163,28 @@ func getCredentials(dsInfo *datasourceInfo) *credentials.Credentials {
} }
credentialCacheLock.Unlock() credentialCacheLock.Unlock()
return creds return creds, nil
} }
func getAwsConfig(req *cwRequest) *aws.Config { func getAwsConfig(req *cwRequest) (*aws.Config, error) {
creds, err := getCredentials(req.GetDatasourceInfo())
if err != nil {
return nil, err
}
cfg := &aws.Config{ cfg := &aws.Config{
Region: aws.String(req.Region), Region: aws.String(req.Region),
Credentials: getCredentials(req.GetDatasourceInfo()), Credentials: creds,
} }
return cfg return cfg, nil
} }
func handleGetMetricStatistics(req *cwRequest, c *middleware.Context) { func handleGetMetricStatistics(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -220,7 +227,11 @@ func handleGetMetricStatistics(req *cwRequest, c *middleware.Context) { ...@@ -220,7 +227,11 @@ func handleGetMetricStatistics(req *cwRequest, c *middleware.Context) {
} }
func handleListMetrics(req *cwRequest, c *middleware.Context) { func handleListMetrics(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -239,7 +250,7 @@ func handleListMetrics(req *cwRequest, c *middleware.Context) { ...@@ -239,7 +250,7 @@ func handleListMetrics(req *cwRequest, c *middleware.Context) {
} }
var resp cloudwatch.ListMetricsOutput var resp cloudwatch.ListMetricsOutput
err := svc.ListMetricsPages(params, err = svc.ListMetricsPages(params,
func(page *cloudwatch.ListMetricsOutput, lastPage bool) bool { func(page *cloudwatch.ListMetricsOutput, lastPage bool) bool {
metrics.M_Aws_CloudWatch_ListMetrics.Inc(1) metrics.M_Aws_CloudWatch_ListMetrics.Inc(1)
metrics, _ := awsutil.ValuesAtPath(page, "Metrics") metrics, _ := awsutil.ValuesAtPath(page, "Metrics")
...@@ -257,7 +268,11 @@ func handleListMetrics(req *cwRequest, c *middleware.Context) { ...@@ -257,7 +268,11 @@ func handleListMetrics(req *cwRequest, c *middleware.Context) {
} }
func handleDescribeAlarms(req *cwRequest, c *middleware.Context) { func handleDescribeAlarms(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -296,7 +311,11 @@ func handleDescribeAlarms(req *cwRequest, c *middleware.Context) { ...@@ -296,7 +311,11 @@ func handleDescribeAlarms(req *cwRequest, c *middleware.Context) {
} }
func handleDescribeAlarmsForMetric(req *cwRequest, c *middleware.Context) { func handleDescribeAlarmsForMetric(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -336,7 +355,11 @@ func handleDescribeAlarmsForMetric(req *cwRequest, c *middleware.Context) { ...@@ -336,7 +355,11 @@ func handleDescribeAlarmsForMetric(req *cwRequest, c *middleware.Context) {
} }
func handleDescribeAlarmHistory(req *cwRequest, c *middleware.Context) { func handleDescribeAlarmHistory(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -368,7 +391,11 @@ func handleDescribeAlarmHistory(req *cwRequest, c *middleware.Context) { ...@@ -368,7 +391,11 @@ func handleDescribeAlarmHistory(req *cwRequest, c *middleware.Context) {
} }
func handleDescribeInstances(req *cwRequest, c *middleware.Context) { func handleDescribeInstances(req *cwRequest, c *middleware.Context) {
cfg := getAwsConfig(req) cfg, err := getAwsConfig(req)
if err != nil {
c.JsonApiErr(500, "Unable to call AWS API", err)
return
}
svc := ec2.New(session.New(cfg), cfg) svc := ec2.New(session.New(cfg), cfg)
reqParam := &struct { reqParam := &struct {
...@@ -388,7 +415,7 @@ func handleDescribeInstances(req *cwRequest, c *middleware.Context) { ...@@ -388,7 +415,7 @@ func handleDescribeInstances(req *cwRequest, c *middleware.Context) {
} }
var resp ec2.DescribeInstancesOutput var resp ec2.DescribeInstancesOutput
err := svc.DescribeInstancesPages(params, err = svc.DescribeInstancesPages(params,
func(page *ec2.DescribeInstancesOutput, lastPage bool) bool { func(page *ec2.DescribeInstancesOutput, lastPage bool) bool {
reservations, _ := awsutil.ValuesAtPath(page, "Reservations") reservations, _ := awsutil.ValuesAtPath(page, "Reservations")
for _, reservation := range reservations { for _, reservation := range reservations {
......
...@@ -248,9 +248,13 @@ func handleGetDimensions(req *cwRequest, c *middleware.Context) { ...@@ -248,9 +248,13 @@ func handleGetDimensions(req *cwRequest, c *middleware.Context) {
} }
func getAllMetrics(cwData *datasourceInfo) (cloudwatch.ListMetricsOutput, error) { func getAllMetrics(cwData *datasourceInfo) (cloudwatch.ListMetricsOutput, error) {
creds, err := getCredentials(cwData)
if err != nil {
return cloudwatch.ListMetricsOutput{}, err
}
cfg := &aws.Config{ cfg := &aws.Config{
Region: aws.String(cwData.Region), Region: aws.String(cwData.Region),
Credentials: getCredentials(cwData), Credentials: creds,
} }
svc := cloudwatch.New(session.New(cfg), cfg) svc := cloudwatch.New(session.New(cfg), cfg)
...@@ -260,7 +264,7 @@ func getAllMetrics(cwData *datasourceInfo) (cloudwatch.ListMetricsOutput, error) ...@@ -260,7 +264,7 @@ func getAllMetrics(cwData *datasourceInfo) (cloudwatch.ListMetricsOutput, error)
} }
var resp cloudwatch.ListMetricsOutput var resp cloudwatch.ListMetricsOutput
err := svc.ListMetricsPages(params, err = svc.ListMetricsPages(params,
func(page *cloudwatch.ListMetricsOutput, lastPage bool) bool { func(page *cloudwatch.ListMetricsOutput, lastPage bool) bool {
metrics.M_Aws_CloudWatch_ListMetrics.Inc(1) metrics.M_Aws_CloudWatch_ListMetrics.Inc(1)
metrics, _ := awsutil.ValuesAtPath(page, "Metrics") metrics, _ := awsutil.ValuesAtPath(page, "Metrics")
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment